From 8a360780db37f576ca1fcbed1ff4093d17e2fb77 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 1 Jul 2017 17:46:27 +0200 Subject: [PATCH 001/187] Restoring repository with new project structure --- Config/DefaultEditor.ini | 8 + .../DefaultEditorPerProjectUserSettings.ini | 2 + Config/DefaultEngine.ini | 20 + Config/DefaultGame.ini | 7 + Config/DefaultInput.ini | 24 + .../AbilityFramework/AbilityFramework.uplugin | 28 + .../AbilityFramework/AFCueInterface.cpp | 7 + .../Source/AbilityFramework/AFCueInterface.h | 26 + .../Source/AbilityFramework/AFCueManager.cpp | 155 ++ .../Source/AbilityFramework/AFCueManager.h | 43 + .../Source/AbilityFramework/AFCueSet.cpp | 8 + .../Source/AbilityFramework/AFCueSet.h | 23 + .../Abilities/AFAbilityActivationSpec.cpp | 13 + .../Abilities/AFAbilityActivationSpec.h | 21 + .../Abilities/AFAbilityCooldownSpec.cpp | 14 + .../Abilities/AFAbilityCooldownSpec.h | 20 + .../AFAbilityInfiniteDurationSpec.cpp | 8 + .../Abilities/AFAbilityInfiniteDurationSpec.h | 20 + .../Abilities/AFAbilityPeriodSpec.cpp | 13 + .../Abilities/AFAbilityPeriodSpec.h | 20 + .../Abilities/AFBlueprintFunctionLibrary.cpp | 46 + .../Abilities/AFBlueprintFunctionLibrary.h | 15 + .../Abilities/GAAbilityBase.cpp | 611 ++++++ .../Abilities/GAAbilityBase.h | 530 ++++++ .../Abilities/GAAbilityBlueprint.cpp | 33 + .../Abilities/GAAbilityBlueprint.h | 31 + .../Abilities/GAAbilitySet.cpp | 8 + .../AbilityFramework/Abilities/GAAbilitySet.h | 21 + .../Tasks/AFAbilityTask_SpawnProjectile.cpp | 30 + .../Tasks/AFAbilityTask_SpawnProjectile.h | 58 + .../Abilities/Tasks/GAAbilityTask.cpp | 37 + .../Abilities/Tasks/GAAbilityTask.h | 72 + .../Tasks/GAAbilityTask_CreateObject.cpp | 64 + .../Tasks/GAAbilityTask_CreateObject.h | 32 + .../Tasks/GAAbilityTask_PlayMontage.cpp | 50 + .../Tasks/GAAbilityTask_PlayMontage.h | 45 + .../Abilities/Tasks/GAAbilityTask_Repeat.cpp | 15 + .../Abilities/Tasks/GAAbilityTask_Repeat.h | 24 + .../Tasks/GAAbilityTask_SpawnActor.cpp | 70 + .../Tasks/GAAbilityTask_SpawnActor.h | 34 + .../Tasks/GAAbilityTask_TargetData.cpp | 163 ++ .../Tasks/GAAbilityTask_TargetData.h | 67 + .../Tasks/GAAbilityTask_TargetDataCircle.cpp | 85 + .../Tasks/GAAbilityTask_TargetDataCircle.h | 43 + .../Tasks/GAAbilityTask_WaitForConfirm.cpp | 33 + .../Tasks/GAAbilityTask_WaitForConfirm.h | 30 + .../Tasks/GAAbilityTask_WaitTargetData.cpp | 94 + .../Tasks/GAAbilityTask_WaitTargetData.h | 47 + .../AbilityCues/GAAbilityCue.cpp | 19 + .../AbilityCues/GAAbilityCue.h | 68 + .../AbilityCues/GACueActor.cpp | 30 + .../AbilityFramework/AbilityCues/GACueActor.h | 73 + .../AbilityFramework.Build.cs | 71 + .../AbilityFramework/AbilityFramework.cpp | 33 + .../AbilityFramework/AbilityFramework.h | 21 + .../AnimNotify/AFAbilityNotifyState.cpp | 33 + .../AnimNotify/AFAbilityNotifyState.h | 30 + .../AnimNotify/AFAnimNotify.cpp | 19 + .../AnimNotify/AFAnimNotify.h | 25 + .../AnimNotify/AFAnimNotifyBase.cpp | 18 + .../AnimNotify/AFAnimNotifyBase.h | 25 + .../AbilityFramework/Async/AsyncUObject.cpp | 12 + .../AbilityFramework/Async/AsyncUObject.h | 47 + .../Async/AsyncUObjectImpl.cpp | 12 + .../AbilityFramework/Async/AsyncUObjectImpl.h | 61 + .../Attributes/GAAttributeBase.cpp | 282 +++ .../Attributes/GAAttributeBase.h | 138 ++ .../Attributes/GAAttributeExtension.cpp | 8 + .../Attributes/GAAttributeExtension.h | 25 + .../Attributes/GAAttributeGlobals.cpp | 5 + .../Attributes/GAAttributeGlobals.h | 15 + .../Attributes/GAAttributesBase.cpp | 296 +++ .../Attributes/GAAttributesBase.h | 129 ++ .../GAAttributesBlueprintFunctionLibrary.cpp | 51 + .../GAAttributesBlueprintFunctionLibrary.h | 34 + .../Attributes/GAAttributesStats.cpp | 4 + .../Attributes/GAAttributesStats.h | 2 + .../AFEffectApplicationRequirement.cpp | 8 + .../Effects/AFEffectApplicationRequirement.h | 27 + .../Effects/AFEffectCustomApplication.cpp | 23 + .../Effects/AFEffectCustomApplication.h | 36 + .../Effects/AFEffectCustomStackingRule.cpp | 14 + .../Effects/AFEffectCustomStackingRule.h | 22 + .../AFAttributeStongerOverride.cpp | 36 + .../AFAttributeStongerOverride.h | 24 + .../AFEffectAlreadyApplied.cpp | 19 + .../AFEffectAlreadyApplied.h | 26 + .../AFAtributeDurationAdd.cpp | 25 + .../AFAtributeDurationAdd.h | 30 + .../AFAttributeDurationInfinite.cpp | 17 + .../AFAttributeDurationInfinite.h | 31 + .../AFAttributeDurationOverride.cpp | 40 + .../AFAttributeDurationOverride.h | 32 + .../AFPeriodApplicationAdd.cpp | 30 + .../AFPeriodApplicationAdd.h | 36 + .../AFPeriodApplicationExtend.cpp | 46 + .../AFPeriodApplicationExtend.h | 37 + .../AFPeriodApplicationInfiniteAdd.cpp | 23 + .../AFPeriodApplicationInfiniteAdd.h | 37 + .../AFPeriodApplicationOverride.cpp | 38 + .../AFPeriodApplicationOverride.h | 35 + .../AFPeriodicApplInfiniteOverride.cpp | 8 + .../AFPeriodicApplInfiniteOverride.h | 24 + .../Effects/EffectTasks/AFEffectTask.cpp | 8 + .../Effects/EffectTasks/AFEffectTask.h | 55 + .../AFEffectTask_AttributeChange.cpp | 83 + .../AFEffectTask_AttributeChange.h | 52 + .../EffectTasks/AFEffectTask_EffectEvent.cpp | 82 + .../EffectTasks/AFEffectTask_EffectEvent.h | 48 + .../Effects/GABlueprintLibrary.cpp | 223 +++ .../Effects/GABlueprintLibrary.h | 75 + .../Effects/GACustomCalculation.cpp | 11 + .../Effects/GACustomCalculation.h | 30 + .../Effects/GAEffectBlueprint.cpp | 33 + .../Effects/GAEffectBlueprint.h | 31 + .../AbilityFramework/Effects/GAEffectCue.cpp | 64 + .../AbilityFramework/Effects/GAEffectCue.h | 61 + .../GAEffectCueBlueprintGeneratedClass.cpp | 13 + .../GAEffectCueBlueprintGeneratedClass.h | 17 + .../Effects/GAEffectCueGlobals.cpp | 51 + .../Effects/GAEffectCueGlobals.h | 26 + .../Effects/GAEffectCueSequence.cpp | 130 ++ .../Effects/GAEffectCueSequence.h | 69 + .../Effects/GAEffectExecution.cpp | 24 + .../Effects/GAEffectExecution.h | 22 + .../Effects/GAEffectExtension.cpp | 77 + .../Effects/GAEffectExtension.h | 86 + .../Effects/GAEffectField.cpp | 48 + .../AbilityFramework/Effects/GAEffectField.h | 60 + .../Effects/GAEffectGlobalTypes.cpp | 143 ++ .../Effects/GAEffectGlobalTypes.h | 155 ++ .../AbilityFramework/Effects/GAEffectSet.cpp | 8 + .../AbilityFramework/Effects/GAEffectSet.h | 20 + .../AbilityFramework/Effects/GAGameEffect.cpp | 689 +++++++ .../AbilityFramework/Effects/GAGameEffect.h | 753 ++++++++ .../AbilityFramework/GAAbilitiesComponent.cpp | 790 ++++++++ .../AbilityFramework/GAAbilitiesComponent.h | 595 ++++++ .../Source/AbilityFramework/GAGlobalTypes.cpp | 312 ++++ .../Source/AbilityFramework/GAGlobalTypes.h | 834 +++++++++ .../Source/AbilityFramework/GAGlobals.cpp | 5 + .../Source/AbilityFramework/GAGlobals.h | 88 + .../AbilityFramework/GAHelperTemplates.cpp | 5 + .../AbilityFramework/GAHelperTemplates.h | 59 + .../AbilityFramework/GAPhysicalMaterial.cpp | 8 + .../AbilityFramework/GAPhysicalMaterial.h | 19 + .../Source/AbilityFramework/GAUIData.cpp | 8 + .../Source/AbilityFramework/GAUIData.h | 16 + .../AbilityFramework/IAbilityFramework.h | 37 + .../Source/AbilityFramework/IGAAbilities.cpp | 10 + .../Source/AbilityFramework/IGAAbilities.h | 48 + .../LatentActions/GALatentFunctionBase.cpp | 71 + .../LatentActions/GALatentFunctionBase.h | 55 + .../LatentActions/GAWaitAction.cpp | 55 + .../LatentActions/GAWaitAction.h | 42 + .../AbilityFramework/Mods/GAAttributeMod.cpp | 11 + .../AbilityFramework/Mods/GAAttributeMod.h | 32 + .../Targeting/GASAbilityTargetingObject.cpp | 36 + .../Targeting/GASAbilityTargetingObject.h | 27 + .../Targeting/GATargetingActor.cpp | 28 + .../Targeting/GATargetingActor.h | 25 + .../Tests/GAAttributesTest.cpp | 13 + .../AbilityFramework/Tests/GAAttributesTest.h | 49 + .../Tests/GAAttributesTests.cpp | 1646 +++++++++++++++++ .../Tests/GACharacterAttributeTest.cpp | 71 + .../Tests/GACharacterAttributeTest.h | 41 + .../Tests/GACustomCalculationTest.cpp | 22 + .../Tests/GACustomCalculationTest.h | 19 + .../Tests/GASpellExecutionTest.cpp | 15 + .../Tests/GASpellExecutionTest.h | 15 + .../Tests/GAffectSpecTestOne.cpp | 8 + .../Tests/GAffectSpecTestOne.h | 20 + .../AFAbilityActionSpecDetails.cpp | 75 + .../AFAbilityActionSpecDetails.h | 31 + .../AFAbilityCooldownSpecDetails.cpp | 75 + .../AFAbilityCooldownSpecDetails.h | 30 + .../AFAbilityPeriodSpecDetails.cpp | 81 + .../AFAbilityPeriodSpecDetails.h | 31 + .../AFEK2Node_AsyncEffectTaskCall.cpp | 89 + .../AFEK2Node_AsyncEffectTaskCall.h | 23 + .../AFEffectCustomizationCommon.cpp | 109 ++ .../AFEffectCustomizationCommon.h | 19 + .../AssetTypeActions_GAAbilityBlueprint.cpp | 57 + .../AssetTypeActions_GAAbilityBlueprint.h | 27 + .../GAAbilityBlueprintFactory.cpp | 334 ++++ .../AbilityEditor/GAAbilityBlueprintFactory.h | 32 + .../AbilityEditor/GAAbilityEditor.cpp | 142 ++ .../AbilityEditor/GAAbilityEditor.h | 64 + .../AbilityEditor/GAAbilityGraph.cpp | 16 + .../AbilityEditor/GAAbilityGraph.h | 15 + .../AbilityEditor/GAAbilityGraphSchema.cpp | 22 + .../AbilityEditor/GAAbilityGraphSchema.h | 38 + .../AbilityFrameworkEditor.Build.cs | 94 + .../AbilityFrameworkEditor.cpp | 134 ++ .../AbilityFrameworkEditor.h | 58 + .../GACurveTableDetailCustomization.cpp | 28 + .../GACurveTableDetailCustomization.h | 23 + .../AssetTypeActions_GAEffectCueBlueprint.cpp | 57 + .../AssetTypeActions_GAEffectCueBlueprint.h | 27 + .../EffectCueEditor/GAEffectCueBlueprint.cpp | 33 + .../EffectCueEditor/GAEffectCueBlueprint.h | 32 + .../GAEffectCueBlueprintFactory.cpp | 334 ++++ .../GAEffectCueBlueprintFactory.h | 32 + .../EffectCueEditor/GAEffectCueEditor.cpp | 315 ++++ .../EffectCueEditor/GAEffectCueEditor.h | 90 + .../EffectCueEditor/GAEffectCueGraph.cpp | 16 + .../EffectCueEditor/GAEffectCueGraph.h | 15 + .../GAEffectCueGraphSchema.cpp | 22 + .../EffectCueEditor/GAEffectCueGraphSchema.h | 38 + .../AssetTypeActions_GAEffectBlueprint.cpp | 57 + .../AssetTypeActions_GAEffectBlueprint.h | 27 + .../EffectEditor/GAEffectBlueprintFactory.cpp | 347 ++++ .../EffectEditor/GAEffectBlueprintFactory.h | 32 + .../EffectEditor/GAEffectEditor.cpp | 124 ++ .../EffectEditor/GAEffectEditor.h | 53 + .../EffectEditor/GAEffectGraph.cpp | 16 + .../EffectEditor/GAEffectGraph.h | 15 + .../EffectEditor/GAEffectGraphSchema.cpp | 22 + .../EffectEditor/GAEffectGraphSchema.h | 38 + .../GAAttributeDetailCustomization.cpp | 90 + .../GAAttributeDetailCustomization.h | 33 + .../GAAttributePanelGraphPinFactory.cpp | 16 + .../GAAttributePanelGraphPinFactory.h | 23 + .../AbilityFrameworkEditor/GAAttributePin.cpp | 105 ++ .../AbilityFrameworkEditor/GAAttributePin.h | 27 + .../GAEK2Node_LatentAbilityTaskCall.cpp | 89 + .../GAEK2Node_LatentAbilityTaskCall.h | 23 + .../GAEK2Node_LatentAction.cpp | 76 + .../GAEK2Node_LatentAction.h | 19 + .../GAEffectClassStructWidget.cpp | 833 +++++++++ .../GAEffectClassStructWidget.h | 57 + .../GAEffectDetails.cpp | 111 ++ .../AbilityFrameworkEditor/GAEffectDetails.h | 32 + .../GAEffectPropertyStructCustomization.cpp | 89 + .../GAEffectPropertyStructCustomization.h | 28 + .../GAGlobalTypesEditor.h | 35 + .../IAbilityFrameworkEditor.h | 36 + .../IGameAttributesEditor.h | 39 + .../SGAAttributeWidget.cpp | 151 ++ .../SGAAttributeWidget.h | 64 + Source/ActionRPGGame.Target.cs | 13 + Source/ActionRPGGame/ActionRPGGame.Build.cs | 13 + Source/ActionRPGGame/ActionRPGGame.cpp | 7 + Source/ActionRPGGame/ActionRPGGame.h | 5 + .../ActionRPGGame/ActionRPGGameCharacter.cpp | 134 ++ Source/ActionRPGGame/ActionRPGGameCharacter.h | 72 + .../ActionRPGGame/ActionRPGGameGameMode.cpp | 15 + Source/ActionRPGGame/ActionRPGGameGameMode.h | 19 + Source/ActionRPGGameClient.Target.cs | 13 + Source/ActionRPGGameEditor.Target.cs | 13 + 249 files changed, 19229 insertions(+) create mode 100644 Config/DefaultEditor.ini create mode 100644 Config/DefaultEditorPerProjectUserSettings.ini create mode 100644 Config/DefaultEngine.ini create mode 100644 Config/DefaultGame.ini create mode 100644 Config/DefaultInput.ini create mode 100644 Plugins/AbilityFramework/AbilityFramework.uplugin create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h create mode 100644 Source/ActionRPGGame.Target.cs create mode 100644 Source/ActionRPGGame/ActionRPGGame.Build.cs create mode 100644 Source/ActionRPGGame/ActionRPGGame.cpp create mode 100644 Source/ActionRPGGame/ActionRPGGame.h create mode 100644 Source/ActionRPGGame/ActionRPGGameCharacter.cpp create mode 100644 Source/ActionRPGGame/ActionRPGGameCharacter.h create mode 100644 Source/ActionRPGGame/ActionRPGGameGameMode.cpp create mode 100644 Source/ActionRPGGame/ActionRPGGameGameMode.h create mode 100644 Source/ActionRPGGameClient.Target.cs create mode 100644 Source/ActionRPGGameEditor.Target.cs diff --git a/Config/DefaultEditor.ini b/Config/DefaultEditor.ini new file mode 100644 index 0000000..56c4d58 --- /dev/null +++ b/Config/DefaultEditor.ini @@ -0,0 +1,8 @@ +[UnrealEd.SimpleMap] +SimpleMapName=/Game/ThirdPersonCPP/Maps/ThirdPersonExampleMap + +[EditoronlyBP] +bAllowClassAndBlueprintPinMatching=true +bReplaceBlueprintWithClass= true +bDontLoadBlueprintOutsideEditor= true +bBlueprintIsNotBlueprintType= true \ No newline at end of file diff --git a/Config/DefaultEditorPerProjectUserSettings.ini b/Config/DefaultEditorPerProjectUserSettings.ini new file mode 100644 index 0000000..4dcc526 --- /dev/null +++ b/Config/DefaultEditorPerProjectUserSettings.ini @@ -0,0 +1,2 @@ +[ContentBrowser] +ContentBrowserTab1.SelectedPaths=/Game/ThirdPersonCPP \ No newline at end of file diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini new file mode 100644 index 0000000..606de6a --- /dev/null +++ b/Config/DefaultEngine.ini @@ -0,0 +1,20 @@ +[/Script/EngineSettings.GameMapsSettings] +GameDefaultMap=/Game/ThirdPersonCPP/Maps/ThirdPersonExampleMap +EditorStartupMap=/Game/ThirdPersonCPP/Maps/ThirdPersonExampleMap +GlobalDefaultGameMode="/Script/ActionRPGGame.ActionRPGGameGameMode" + +[/Script/IOSRuntimeSettings.IOSRuntimeSettings] +MinimumiOSVersion=IOS_8 + + +[/Script/HardwareTargeting.HardwareTargetingSettings] +TargetedHardwareClass=Desktop +DefaultGraphicsPerformance=Maximum + + + +[/Script/Engine.Engine] ++ActiveGameNameRedirects=(OldGameName="TP_ThirdPerson",NewGameName="/Script/ActionRPGGame") ++ActiveGameNameRedirects=(OldGameName="/Script/TP_ThirdPerson",NewGameName="/Script/ActionRPGGame") ++ActiveClassRedirects=(OldClassName="TP_ThirdPersonGameMode",NewClassName="ActionRPGGameGameMode") ++ActiveClassRedirects=(OldClassName="TP_ThirdPersonCharacter",NewClassName="ActionRPGGameCharacter") diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini new file mode 100644 index 0000000..d913b55 --- /dev/null +++ b/Config/DefaultGame.ini @@ -0,0 +1,7 @@ +[/Script/EngineSettings.GeneralProjectSettings] +ProjectID=53E63CC7411F280A64FAD489EBFD3E33 +ProjectName=Third Person Game Template + +[StartupActions] +bAddPacks=True +InsertPack=(PackSource="StarterContent.upack,PackName="StarterContent") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini new file mode 100644 index 0000000..1641e20 --- /dev/null +++ b/Config/DefaultInput.ini @@ -0,0 +1,24 @@ +[/Script/Engine.InputSettings] ++ActionMappings=(ActionName="Jump", Key=SpaceBar) ++ActionMappings=(ActionName="Jump", Key=Gamepad_FaceButton_Bottom) + ++AxisMappings=(AxisName="MoveForward", Key=W, Scale=1.f) ++AxisMappings=(AxisName="MoveForward", Key=S, Scale=-1.f) ++AxisMappings=(AxisName="MoveForward", Key=Up, Scale=1.f) ++AxisMappings=(AxisName="MoveForward", Key=Down, Scale=-1.f) ++AxisMappings=(AxisName="MoveForward", Key=Gamepad_LeftY, Scale=1.f) + ++AxisMappings=(AxisName="MoveRight", Key=A, Scale=-1.f) ++AxisMappings=(AxisName="MoveRight", Key=D, Scale=1.f) ++AxisMappings=(AxisName="MoveRight", Key=Gamepad_LeftX, Scale=1.f) + ++AxisMappings=(AxisName="TurnRate", Key=Gamepad_RightX, Scale=1.f) ++AxisMappings=(AxisName="TurnRate", Key=Left, Scale=-1.f) ++AxisMappings=(AxisName="TurnRate", Key=Right, Scale=1.f) ++AxisMappings=(AxisName="Turn", Key=MouseX, Scale=1.f) + ++AxisMappings=(AxisName="LookUpRate", Key=Gamepad_RightY, Scale=1.f) ++AxisMappings=(AxisName="LookUp", Key=MouseY, Scale=-1.f) + ++ActionMappings=(ActionName="ResetVR", Key=R) ++ActionMappings=(ActionName="ResetVR",Key=MotionController_Left_Grip1,bShift=False,bCtrl=False,bAlt=False,bCmd=False) diff --git a/Plugins/AbilityFramework/AbilityFramework.uplugin b/Plugins/AbilityFramework/AbilityFramework.uplugin new file mode 100644 index 0000000..b2c0f8b --- /dev/null +++ b/Plugins/AbilityFramework/AbilityFramework.uplugin @@ -0,0 +1,28 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "AbilityFramework", + "Description": "", + "Category": "Gameplay", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": true, + "Installed": false, + "Modules": [ + { + "Name": "AbilityFramework", + "Type": "Runtime", + "LoadingPhase": "Default" + }, + { + "Name": "AbilityFrameworkEditor", + "Type": "Editor", + "LoadingPhase": "Default" + } + ] +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp new file mode 100644 index 0000000..2fac5ab --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFCueInterface.h" + + +// Add default functionality here for any IAFCueInterface functions that are not pure virtual. diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h new file mode 100644 index 0000000..26baa08 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AFCueInterface.generated.h" + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UAFCueInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class ABILITYFRAMEWORK_API IAFCueInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp new file mode 100644 index 0000000..4775895 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -0,0 +1,155 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/GAEffectCue.h" +#include "AFCueSet.h" +#include "AFCueManager.h" +#if WITH_EDITOR +#include "Editor.H" +#endif + +UAFCueManager* UAFCueManager::ManagerInstance = nullptr; +//UWorld* UAFCueManager::CurrentWorld = nullptr; + +UAFCueManager* UAFCueManager::Get() +{ + if (ManagerInstance) + { + return ManagerInstance; + } + ManagerInstance = NewObject(GEngine, UAFCueManager::StaticClass(), "UAFCueManagerInstance", + RF_MarkAsRootSet); + ManagerInstance->AddToRoot(); + ManagerInstance->Initialize(); + ManagerInstance->LoadCueSet(); + + return ManagerInstance; +} +void UAFCueManager::Initialize() +{ +#if WITH_EDITOR + FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); +#endif //WITH_EDITOR +} +void UAFCueManager::LoadCueSet() +{ + CueSet = DefaultCueSet.LoadSynchronous(); +} +#if WITH_EDITOR +void UAFCueManager::HandleOnPIEEnd(bool InVal) +{ + CurrentWorld = nullptr; + for (auto It = InstancedCues.CreateIterator(); It; ++It) + { + if (It->Value.IsValid()) + { + while (!It->Value->IsEmpty()) + { + AGAEffectCue* ToDestroy = nullptr; + It->Value->Dequeue(ToDestroy); + if (ToDestroy) + { + ToDestroy->Destroy(); + } + } + } + } + for (auto It = UsedCues.CreateIterator(); It; ++It) + { + if (It->Value.IsValid()) + { + while (!It->Value->IsEmpty()) + { + AGAEffectCue* ToDestroy = nullptr; + It->Value->Dequeue(ToDestroy); + if (ToDestroy) + { + ToDestroy->Destroy(); + } + } + } + } +} +#endif //WITH_EDITOR +void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams) +{ + if (!CurrentWorld) + CurrentWorld = CueParams.Instigator->GetWorld(); + for (const FGameplayTag& Tag : CueParams.CueTags) + { + TSubclassOf CueClass = CueSet->Cues.FindRef(Tag); + if (!CueClass) + continue; + + ENetRole mode = CueParams.Instigator->GetRemoteRole(); + FString role; + switch (mode) + { + case ROLE_None: + role = "ROLE_None"; + break; + case ROLE_SimulatedProxy: + role = "ROLE_SimulatedProxy"; + break; + case ROLE_AutonomousProxy: + role = "ROLE_AutonomousProxy"; + break; + case ROLE_Authority: + role = "ROLE_Authority"; + break; + case ROLE_MAX: + role = "ROLE_MAX"; + break; + default: + break; + } + + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + } + + UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), + *prefix, + *Tag.ToString(), + CueParams.Instigator.IsValid() ? *CueParams.Instigator->GetName() : TEXT("Invalid Instigator"), + *CueParams.HitResult.Location.ToString(), + *CurrentWorld->GetName(), + *role + ); + + FActorSpawnParameters SpawnParams; + FVector Location = CueParams.HitResult.Location; + FRotator Rotation = FRotator::ZeroRotator; + AGAEffectCue* actor = nullptr; + /* TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); + if (!Cues.IsValid()) + { + Cues = MakeUnique>(); + } + TUniquePtr>& UseCues = UsedCues.FindOrAdd(Tag); + if (!UseCues.IsValid()) + { + UseCues = MakeUnique>(); + } + + if (Cues->IsEmpty()) + { + actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); + Cues->Enqueue(actor); + } + else + { + Cues->Dequeue(actor); + UseCues->Enqueue(actor); + }*/ + + actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); + actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), + CueParams.Causer.Get(), CueParams.HitResult); + + /*UseCues->Dequeue(actor); + Cues->Enqueue(actor);*/ + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h new file mode 100644 index 0000000..af0691c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h @@ -0,0 +1,43 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "GAGlobalTypes.h" +#include "Effects/GAEffectCue.h" +#include "AFCueManager.generated.h" + +/** + * + */ +UCLASS(config = Game) +class ABILITYFRAMEWORK_API UAFCueManager : public UObject +{ + GENERATED_BODY() +protected: + //UPROPERTY() + static UAFCueManager* ManagerInstance; + UWorld* CurrentWorld; + UPROPERTY(config, EditAnywhere, Category = "Cue Set") + TAssetPtr DefaultCueSet; + + UPROPERTY() + UAFCueSet* CueSet; + + //stores unused instanced cues. + TMap>> InstancedCues; + //stores used cues. + TMap>> UsedCues; +public: + void Initialize(); + void LoadCueSet(); +#if WITH_EDITOR + //handle clearing up cache when PIE mode is ending. + void HandleOnPIEEnd(bool InVal); +#endif //WITH_EDITOR +public: + static UAFCueManager* Get(); + void HandleCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp new file mode 100644 index 0000000..f946e48 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFCueSet.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h new file mode 100644 index 0000000..fd829bc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Engine/DataAsset.h" +#include "GameplayTags.h" +#include "AFCueSet.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFCueSet : public UDataAsset +{ + GENERATED_BODY() + +public: + UPROPERTY(EditAnywhere) + TMap> Cues; + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp new file mode 100644 index 0000000..dbb9013 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp @@ -0,0 +1,13 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../Effects/CustomApplications/AFAtributeDurationAdd.h" +#include "AFAbilityActivationSpec.h" + + + +UAFAbilityActivationSpec::UAFAbilityActivationSpec() + :Super() +{ + Application = UAFAtributeDurationAdd::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h new file mode 100644 index 0000000..d9d6bfb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h @@ -0,0 +1,21 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityActivationSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityActivationSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() + +public: + UAFAbilityActivationSpec(); + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp new file mode 100644 index 0000000..045614d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/CustomApplications/AFAtributeDurationAdd.h" +#include "AFAbilityCooldownSpec.h" + + + + +UAFAbilityCooldownSpec::UAFAbilityCooldownSpec() + : Super() +{ + Application = UAFAtributeDurationAdd::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h new file mode 100644 index 0000000..238e495 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityCooldownSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityCooldownSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityCooldownSpec(); + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp new file mode 100644 index 0000000..51665d7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInfiniteDurationSpec.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h new file mode 100644 index 0000000..cc0f2ae --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityInfiniteDurationSpec.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFAbilityInfiniteDurationSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp new file mode 100644 index 0000000..49cb210 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp @@ -0,0 +1,13 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityPeriodSpec.h" +#include "../Effects/CustomApplications/AFPeriodApplicationAdd.h" + + + +UAFAbilityPeriodSpec::UAFAbilityPeriodSpec() + :Super() +{ + Application = UAFPeriodApplicationAdd::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h new file mode 100644 index 0000000..7c6f1eb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityPeriodSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityPeriodSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityPeriodSpec(); + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..e0d984d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp @@ -0,0 +1,46 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" + +#include "GAAbilityBase.h" +#include "../Effects/GAEffectField.h" +#include "../IGAAbilities.h" +#include "../GAAbilitiesComponent.h" +#include "AFBlueprintFunctionLibrary.h" + +void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, + const FGameplayTag& AbilityTag, FGameplayTag ActionTag) +{ + IIGAAbilities* Interface = Cast(Target); + if (!Interface) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Invalid Target")); + return; + } + UGAAbilitiesComponent* Comp = Interface->GetAbilityComp(); + if (!Comp) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Target %s InvalidComponent"), *Target->GetName()); + return; + } + + Comp->NativeInputPressed(AbilityTag, ActionTag); +} +void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, + const FGameplayTag& AbilityTag, FGameplayTag ActionTag) +{ + IIGAAbilities* Interface = Cast(Target); + if (!Interface) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Invalid Target")); + return; + } + UGAAbilitiesComponent* Comp = Interface->GetAbilityComp(); + if (!Comp) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Target %s InvalidComponent"), *Target->GetName()); + return; + } + + Comp->NativeInputReleased(AbilityTag, ActionTag); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h new file mode 100644 index 0000000..2ec187d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h @@ -0,0 +1,15 @@ +#pragma once +#include "AFBlueprintFunctionLibrary.generated.h" +/* + Some static helper functions, to interact with Attribute system. +*/ +UCLASS() +class ABILITYFRAMEWORK_API UAFBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + static void TriggerAbilityPressedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + static void TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp new file mode 100644 index 0000000..f7cdf31 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -0,0 +1,611 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + + +#include "../AbilityFramework.h" +#include "Tasks/GAAbilityTask.h" +#include "../Effects/GAGameEffect.h" +#include "../GAGlobalTypes.h" +#include "../Effects/GAEffectGlobalTypes.h" +#include "../GAAbilitiesComponent.h" + +#include "../AbilityCues/GACueActor.h" +#include "GameplayTagContainer.h" +#include "Net/UnrealNetwork.h" +#include "Animation/AnimMontage.h" +#include "../AbilityCues/GAAbilityCue.h" +#include "../Effects/GABlueprintLibrary.h" +#include "Camera/CameraComponent.h" +#include "Kismet/KismetSystemLibrary.h" + +#include "GAAbilityBase.h" + +void FGAAbilityTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) +{ + if (Target && !Target->IsPendingKillOrUnreachable()) + { + FScopeCycleCounterUObject ActorScope(Target); + Target->TickAbility(DeltaTime, TickType, *this); + } +} + +FString FGAAbilityTick::DiagnosticMessage() +{ + return Target->GetFullName() + TEXT("[TickAction]"); +} + +UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bReplicate = true; + bIsNameStable = false; + + TickFunction.TickGroup = TG_PrePhysics; + // Default to no tick function, but if we set 'never ticks' to false (so there is a tick function) it is enabled by default + TickFunction.bCanEverTick = true; + TickFunction.bStartWithTickEnabled = true; + TickFunction.bAllowTickOnDedicatedServer = true; + TickFunction.bRunOnAnyThread = true; + + TickFunction.SetTickFunctionEnable(true); +} +void UGAAbilityBase::TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction) +{ + +} + +void UGAAbilityBase::InitAbility() +{ + //still want to initialize, as Spec is used in multiple places. + ActivationEffect.InitializeIfNotInitialized(); + CooldownEffect.InitializeIfNotInitialized(); + DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, this, FHitResult(ForceInit)); + if (AbilityComponent) + { + World = AbilityComponent->GetWorld(); + } + if (POwner && POwner->GetNetMode() != ENetMode::NM_Standalone) + { + InitAbilityCounter++; + } + else + { + OnRep_InitAbility(); + } + if (!AbilityComponent) + { + AbilityComponent = GetAbilityComp(); + if (AbilityComponent) + { + AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes); + } + } + if (Attributes) + { + Attributes->InitializeAttributes(GetAbilityComp()); + } + + if (!OwnerCamera) + { + OwnerCamera = POwner->FindComponentByClass(); + } + TickFunction.Target = this; + TickFunction.RegisterTickFunction(AbilityComponent->GetWorld()->GetCurrentLevel()); + TickFunction.SetTickFunctionEnable(true); +} +void UGAAbilityBase::OnRep_InitAbility() +{ + +} +void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName) +{ + { + UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); + OnInputPressed(ActionName); + OnInputPressedDelegate.Broadcast(); + } +} + +void UGAAbilityBase::OnNativeInputReleased(FGameplayTag ActionName) +{ + { + UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputReleased in ability %s"), *GetName()); + OnInputReleased(ActionName); + OnInputReleasedDelegate.Broadcast(); + } +} + +void UGAAbilityBase::StartActivation(bool bApplyActivationEffect) +{ + if (!CanUseAbility()) + { + return; + } + //AbilityComponent->ExecutingAbility = this; + AbilityState = EAFAbilityState::Activating; + NativeOnBeginAbilityActivation(bApplyActivationEffect); +} + +void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) +{ + UE_LOG(AbilityFramework, Log, TEXT("Begin Executing Ability: %s"), *GetName()); + + if (OnConfirmCastingEndedDelegate.IsBound()) + { + OnConfirmCastingEndedDelegate.Broadcast(); + } + //ActivationInfo.SetActivationInfo(); + ApplyActivationEffect(bApplyActivationEffect); + OnActivate(); + OnActivateBeginDelegate.Broadcast(); + AbilityComponent->AppliedTags.AddTagContainer(ActivationAddedTags); + //OnAbilityExecuted(); +} + +void UGAAbilityBase::OnCooldownEffectExpired() +{ + UE_LOG(AbilityFramework, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); + CooldownEffectExpiredCounter++; + if (CooldownEffectHandle.IsValid()) + { + CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect); + } +} +/* Functions for activation effect delegates */ +void UGAAbilityBase::NativeOnAbilityActivationFinish(const FGAEffectHandle& InHandle) +{ + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); + OnActivationFinished(); + OnActivationFinishedDelegate.Broadcast(); +} +void UGAAbilityBase::NativeOnAbilityActivationCancel() +{ + //OnAbilityExecutedNative(); + //this works under assumption that current state == activation state. + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Removed In Ability: %s"), *GetName()); + //AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + + OnActivationCancel(); + //AbilityActivatedCounter++; +} +void UGAAbilityBase::OnActivationEffectPeriod(const FGAEffectHandle& InHandle) +{ + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); + AbilityPeriodCounter++; + OnPeriod(); +} +void UGAAbilityBase::FinishAbility() +{ + UE_LOG(AbilityFramework, Log, TEXT("FinishExecution in ability %s"), *GetName()); + OnFinished(); + NativeFinishAbility(); + AbilityState = EAFAbilityState::Waiting; + AbilityComponent->AppliedTags.RemoveTagContainer(ActivationAddedTags); +} +void UGAAbilityBase::NativeFinishAbility() +{ + UE_LOG(AbilityFramework, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); + AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + //if (ActivationEffect.Handle.IsValid()) + { + AbilityComponent->RemoveEffect(ActivationEffect); + } + //remove effect. +} +/* Functions for activation effect delegates */ +void UGAAbilityBase::CancelActivation() +{ + NativeCancelActivation(); +} +void UGAAbilityBase::NativeCancelActivation() +{ + UGAAbilitiesComponent* AttrComp = ActivationEffect.Handle.GetContext().InstigatorComp.Get(); + if (AbilityComponent) + { + AbilityComponent->RemoveEffect(ActivationEffect); + } +} + +bool UGAAbilityBase::IsWaitingForConfirm() +{ + if (OnConfirmDelegate.IsBound()) + return true; + else + return false; +} +void UGAAbilityBase::ConfirmAbility() +{ + if (OnConfirmDelegate.IsBound()) + OnConfirmDelegate.Broadcast(); + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); +} + +bool UGAAbilityBase::ApplyCooldownEffect() +{ + if (!CooldownEffect.GetSpec()) + { + return false; + } + + return false; +} +bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) +{ + if (!ActivationEffect.GetSpec()) + return false; + FHitResult Hit(ForceInit); + + UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); + float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); + float PeriodCheck = Spec->Period.GetFloatValue(DefaultContext); + if (DurationCheck > 0 || PeriodCheck > 0) + { + bApplyActivationEffect = true; + } + ActivationInfo.SetActivationInfo(GetWorld()->TimeSeconds, DurationCheck, PeriodCheck, bApplyActivationEffect); + if (bApplyActivationEffect) + { + FHitResult HitIn; + if (ActivationEffectHandle.IsValid()) + ActivationEffectHandle.Reset(); + + FAFFunctionModifier Modifier; + ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(ActivationEffect, + this, POwner, this, Modifier); + + //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) + ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); + + + if (PeriodCheck > 0) + { + //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) + ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); + } + } + else + { + NativeOnAbilityActivationFinish(FGAEffectHandle()); + } + return false; +} + +bool UGAAbilityBase::CanUseAbility() +{ + bool CanUse = true; + bool bIsOnCooldown = IsOnCooldown(); + bool bIsActivating = IsActivating(); + //if (!AbilityComponent->ExecutingAbility) + // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); + + CanUse = !bIsOnCooldown && !bIsActivating; + return CanUse; +} + +bool UGAAbilityBase::CanReleaseAbility() +{ + bool bCanUse = true; + /*if (AbilityComponent->ExecutingAbility == this) + { + bCanUse = true; + }*/ + if (IsOnCooldown()) + { + bCanUse = false; + UE_LOG(AbilityFramework, Log, TEXT("CanReleaseAbility can't release ability is on cooldown")); + } + return bCanUse; +} +float UGAAbilityBase::GetCurrentActivationTime() const +{ + if (ActivationEffect.Handle.IsValid()) + { + return ActivationEffect.Handle.GetEffectPtr()->GetCurrentActivationTime(); + } + return 0; +} +float UGAAbilityBase::BP_GetCurrentActivationTime() const +{ + return GetCurrentActivationTime(); +} +float UGAAbilityBase::GetCurrentCooldownTime() const +{ + return 0; +} + +float UGAAbilityBase::GetPeriodTime() const +{ + //if(Activation) + return 0; +} +float UGAAbilityBase::BP_GetPeriodTime() const +{ + return GetPeriodTime(); +} + +float UGAAbilityBase::GetCooldownTime() const +{ + return GetWorld()->GetTimeSeconds() - LastCooldownTime; +} +float UGAAbilityBase::BP_GetCooldownTime() const +{ + return GetCooldownTime(); +} +float UGAAbilityBase::GetActivationTime() const +{ + return GetWorld()->GetTimeSeconds() - LastActivationTime; +} +float UGAAbilityBase::BP_GetActivationTime() const +{ + return GetActivationTime(); +} + +void UGAAbilityBase::OnGameplayTaskInitialized(UGameplayTask& Task) +{ + if (UGAAbilityTask* task = Cast(&Task)) + { + task->Ability = this; + } +} +UGameplayTasksComponent* UGAAbilityBase::GetGameplayTasksComponent(const UGameplayTask& Task) const +{ + return AbilityComponent; +} +/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ +void UGAAbilityBase::OnGameplayTaskActivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Add(&Task); + //AbilityComponent->OnGameplayTaskActivated(Task); +} +/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ +void UGAAbilityBase::OnGameplayTaskDeactivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Remove(&Task); + //AbilityComponent->OnGameplayTaskDeactivated(Task); +} +AActor* UGAAbilityBase::GetGameplayTaskOwner(const UGameplayTask* Task) const +{ + return POwner; +} +AActor* UGAAbilityBase::GetGameplayTaskAvatar(const UGameplayTask* Task) const +{ + return AvatarActor; +} + +class UGAAttributesBase* UGAAbilityBase::GetAttributes() +{ + return Attributes; +} +UGAAbilitiesComponent* UGAAbilityBase::GetAbilityComp() +{ + IIGAAbilities* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->GetAbilityComp(); + } + return nullptr; +} +float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const +{ + return NativeGetAttributeValue(AttributeIn); +} +float UGAAbilityBase::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return Attributes->GetCurrentAttributeValue(AttributeIn); +} +float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const +{ + return Attributes->GetCurrentAttributeValue(AttributeIn); +} +FGAEffectHandle UGAAbilityBase::ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) +{ + return AbilityComponent->ApplyEffectToTarget(EffectIn, InProperty, InContext); +}; +void UGAAbilityBase::RemoveTagContainer(const FGameplayTagContainer& TagsIn) +{ + AbilityComponent->RemoveTagContainer(TagsIn); +}; + +bool UGAAbilityBase::ApplyAttributeCost() +{ + return false; +} +bool UGAAbilityBase::ApplyAbilityAttributeCost() +{ + return true; +} +bool UGAAbilityBase::BP_ApplyAttributeCost() +{ + return ApplyAttributeCost(); +} +bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() +{ + return ApplyAbilityAttributeCost(); +} +bool UGAAbilityBase::IsOnCooldown() +{ + bool bOnCooldown = false; + bOnCooldown = AbilityComponent->IsEffectActive(CooldownEffectHandle); + return bOnCooldown; //temp +} +bool UGAAbilityBase::IsActivating() +{ + bool bAbilityActivating = false; + bAbilityActivating = AbilityComponent->IsEffectActive(ActivationEffect.Handle) || AbilityState == EAFAbilityState::Activating; + return bAbilityActivating; //temp +} +void UGAAbilityBase::BP_ApplyCooldown() +{ + ApplyCooldownEffect(); +} + +float UGAAbilityBase::GetCurrentActivationTime() +{ + if (ActivationEffectHandle.IsValid()) + { + return ActivationEffectHandle.GetEffectPtr()->GetCurrentActivationTime(); + } + return 0; +} + +float UGAAbilityBase::CalculateAnimationSpeed(UAnimMontage* MontageIn) +{ + float ActivationTime = MontageIn->GetPlayLength(); + UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); + float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); + if (DurationCheck > 0) + { + ActivationTime = DurationCheck; + } + float Duration = MontageIn->GetPlayLength(); + + float PlaySpeed = Duration / ActivationTime; + return PlaySpeed; +} + + +bool UGAAbilityBase::IsNameStableForNetworking() const +{ + return bIsNameStable; +} + +void UGAAbilityBase::SetNetAddressable() +{ + bIsNameStable = true; +} + +class UWorld* UGAAbilityBase::GetWorld() const +{ + return World; +} +void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) +{ + AbilityComponent->PlayMontage(MontageIn, SectionName, Speed); +} + +//replication +void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + DOREPLIFETIME(UGAAbilityBase, POwner); + DOREPLIFETIME(UGAAbilityBase, Character); + DOREPLIFETIME(UGAAbilityBase, PCOwner); + DOREPLIFETIME(UGAAbilityBase, AICOwner); + //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. + DOREPLIFETIME(UGAAbilityBase, CooldownStartedCounter); + DOREPLIFETIME(UGAAbilityBase, CooldownEffectExpiredCounter); + DOREPLIFETIME_CONDITION(UGAAbilityBase, ActivationInfo, COND_SkipOwner); + //DOREPLIFETIME(UGAAbilityBase, ActivationInfo); + DOREPLIFETIME(UGAAbilityBase, AbilityActivationStartedCounter); + DOREPLIFETIME(UGAAbilityBase, AbilityPeriodCounter); + DOREPLIFETIME(UGAAbilityBase, InitAbilityCounter); + DOREPLIFETIME(UGAAbilityBase, AbilityHits); + //DOREPLIFETIME(UGAAbilitiesComponent, RepMontage); +} +/* + Do some yet undertemined client stuff. + Call events ? +*/ +void UGAAbilityBase::OnRep_CooldownStarted() +{ + +} +void UGAAbilityBase::OnRep_CooldownExpired() +{ + +} +void UGAAbilityBase::OnRep_AbilityActivationStarted() +{ + +} +void UGAAbilityBase::OnRep_AbilityActivated() +{ + //ApplyActivationEffect(); +} +void UGAAbilityBase::OnRep_AbilityPeriod() +{ + +} +void UGAAbilityBase::OnRep_AbilityHits() +{ + +} + +void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) +{ + AbilityComponent->NativeInputPressed(AbilityTag, ActionName); +} +void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) +{ + AbilityComponent->NativeInputReleased(AbilityTag, ActionName); +} + +/* Tracing Helpers Start */ +bool UGAAbilityBase::LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit) +{ + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); + FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); + + bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); + return bHit; +} +bool UGAAbilityBase::LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + FVector Start = FVector::ZeroVector; + if (OwnerCamera) + { + Start = OwnerCamera->GetComponentLocation(); + } + else + { + FRotator UnusedRot; + POwner->GetActorEyesViewPoint(Start, UnusedRot); + } + FVector End = (POwner->GetBaseAimRotation().Vector() * Range) + Start; + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); + FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); + bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); +#if ENABLE_DRAW_DEBUG + if (DrawDebugType != EDrawDebugTrace::None) + { + bool bPersistent = DrawDebugType == EDrawDebugTrace::Persistent; + float LifeTime = (DrawDebugType == EDrawDebugTrace::ForDuration) ? DrawTime : 0.f; + + // @fixme, draw line with thickness = 2.f? + if (bHit && OutHit.bBlockingHit) + { + // Red up to the blocking hit, green thereafter + ::DrawDebugLine(World, Start, OutHit.ImpactPoint, TraceColor.ToFColor(true), bPersistent, LifeTime); + ::DrawDebugLine(World, OutHit.ImpactPoint, End, TraceHitColor.ToFColor(true), bPersistent, LifeTime); + ::DrawDebugPoint(World, OutHit.ImpactPoint, 16, TraceColor.ToFColor(true), bPersistent, LifeTime); + } + else + { + // no hit means all red + ::DrawDebugLine(World, Start, End, TraceColor.ToFColor(true), bPersistent, LifeTime); + } + } +#endif + return bHit; +} +bool UGAAbilityBase::LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + return false; +} +bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + return false; +} +/* Tracing Helpers End */ \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h new file mode 100644 index 0000000..7ae6152 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -0,0 +1,530 @@ +#pragma once +#include "GAGlobals.h" +#include "../Effects/GAGameEffect.h" +#include "GameplayTasksComponent.h" +#include "GameplayTask.h" +#include "GameplayTaskOwnerInterface.h" +#include "../Attributes/GAAttributesBase.h" +#include "IGAAbilities.h" +#include "AFAbilityActivationSpec.h" +#include "GAAbilityBase.generated.h" + +/* + TODO:: + 1. Add virtual functions, for default behaviours inside ability. + And figure out some clever names for them. Functions like: + ExecuteAbility() + Possibly default input functions. + The interface for it, is not yet fully determined. + It would be best if the functions and names of them, made sense.. For both AI and player + pawns. + 2. Add linked abilities. I'm not 100% sure if it really should be default functionality, + but the idea is that after first ability is executed, it will automatically set next, ability + for execution in chain, and so on, until last ability. Last ability will, simply back to first. + This can be implement as very simple linked list (though I'm not sure about nice BP workflow), + at ability level, OR it can be implemented at component level as queue. + But, from game design perspective implementation on ability level makes more sense. + + Moar TODO: (idk, if the above is still relevelant). + 1. Add simple tracing directly inside ability. Aside from targeting tasks. + + 2. Add caching for effects, so we don;'t create new ones every time, just reference handle. +*/ +/* + Base class for abilities. It will only implement few generic virtual functions, needed by all + abilities. + + Ability is what actor can do, not nessesarly, how actor will go about doing it. + For example we can have jump ability, which is nothing else, than object encapsulating, + access jump function inside Movement Component. + + This way you can give actors, certain abilities, which they can then used based on + some critera (for example defined in Blackboard and Behaviour tree), and if it is + possible for actor to perform ability, he will do it (though, one must be careful to + give abilities, which can be performed by actors, an ordinary actor, can't jump). + + More complicated abilities, can be actions in their own right. Like spells. + + Abilities are using state machine, combined with effects, to perform actions, like + casting, channeling etc. + It needs to be better explained on how each state makes use of effect parameters (Duration, Period). +*/ +DECLARE_MULTICAST_DELEGATE(FGASSimpleAbilityDynamicDelegate); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASGenericAbilityDelegate); +USTRUCT() +struct FGAAbilityTick : public FTickFunction +{ + GENERATED_USTRUCT_BODY() + /** AActor that is the target of this tick **/ + class UGAAbilityBase* Target; + + /** + * Abstract function actually execute the tick. + * @param DeltaTime - frame time to advance, in seconds + * @param TickType - kind of tick for this frame + * @param CurrentThread - thread we are executing on, useful to pass along as new tasks are created + * @param MyCompletionGraphEvent - completion event for this task. Useful for holding the completetion of this task until certain child tasks are complete. + **/ + virtual void ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) override; + /** Abstract function to describe this tick. Used to print messages about illegal cycles in the dependency graph **/ + virtual FString DiagnosticMessage() override; +}; +template<> +struct TStructOpsTypeTraits : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = false + }; +}; +USTRUCT() +struct FGAActiationInfo +{ + GENERATED_USTRUCT_BODY(); + + UPROPERTY() + float TimeStamp; + UPROPERTY() + float Duration; + UPROPERTY() + float Period; + UPROPERTY() + bool bApplyActivationEffect; + + inline void SetActivationInfo(float TimeStampIn, float DurationIn, float PeriodIn, + bool bApplyActivationEffectIn) + { + TimeStamp = TimeStampIn; + Duration = DurationIn; + Period = PeriodIn; + bApplyActivationEffect = bApplyActivationEffectIn; + //always increment to make sure it is replicated. + ForceReplication++; + } + + UPROPERTY() + int8 ForceReplication; +}; + +enum EAFAbilityState +{ + Waiting, + Activating +}; + +UCLASS(BlueprintType, Blueprintable) +class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTaskOwnerInterface, public IIGAAbilities +{ + GENERATED_BODY() +public: + FGAAbilityTick TickFunction; + + /* By default all abilities are considered to be replicated. */ + UPROPERTY(EditAnywhere, Category = "Replication") + bool bReplicate; + + bool bIsNameStable; + + //possibly map TMap ? + UPROPERTY() + TSet ActiveTasks; + /* List of tasks, this ability have. */ + UPROPERTY() + TMap AbilityTasks; + + /* + Delegate is used to confirm ability execution. + After confirming ability will proceed to activation state and either casts instatly or start + casting effect. + */ + FGASSimpleAbilityDynamicDelegate OnConfirmDelegate; + /* + Delegate which is called after ability is confirmed and then cast time ended. + */ + FGASSimpleAbilityDynamicDelegate OnConfirmCastingEndedDelegate; + FSimpleDelegate ConfirmDelegate; + + /* Attributes specific to ability. */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "AbilityFramework|Abilities") + UGAAttributesBase* Attributes; + + UPROPERTY() + class UWorld* World; + /* + Replicated to everyone because we will need it, to determine cosmetic stuff on clients. + */ + /* + */ + UPROPERTY(VisibleAnywhere, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") + APawn* POwner; + UPROPERTY(VisibleAnywhere, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") + ACharacter* Character; + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + APlayerController* PCOwner; + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + class AAIController* AICOwner; + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + class UGAAbilitiesComponent* AbilityComponent; + + /* + Physical reprsentation of ability in game world. It might be sword, gun, or character. + What differs it from pawn or controller is that Avatar is actually used by ability to perform actions. + + It will need some common interfaces for getting data out. + */ + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + class AActor* AvatarActor; + + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UCameraComponent* OwnerCamera; + + FGAEffectContext DefaultContext; + + /* + Tags applied to instigator of this ability, for duration of cooldown. + Duration of this effect equals cooldown of ability. + */ + UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") + FGAEffectProperty CooldownEffect; + FGAEffectHandle CooldownEffectHandle; + /* + Tags applied to the time of activation ability. + Only applies to abilities, which are not instant (for now). + Though even instant abilities have animation time, + they probabaly never apply activation tags, since + main usecase for those tags is to make other abilities + being able to interrupt them. + All abilities with casting/channeling time use it. + + Add Periodic Effect ? (For abilities with period). + */ + UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec"), Category = "Config") + FGAEffectProperty ActivationEffect; + FGAEffectHandle ActivationEffectHandle; + /* + These attributes will be reduced by specified amount when ability is activated. + Attribute cost from Ability Owner attributes + */ + UPROPERTY(EditAnywhere, Category = "Config") + FGAEffectProperty AttributeCost; + /* + Attribute cost from ability own attributes + */ + UPROPERTY(EditAnywhere, Category = "Config") + FGAEffectProperty AbilityAttributeCost; + /* + Probably need that + as well as separate spawned actor, which takes care on it's own for + abilities effect (like lighting strike from heaves into certain hit point); + */ + /* What/Where ability hits landed. Replicated back to client ? */ + UPROPERTY(BlueprintReadOnly, ReplicatedUsing=OnRep_AbilityHits) + FGASAbilityHitArray AbilityHits; + UFUNCTION() + void OnRep_AbilityHits(); + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTag AbilityTag; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer OwnedTags; + /* + These tags are added to owner while ability is activating (or channeled). + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationAddedTags; + /* + These tags must be present on onwer to activate this ability. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationRequiredTags; + /* + If any of these tags is present ability activation is blocked. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationBlockedTags; + +public: //because I'm to lazy to write all those friend states.. + UPROPERTY() + float LastActivationTime; + UPROPERTY() + float LastCooldownTime; + virtual void TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction); + UFUNCTION() + void OnActivationEffectPeriod(const FGAEffectHandle& InHandle); + + UFUNCTION() + void OnRep_CooldownStarted(); + UFUNCTION() + void OnRep_CooldownExpired(); + UFUNCTION() + void OnRep_AbilityActivationStarted(); + UFUNCTION() + void OnRep_AbilityActivated(); + UFUNCTION() + void OnRep_AbilityPeriod(); + /* + Do any needed client side initialization here. + Note that anything created trough this function will exist ONLY on client, this function + was called. + */ + UFUNCTION() + virtual void OnRep_InitAbility(); + + /* Replication counters for above events. */ + UPROPERTY(ReplicatedUsing = OnRep_CooldownStarted) + uint8 CooldownStartedCounter; + UPROPERTY(ReplicatedUsing = OnRep_CooldownExpired) + uint8 CooldownEffectExpiredCounter; + UPROPERTY(ReplicatedUsing = OnRep_AbilityActivationStarted) + uint8 AbilityActivationStartedCounter; + UPROPERTY(ReplicatedUsing = OnRep_AbilityActivated) + FGAActiationInfo ActivationInfo; + UPROPERTY(ReplicatedUsing = OnRep_AbilityPeriod) + uint8 AbilityPeriodCounter; + UPROPERTY(ReplicatedUsing = OnRep_InitAbility) + uint8 InitAbilityCounter; + + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnInputPressedDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnInputReleasedDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnActivateBeginDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnActivationFinishedDelegate; +protected: + EAFAbilityState AbilityState; + +public: + UGAAbilityBase(const FObjectInitializer& ObjectInitializer); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + + virtual void InitAbility(); + /* + Called when ability received input. + One ability can receive multiple input calls, how those will be handled + is up to ability. + */ + void OnNativeInputPressed(FGameplayTag ActionName); + /* + Called when ability receive input press. Does not start ability execution automatically, so it + is safe to make any pre execution preparations of ability here. + + To start ability execution you must call ExecuteAbility. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnInputPressed(FGameplayTag ActionName); + + void OnNativeInputReleased(FGameplayTag ActionName); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnInputReleased(FGameplayTag ActionName); + + + virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); + + void NativeOnAbilityConfirmed(); + + /* + Called when ability get message to activate. + For player it usually means on button press. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivate(); + + /* + Called When activation effect expired. + In case of instant effects, called right after OnActivate. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivationFinished(); + + /* + Called when ability deactivates. + For player it usually means in input release. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnDeactivate(); + /* + In blueprint, call this function to trigger event of the same name, + after ability is ready to be executed (like after targeting is done, input is confirmed, + or simply after receiving first input press. + + This function will trigger selected Activation State, which then will trigger Event OnAbilityExecuted. + In C++ it will trigger OnAbilityExecutedNative(). + + ActiveState will always be called first, so it is possible to bypass entire state stage if ActivationState will + go straight away for event call. + + bApplyActivationEffect - should apply activation effect ? + if Period or Activation is > 0, it will be overrided to true. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void StartActivation(bool bApplyActivationEffect); + + + /* Event called when ability activation has been canceled. */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivationCancel(); + + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnPeriod(); + + /* Event called when ability finishes it's execution. Called AFTER OnAbilityExecuted. */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnFinished(); + + UFUNCTION() + void OnCooldownEffectExpired(); + UFUNCTION() + void NativeOnAbilityActivationFinish(const FGAEffectHandle& InHandle); + UFUNCTION() + void NativeOnAbilityActivationCancel(); + + /* + Finishes ability. Use it to finish ability after activation or released input. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void FinishAbility(); + void NativeFinishAbility(); + /* + Stop effect activation and remove activation effect. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void CancelActivation(); + void NativeCancelActivation(); + + bool IsWaitingForConfirm(); + void ConfirmAbility(); + + bool CanUseAbility(); + bool CanReleaseAbility(); + + float GetCurrentActivationTime() const; + UFUNCTION(BlueprintPure, meta = (DisplayName = "Get Current Activation Time"), Category = "AbilityFramework|Abilities") + float BP_GetCurrentActivationTime() const; + float GetCurrentCooldownTime() const; + + float GetPeriodTime() const; + UFUNCTION(BlueprintPure, meta = (DisplayName = "Get Period Time"), Category = "AbilityFramework|Abilities") + float BP_GetPeriodTime() const; + + float GetCooldownTime() const; + UFUNCTION(BlueprintPure, meta=(DisplayName = "Get Cooldown Time"), Category = "AbilityFramework|Abilities") + float BP_GetCooldownTime() const; + + float GetActivationTime() const; + UFUNCTION(BlueprintPure, meta = (DisplayName = "Get Activation Time"), Category = "AbilityFramework|Abilities") + float BP_GetActivationTime() const; + + /** GameplayTaskOwnerInterface - Begin */ + virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; + /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ + /** Get owner of a task or default one when task is null */ + virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; + + /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ + virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; + + /** Get default priority for running a task */ + virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; + + /** Notify called after GameplayTask finishes initialization (not active yet) */ + virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; + + /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ + virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + + /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ + virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; + /** GameplayTaskOwnerInterface - end */ + + /** IIGAAbilities Begin */ + virtual class UGAAttributesBase* GetAttributes() override; + virtual class UGAAbilitiesComponent* GetAbilityComp() override; + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty) override { Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); }; + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; + + /* IIGAAbilities End **/ + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") + virtual float GetAttributeVal(FGAAttribute AttributeIn) const; + +public: //protected ? + bool ApplyCooldownEffect(); + bool ApplyActivationEffect(bool bApplyActivationEffect); + bool ApplyAttributeCost(); + bool ApplyAbilityAttributeCost(); + bool IsOnCooldown(); + bool IsActivating(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Cooldown"), Category = "AbilityFramework|Abilities") + void BP_ApplyCooldown(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_ApplyAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_ApplyAbilityAttributeCost(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + float GetCurrentActivationTime(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + float CalculateAnimationSpeed(UAnimMontage* MontageIn); + + /* Replication */ + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return bReplicate; + } + void SetNetAddressable(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); + + virtual class UWorld* GetWorld() const override; + + inline void AddAbilityTask(FName InName, class UGAAbilityTask* InTask) + { + if (!AbilityTasks.Contains(InName)) + { + AbilityTasks.Add(InName, InTask); + } + } + inline class UGAAbilityTask* GetAbilityTask(const FName& InName) + { + return AbilityTasks.FindRef(InName); + } + + /* Tracing Helpers Start */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit); + /* Traces location from owner camera position if no camera available traces from eyes */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Traces from ability avatar socket. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Make first trace from camera location and then second trace from avatar socket in direction of first trace. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Tracing Helpers End */ +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp new file mode 100644 index 0000000..71133ea --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAAbilityBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAAbilityBlueprint::UGAAbilityBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAAbilityBlueprint* UGAAbilityBlueprint::FindRootGameplayAbilityBlueprint(UGAAbilityBlueprint* DerivedBlueprint) +{ + UGAAbilityBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAAbilityBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h new file mode 100644 index 0000000..e1c6fef --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h @@ -0,0 +1,31 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAAbilityBlueprint.generated.h" + +/** + * Game Ability Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAAbilityBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() + +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAAbilityBlueprint* FindRootGameplayAbilityBlueprint(UGAAbilityBlueprint* DerivedBlueprint); + +#endif +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp new file mode 100644 index 0000000..fa676e4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAAbilitySet.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h new file mode 100644 index 0000000..68c8637 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h @@ -0,0 +1,21 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Object.h" +#include "../GAGlobals.h" +#include "GAAbilitySet.generated.h" + +/** + * + */ +UCLASS(Blueprintable) +class ABILITYFRAMEWORK_API UGAAbilitySet : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Config") + FGameplayTag AbilityTag; + UPROPERTY(EditAnywhere, Category = "Config") + FGASAbilitySetContainer AbilitySet; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp new file mode 100644 index 0000000..c7db9d7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityTask_SpawnProjectile.h" + + + + +UAFAbilityTask_SpawnProjectile* UAFAbilityTask_SpawnProjectile::Ability_SpawnProjectile(UObject* WorldContextObject, + FName InTaskName, + FVector InStartLocation, + FVector InEndLocation, + float InLaunchSpeed, + float InOverrideGravityZ, + EAFPRojectileSpawnTraceOption InTraceOption, + float InCollisionRadius, + bool InbFavorHighArc, + bool InbDrawDebug) +{ + auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); + MyObj->StartLocation = InStartLocation; + MyObj->EndLocation = InEndLocation; + MyObj->LaunchSpeed = InLaunchSpeed; + MyObj->OverrideGravityZ = InOverrideGravityZ; + MyObj->TraceOption = InTraceOption; + MyObj->CollisionRadius = InCollisionRadius; + MyObj->bFavorHighArc = InbFavorHighArc; + MyObj->bDrawDebug = InbDrawDebug; + return MyObj; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h new file mode 100644 index 0000000..fd47dd4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h @@ -0,0 +1,58 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Abilities/Tasks/GAAbilityTask.h" +#include "AFAbilityTask_SpawnProjectile.generated.h" + +UENUM() +enum class EAFPRojectileSpawnTraceOption : uint8 +{ + DoNotTrace, + TraceFullPath, + OnlyTraceWhileAscending, +}; + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FAFOnPRojectileSpawned); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFAbilityTask_SpawnProjectile : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY() + FVector StartLocation; + UPROPERTY() + FVector EndLocation; + UPROPERTY() + float LaunchSpeed; + UPROPERTY() + float OverrideGravityZ; + UPROPERTY() + EAFPRojectileSpawnTraceOption TraceOption; + UPROPERTY() + float CollisionRadius; + UPROPERTY() + bool bFavorHighArc; + UPROPERTY() + bool bDrawDebug; + + UPROPERTY(BlueprintAssignable) + FAFOnPRojectileSpawned Played; +public: + static UAFAbilityTask_SpawnProjectile* Ability_SpawnProjectile(UObject* WorldContextObject, + FName InTaskName, + FVector InStartLocation, + FVector InEndLocation, + float InLaunchSpeed, + float InOverrideGravityZ, + EAFPRojectileSpawnTraceOption InTraceOption, + float InCollisionRadius, + bool InbFavorHighArc, + bool InbDrawDebug); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp new file mode 100644 index 0000000..294b044 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp @@ -0,0 +1,37 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../../AbilityFramework.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask.h" + +UGAAbilityTask::UGAAbilityTask(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + bTickingTask = false; + bSimulatedTask = false; + bIsSimulating = false; + bOwnedByTasksComponent = false; + bClaimRequiredResources = true; + TaskState = EGameplayTaskState::Uninitialized; + ResourceOverlapPolicy = ETaskResourceOverlapPolicy::StartOnTop; + Priority = FGameplayTasks::DefaultPriority; + + SetFlags(RF_StrongRefOnFrame); +} + +//UWorld* UGAAbilityTask::GetWorld() const +//{ +// return GetOuterUGAAbilityBase()->GetWorld(); +//} + +void UGAAbilityTask::Initialize() +{ + +} + + + +void UGAAbilityTask::EndAbilityTask() +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h new file mode 100644 index 0000000..97572ca --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -0,0 +1,72 @@ +#pragma once +#include "GameplayTask.h" +#include "../GAAbilityBase.h" +#include "../../GAAbilitiesComponent.h" + +//#include "Messaging.h" +#include "MessageEndpoint.h" +#include "MessageEndpointBuilder.h" + +#include "GAAbilityTask.generated.h" +/* + AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and + the should be activated from ability. + Then can perform tasks, like spawn tagetting helpers (splines, circles), spawn actors, + gather targeting data etc. + + Should they be activated automatically after ability is initialized, (it'e ability enterted in + active state, which means it's ready to be fired and display helpers, but did not yet received input, + or should designer in blueprint decide when to launch actions ?). +*/ + +UCLASS(BlueprintType, Blueprintable, Within=GAAbilityBase) +class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask +{ + GENERATED_UCLASS_BODY() + friend struct FAFAbilityTaskMessageTick; +public: + /* Ability owning this task */ + TWeakObjectPtr Ability; + /* Ability owning this task */ + TWeakObjectPtr AbilityComponent; +public: + //virtual UWorld* GetWorld() const override; + + //virtual void Tick(float DeltaSecondsIn); + + virtual void Initialize(); + template + static T* NewAbilityTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) + { + check(WorldContextObject); + + T* MyObj = NewObject(WorldContextObject); + UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); + if (UGAAbilityTask* CachedTask = ThisAbility->GetAbilityTask(InTaskName)) + { + CachedTask->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); + return Cast(CachedTask); + } + MyObj->Ability = ThisAbility; + MyObj->AbilityComponent = ThisAbility->AbilityComponent; + MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); + MyObj->InstanceName = InstanceName; + ThisAbility->AddAbilityTask(InTaskName, MyObj); + return MyObj; + } + + template + static bool DelayedFalse() + { + return false; + } + + // this function has been added to make sure AbilityTasks don't use this method + template + FORCEINLINE static T* NewTask(UObject* WorldContextObject, FName InstanceName = FName()) + { + static_assert(DelayedFalse(), "UAbilityTask::NewTask should never be used. Use NewAbilityTask instead"); + } +protected: + void EndAbilityTask(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp new file mode 100644 index 0000000..ff4e38b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp @@ -0,0 +1,64 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_CreateObject.h" + +UGAAbilityTask_CreateObject* UGAAbilityTask_CreateObject::CreateObject(UObject* WorldContextObject, + FName InTaskName, TSubclassOf Class, UObject* Outer) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + //if(MyObj) + // MyObj->SpawnObject(WorldContextObject, InClass, Outer); + //MyObj->CachedTargetDataHandle = TargetData; + return MyObj; +} + +// --------------------------------------------------------------------------------------- + +bool UGAAbilityTask_CreateObject::BeginSpawningActor(UObject* WorldContextObject, + TSubclassOf Class, UObject*& SpawnedActor) +{ + //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) + //{ + //UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject); + //if (World) + //{ + SpawnedActor = NewObject(WorldContextObject, Class); + //} + //} + + if (SpawnedActor == nullptr) + { + Failure.Broadcast(nullptr); + return false; + } + UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); + return true; +} + +void UGAAbilityTask_CreateObject::FinishSpawningActor(UObject* WorldContextObject, UObject* SpawnedActor) +{ + if (SpawnedActor) + { + FTransform SpawnTransform;// = AbilitySystemComponent->GetOwner()->GetTransform(); + + //if (FGameplayAbilityTargetData* LocationData = CachedTargetDataHandle.Get(0)) //Hardcode to use data 0. It's OK if data isn't useful/valid. + //{ + // //Set location. Rotation is unaffected. + // if (LocationData->HasHitResult()) + // { + // SpawnTransform.SetLocation(LocationData->GetHitResult()->Location); + // } + // else if (LocationData->HasEndPoint()) + // { + // SpawnTransform.SetLocation(LocationData->GetEndPoint()); + // } + //} + + //SpawnedActor->FinishSpawning(SpawnTransform); + + Success.Broadcast(SpawnedActor); + } + UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); + EndTask(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h new file mode 100644 index 0000000..6aa3bed --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_CreateObject.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASSpawnObjectDelegate, class UObject*, SpawnedObject); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_CreateObject : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASSpawnObjectDelegate Success; + UPROPERTY(BlueprintAssignable) + FGASSpawnObjectDelegate Failure; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_CreateObject* CreateObject(UObject* WorldContextObject, + FName InTaskName, TSubclassOf Class, UObject* Outer); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class UObject*& SpawnedActor); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + void FinishSpawningActor(UObject* WorldContextObject, class UObject* SpawnedActor); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp new file mode 100644 index 0000000..4f4622c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../../GAAbilitiesComponent.h" +#include "GAAbilityTask_PlayMontage.h" + +UGAAbilityTask_PlayMontage* UGAAbilityTask_PlayMontage::AbilityPlayMontage(UObject* WorldContextObject, + FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, + bool bInUseActivationTime) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + MyObj->Montage = MontageIn; + MyObj->SectionName = SectionNameIn; + MyObj->PlayRate = PlayRateIn; + MyObj->bUseActivationTime = bInUseActivationTime; + return MyObj; +} + +void UGAAbilityTask_PlayMontage::Activate() +{ + AbilityComponent->OnAbilityNotifyBegin.Unbind(); + AbilityComponent->OnAbilityNotifyTick.Unbind(); + AbilityComponent->OnAbilityNotifyEnd.Unbind(); + + AbilityComponent->OnAbilityNotifyBegin.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastStartNotifyState); + AbilityComponent->OnAbilityNotifyTick.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastTickNotifyState); + AbilityComponent->OnAbilityNotifyEnd.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastEndNotifyState); + if (bUseActivationTime) + { + PlayRate = Ability->CalculateAnimationSpeed(Montage); + Ability->PlayMontage(Montage, SectionName, PlayRate); + } + else + { + Ability->PlayMontage(Montage, SectionName, PlayRate); + } +} + +void UGAAbilityTask_PlayMontage::BroadcastStartNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName) +{ + NotifyBegin.Broadcast(DataIn, InTag, InName); +} +void UGAAbilityTask_PlayMontage::BroadcastEndNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName) +{ + NotifyTick.Broadcast(DataIn, InTag, InName); +} +void UGAAbilityTask_PlayMontage::BroadcastTickNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName) +{ + NotifyEnd.Broadcast(DataIn, InTag, InName); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h new file mode 100644 index 0000000..e7aeb21 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h @@ -0,0 +1,45 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAGlobals.h" +#include "GAAbilityTask_PlayMontage.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FGASGenericMontageDelegate, FAFAbilityNotifyData, Data, FGameplayTag, Tag, FName, NotifyName); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_PlayMontage : public UGAAbilityTask +{ + GENERATED_BODY() + +public: + UPROPERTY(BlueprintReadOnly, meta = (ExposeOnSpawn = true)) + UAnimMontage* Montage; + FName SectionName; + float PlayRate; + bool bUseActivationTime; + + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate Played; + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate NotifyBegin; + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate NotifyTick; + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate NotifyEnd; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_PlayMontage* AbilityPlayMontage(UObject* WorldContextObject, + FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, + bool bInUseActivationTime); + + virtual void Activate() override; + + void BroadcastStartNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName); + void BroadcastEndNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName); + void BroadcastTickNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp new file mode 100644 index 0000000..214da95 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_Repeat.h" + + + + +UGAAbilityTask_Repeat* UGAAbilityTask_Repeat::CreateRepeatTask(UObject* WorldContextObject, + FName InTaskName) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + //MyObj->CachedTargetDataHandle = TargetData; + return MyObj; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h new file mode 100644 index 0000000..338343e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_Repeat.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnTaskRepeated); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_Repeat : public UGAAbilityTask +{ + GENERATED_BODY() + + UPROPERTY(BlueprintAssignable) + FGASOnTaskRepeated OnTaskRepeated; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_Repeat* CreateRepeatTask(UObject* WorldContextObject, + FName InTaskName); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp new file mode 100644 index 0000000..370a513 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp @@ -0,0 +1,70 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_SpawnActor.h" + + + + + +UGAAbilityTask_SpawnActor* UGAAbilityTask_SpawnActor::SpawnActor(UObject* WorldContextObject, + FName InTaskName, TSubclassOf InClass) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + //MyObj->CachedTargetDataHandle = TargetData; + return MyObj; +} + +// --------------------------------------------------------------------------------------- +void UGAAbilityTask_SpawnActor::Activate() +{ + UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); + //EndTask(); +} + +bool UGAAbilityTask_SpawnActor::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf InClass, AActor*& SpawnedActor) +{ + //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) + //{ + UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); + if (World) + { + SpawnedActor = World->SpawnActorDeferred(InClass, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); + } + //} + + if (SpawnedActor == nullptr) + { + Failure.Broadcast(nullptr); + return false; + } + UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); + return true; +} + +void UGAAbilityTask_SpawnActor::FinishSpawningActor(UObject* WorldContextObject, AActor* SpawnedActor) +{ + if (SpawnedActor) + { + FTransform SpawnTransform;// = AbilitySystemComponent->GetOwner()->GetTransform(); + + //if (FGameplayAbilityTargetData* LocationData = CachedTargetDataHandle.Get(0)) //Hardcode to use data 0. It's OK if data isn't useful/valid. + //{ + // //Set location. Rotation is unaffected. + // if (LocationData->HasHitResult()) + // { + // SpawnTransform.SetLocation(LocationData->GetHitResult()->Location); + // } + // else if (LocationData->HasEndPoint()) + // { + // SpawnTransform.SetLocation(LocationData->GetEndPoint()); + // } + //} + + SpawnedActor->FinishSpawning(SpawnTransform); + + Success.Broadcast(SpawnedActor); + } + UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); + //EndTask(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h new file mode 100644 index 0000000..162fb88 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_SpawnActor.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASSpawnActorDelegate, AActor*, SpawnedActor); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_SpawnActor : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASSpawnActorDelegate Success; + UPROPERTY(BlueprintAssignable) + FGASSpawnActorDelegate Failure; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_SpawnActor* SpawnActor(UObject* WorldContextObject, + FName InTaskName, TSubclassOf Class); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AActor*& SpawnedActor); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + void FinishSpawningActor(UObject* WorldContextObject, AActor* SpawnedActor); + + virtual void Activate() override; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp new file mode 100644 index 0000000..4e137d1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp @@ -0,0 +1,163 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../../Targeting/GASAbilityTargetingObject.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask_TargetData.h" + + +UGAAbilityTask_TargetData* UGAAbilityTask_TargetData::CreateTargetDataTask(UObject* WorldContextObject, + FName InTaskName, + bool bDrawDebug, + bool bDrawCorrectedDebug, + bool bUseCorrectedTrace, + EGASConfirmType ConfirmTypeIn, + float Range) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + + if (MyObj) + { + MyObj->Range = Range; + MyObj->ConfirmType = ConfirmTypeIn; + MyObj->bIsTickable = false; + MyObj->bDrawDebug = bDrawDebug; + MyObj->bDrawCorrectedDebug = bDrawCorrectedDebug; + MyObj->bUseCorrectedTrace = bUseCorrectedTrace; + } + return MyObj; +} + +void UGAAbilityTask_TargetData::Activate() +{ + switch (ConfirmType) + { + case EGASConfirmType::Instant: + { + FHitResult Hit = LineTrace(); + OnReceiveTargetData.Broadcast(Hit); + EndTask(); + break; + } + case EGASConfirmType::WaitForConfirm: + { + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetData::OnConfirm); + bIsTickable = true; + } + if (!Ability->OnConfirmCastingEndedDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmCastingEndedDelegate.AddUObject(this, &UGAAbilityTask_TargetData::OnCastEndedConfirm); + } + } + break; + } + } + if (TargetObj) + { + UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); + } + else + { + UE_LOG(AbilityFramework, Log, TEXT("TArget object is null.")); + } +} + +// --------------------------------------------------------------------------------------- + +void UGAAbilityTask_TargetData::OnConfirm() +{ + FHitResult Hit(ForceInit);// = LineTrace(); + OnConfirmed.Broadcast(Hit); + Ability->OnConfirmDelegate.RemoveAll(this); +} +void UGAAbilityTask_TargetData::OnCastEndedConfirm() +{ + FHitResult Hit = LineTrace(); + OnReceiveTargetData.Broadcast(Hit); + bIsTickable = false; + EndTask(); +} +void UGAAbilityTask_TargetData::Tick(float DeltaTime) +{ + //FHitResult HitOut = LineTrace(); +} + +FHitResult UGAAbilityTask_TargetData::LineTrace() +{ + FHitResult HitOut; + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + UCameraComponent* Camera = Ability->OwnerCamera; + FVector TraceStart; + FRotator UnusedRot; + if (PC) + { + PC->PlayerCameraManager->GetCameraViewPoint(TraceStart, UnusedRot); +// TraceStart = Camera->GetComponentLocation(); + } + else + { + UnusedRot = P->GetBaseAimRotation(); + TraceStart = P->GetPawnViewLocation(); + } + + FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; + UWorld* World = GetWorld(); + FCollisionQueryParams ColParams; + ColParams.AddIgnoredActor(P); + FCollisionResponseParams ColResp; + World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + if (HitOut.bBlockingHit) + { + FHitResult NewHit; + FVector Start = P->GetPawnViewLocation(); + FVector NewDir = (HitOut.Location - Start).GetSafeNormal(); + float Distance = FVector::Dist(Start, HitOut.Location); + FVector End = Start + (NewDir * Range); + World->LineTraceSingleByChannel(NewHit, Start, End, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + + if (bDrawCorrectedDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, true, 2);// GetWorld()->DeltaTimeSeconds); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + } + } + } + else + { + FHitResult NewHit; + FVector Start = P->GetPawnViewLocation(); + FVector NewDir = (TraceEnd - Start).GetSafeNormal(); + float Distance = Range - FVector::Dist(TraceStart, Start); + FVector End = Start + (NewDir * Distance); + + World->LineTraceSingleByChannel(NewHit, Start, End, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + + if (bDrawCorrectedDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, true, 2);//GetWorld()->DeltaTimeSeconds); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + } + } + } + if (bDrawDebug) + { + if (HitOut.bBlockingHit) + { + DrawDebugLine(GetWorld(), TraceStart, HitOut.ImpactPoint, FColor::Red, true, 2);//GetWorld()->DeltaTimeSeconds); + DrawDebugPoint(GetWorld(), HitOut.Location, 8, FColor::Red, true, 2);//GetWorld()->DeltaTimeSeconds); + } + DrawDebugLine(GetWorld(), TraceStart, TraceEnd, FColor::Green, true, 2);//GetWorld()->DeltaTimeSeconds); + } + return HitOut; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h new file mode 100644 index 0000000..7f023be --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h @@ -0,0 +1,67 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_TargetData.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASOnReceiveTargetData, const FHitResult&, HitResult); + +UENUM() +enum class EGASConfirmType : uint8 +{ + Instant, + WaitForConfirm +}; + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_TargetData : public UGAAbilityTask, public FTickableGameObject +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnReceiveTargetData OnConfirmed; + UPROPERTY(BlueprintAssignable) + FGASOnReceiveTargetData OnReceiveTargetData; + + UPROPERTY() + class UGASAbilityTargetingObject* TargetObj; + + EGASConfirmType ConfirmType; + + float Range; + bool bIsTickable; + bool bDrawDebug; + bool bDrawCorrectedDebug; + bool bUseCorrectedTrace; +public: + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_TargetData* CreateTargetDataTask(UObject* WorldContextObject, + FName InTaskName, + bool bDrawDebug, + bool bDrawCorrectedDebug, + bool bUseCorrectedTrace, + EGASConfirmType ConfirmTypeIn, + float Range); + + virtual void Activate() override; + + UFUNCTION() + void OnConfirm(); + + UFUNCTION() + void OnCastEndedConfirm(); + + /* FTickableGameObject Begin */ + virtual void Tick(float DeltaTime) override; + virtual bool IsTickable() const override { return bIsTickable; } + virtual TStatId GetStatId() const override { RETURN_QUICK_DECLARE_CYCLE_STAT(UGAAbilityTask_TargetData, STATGROUP_Tickables); }; + /* FTickableGameObject End */ + +protected: + FHitResult LineTrace(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp new file mode 100644 index 0000000..a2f56eb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp @@ -0,0 +1,85 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../../Targeting/GASAbilityTargetingObject.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask_TargetDataCircle.h" + + +UGAAbilityTask_TargetDataCircle* UGAAbilityTask_TargetDataCircle::TargetCircleDataTask(UObject* WorldContextObject, + FName InTaskName, TSubclassOf Class, EGASConfirmType ConfirmTypeIn) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + + if (MyObj) + { + MyObj->ConfirmType = ConfirmTypeIn; + } + return MyObj; +} + +void UGAAbilityTask_TargetDataCircle::Activate() +{ + switch (ConfirmType) + { + case EGASConfirmType::Instant: + { + TargetObj2->GetTarget(); + } + case EGASConfirmType::WaitForConfirm: + { + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetDataCircle::OnConfirm); + } + } + } + } + if (TargetObj2) + { + UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); + } + else + { + UE_LOG(AbilityFramework, Log, TEXT("TArget object is null.")); + } + //EndTask(); +} + +// --------------------------------------------------------------------------------------- + +bool UGAAbilityTask_TargetDataCircle::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, UGASAbilityTargetingObject*& SpawnedActor) +{ + SpawnedActor = Class.GetDefaultObject();//NewObject(WorldContextObject, Class); + + if (SpawnedActor == nullptr) + { + //Failure.Broadcast(nullptr); + return false; + } + else + { + TargetObj2 = SpawnedActor; + SpawnedActor->AbilityOwner = Ability; + } + UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); + return true; +} + +void UGAAbilityTask_TargetDataCircle::FinishSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject* SpawnedActor) +{ + if (SpawnedActor) + { + //Success.Broadcast(SpawnedActor); + } + UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); + ReadyForActivation(); +} + +void UGAAbilityTask_TargetDataCircle::OnConfirm() +{ + TargetObj2->GetTarget(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h new file mode 100644 index 0000000..39a60b7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h @@ -0,0 +1,43 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_TargetData.h" +#include "GAAbilityTask_TargetDataCircle.generated.h" + +//DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASOnReceiveTargetData, const FHitResult&, HitResult); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataCircle : public UGAAbilityTask_TargetData +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnReceiveTargetData OnReceiveTargetDataCircle; + + UPROPERTY() + class UGASAbilityTargetingObject* TargetObj2; + + EGASConfirmType ConfirmType; + +public: + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_TargetDataCircle* TargetCircleDataTask(UObject* WorldContextObject, + FName InTaskName, TSubclassOf Class, EGASConfirmType ConfirmTypeIn); + + virtual void Activate() override; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class UGASAbilityTargetingObject*& SpawnedActor); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + void FinishSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject* SpawnedActor); + // + + UFUNCTION() + void OnConfirm(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp new file mode 100644 index 0000000..6114296 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp @@ -0,0 +1,33 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask_WaitForConfirm.h" + + + + +UGAAbilityTask_WaitForConfirm* UGAAbilityTask_WaitForConfirm::CreateWaitConfirmTask(UObject* WorldContextObject, + FName InTaskName) +{ + auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); + return MyObj; +} +void UGAAbilityTask_WaitForConfirm::Activate() +{ + if (AbilityComponent.IsValid() && Ability.IsValid()) + { + GetOuterUGAAbilityBase()->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_WaitForConfirm::OnConfirm); + } +} +void UGAAbilityTask_WaitForConfirm::Initialize() +{ + +} + +void UGAAbilityTask_WaitForConfirm::OnConfirm() +{ + Ability->OnConfirmDelegate.Clear(); + OnConfirmed.Broadcast(); + EndAbilityTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h new file mode 100644 index 0000000..39c8203 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_WaitForConfirm.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnConfirmed); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_WaitForConfirm : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnConfirmed OnConfirmed; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_WaitForConfirm* CreateWaitConfirmTask(UObject* WorldContextObject, + FName InTaskName); + + virtual void Activate() override; + virtual void Initialize() override; + + UFUNCTION() + void OnConfirm(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp new file mode 100644 index 0000000..16f4455 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp @@ -0,0 +1,94 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../../Targeting/GATargetingActor.h" +#include "GAAbilityTask_WaitTargetData.h" + + +UGAAbilityTask_WaitTargetData::UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bTickingTask = true; +} + + +UGAAbilityTask_WaitTargetData* UGAAbilityTask_WaitTargetData::WaitTargetData(UObject* WorldContextObject, + FName InTaskName, TSubclassOf InClass, float InRange, ETraceTypeQuery InTraceChannel) +{ + auto MyObj = NewAbilityTask(WorldContextObject, "UGAAbilityTask_WaitTargetData"); + MyObj->Range = InRange; + MyObj->TraceChannel = InTraceChannel; + return MyObj; +} + +// --------------------------------------------------------------------------------------- +void UGAAbilityTask_WaitTargetData::Activate() +{ + UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_WaitTargetData::OnConfirm); + //Ability->ConfirmDelegate.CreateUObject(this, &UGAAbilityTask_WaitForConfirm::OnConfirm); + } +} + +bool UGAAbilityTask_WaitTargetData::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AGATargetingActor*& SpawnedActor) +{ + UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); + if (World) + { + SpawnedActor = World->SpawnActorDeferred(Class, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); + } + + if (SpawnedActor == nullptr) + { + return false; + } + UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); + return true; +} + +void UGAAbilityTask_WaitTargetData::FinishSpawningActor(UObject* WorldContextObject, AGATargetingActor* SpawnedActor) +{ + if (SpawnedActor) + { + FTransform SpawnTransform; + SpawnedActor->FinishSpawning(SpawnTransform); + TargetActor = SpawnedActor; + } + ReadyForActivation(); + UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); +} +void UGAAbilityTask_WaitTargetData::TickTask(float DeltaTime) +{ + if (TargetActor && Ability.IsValid()) + { + FHitResult OutHit; + bool bHit = Ability->LineTraceSingleByChannelFromCamera(Range, TraceChannel, false, OutHit, + EDrawDebugTrace::Type::None, true, FLinearColor::Green, FLinearColor::Red, 2); + if (bHit) + { + TargetActor->SetActorLocation(OutHit.Location); + } + else + { + TargetActor->SetActorLocation(OutHit.TraceEnd); + } + } +} +void UGAAbilityTask_WaitTargetData::OnDestroy(bool bInOwnerFinished) +{ + Super::OnDestroy(bInOwnerFinished); + if (TargetActor) + { + TargetActor->SetActorHiddenInGame(true); + TargetActor->Destroy(); + } +} +void UGAAbilityTask_WaitTargetData::OnConfirm() +{ + Ability->OnConfirmDelegate.Clear(); + OnConfirmed.Broadcast(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h new file mode 100644 index 0000000..b39ec7f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h @@ -0,0 +1,47 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_WaitTargetData.generated.h" +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnTargetingTaskConfimred); + +/** + * + */ +UCLASS(meta = (ExposedAsyncProxy)) +class ABILITYFRAMEWORK_API UGAAbilityTask_WaitTargetData : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnTargetingTaskConfimred OnConfirmed; + + UPROPERTY() + float Range; + ETraceTypeQuery TraceChannel; + UPROPERTY() + class AGATargetingActor* TargetActor; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_WaitTargetData* WaitTargetData(UObject* WorldContextObject, + FName InTaskName, TSubclassOf Class, float InRange, ETraceTypeQuery InTraceChannel); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class AGATargetingActor*& SpawnedActor); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + void FinishSpawningActor(UObject* WorldContextObject, class AGATargetingActor* SpawnedActor); + + virtual void Activate() override; + + virtual void TickTask(float DeltaTime) override; + + virtual void OnDestroy(bool bInOwnerFinished) override; + + UFUNCTION() + void OnConfirm(); + +public: + UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp new file mode 100644 index 0000000..637d50f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp @@ -0,0 +1,19 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../Abilities/GAAbilityBase.h" +#include "GAAbilityCue.h" + +UGAAbilityCue::UGAAbilityCue(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} +UWorld* UGAAbilityCue::GetWorld() const +{ + return GetOuterUGAAbilityBase()->GetWorld(); +} +APawn* UGAAbilityCue::GetPawnOwner() const +{ + return GetOuterUGAAbilityBase()->POwner; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h new file mode 100644 index 0000000..c311aea --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h @@ -0,0 +1,68 @@ +#pragma once +#include "GAAbilityCue.generated.h" +/* + Ability cues are object, which will spawn cosmetic effects, for abilities. + + Make it actor, or make them spawn actors and/or component ? + + If the former I would need to replicate this trough ability actor, which would + own particular cue. + ///bla bla don't know if above is still relevelant. + + But. + AbilityCues will spawn only effects, sounds, etc at locations, which are available trough Pawn. + Be it socket on weapon, skeleton, or direct pawn location. + + For spawning effects at arbitrary world location, one should use GACueActor. + Though technically there is nothing stoping anyone from spawning PSC at world location, trough trace. + + Neither AbilityCue or CueActor will spawn effects on other actor/pawn, since they don't have information + about target. + + Only Effects, can spawn Cues, which will add Cues at Other Actor/Target location. +*/ +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInLineNew, Within = GAAbilityBase) +class ABILITYFRAMEWORK_API UGAAbilityCue : public UObject +{ + GENERATED_UCLASS_BODY() +public: + virtual UWorld* GetWorld() const override; + + UFUNCTION(BlueprintPure, Category = "Game Abilities") + APawn* GetPawnOwner() const; + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnCooldownStart(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnCooldownExpired(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityActivationStart(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityActivated(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityPeriod(); + + //from ability anim notifies: + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityStartNotify(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityEndNotify(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotify(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotifyStateStart(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotifyStateTick(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotifyStateEnd(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp new file mode 100644 index 0000000..9fc3290 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GACueActor.h" + + +// Sets default values +AGACueActor::AGACueActor(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + DefaultRoot = ObjectInitializer.CreateDefaultSubobject(this, TEXT("DefaultRoot")); + RootComponent = DefaultRoot; +} + +// Called when the game starts or when spawned +void AGACueActor::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AGACueActor::Tick( float DeltaTime ) +{ + Super::Tick( DeltaTime ); + +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h new file mode 100644 index 0000000..cbb5616 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h @@ -0,0 +1,73 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Actor.h" +#include "GACueActor.generated.h" + +UCLASS() +class ABILITYFRAMEWORK_API AGACueActor : public AActor +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "Abilities") + class UGAAbilityBase* OwningAbility; + + UPROPERTY(BlueprintReadOnly, VisibleAnywhere, Category = "Root") + USceneComponent* DefaultRoot; + +public: + // Sets default values for this actor's properties + AGACueActor(const FObjectInitializer& ObjectInitializer); + + // Called when the game starts or when spawned + virtual void BeginPlay() override; + + // Called every frame + virtual void Tick( float DeltaSeconds ) override; + + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnActivated(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnDeactivated(); + /* + Mirros what is inside Object version. + */ + /**/ + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnCooldownStart(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnCooldownExpired(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityActivationStart(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityActivated(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityPeriod(); + + //from ability anim notifies: + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityStartNotify(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityEndNotify(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotify(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotifyStateStart(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotifyStateTick(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") + void OnAbilityNotifyStateEnd(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs new file mode 100644 index 0000000..df3c7a8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -0,0 +1,71 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +namespace UnrealBuildTool.Rules +{ + public class AbilityFramework : ModuleRules + { + public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) + { + PublicIncludePaths.AddRange( + new string[] { + "AbilityFramework", + "AbilityFramework/Abilities", + "AbilityFramework/Attributes", + "AbilityFramework/Effects" + // ... add public include paths required here ... + } + ); + + PrivateIncludePaths.AddRange( + new string[] { + "AbilityFramework", + "AbilityFramework/Abilities", + "AbilityFramework/Attributes", + "AbilityFramework/Effects", + "AbilityFramework/Private", + // ... add other private include paths required here ... + } + ); + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + "CoreUObject", + "Engine", + "GameplayTags", + "InputCore", + "UMG", + "Slate", + "SlateCore", + "GameplayTasks", + "AIModule", + "MovieScene", + "MovieSceneTracks", + + // ... add other public dependencies that you statically link with here ... + } + ); + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "ActorSequence" + // ... add private dependencies that you statically link with here ... + } + ); + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + + // ... add any modules that your module loads dynamically here ... + } + ); + if (Target.Type == TargetRules.TargetType.Editor) + { + PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); + } + } + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp new file mode 100644 index 0000000..4f11d80 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "AbilityFramework.h" +#include "IAbilityFramework.h" +DEFINE_LOG_CATEGORY(AbilityFramework); +DEFINE_LOG_CATEGORY(GameAttributesGeneral); +DEFINE_LOG_CATEGORY(GameAttributes); +DEFINE_LOG_CATEGORY(GameAttributesEffects); +class FAbilityFramework : public IAbilityFramework +{ + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; + +IMPLEMENT_MODULE( FAbilityFramework, AbilityFramework) + + + +void FAbilityFramework::StartupModule() +{ + // This code will execute after your module is loaded into memory (but after global variables are initialized, of course.) +} + + +void FAbilityFramework::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h new file mode 100644 index 0000000..59764c8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h @@ -0,0 +1,21 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "Engine.h" + +#include "InputCoreTypes.h" + +#include "Runtime/UMG/Public/UMG.h" +#include "Runtime/UMG/Public/UMGStyle.h" +#include "Runtime/UMG/Public/Slate/SObjectWidget.h" +#include "Runtime/UMG/Public/IUMGModule.h" +#include "Runtime/UMG/Public/Blueprint/UserWidget.h" +//#include "GameTrace.h" + +DECLARE_LOG_CATEGORY_EXTERN(AbilityFramework, Log, All); + +DECLARE_LOG_CATEGORY_EXTERN(GameAttributesGeneral, Log, All); + +DECLARE_LOG_CATEGORY_EXTERN(GameAttributes, Log, All); + +DECLARE_LOG_CATEGORY_EXTERN(GameAttributesEffects, Log, All); \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp new file mode 100644 index 0000000..8582b2b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp @@ -0,0 +1,33 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "IGAAbilities.h" +#include "GAAbilitiesComponent.h" +#include "AFAbilityNotifyState.h" + + + + +void UAFAbilityNotifyState::NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) +{ + IIGAAbilities* IAbilities = Cast(MeshComp->GetOwner()); + if (IAbilities) + { + CachedAbilitiesComp = IAbilities->GetAbilityComp(); + CachedAbilitiesComp->OnAbilityNotifyBegin.ExecuteIfBound(Data, Tag, Name); + } +} +void UAFAbilityNotifyState::NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) +{ + if (CachedAbilitiesComp) + { + CachedAbilitiesComp->OnAbilityNotifyTick.ExecuteIfBound(Data, Tag, Name); + } +} +void UAFAbilityNotifyState::NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) +{ + if (CachedAbilitiesComp) + { + CachedAbilitiesComp->OnAbilityNotifyEnd.ExecuteIfBound(Data, Tag, Name); + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h new file mode 100644 index 0000000..26b8d67 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Animation/AnimNotifies/AnimNotifyState.h" +#include "GAGlobals.h" +#include "AFAbilityNotifyState.generated.h" + +/** + * + */ +UCLASS(meta = (DisplayName = "Ability Notify State")) +class ABILITYFRAMEWORK_API UAFAbilityNotifyState : public UAnimNotifyState +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Data") + FAFAbilityNotifyData Data; + UPROPERTY(EditAnywhere) + FGameplayTag Tag; + UPROPERTY(EditAnywhere) + FName Name; + UPROPERTY() + class UGAAbilitiesComponent* CachedAbilitiesComp; +public: + virtual void NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) override; + virtual void NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) override; + virtual void NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) override; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp new file mode 100644 index 0000000..04bfe19 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAAbilitiesComponent.h" +#include "IGAAbilities.h" +#include "AFAnimNotify.h" + + + + +void UAFAnimNotify::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) +{ + IIGAAbilities* IAbilities = Cast(MeshComp->GetOwner()); + if (!IAbilities) + return; + + UGAAbilitiesComponent* Comp = IAbilities->GetAbilityComp(); + Comp->OnAbilityNotifyBegin.ExecuteIfBound(Data, Tag, Name); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h new file mode 100644 index 0000000..dbc5ecd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Animation/AnimNotifies/AnimNotify.h" +#include "GAGlobals.h" +#include "AFAnimNotify.generated.h" + +/** + * + */ +UCLASS(meta=(DisplayName = "Ability Notify")) +class ABILITYFRAMEWORK_API UAFAnimNotify : public UAnimNotify +{ + GENERATED_BODY() + + virtual void Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) override; + + UPROPERTY(EditAnywhere) + FAFAbilityNotifyData Data; + UPROPERTY(EditAnywhere) + FGameplayTag Tag; + UPROPERTY(EditAnywhere) + FName Name; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp new file mode 100644 index 0000000..c4ab571 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp @@ -0,0 +1,18 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAAbilitiesComponent.h" +#include "IGAAbilities.h" +#include "AFAnimNotifyBase.h" + + + + +void UAFAnimNotifyBase::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) +{ + IIGAAbilities* IAbilities = Cast(MeshComp->GetOwner()); + if (!IAbilities) + return; + + UGAAbilitiesComponent* Comp = IAbilities->GetAbilityComp(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h new file mode 100644 index 0000000..e6172d5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Animation/AnimNotifies/AnimNotify.h" +#include "GAGlobals.h" +#include "AFAnimNotifyBase.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFAnimNotifyBase : public UAnimNotify +{ + GENERATED_BODY() + + virtual void Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) override; + + UPROPERTY(EditAnywhere) + FAFAbilityNotifyData Data; + UPROPERTY(EditAnywhere) + FGameplayTag Tag; + UPROPERTY(EditAnywhere) + FName Name; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp new file mode 100644 index 0000000..3b3fd86 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp @@ -0,0 +1,12 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AsyncUObject.h" + + +void UAsyncUObject::JustTestFunction() +{ + float qwe = 0; + float vcx = 0; +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h new file mode 100644 index 0000000..c9e61f5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h @@ -0,0 +1,47 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "UObject/NoExportTypes.h" +#include "HAL/Runnable.h" +#include "AsyncUObject.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAsyncUObject : public UObject, public FRunnable +{ + GENERATED_BODY() + +public: + void JustTestFunction(); + + virtual uint32 Run() override + { + /* Obj = NewObject(Outer.Get(), UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); + if (Obj.IsValid()) + { + Obj->JustTestFunction(); + }*/ + JustTestFunction(); + float somerandomcrap = 0; + return 0; + } + + /** + * Stops the runnable object. + * + * This is called if a thread is requested to terminate early. + * @see Init, Run, Exit + */ + virtual void Stop() override { } + + /** + * Exits the runnable object. + * + * Called in the context of the aggregating thread to perform any cleanup. + * @see Init, Run, Stop + */ + virtual void Exit() override { } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp new file mode 100644 index 0000000..64522ae --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp @@ -0,0 +1,12 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AsyncUObjectImpl.h" + +AsyncUObjectImpl::AsyncUObjectImpl() +{ +} + +AsyncUObjectImpl::~AsyncUObjectImpl() +{ +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h new file mode 100644 index 0000000..a5c4c99 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h @@ -0,0 +1,61 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "HAL/Runnable.h" +#include "AsyncUObject.h" +class FAsyncUObjectRunnable : public FRunnable +{ +public: + FAsyncUObjectRunnable() + { + + } + FAsyncUObjectRunnable(class UObject* InOuter) + { + Outer = InOuter; + } + /*Runs the runnable object. + * + * This is where all per object thread work is done.This is only called if the initialization was successful. + * + * @return The exit code of the runnable object + * @see Init, Stop, Exit + */ + virtual uint32 Run() override + { + Obj = NewObject(Outer.Get(), UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); + if (Obj.IsValid()) + { + Obj->JustTestFunction(); + } + return 0; + } + + /** + * Stops the runnable object. + * + * This is called if a thread is requested to terminate early. + * @see Init, Run, Exit + */ + virtual void Stop() override { } + + /** + * Exits the runnable object. + * + * Called in the context of the aggregating thread to perform any cleanup. + * @see Init, Run, Stop + */ + virtual void Exit() override { } +private: + TWeakObjectPtr Obj; + TWeakObjectPtr Outer; +}; +/** + * + */ +class ABILITYFRAMEWORK_API AsyncUObjectImpl +{ +public: + AsyncUObjectImpl(); + ~AsyncUObjectImpl(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp new file mode 100644 index 0000000..80cb475 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -0,0 +1,282 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GameplayTagContainer.h" +#include "../GAAbilitiesComponent.h" +#include "GAAttributesBase.h" +#include "../IGAAbilities.h" + +#include "GAAttributeBase.h" +DEFINE_STAT(STAT_CalculateBonus); +DEFINE_STAT(STAT_CurrentBonusByTag); +DEFINE_STAT(STAT_FinalBonusByTag); +//UGAAttributeBase::UGAAttributeBase(const FObjectInitializer& ObjectInitializer) +// : Super(ObjectInitializer) +//{ +// +//} +FAFAttributeBase::FAFAttributeBase() + : CurrentValue(0), + BonusValue(0) +{ + Modifiers.AddDefaulted(7); +}; +FAFAttributeBase::FAFAttributeBase(float BaseValueIn) + : BaseValue(BaseValueIn), + CurrentValue(BaseValue), + BonusValue(0) +{ + Modifiers.AddDefaulted(7); +}; + + +void FAFAttributeBase::InitializeAttribute() +{ + CurrentValue = BaseValue; + CalculateBonus(); + CurrentValue = GetFinalValue(); + Modifiers.Empty(); + Modifiers.AddDefaulted(7);// static_cast(EGAAttributeMod::Invalid)); + //Modifiers.AddDefaulted(static_cast(EGAAttributeMod::Invalid)); + +} + +void FAFAttributeBase::CalculateBonus() +{ + SCOPE_CYCLE_COUNTER(STAT_CalculateBonus); + float AdditiveBonus = 0; + float SubtractBonus = 0; + float MultiplyBonus = 1; + float DivideBonus = 1; + //auto ModIt = Modifiers.CreateConstIterator(); + TMap& Additive = Modifiers[static_cast(EGAAttributeMod::Add)]; + TMap& Subtractive = Modifiers[static_cast(EGAAttributeMod::Subtract)]; + TMap& Multiplicative = Modifiers[static_cast(EGAAttributeMod::Multiply)]; + TMap& Divide = Modifiers[static_cast(EGAAttributeMod::Divide)]; + for (auto ModIt = Additive.CreateConstIterator(); ModIt; ++ModIt) + { + AdditiveBonus += ModIt->Value.Value; + } + for (auto ModIt = Subtractive.CreateConstIterator(); ModIt; ++ModIt) + { + SubtractBonus += ModIt->Value.Value; + } + for (auto ModIt = Multiplicative.CreateConstIterator(); ModIt; ++ModIt) + { + MultiplyBonus += ModIt->Value.Value; + } + for (auto ModIt = Divide.CreateConstIterator(); ModIt; ++ModIt) + { + DivideBonus += ModIt->Value.Value; + } + //for (ModIt; ModIt; ++ModIt) + //{ + // const FGAEffectMod& mod = ModIt->Value; + // switch (mod.AttributeMod) + // { + // case EGAAttributeMod::Add: + // AdditiveBonus += mod.Value; + // break; + // case EGAAttributeMod::Subtract: + // SubtractBonus += mod.Value; + // break; + // case EGAAttributeMod::Multiply: + // MultiplyBonus += mod.Value; + // break; + // case EGAAttributeMod::Divide: + // DivideBonus += mod.Value; + // break; + // default: + // break; + // } + //} + float OldBonus = BonusValue; + //calculate final bonus from modifiers values. + //we don't handle stacking here. It's checked and handled before effect is added. + BonusValue = (AdditiveBonus - SubtractBonus); + BonusValue = (BonusValue * MultiplyBonus); + BonusValue = (BonusValue / DivideBonus); + //this is absolute maximum (not clamped right now). + float addValue = BonusValue - OldBonus; + //reset to max = 200 + CurrentValue = CurrentValue + addValue; + /* + BaseValue = 200; + CurrentValue = 200; + BonusValue = 50; + CurrentValue = 200 + 50; + CurentValue == 250; + + Damage taken. + CurrentValue = 250 - 25; + CurrentValue == 225; + Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; + Expected Result : 175; (225 - 50) + OldBonusValue = 50; + BonusValue = 0; + CurrentValue == 225; + BonusValue - OldBonusValue = -50; + CurrentValue = CurrentValue + (-50); ?? + + TwoBonuses 50 + 50; + CurrentValue = 300 - 25; + CurrentValue == 275; + Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; + Expected Result : 225; (275 - 50) + OldBonusValue = 100; + BonusValue = 50; + CurrentValue == 225; + BonusValue - OldBonusValue = -50; + CurrentValue = CurrentValue + (-50); ?? + + Inverse Bonus is going to be Increased: + TwoBonuses 50 + 50; + CurrentValue = 300 - 25; + CurrentValue == 275; + Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; + Expected Result : 325; (275 + 50) + OldBonusValue = 100; + new BonusValue = 150; (new bonus gives +50) + CurrentValue == 275; + BonusValue - OldBonusValue = 50; (150 - 100) = 50 + CurrentValue = CurrentValue + (50); ?? + */ +} +//check for tags. +bool FAFAttributeBase::CheckIfModsMatch(const FGAEffectHandle& InHandle, const FGAEffectMod& InMod) +{ + TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; + auto It = mods.CreateConstIterator(); + for (It; It; ++It) + { + if (It->Key.HasAllAttributeTags(InHandle)) //or maybe the other way around ? + { + return true; + } + } + if (mods.Num() <= 0) + return true; + return false; +} +bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) +{ + TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; + auto It = mods.CreateConstIterator(); + for (It; It; ++It) + { + if (InMod > It->Value) + { + return true; + } + } + if (mods.Num() <= 0) + { + return true; + } + return false; +} +float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + FGAEffectProperty& InProperty) +{ + float returnValue = -1; + bool isPeriod = InProperty.Period > 0; + bool IsDuration = InProperty.Duration > 0; + if ( !isPeriod & IsDuration) + { + FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); + AttrMod.Tags.AppendTags(HandleIn.GetEffectSpec()->AttributeTags); + AddBonus(ModIn, HandleIn); + return ModIn.Value; + } + else + { + switch (ModIn.AttributeMod) + { + case EGAAttributeMod::Add: + { + float OldCurrentValue = CurrentValue; + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: OldCurrentValue: %f"), OldCurrentValue); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: AddValue: %f"), ModIn.Value); + float Val = CurrentValue - (OldCurrentValue + ModIn.Value); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: ActuallAddVal: %f"), Val); + CurrentValue -= Val; + CurrentValue = FMath::Clamp(CurrentValue, 0, GetFinalValue()); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: CurrentValue: %f"), CurrentValue); + returnValue = CurrentValue; + break; + } + case EGAAttributeMod::Subtract: + { + float OldCurrentValue = CurrentValue; + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: OldCurrentValue: %f"), OldCurrentValue); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: SubtractValue: %f"), ModIn.Value); + float Val = CurrentValue - (OldCurrentValue - ModIn.Value); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: ActuallSubtractVal: %f"), Val); + CurrentValue -= Val; + CurrentValue = FMath::Clamp(CurrentValue, 0, GetFinalValue()); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: CurrentValue: %f"), CurrentValue); + + returnValue = CurrentValue; + break; + } + case EGAAttributeMod::Multiply: + { + returnValue = -1; + break; + } + case EGAAttributeMod::Divide: + { + returnValue = -1; + break; + } + } + } + return returnValue; +} + +void FAFAttributeBase::AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle) +{ + TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; + FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); + modsTemp = ModIn; + //switch (Stacking) + //{ + // case EAFAttributeStacking::Add: + // { + // TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; + // FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); + // modsTemp = ModIn; + // break; + // } + // case EAFAttributeStacking::Override: + // { + // if (CheckIfModsMatch(Handle, ModIn)) + // { + // RemoveBonus(Handle, ModIn.AttributeMod); + // TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; + // FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); + // modsTemp = ModIn; + // } + // break; + // } + // case EAFAttributeStacking::StrongerOverride: + // { + // if (CheckIfStronger(ModIn)) + // { + // RemoveBonus(Handle, ModIn.AttributeMod); + // TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; + // FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); + // modsTemp = ModIn; + // } + // break; + // } + //} + CalculateBonus(); +} +void FAFAttributeBase::RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod) +{ + TMap& mods = Modifiers[static_cast(InMod)]; + mods.Remove(Handle); + //Modifiers.Remove(Handle); + CalculateBonus(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h new file mode 100644 index 0000000..74d2c40 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -0,0 +1,138 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "./Effects/GAGameEffect.h" +#include "../Effects/GAEffectGlobalTypes.h" + +// Messaging +#include "Messaging.h" + +#include "GAAttributeBase.generated.h" + +DECLARE_MULTICAST_DELEGATE(FGAGenericAttributeDelegate); + +DECLARE_STATS_GROUP(TEXT("Attribute"), STATGROUP_Attribute, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("CalculateBonus"), STAT_CalculateBonus, STATGROUP_Attribute, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("CurrentBonusByTag"), STAT_CurrentBonusByTag, STATGROUP_Attribute, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("FinalBonusByTag"), STAT_FinalBonusByTag, STATGROUP_Attribute, ); + + +struct QueuedAttributeMods +{ +public: + FGAEffectHandle Handle; + FGAEffectMod Mod; + + void operator=(const QueuedAttributeMods& Other) + { + Handle = Other.Handle; + Mod = Other.Mod; + } +}; +/* + I probabaly should chaange attribute to use int's instead of floats. Stable, accurate and + I can still have decimal values with them. +*/ +/* + Base data structure describing Attribute: + 1. Base Value - the base value attribute has been initialized with. + 2. Current value - current value of attribute. + 3. Bonuses value. + 4. One bonus value (if need be attribute can take care of calculating it's own bonus value). + + As for now it's made to in mind to use it as meta attribute. Meta attributes, have always + 0 value and are used to change other attributes. Like Damage is used to subtract health. + LifeSteal is used to transfer health from target to instigator etc. + + We could extend attributes, to also support tags, so their bonus can be recalculated, + based on on tags requiremnts from effect asking for this particular attribute. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAttributeBase +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + float BaseValue; + UPROPERTY(EditAnywhere) + float MinValue; + UPROPERTY(EditAnywhere) + float MaxValue; + UPROPERTY() + float CurrentValue; + UPROPERTY() + float BonusValue; + + //UPROPERTY(EditAnywhere) + // EAFAttributeStacking Stacking; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") + TSubclassOf ExtensionClass; + + TArray> Modifiers; + FAFAttributeBase(); + FAFAttributeBase(float BaseValueIn); + void InitializeAttribute(); + /* You should never use those tree function to set attributes. + Only use them for testing/debugging and setting initial values for attributes. */ + inline void SetBaseValue(float ValueIn) { BaseValue = ValueIn; } + inline void SetMinValue(float ValueIn) { MinValue = ValueIn; } + inline void SetMaxValue(float ValueIn) { MaxValue = ValueIn; } + + inline float GetFinalValue() + { + return FMath::Clamp(BaseValue + BonusValue, MinValue, MaxValue); + }; + inline float GetCurrentValue() { return CurrentValue; }; + void CalculateBonus(); + bool CheckIfModsMatch(const FGAEffectHandle& InHandle, const FGAEffectMod& InMod); + bool CheckIfStronger(const FGAEffectMod& InMod); + float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); + void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); + void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); + //EAFAttributeStacking GetStacking() const { return Stacking; } +}; +template<> +struct TStructOpsTypeTraits : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = false + }; +}; +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAModifiedAttribute +{ + GENERATED_USTRUCT_BODY() +public: + /** + * Always increment it, to make sure it will replicate. + */ + UPROPERTY() + int8 ReplicationCounter; + + /** + * Attribute we have modified. + */ + UPROPERTY() + FGAAttribute Attribute; + + /** + * Final value by which we modified attribute. + */ + UPROPERTY(BlueprintReadOnly, Category = "UI") + float ModifiedByValue; + + /** + * Final tags appiled by this change. + */ + UPROPERTY() + FGameplayTagContainer Tags; + + UPROPERTY(BlueprintReadOnly, Category = "UI") + FVector TargetLocation; //change to vector, we need only position. + UPROPERTY(BlueprintReadOnly, Category = "UI") + FVector InstigatorLocation; + + UPROPERTY() + TWeakObjectPtr Causer; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp new file mode 100644 index 0000000..973393c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAAttributeExtension.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h new file mode 100644 index 0000000..57f9a70 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "GAAttributeExtension.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAttributeExtension : public UObject +{ + GENERATED_BODY() +public: + virtual void PreAttributeModify() {}; + virtual void PostAttributeModify() {}; + virtual void OnPreAttributeModified() {}; + virtual void OnPostAttributeModified() {}; + virtual float CalculateBonusValueByTags(const FGAIndividualMods& Mods) { return 0; } + virtual float CalculateCurentValue() { return 0; } + virtual bool CanModifyAttribute() { return true; } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp new file mode 100644 index 0000000..de1a982 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp @@ -0,0 +1,5 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAAttributeGlobals.h" + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h new file mode 100644 index 0000000..e82dfdf --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "GAAttributeGlobals.generated.h" +/** + * + */ + +USTRUCT() +struct FDumbStruct +{ + GENERATED_BODY() +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp new file mode 100644 index 0000000..357f2f1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -0,0 +1,296 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAGlobalTypes.h" +#include "../GAAbilitiesComponent.h" +#include "GAAttributesBase.h" + +UGAAttributesBase::UGAAttributesBase(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + bNetAddressable = false; + LastAttributeProp = nullptr; + CachedFloatPropety = nullptr; +} +UGAAttributesBase::~UGAAttributesBase() +{ + LastAttributeProp = nullptr; //make sure we clear this pointer. + CachedFloatPropety = nullptr; +} + +void UGAAttributesBase::InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp) +{ + OwningAttributeComp = InOwningAttributeComp; + for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) + { + FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); + if (attr) + { + attr->InitializeAttribute(); + TickableAttributes.Add(attr); + } + } + /* + Bind Delegates to map > For each attribute, so we don't store them inside attribute + but in this class. + */ + /*for (TFieldIterator PropIt(GetClass(), EFieldIteratorFlags::IncludeSuper); PropIt; ++PropIt) + { + int32 FoundIndex = -1; + FoundIndex = PropIt->GetName().Find("PostAttribute"); + FAFAttributeBase* attrPtr = GetAttribute(FGAAttribute(PropIt->GetFName())); + if (attrPtr) + { + return attrPtr->InitializeAttribute(); + } + }*/ + BP_InitializeAttributes(); +} + +void UGAAttributesBase::InitializeAttributesFromTable() +{ + if (!AttributeValues) + return; + + for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) + { + FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); + if (attr) + { + FName fieldName = StrIt->GetFName(); + FString OutString; + FAFAtributeRowData* row = AttributeValues->FindRow(fieldName, OutString); + if (row) + { + attr->SetBaseValue(row->BaseValue); + attr->SetMaxValue(row->MaxValue); + attr->SetMinValue(row->MinValue); + attr->InitializeAttribute(); + } + //TickableAttributes.Add(attr); + } + } +} + +void UGAAttributesBase::Tick(float DeltaTime) +{ + for (FAFAttributeBase* Attribute : TickableAttributes) + { + } +} + + +UProperty* UGAAttributesBase::FindProperty(const FGAAttribute& AttributeIn) +{ + //if new attribute name is the same as last attribute name and pointer to last property + //is not null, then we just return last pointer instead of performing new search. + if ((AttributeIn.AttributeName == LastAttributeName) && LastAttributeProp) + return LastAttributeProp; + + LastAttributeName = AttributeIn.AttributeName; + LastAttributeProp = FindFieldChecked(this->GetClass(), LastAttributeName); + return LastAttributeProp; + return nullptr; +} +UStructProperty* UGAAttributesBase::GetStructAttribute(const FGAAttribute& Name) +{ + return FindField(this->GetClass(), Name.AttributeName); +} +FAFAttributeBase* UGAAttributesBase::GetAttribute(const FGAAttribute& Name) +{ + UStructProperty* tempStruct = FindField(this->GetClass(), Name.AttributeName); + + FAFAttributeBase* attr = nullptr; + if (tempStruct) + { + attr = tempStruct->ContainerPtrToValuePtr(this); + return attr; + } + return attr; +} +void UGAAttributesBase::SetAttribute(const FGAAttribute& NameIn, UObject* NewVal) +{ + //UStructProperty* tempStruct = FindField(this->GetClass(), NameIn.AttributeName); +} +void UGAAttributesBase::SetAttributeAdditiveBonus(const FGAAttribute& NameIn, float NewValue) +{ + UStructProperty* tempStruct = FindField(this->GetClass(), NameIn.AttributeName); + UScriptStruct* scriptStruct = tempStruct->Struct; + + uint8* StructData = tempStruct->ContainerPtrToValuePtr(this); + + //omg figured it out! + //for (TFieldIterator It(scriptStruct); It; ++It) + //{ + // if (UProperty* Prop = *It) + // { + // if (Prop->GetFName() == "AdditiveBonus") + // { + // if (Prop->IsA(UFloatProperty::StaticClass())) + // { + // float testValue = NewValue; + // Cast(Prop)->SetPropertyValue_InContainer(StructData, testValue); + // break; + // } + // } + // } + //} +} + +float UGAAttributesBase::GetFinalAttributeValue(const FGAAttribute& Name) +{ + FAFAttributeBase* attrPtr = GetAttribute(Name); + if (attrPtr) + { + return attrPtr->GetFinalValue(); + } + return 0; +} +float UGAAttributesBase::GetCurrentAttributeValue(const FGAAttribute& Name) +{ + FAFAttributeBase* attrPtr = GetAttribute(Name); + if (attrPtr) + { + return attrPtr->GetCurrentValue(); + } + return 0; +} +float UGAAttributesBase::GetFloatValue(const FGAAttribute& AttributeIn) +{ + if ((AttributeIn.AttributeName == LastAttributeName)) + { + if (CachedFloatPropety) + { + const void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); + return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); + } + } + //LastAttributeName = AttributeIn.AttributeName; + UNumericProperty* NumericProperty = CastChecked(FindProperty(AttributeIn)); + CachedFloatPropety = NumericProperty; + const void* ValuePtr = NumericProperty->ContainerPtrToValuePtr(this); + return NumericProperty->GetFloatingPointPropertyValue(ValuePtr); + + return 0; +} + +float UGAAttributesBase::SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn) +{ + if ((AttributeIn.AttributeName == LastAttributeName)) + { + if (CachedFloatPropety) + { + void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); + CachedFloatPropety->SetFloatingPointPropertyValue(ValuePtr, ValueIn); + return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); + } + } + //LastAttributeName = AttributeIn.AttributeName; + UNumericProperty* NumericProperty = CastChecked(FindProperty(AttributeIn)); + CachedFloatPropety = NumericProperty; + void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); + NumericProperty->SetFloatingPointPropertyValue(ValuePtr, ValueIn); + return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); + return 0; +} + +float UGAAttributesBase::AttributeOperation(const FGAAttribute& AttributeIn, float ValueIn, EGAAttributeMod Operation) +{ + switch (Operation) + { + case EGAAttributeMod::Add: + return AddAttributeFloat(GetFloatValue(AttributeIn), ValueIn); //don't want to set. + case EGAAttributeMod::Subtract: + return SubtractAttributeFloat(GetFloatValue(AttributeIn), ValueIn); + case EGAAttributeMod::Multiply: + return MultiplyAttributeFloat(GetFloatValue(AttributeIn), ValueIn); + case EGAAttributeMod::Divide: + return DivideAttributeFloat(GetFloatValue(AttributeIn), ValueIn); + case EGAAttributeMod::Set: + return SetFloatValue(AttributeIn, ValueIn); + default: + return 0; + } + return 0; +} + +float UGAAttributesBase::AddAttributeFloat(float ValueA, float ValueB) +{ + return ValueA + ValueB; +} +float UGAAttributesBase::SubtractAttributeFloat(float ValueA, float ValueB) +{ + return ValueA - ValueB; +} +float UGAAttributesBase::MultiplyAttributeFloat(float ValueA, float ValueB) +{ + return ValueA * ValueB; +} +float UGAAttributesBase::DivideAttributeFloat(float ValueA, float ValueB) +{ + return ValueA / ValueB; +} + +bool UGAAttributesBase::IsNameStableForNetworking() const +{ + /** + * IsNameStableForNetworking means an attribute set can be referred to its path name (relative to owning AActor*) over the network + * + * Attribute sets are net addressable if: + * -They are Default Subobjects (created in C++ constructor) + * -They were loaded directly from a package (placed in map actors) + * -They were explicitly set to bNetAddressable + */ + + return bNetAddressable;// || Super::IsNameStableForNetworking(); +} + + +void UGAAttributesBase::SetNetAddressable() +{ + bNetAddressable = true; +} +void UGAAttributesBase::ModifyAttribute(const FGAEffect& EffectIn) +{ + +} + +float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn, + const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty) +{ + FAFAttributeBase* attr = nullptr; + + attr = GetAttribute(ModIn.Attribute); + float OutVal = -1; + if (attr) + { + OutVal = attr->Modify(ModIn, HandleIn, InProperty); + } + OnAttributeModified(ModIn, HandleIn); + return OutVal; +} + +void UGAAttributesBase::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) +{ + FAFAttributeBase* attr = nullptr; + + attr = GetAttribute(AttributeIn); + if (attr) + { + return attr->RemoveBonus(HandleIn, InMod); + } +} + +void UGAAttributesBase::OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle) +{ + OwningAttributeComp->OnAttributeModified(InMod, InHandle, this); + FAFAttributeChangedData Data; + OwningAttributeComp->BroadcastAttributeChange(InMod.Attribute, Data); +} +void UGAAttributesBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly replicate it to everyone + //to allow prediction for UI. + DOREPLIFETIME(UGAAttributesBase, OwningAttributeComp); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h new file mode 100644 index 0000000..34d9cb2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h @@ -0,0 +1,129 @@ +#pragma once +#include "../Effects/GAGameEffect.h" +#include "../GAGlobalTypes.h" +#include "GAAttributeBase.h" +#include "GAAttributesBase.generated.h" + +/* + What I need. + Easy way to create Targeted modifications. + For Example, we have ability Fireball, which have cast time 3s, and recharge time 5 seconds. + Targeted modification, will only affect this one ability! + + So we want attribute which will decrease recharge time of this ability by 2 seconds (or decrease recharge time by 25% + or increase recharge speed). How to do it ? + + Path of least resistance is to create special object, which will be instanced, which will listen for abilities + which are activated, and you can cast to your particular ability (or check for tags), and just modify it's + properties directly. + + Second way, (??) would be to create small objects, contained within array (structs), which would do the same thing. + Except they would only be able to catch something like ability activation by tag. They wouldn't know, what kind of + properties are on ability. + + The ability in this case would be needed to be treated as source of incoming attribute, and that object would check + for this attribute and modify it. + Well kind of. + + The same problems exist for any kind of abilities more broad (like Hex), more narrow (only Necromancer Hex), + or for weapons (we want to increase fire rate, if you have equiped machine gun). + + Though on the very base level attribute system have no idea, what kind of properties you might have on + your machine gun. + + + This bring us to the core issue. How to create system like Traits/Feats/Talents, which can contain + myriads of possible combinations of those tree systems. We would need to mix some instanced/non-instanced UObjects + along with plain structs. Which is probabaly going to be total mess. +*/ +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInlineNew) +class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject +{ + GENERATED_BODY() +public: + + UPROPERTY(EditAnywhere, BlueprintReadOnly, meta=(ExposeOnSpawn)) + UDataTable* AttributeValues; + UGAAttributesBase(const FObjectInitializer& ObjectInitializer); + ~UGAAttributesBase(); + + virtual void InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp); + void InitializeAttributesFromTable(); + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) + bool BP_InitializeAttributes(); + /* + Updates attributes. + @param AttributeIn - attribute which changed value. + + You can use this function to update other attributes (for example derived ones), + based on the primary attribute, if the primary attribute (AttributeIn), changed. + + I have yet to fully figure out how do I want it to work. But one thing for certain is + that it must be fully functional from within blueprint. + */ + UPROPERTY(Replicated) + class UGAAbilitiesComponent* OwningAttributeComp; +protected: + UProperty* FindProperty(const FGAAttribute& AttributeIn); + +public: + /* + Ticked called from owning component. + */ + virtual void Tick(float DeltaTime);// {}; + /* + Helper C++ functions. Shouldn't ever be exposed or called from blueprint. Also never + try to override them. + + probabaly could also add support for int32 values. + */ + UStructProperty* GetStructAttribute(const FGAAttribute& Name); + /* + Gets pointer to compelx attribute. + */ + FAFAttributeBase* GetAttribute(const FGAAttribute& Name); + /* + Deprecated. I'm going to remove it, since it does not work as intended! + */ + void SetAttribute(const FGAAttribute& NameIn, UObject* NewVal); + + void SetAttributeAdditiveBonus(const FGAAttribute& NameIn, float NewValue); + + /* + Gets value from complex attribute (FAFAttributeBase). + */ + float GetFinalAttributeValue(const FGAAttribute& Name); + float GetCurrentAttributeValue(const FGAAttribute& Name); + + float GetFloatValue(const FGAAttribute& AttributeIn); + float SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn); + float AttributeOperation(const FGAAttribute& AttributeIn, float ValueIn, EGAAttributeMod Operation); + + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return true; + } + void SetNetAddressable(); + + void ModifyAttribute(const FGAEffect& EffectIn); + float ModifyAttribute(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod); +protected: + bool bNetAddressable; + +private: + TArray TickableAttributes; + UProperty* LastAttributeProp; + FName LastAttributeName; + // cached numeric property. WEll we probabaly don't need UProperty cache then.. + UNumericProperty* CachedFloatPropety; + + float AddAttributeFloat(float ValueA, float ValueB); + float SubtractAttributeFloat(float ValueA, float ValueB); + float MultiplyAttributeFloat(float ValueA, float ValueB); + float DivideAttributeFloat(float ValueA, float ValueB); + + void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..b5bc78d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp @@ -0,0 +1,51 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" + +#include "../IGAAbilities.h" +#include "GAAttributesBase.h" +#include "../GAAbilitiesComponent.h" + +#include "GAAttributesBlueprintFunctionLibrary.h" + + + +UGAAttributesBlueprintFunctionLibrary::UGAAttributesBlueprintFunctionLibrary(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} + +bool UGAAttributesBlueprintFunctionLibrary::EqualAttribute(const FGAAttribute& Compare, FGAAttribute Against) +{ + return Compare == Against; +} +FName UGAAttributesBlueprintFunctionLibrary::GetAttribute(FGAAttribute AttributeIn) +{ + return AttributeIn.AttributeName; +} +float UGAAttributesBlueprintFunctionLibrary::GetFinalAttributeValue(AActor* Target, FGAAttribute Name) +{ + IIGAAbilities* attributeInt = Cast(Target); + if (!attributeInt) + return 0; + if (!attributeInt->GetAttributes()) + return 0; + + return attributeInt->GetAttributes()->GetFinalAttributeValue(Name); +} +float UGAAttributesBlueprintFunctionLibrary::GetCurrentAttributeValue(AActor* Target, FGAAttribute Name) +{ + IIGAAbilities* attributeInt = Cast(Target); + if (!attributeInt) + return 0; + return attributeInt->GetAttributes()->GetCurrentAttributeValue(Name); +} +float UGAAttributesBlueprintFunctionLibrary::GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn) +{ + IIGAAbilities* attributeInt = Cast(Target); + if (!attributeInt) + return 0; + + return attributeInt->GetAttributes()->GetFloatValue(AttributeIn); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h new file mode 100644 index 0000000..d60bef2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h @@ -0,0 +1,34 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "GAAttributesBlueprintFunctionLibrary.generated.h" +/* + Some static helper functions, to interact with Attribute system. +*/ +UCLASS() +class ABILITYFRAMEWORK_API UGAAttributesBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_UCLASS_BODY() +public: + UFUNCTION(BlueprintPure, meta=(DisplayName="Equal"), Category = "AbilityFramework|Attributes") + static bool EqualAttribute(const FGAAttribute& Compare, FGAAttribute Against); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + static FName GetAttribute(FGAAttribute AttributeIn); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") + static float GetFinalAttributeValue(AActor* Target, FGAAttribute Name); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") + static float GetCurrentAttributeValue(AActor* Target, FGAAttribute Name); + + /** + * Takes actor, and return value of specified attribute. + * + * @param Target - Actrom from which take attribute + * @param AttributeIn - Attribute from which we want to get value + * + * @return value of attribute from actor. + */ + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") + static float GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp new file mode 100644 index 0000000..110fd10 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp @@ -0,0 +1,4 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAAttributesStats.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h new file mode 100644 index 0000000..3f59c93 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h @@ -0,0 +1,2 @@ +#pragma once + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp new file mode 100644 index 0000000..a6e6ad6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectApplicationRequirement.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h new file mode 100644 index 0000000..0701ab1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "AFEffectApplicationRequirement.generated.h" + +/** + * Default requirment always passes. + */ +UCLASS(meta=(DisplayName = "No Requirement")) +class ABILITYFRAMEWORK_API UAFEffectApplicationRequirement : public UObject +{ + GENERATED_BODY() + +public: + virtual bool CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, + struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle) + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp new file mode 100644 index 0000000..05bb6d0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectCustomApplication.h" + + + + +bool UAFEffectCustomApplication::ApplyEffect(const FGAEffectHandle& InHandle, FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + return true; +} + +void UAFEffectCustomApplication::ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + InHandle.GetContext().TargetComp->ExecuteEffect(InHandle, InProperty, Modifier, InContext); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h new file mode 100644 index 0000000..b06fefe --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" +#include "AFEffectCustomApplication.generated.h" + +/** + * Default application used for instant effects. + */ +UCLASS(meta = (DisplayName = "Default Application")) +class ABILITYFRAMEWORK_API UAFEffectCustomApplication : public UObject +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool ShowPeriod() + { + return false; + } + virtual bool ShowDuration() + { + return false; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp new file mode 100644 index 0000000..f3736ac --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectCustomStackingRule.h" + + + + +bool UAFEffectCustomStackingRule::CanStack(class UGAAbilitiesComponent* InComp, struct FGAEffectContainer* InContainer, + const FGAEffectHandle& InHandle) +{ + //InHandle.GetContext().TargetComp->ExecuteEffect(InHandle); + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h new file mode 100644 index 0000000..63e6f8e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "AFEffectCustomStackingRule.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectCustomStackingRule : public UObject +{ + GENERATED_BODY() + +public: + virtual bool CanStack(class UGAAbilitiesComponent* InComp, struct FGAEffectContainer* InContainer, + const FGAEffectHandle& InHandle); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp new file mode 100644 index 0000000..49266af --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../../Attributes/GAAttributeBase.h" +#include "../../IGAAbilities.h" +#include "AFAttributeStongerOverride.h" + + + + +bool UAFAttributeStongerOverride::CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, + struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle) +{ + bool bCanApply = true; + FGAAttribute Attribute = InProperty.Spec->AtributeModifier.Attribute; + FAFAttributeBase* AttributePtr = EffectIn->Context.TargetInterface->GetAttribute(Attribute); + if (AttributePtr) + { + FGAEffectMod mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() + , InProperty.GetSpec() + , InContext + , InHandle); + + if (AttributePtr->CheckIfStronger(mod)) + { + bCanApply = true; + } + else + { + bCanApply = false; + } + } + return bCanApply; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h new file mode 100644 index 0000000..15eb56f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectApplicationRequirement.h" +#include "AFAttributeStongerOverride.generated.h" + +/** + * USe only with Duration Based application. + * Effect will be applied if the attribute modifier is stronger than the current one on Attribute. + */ +UCLASS(BlueprintType, meta = (DisplayName = "Attribute Stronger")) +class ABILITYFRAMEWORK_API UAFAttributeStongerOverride : public UAFEffectApplicationRequirement +{ + GENERATED_BODY() +public: + virtual bool CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, + struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle) override; + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp new file mode 100644 index 0000000..b55d7d6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectAlreadyApplied.h" + + + + +bool UAFEffectAlreadyApplied::CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, + struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle) +{ + if (InContainer->ContainsEffectOfClass(InProperty)) + { + return false; + } + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h new file mode 100644 index 0000000..41469ee --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectApplicationRequirement.h" +#include "AFEffectAlreadyApplied.generated.h" + +/** + * If effect of the same type is already applied, it will be skipped. + */ +UCLASS(meta = (DisplayName = "Only One Of Type")) +class ABILITYFRAMEWORK_API UAFEffectAlreadyApplied : public UAFEffectApplicationRequirement +{ + GENERATED_BODY() +public: + virtual bool CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, + struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle) override; + + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp new file mode 100644 index 0000000..75eb053 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "../../GAAbilitiesComponent.h" +#include "AFAtributeDurationAdd.h" + + + + +bool UAFAtributeDurationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, + InProperty.Duration, false); + + InContainer->AddEffect(InHandle); + //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h new file mode 100644 index 0000000..7dc5b74 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAtributeDurationAdd.generated.h" + +/** + * Adds New duration Effect. + */ +UCLASS(meta = (DisplayName = "Duration Add")) +class ABILITYFRAMEWORK_API UAFAtributeDurationAdd : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return true; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp new file mode 100644 index 0000000..3cb3784 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp @@ -0,0 +1,17 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAttributeDurationInfinite.h" + + + + +bool UAFAttributeDurationInfinite::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + InContainer->AddEffect(InHandle, true); + //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h new file mode 100644 index 0000000..187516a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAttributeDurationInfinite.generated.h" + +/** + * Adds infinite duration effect. + */ +UCLASS(meta = (DisplayName = "Duration Infinite Add")) +class ABILITYFRAMEWORK_API UAFAttributeDurationInfinite : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return false; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp new file mode 100644 index 0000000..a5a41d6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -0,0 +1,40 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "../../GAAbilitiesComponent.h" +#include "AFAttributeDurationOverride.h" + + + + +bool UAFAttributeDurationOverride::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + //TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); + //for (const FGAEffectHandle& handle : handles) + //{ + // InContainer->RemoveEffect(InProperty); + //} + ////if (!InHandle.GetWithPeriod()) + //{ + // handles = InContainer->GetHandlesByAttribute(InHandle); + // for (const FGAEffectHandle& handle : handles) + // { + // InContainer->RemoveEffect(InProperty); + // } + //} + InContainer->RemoveEffect(InProperty); + + FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, + InProperty.Duration, false); + + InContainer->AddEffect(InHandle); + //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h new file mode 100644 index 0000000..865b129 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAttributeDurationOverride.generated.h" + +/** + * If effect of the same class is already applied it will be removed, and new one will be applied. + */ +UCLASS(meta = (DisplayName = "Duration Override")) +class ABILITYFRAMEWORK_API UAFAttributeDurationOverride : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp new file mode 100644 index 0000000..64ca21f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "../../GAAbilitiesComponent.h" +#include "AFPeriodApplicationAdd.h" + + +bool UAFPeriodApplicationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, + InProperty.Duration, false); + + FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, + InProperty.Period, true); + + InContainer->AddEffect(InHandle); + //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); + return true; +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h new file mode 100644 index 0000000..7964305 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationAdd.generated.h" + +/** + * Adds new periodic effect. + */ +UCLASS(meta = (DisplayName = "Periodic Add")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationAdd : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()) override; + virtual void ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp new file mode 100644 index 0000000..a7c60f7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -0,0 +1,46 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "../../GAAbilitiesComponent.h" +#include "AFPeriodApplicationExtend.h" + + + + +bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier) +{ + TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); + for (const FGAEffectHandle& handle : handles) + { + FGAEffect& ExtEffect = handle.GetEffectRef(); + FGAEffect& Effect = InHandle.GetEffectRef(); + FTimerManager& DurationTimer = handle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + float RemainingTime = DurationTimer.GetTimerRemaining(handle.GetEffectPtr()->DurationTimerHandle); + float NewDuration = RemainingTime + Effect.GetDurationTime(); + DurationTimer.ClearTimer(handle.GetEffectPtr()->DurationTimerHandle); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(handle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + DurationTimer.SetTimer(handle.GetEffectPtr()->DurationTimerHandle, delDuration, + NewDuration, false); + } + if (handles.Num() <= 0) + { + FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, + InProperty.Duration, false); + + FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, + InProperty.Period, true); + + InContainer->AddEffect(InHandle); + } + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h new file mode 100644 index 0000000..2cd0917 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h @@ -0,0 +1,37 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationExtend.generated.h" + +/** + * If periodic effect of the same class already exists it duration will be extended. If not new effect + * will be applied. + */ +UCLASS(meta = (DisplayName = "Periodic Extend")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationExtend : public UAFEffectCustomApplication +{ + GENERATED_BODY() + +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return true; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp new file mode 100644 index 0000000..d22b228 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "../../GAAbilitiesComponent.h" +#include "AFPeriodApplicationInfiniteAdd.h" + + +bool UAFPeriodApplicationInfiniteAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, + InProperty.Period, true); + InContainer->AddEffect(InHandle, true); + //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); + return true; +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h new file mode 100644 index 0000000..ee9fc23 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h @@ -0,0 +1,37 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationInfiniteAdd.generated.h" + +/** + * Periodic effect will be applied for infinite amount of time. + */ +UCLASS(meta = (DisplayName = "Periodic Infinite Add")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationInfiniteAdd : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return false; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp new file mode 100644 index 0000000..caa4116 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "../../GAAbilitiesComponent.h" +#include "AFPeriodApplicationOverride.h" + + + + +bool UAFPeriodApplicationOverride::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier) +{ + //TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); + //for (const FGAEffectHandle& handle : handles) + //{ + // InContainer->RemoveEffect(InProperty); + //} + InContainer->RemoveEffect(InProperty); + + FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, + InProperty.Duration, false); + + FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, + InProperty.Period, true); + + InContainer->AddEffect(InHandle); + //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h new file mode 100644 index 0000000..187ecfd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h @@ -0,0 +1,35 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationOverride.generated.h" + +/** + * If effect of the same class already exist it will be removed and new effect will be appllied. + */ +UCLASS(meta = (DisplayName = "Periodic Override")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationOverride : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, + FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual void ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp new file mode 100644 index 0000000..4585496 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFPeriodicApplInfiniteOverride.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h new file mode 100644 index 0000000..2d65233 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodicApplInfiniteOverride.generated.h" + +/** + * Adds infinite periodic effect. If effect of the same class already exists, it will be removed first. + */ +UCLASS(meta=(DisplayName = "Periodic Infinite Override")) +class ABILITYFRAMEWORK_API UAFPeriodicApplInfiniteOverride : public UAFEffectCustomApplication +{ + GENERATED_BODY() + + + virtual void ExecuteEffect(const FGAEffectHandle& InHandle, + FGAEffectProperty& InProperty, + const FGAEffectContext& InContext, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp new file mode 100644 index 0000000..d24b545 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "AFEffectTask.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h new file mode 100644 index 0000000..ccf1937 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -0,0 +1,55 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameplayTask.h" +#include "../GAEffectExtension.h" +#include "../../GAGlobalTypes.h" +#include "../../GAAbilitiesComponent.h" +#include "AFEffectTask.generated.h" + +/** + * + */ +UCLASS(BlueprintType, meta = (ExposedAsyncProxy = "true") ) +class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask +{ + GENERATED_BODY() +public: + UPROPERTY() + class UGAEffectExtension* Effect; + UPROPERTY() + class UGAAbilitiesComponent* AbilityComponent; +public: + template + static T* NewEffectTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) + { + check(WorldContextObject); + + T* MyObj = NewObject(WorldContextObject); + UGAEffectExtension* ThisAbility = CastChecked(WorldContextObject); + /* if (UGAAbilityTask* CachedTask = ThisAbility->GetAbilityTask(InTaskName)) + { + return Cast(CachedTask); + }*/ + MyObj->Effect = ThisAbility; + MyObj->AbilityComponent = ThisAbility->OwningComponent; + MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); + MyObj->InstanceName = InstanceName; + //ThisAbility->AddAbilityTask(InTaskName, MyObj); + return MyObj; + } + + template + static bool DelayedFalse() + { + return false; + } + + // this function has been added to make sure AbilityTasks don't use this method + template + FORCEINLINE static T* NewTask(UObject* WorldContextObject, FName InstanceName = FName()) + { + static_assert(DelayedFalse(), "UAbilityTask::NewTask should never be used. Use NewAbilityTask instead"); + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp new file mode 100644 index 0000000..89803ea --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp @@ -0,0 +1,83 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectTask_AttributeChange.h" + + +UAFEffectTask_AttributeChange::UAFEffectTask_AttributeChange(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeChanged(UObject* OwningExtension, + FGAAttribute InAttribute, + AActor* OptionalExternalTarget, + bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension); + MyObj->Attribute = InAttribute; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_AttributeChange::Activate() +{ + UGAAbilitiesComponent* ASC = GetTargetASC(); + if (ASC) + { + MyHandle = ASC->AttributeChanged.FindOrAdd(Attribute).AddUObject(this, &UAFEffectTask_AttributeChange::AttributeChangedCallback); + } + + Super::Activate(); +} + +void UAFEffectTask_AttributeChange::AttributeChangedCallback(FAFAttributeChangedData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_AttributeChange::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + if (IIGAAbilities* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetAbilityComp(); + } + + } +} + +UGAAbilitiesComponent* UAFEffectTask_AttributeChange::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return AbilityComponent; +} + +void UAFEffectTask_AttributeChange::OnDestroy(bool AbilityEnding) +{ + UGAAbilitiesComponent* ASC = GetTargetASC(); + if (ASC && MyHandle.IsValid()) + { + ASC->AttributeChanged.FindOrAdd(Attribute).Remove(MyHandle); + } + + Super::OnDestroy(AbilityEnding); +} + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h new file mode 100644 index 0000000..1d3ed3f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h @@ -0,0 +1,52 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "AFEffectTask_AttributeChange.generated.h" +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFTaskAttributeChangedDelegate, FAFAttributeChangedData, Payload); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FAFTaskAttributeChangedDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_AttributeChange* ListenAttributeChanged(UObject* OwningExtension, + FGAAttribute InAttribute, + AActor* OptionalExternalTarget = nullptr, + bool OnlyTriggerOnce = false); + + UAFEffectTask_AttributeChange(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UGAAbilitiesComponent* GetTargetASC(); + + virtual void Activate() override; + + void AttributeChangedCallback(FAFAttributeChangedData Payload); + + void OnDestroy(bool AbilityEnding) override; + + FGAAttribute Attribute; + + UPROPERTY() + UGAAbilitiesComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp new file mode 100644 index 0000000..d924ed9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -0,0 +1,82 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../../IGAAbilities.h" +#include "AFEffectTask_EffectEvent.h" + + + + +UAFEffectTask_EffectEvent::UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UObject* OwningExtension, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension); + MyObj->Tag = Tag; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_EffectEvent::Activate() +{ + UGAAbilitiesComponent* ASC = GetTargetASC(); + if (ASC) + { + MyHandle = ASC->EffectEvents.FindOrAdd(Tag).AddUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); + } + + Super::Activate(); +} + +void UAFEffectTask_EffectEvent::GameplayEventCallback(FAFEventData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IIGAAbilities* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetAbilityComp(); + } + + } +} + +UGAAbilitiesComponent* UAFEffectTask_EffectEvent::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return AbilityComponent; +} + +void UAFEffectTask_EffectEvent::OnDestroy(bool AbilityEnding) +{ + UGAAbilitiesComponent* ASC = GetTargetASC(); + if (ASC && MyHandle.IsValid()) + { + ASC->EffectEvents.FindOrAdd(Tag).Remove(MyHandle); + } + + Super::OnDestroy(AbilityEnding); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h new file mode 100644 index 0000000..21bdb3e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -0,0 +1,48 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "../../GAGlobalTypes.h" +#include "AFEffectTask_EffectEvent.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_EffectEvent* ListenEffectEvent(UObject* OwningExtension, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UGAAbilitiesComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFEventData Payload); + + void OnDestroy(bool AbilityEnding) override; + + FGameplayTag Tag; + + UPROPERTY() + UGAAbilitiesComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp new file mode 100644 index 0000000..8a7990c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -0,0 +1,223 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAAbilitiesComponent.h" + + +#include "GABlueprintLibrary.h" +#include "../IGAAbilities.h" +#include "GAEffectExtension.h" + +UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} + + +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToObject(UPARAM(ref) FGAEffectProperty& InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier) +{ + return ApplyEffectToObject(InEffect, Target, Instigator, Causer, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToActor(UPARAM(ref) FGAEffectProperty& InEffect, + class AActor* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier) +{ + return ApplyEffectToActor(InEffect, Target, Instigator, Causer, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation(UPARAM(ref) FGAEffectProperty& InEffect, + const FHitResult& Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier) +{ + return ApplyEffectFromHit(InEffect, Target, Instigator, Causer, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier ) +{ + InEffect.InitializeIfNotInitialized(); + + if (!InEffect.IsInitialized()) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + return FGAEffectHandle(); + } + FGAEffectContext Context = MakeContext(Target, Instigator, Causer, HitIn); + /*if (!Context.IsValid()) + { + return FGAEffectHandle(); + }*/ + UGAAbilitiesComponent* Target2 = Context.TargetComp.Get(); + if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) + { + return FGAEffectHandle(); + } + if (Target2->DenyEffectApplication(InEffect.GetSpec()->DenyTags)) + { + return FGAEffectHandle(); + } + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); + InEffect.Duration = InEffect.GetSpec()->Duration.GetFloatValue(Context); + InEffect.Period = InEffect.GetSpec()->Period.GetFloatValue(Context); + FGAEffect* effect = nullptr; + if (InEffect.Duration <= 0 && InEffect.Period <= 0) + { + if (!InEffect.Handle.IsValid()) + { + effect = new FGAEffect(InEffect.GetSpec(), Context); + AddTagsToEffect(effect); + effect->Context = Context; + effect->GameEffect = InEffect.GetSpec(); + } + else + { + effect = InEffect.Handle.GetEffectPtr().Get(); + } + } + else + { + effect = new FGAEffect(InEffect.GetSpec(), Context); + AddTagsToEffect(effect); + effect->Context = Context; + effect->GameEffect = InEffect.GetSpec(); + } + + return Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit(FGAEffectProperty& InEffect, + const FHitResult& Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier) +{ + return ApplyEffect(InEffect, Target.GetActor(), Instigator, Causer, Target, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffectToActor(FGAEffectProperty& InEffect, + class AActor* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier) +{ + FHitResult Hit(ForceInit); + return ApplyEffect(InEffect, Target, Instigator, Causer, Hit, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject(FGAEffectProperty& InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier) +{ + FHitResult Hit(ForceInit); + return ApplyEffect(InEffect, Target, Instigator, Causer, Hit, Modifier); +} +FGAEffectHandle UGABlueprintLibrary::MakeEffect(UGAGameEffectSpec* SpecIn, + FGAEffectHandle HandleIn, class UObject* Target, class APawn* Instigator, + UObject* Causer, const FHitResult& HitIn) +{ + if (!SpecIn) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + return FGAEffectHandle(); + } + + FGAEffectContext Context = MakeContext(Target, Instigator, Causer, HitIn); + if (!Context.IsValid()) + { + //if the handle is valid (valid pointer to effect and id) + //we want to preseve it and just set bad context. + if (HandleIn.IsValid()) + { + HandleIn.SetContext(Context); + return HandleIn; + } + else + { + return FGAEffectHandle(); + } + } + + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); + + if (HandleIn.IsValid()) + { + HandleIn.SetContext(Context); + } + else + { + FGAEffect* effect = new FGAEffect(SpecIn, Context); + AddTagsToEffect(effect); + HandleIn = FGAEffectHandle::GenerateHandle(effect); + effect->Handle = HandleIn; + } + return HandleIn; +} + +FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn) +{ + IIGAAbilities* targetAttr = Cast(Target); + IIGAAbilities* instiAttr = Cast(Instigator); + if (!targetAttr && !instiAttr) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Target and Instigator does not implement IIGAAbilities interface")); + return FGAEffectContext(); + } + UGAAbilitiesComponent* targetComp = nullptr; + UGAAbilitiesComponent* instiComp = nullptr; + if (targetAttr) + { + targetComp = targetAttr->GetAbilityComp(); + } + if (instiAttr) + { + instiComp = instiAttr->GetAbilityComp(); + } + + FVector location = targetComp ? targetComp->GetOwner()->GetActorLocation() : HitIn.ImpactPoint; + FGAEffectContext Context( + targetAttr ? targetAttr->GetAttributes() : nullptr, + instiAttr ? instiAttr->GetAttributes() : nullptr, + location, Target, Causer, + Instigator, targetComp, instiComp); + Context.HitResult = HitIn; + return Context; +} + +void UGABlueprintLibrary::AddTagsToEffect(FGAEffect* EffectIn) +{ + if (EffectIn) + { + EffectIn->OwnedTags.AppendTags(EffectIn->GameEffect->OwnedTags); + EffectIn->ApplyTags.AppendTags(EffectIn->GameEffect->ApplyTags); + } +} + +FGAEffectContext& UGABlueprintLibrary::GetContext(const FGAEffectHandle& InHandle) +{ + return InHandle.GetContextRef(); +} + +UGAAbilitiesComponent* UGABlueprintLibrary::GetTargetComponent(const FGAEffectHandle& InHandle) +{ + return InHandle.GetContextRef().InstigatorComp.Get(); +} + +UGAAbilitiesComponent* UGABlueprintLibrary::GetInstigatorComponent(const FGAEffectHandle& InHandle) +{ + return InHandle.GetContextRef().TargetComp.Get(); +} + +void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag) +{ + IIGAAbilities* targetAttr = Cast(Target); + if (!targetAttr) + return; + + UGAAbilitiesComponent* TargetComp = targetAttr->GetAbilityComp(); + if (!TargetComp) + return; + + FAFEventData EventData; + TargetComp->NativeTriggerTagEvent(EventTag, EventData); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h new file mode 100644 index 0000000..ccee9e6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h @@ -0,0 +1,75 @@ +#pragma once +#include "../Effects/GAGameEffect.h" +#include "../GAGlobalTypes.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAEffectGlobalTypes.h" +#include "GABlueprintLibrary.generated.h" + +UCLASS(BlueprintType, Blueprintable) +class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_UCLASS_BODY() +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static FGAEffectHandle ApplyGameEffectToObject(UPARAM(ref) FGAEffectProperty& InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier); + + /* + Makes outgoing effect spec and assign handle to it. + If valid handle is provided it will instead reuse existing effect spec from handle, + and just change context of effect. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static FGAEffectHandle ApplyGameEffectToActor(UPARAM(ref) FGAEffectProperty& InEffect, + class AActor* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier); + /* + Makes outgoing effect spec and assign handle to it. + If valid handle is provided it will instead reuse existing effect spec from handle, + and just change context of effect. + */ + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static FGAEffectHandle ApplyGameEffectToLocation(UPARAM(ref) FGAEffectProperty& InEffect, + const FHitResult& Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier); + + static FGAEffectHandle ApplyEffect(FGAEffectProperty& InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + static FGAEffectHandle ApplyEffectFromHit(FGAEffectProperty& InEffect, + const FHitResult& Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier); + + static FGAEffectHandle ApplyEffectToActor(FGAEffectProperty& InEffect, + class AActor* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier); + + static FGAEffectHandle ApplyEffectToObject(FGAEffectProperty& InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FAFFunctionModifier& Modifier); + /* + Create Effect but does not apply it. + */ + static FGAEffectHandle MakeEffect(UGAGameEffectSpec* SpecIn, + FGAEffectHandle HandleIn, class UObject* Target, class APawn* Instigator, + UObject* Causer, const FHitResult& HitIn); + + + static FGAEffectContext MakeContext(class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn); + static void AddTagsToEffect(FGAEffect* EffectIn); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") + static FGAEffectContext& GetContext(const FGAEffectHandle& InHandle); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") + static UGAAbilitiesComponent* GetTargetComponent(const FGAEffectHandle& InHandle); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") + static UGAAbilitiesComponent* GetInstigatorComponent(const FGAEffectHandle& InHandle); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static void BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp new file mode 100644 index 0000000..2fa6e5d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp @@ -0,0 +1,11 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAGlobalTypes.h" +#include "GACustomCalculation.h" + +UGACustomCalculation::UGACustomCalculation(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h new file mode 100644 index 0000000..83f99cd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h @@ -0,0 +1,30 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "../GAHelperTemplates.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAGameEffect.h" +#include "GACustomCalculation.generated.h" + +/* + Simple base class for custom magnitude calculation. + You can implement here any kind of formula, taking arbitrary information, for calculations. + + Object is instanced inside effect spec, so you can add custom properties set up, as per + effect spec base. + + Please refrain from making super complicated things, which calculate everything, it's + generally not purpose of this class, but if you really want.. (;. +*/ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class ABILITYFRAMEWORK_API UGACustomCalculation : public UObject +{ + GENERATED_BODY() +public: + UGACustomCalculation(const FObjectInitializer& ObjectInitializer); + + //UFUNCTION(BlueprintNativeEvent, Category = "Attributes") + // float CalculateMagnitude(const FGAEffectContext& ContextIn); + + + virtual float NativeCalculateMagnitude(const FGAEffectHandle& HandleIn) { return 0; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp new file mode 100644 index 0000000..1edd0b9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAEffectBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectBlueprint::UGAEffectBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAEffectBlueprint* UGAEffectBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectBlueprint* DerivedBlueprint) +{ + UGAEffectBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAEffectBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h new file mode 100644 index 0000000..953751b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h @@ -0,0 +1,31 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAEffectBlueprint.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAEffectBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() + +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAEffectBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectBlueprint* DerivedBlueprint); + +#endif +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp new file mode 100644 index 0000000..5bd46db --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp @@ -0,0 +1,64 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "MovieScene.h" +#include "GAEffectCueSequence.h" +#include "ActorSequencePlayer.h" +#include "GAEffectCue.h" + +AGAEffectCue::AGAEffectCue(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + PrimaryActorTick.bCanEverTick = true; + PrimaryActorTick.bStartWithTickEnabled = true; + StartTime = 0; + EndTime = 5; + if (HasAnyFlags(RF_ClassDefaultObject) || GetArchetype() == GetDefault()) + { + Sequence = ObjectInitializer.CreateDefaultSubobject(this, "Sequence"); + Sequence->SetFlags(RF_Public | RF_Transactional); + SequencePlayer = ObjectInitializer.CreateDefaultSubobject(this, "SequencePlayer"); + } +} +void AGAEffectCue::PostInitProperties() +{ + Super::PostInitProperties(); +} +void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) +{ + Sequence = InSequence; +} +// Called when the game starts or when spawned +void AGAEffectCue::BeginPlay() +{ + SequencePlayer->Initialize(Sequence, PlaybackSettings); + if (Period > 0) + { + FTimerDelegate del = FTimerDelegate::CreateUObject(this, &AGAEffectCue::NativeOnPeriod); + FTimerManager& Timer = GetWorld()->GetTimerManager(); + Timer.SetTimer(PeriodTimer, del, Period, true); + } + Super::BeginPlay(); + //NativeBeginCue(); +} + +// Called every frame +void AGAEffectCue::Tick( float DeltaTime ) +{ + Super::Tick( DeltaTime ); + if (SequencePlayer) + { + SequencePlayer->Update(DeltaTime); + } +} +void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, + const FHitResult& HitInfo) +{ + BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); + SequencePlayer->Play(); +} + +void AGAEffectCue::NativeOnPeriod() +{ + OnPeriod(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h new file mode 100644 index 0000000..026acb7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h @@ -0,0 +1,61 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Actor.h" +#include "MovieSceneSequencePlayer.h" +#include "GAEffectCue.generated.h" +class UActorSequencePlayer; +UCLASS() +class ABILITYFRAMEWORK_API AGAEffectCue : public AActor +{ + GENERATED_BODY() +public: + // Sets default values for this actor's properties + AGAEffectCue(const FObjectInitializer& ObjectInitializer); + virtual void PostInitProperties() override; + // Called when the game starts or when spawned + virtual void BeginPlay() override; + + // Called every frame + virtual void Tick( float DeltaSeconds ) override; + + + UFUNCTION(BlueprintImplementableEvent) + void BeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, + const FHitResult& HitInfo); + + UFUNCTION(BlueprintImplementableEvent) + void OnPeriod(); + + UFUNCTION(BlueprintImplementableEvent) + void OnExpired(); + + UFUNCTION(BlueprintImplementableEvent) + void OnRemoved(); + + void NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, + const FHitResult& HitInfo); + + void NativeOnPeriod(); + + UPROPERTY() + float Duration; + UPROPERTY() + float Period; + + void SetAnimation(class UGAEffectCueSequence* InSequence); + UPROPERTY() + double StartTime; + UPROPERTY() + double EndTime; + /** Animation being played */ + UPROPERTY(Instanced) + class UGAEffectCueSequence* Sequence; + UPROPERTY(Instanced) + UActorSequencePlayer* SequencePlayer; + UPROPERTY(EditAnywhere, Category = "Playback", meta = (ShowOnlyInnerProperties)) + FMovieSceneSequencePlaybackSettings PlaybackSettings; + + FTimerHandle PeriodTimer; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp new file mode 100644 index 0000000..580daab --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp @@ -0,0 +1,13 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAEffectCueBlueprintGeneratedClass.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectCueBlueprintGeneratedClass::UGAEffectCueBlueprintGeneratedClass(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h new file mode 100644 index 0000000..d6af270 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h @@ -0,0 +1,17 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "GAEffectCueBlueprintGeneratedClass.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAEffectCueBlueprintGeneratedClass : public UBlueprintGeneratedClass +{ + GENERATED_UCLASS_BODY() +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp new file mode 100644 index 0000000..7b2ed0a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp @@ -0,0 +1,51 @@ +#pragma once +#include "../AbilityFramework.h" +#include "../GAAbilitiesComponent.h" +#include "GAEffectCueGlobals.h" + +void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn) +{ + //if (!CueIn) + //{ + // return; + //} + //UGAEffectCue* Cue = NewObject(OwningComponent.Get(), CueIn); + //Cues.Add(HandleIn, Cue); + //Cue->SetParameters(OwningComponent->GetOwner(), CueParamsIn); + //Cue->BeginCue(); +} +void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn) +{ + //Cues.Add(HandleIn, CueIn); +} +class UGAEffectCue* FGACueContainer::GetCue(const FGAEffectHandle& HandleIn) +{ + //UGAEffectCue* Cue = nullptr; + //Cue = Cues.FindRef(HandleIn); + return nullptr; +} +void FGACueContainer::ExecuteCue(const FGAEffectHandle& HandleIn) +{ + //UGAEffectCue* Cue = GetCue(HandleIn); + //if (Cue) + //{ + // Cue->ExecuteCue(); + //} +} +void FGACueContainer::RemoveCue(const FGAEffectHandle& HandleIn) +{ + //UGAEffectCue* Cue; + //if (Cues.Num() > 0) + //{ + // Cues.RemoveAndCopyValue(HandleIn, Cue); + // if (Cue) + // { + // Cue->EndCue(); + // Cue->MarkPendingKill(); + // } + //} +} +void FGACueContainer::CueExpired(const FGAEffectHandle& HandleIn) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h new file mode 100644 index 0000000..50ffecf --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h @@ -0,0 +1,26 @@ +#pragma once +#include "GameplayTagContainer.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" +#include "GAEffectCueGlobals.generated.h" + +USTRUCT() +struct FGACueContainer +{ + GENERATED_USTRUCT_BODY() +public: + TWeakObjectPtr OwningComponent; + + void AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn); + + void AddCue(const FGAEffectHandle& HandleIn); + + /* Return cue. Might return null so always check it first! */ + class UGAEffectCue* GetCue(const FGAEffectHandle& HandleIn); + + void ExecuteCue(const FGAEffectHandle& HandleIn); + + void RemoveCue(const FGAEffectHandle& HandleIn); + + void CueExpired(const FGAEffectHandle& HandleIn); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp new file mode 100644 index 0000000..55157b3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp @@ -0,0 +1,130 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAEffectCue.h" +#include "MovieScene.h" +#include "MovieSceneCommonHelpers.h" +#include "Modules/ModuleManager.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Engine/Blueprint.h" +#include "GameFramework/Actor.h" +#include "Classes/Engine/SCS_Node.h" +#include "Classes/Engine/SimpleConstructionScript.h" +#include "Engine/Blueprint.h" +#include "UObject/Package.h" + +#include "GAEffectCueSequence.h" + + +#if WITH_EDITOR +UGAEffectCueSequence::FOnInitialize UGAEffectCueSequence::OnInitializeSequenceEvent; +#endif + +UGAEffectCueSequence::UGAEffectCueSequence(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) + , MovieScene(nullptr) +#if WITH_EDITOR + , bHasBeenInitialized(false) +#endif +{ + bParentContextsAreSignificant = true; + + MovieScene = ObjectInitializer.CreateDefaultSubobject(this, "MovieScene"); + MovieScene->SetFlags(RF_Transactional); +} + +void UGAEffectCueSequence::PostInitProperties() +{ +#if WITH_EDITOR && WITH_EDITORONLY_DATA + AGAEffectCue* OwnerCue = Cast(GetOuter()); + if (!bHasBeenInitialized && !HasAnyFlags(RF_ClassDefaultObject) && OwnerCue && !OwnerCue->HasAnyFlags(RF_ClassDefaultObject)) + { + FGuid BindingID = MovieScene->AddPossessable(OwnerCue ? OwnerCue->GetActorLabel() : TEXT("Owner"), OwnerCue ? OwnerCue->GetClass() : AGAEffectCue::StaticClass()); + ObjectReferences.CreateBinding(BindingID, FActorSequenceObjectReference::CreateForContextActor()); + + OnInitializeSequenceEvent.Broadcast(this); + bHasBeenInitialized = true; + } +#endif + + Super::PostInitProperties(); +} +#if WITH_EDITOR +UGAEffectCueSequence* UGAEffectCueSequence::GetNullAnimation() +{ + static UGAEffectCueSequence* NullAnimation = nullptr; + + if (!NullAnimation) + { + NullAnimation = NewObject(GetTransientPackage(), NAME_None); + NullAnimation->AddToRoot(); + NullAnimation->MovieScene = NewObject(NullAnimation, FName("No Animation")); + NullAnimation->MovieScene->AddToRoot(); + } + + return NullAnimation; +} +#endif //WITH_EDITOR +float UGAEffectCueSequence::GetStartTime() const +{ + return MovieScene->GetPlaybackRange().GetLowerBoundValue(); +} + + +float UGAEffectCueSequence::GetEndTime() const +{ + return MovieScene->GetPlaybackRange().GetUpperBoundValue(); +} + + +/* UMovieSceneAnimation overrides +*****************************************************************************/ + + +void UGAEffectCueSequence::BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) +{ + AActor* ActorContext = CastChecked(Context); + + if (AActor* Actor = Cast(&PossessedObject)) + { + ObjectReferences.CreateBinding(ObjectId, FActorSequenceObjectReference::CreateForActor(Actor, ActorContext)); + } +} + + +bool UGAEffectCueSequence::CanPossessObject(UObject& Object, UObject* InPlaybackContext) const +{ + AActor* ActorContext = CastChecked(InPlaybackContext); + + if (AActor* Actor = Cast(&Object)) + { + return Actor == InPlaybackContext || Actor->GetLevel() == ActorContext->GetLevel(); + } + return true; +} + +void UGAEffectCueSequence::LocateBoundObjects(const FGuid& ObjectId, UObject* Context, TArray>& OutObjects) const +{ + if (Context) + { + ObjectReferences.ResolveBinding(ObjectId, CastChecked(Context), OutObjects); + } +} + + +UMovieScene* UGAEffectCueSequence::GetMovieScene() const +{ + return MovieScene; +} + + +UObject* UGAEffectCueSequence::GetParentObject(UObject* Object) const +{ + + return GetOuter(); +} + +void UGAEffectCueSequence::UnbindPossessableObjects(const FGuid& ObjectId) +{ + ObjectReferences.RemoveBinding(ObjectId); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h new file mode 100644 index 0000000..9d46082 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h @@ -0,0 +1,69 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Actor.h" +#include "MovieSceneSequence.h" +#include "MovieScene.h" +#include "LazyObjectPtr.h" +///D:\Unreal\UnrealEngine-Master\Engine\Source\Runtime\ActorSequence\Public\ActorSequenceObjectReference.h +#include "Runtime/ActorSequence/Public/ActorSequenceObjectReference.h" +#include "GAEffectCueSequence.generated.h" + +UCLASS(BlueprintType, DefaultToInstanced) +class ABILITYFRAMEWORK_API UGAEffectCueSequence : public UMovieSceneSequence +{ + GENERATED_BODY() + +public: + UPROPERTY(Instanced) + UMovieScene* MovieScene; +private: + /** Collection of object references. */ + UPROPERTY() + FActorSequenceObjectReferenceMap ObjectReferences; + +#if WITH_EDITORONLY_DATA +private: + bool bHasBeenInitialized; +#endif +public: + // Sets default values for this actor's properties + UGAEffectCueSequence(const FObjectInitializer& ObjectInitializer); + virtual void PostInitProperties() override; +#if WITH_EDITOR + /** + * Get a placeholder animation. + * + * @return Placeholder animation. + */ + static UGAEffectCueSequence* GetNullAnimation(); + + /** Event that is fired to initialize default state for a sequence */ + DECLARE_EVENT_OneParam(UGAEffectCueSequence, FOnInitialize, UGAEffectCueSequence*) + static FOnInitialize OnInitializeSequenceEvent; +public: + static FOnInitialize& OnInitializeSequence() { return OnInitializeSequenceEvent; } + + +#endif +public: + inline UMovieScene* GetMovieScene() { return MovieScene; } + UFUNCTION(BlueprintCallable, Category = "Animation") + float GetStartTime() const; + + /** + * Get the end time of this animation. + * + * @return End time in seconds. + * @see GetStartTime + */ + UFUNCTION(BlueprintCallable, Category = "Animation") + float GetEndTime() const; + virtual void BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) override; + virtual bool CanPossessObject(UObject& Object, UObject* InPlaybackContext) const override; + virtual UMovieScene* GetMovieScene() const override; + virtual UObject* GetParentObject(UObject* Object) const override; + virtual void UnbindPossessableObjects(const FGuid& ObjectId) override; + virtual void LocateBoundObjects(const FGuid& ObjectId, UObject* Context, TArray>& OutObjects) const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp new file mode 100644 index 0000000..0837a54 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp @@ -0,0 +1,24 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAGlobalTypes.h" +#include "../Attributes/GAAttributeBase.h" +#include "../GAAbilitiesComponent.h" +#include "GAEffectExecution.h" + +UGAEffectExecution::UGAEffectExecution(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} +void UGAEffectExecution::PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context) +{ + UE_LOG(GameAttributesEffects, Log, TEXT("Sample execution class implementation")); +} +void UGAEffectExecution::ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, + FGAEffectContext& Context, FGAEffectProperty& InProperty, + const FAFFunctionModifier& Modifier) +{ + PreModifyAttribute(HandleIn, ModIn, Context); + Context.TargetInterface->ModifyAttribute(ModIn, HandleIn, InProperty); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h new file mode 100644 index 0000000..5d6352b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h @@ -0,0 +1,22 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAGameEffect.h" +#include "GAEffectGlobalTypes.h" +#include "GAEffectExecution.generated.h" + +/* + +*/ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class ABILITYFRAMEWORK_API UGAEffectExecution : public UObject +{ + GENERATED_BODY() +public: + UGAEffectExecution(const FObjectInitializer& ObjectInitializer); + + virtual void PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context); + virtual void ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, + FGAEffectContext& Context, FGAEffectProperty& InProperty, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp new file mode 100644 index 0000000..29303cc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp @@ -0,0 +1,77 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAAbilitiesComponent.h" +#include "GAEffectExtension.h" + +UGAEffectExtension::UGAEffectExtension(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} +void UGAEffectExtension::SetParameters(const FGAEffectContext& ContextIn) +{ + Context = ContextIn; +} +void UGAEffectExtension::BeginEffect() +{ +} + +void UGAEffectExtension::NativeOnEffectApplied() +{ + OnEffectApplied(); +} +void UGAEffectExtension::NativeOnEffectExecuted() +{ + OnEffectExecuted(); +} +void UGAEffectExtension::NativeOnEffectExpired() +{ + OnEffectExpired(); +} +void UGAEffectExtension::NativeOnEffectRemoved() +{ + OnEffectRemoved(); +} +/** GameplayTaskOwnerInterface - Begin */ +void UGAEffectExtension::OnGameplayTaskInitialized(UGameplayTask& Task) +{ + //if (UGAAbilityTask* task = Cast(&Task)) + //{ + // task->Ability = this; + //} +} +UGameplayTasksComponent* UGAEffectExtension::GetGameplayTasksComponent(const UGameplayTask& Task) const +{ + return OwningComponent; +} +/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ +void UGAEffectExtension::OnGameplayTaskActivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Add(&Task); + //AbilityComponent->OnGameplayTaskActivated(Task); +} +/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ +void UGAEffectExtension::OnGameplayTaskDeactivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Remove(&Task); + //AbilityComponent->OnGameplayTaskDeactivated(Task); +} +AActor* UGAEffectExtension::GetGameplayTaskOwner(const UGameplayTask* Task) const +{ + return OwningComponent->GetOwner(); +} +AActor* UGAEffectExtension::GetGameplayTaskAvatar(const UGameplayTask* Task) const +{ + return Avatar; +} +/** GameplayTaskOwnerInterface - end */ + +UWorld* UGAEffectExtension::GetWorld() const +{ + if (Context.Target.IsValid()) + return Context.Target->GetWorld(); + + return nullptr; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h new file mode 100644 index 0000000..3ead376 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h @@ -0,0 +1,86 @@ +#pragma once +#include "GameplayTagContainer.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" + +#include "GameplayTaskOwnerInterface.h" +#include "GAEffectExtension.generated.h" +/* + Instanced effect with active event graph, where you can bind events + on application. + + One instance per ability is applied per actor. (ie, one ability can apply only one instanced + effect to each actor). + So this is not suitable for effects which should have ability to be applied multiple times the same + actor to stack in intensity and still have different durations. + + When the same type of instanced effect from the same instigator will be applied to the same actor + old effect will be terminated and new one will be applied. + Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). +*/ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplayTaskOwnerInterface +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "Context") + FGAEffectContext Context; + UPROPERTY() + class UGAAbilitiesComponent* OwningComponent; + UPROPERTY() + class AActor* Avatar; + + TSet ActiveTasks; + +public: + UGAEffectExtension(const FObjectInitializer& ObjectInitializer); + void SetParameters(const FGAEffectContext& ContextIn); + void BeginEffect(); + + /* + This event is always executed once upon application. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectApplied(); + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectExecuted(); + /* + Event executed when effet naturally expires. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectExpired(); + /* + Event executed when this effect is removed by force. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectRemoved(); + + void NativeOnEffectApplied(); + void NativeOnEffectExecuted(); + void NativeOnEffectExpired(); + void NativeOnEffectRemoved(); + + /** GameplayTaskOwnerInterface - Begin */ + virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; + /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ + /** Get owner of a task or default one when task is null */ + virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; + + /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ + virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; + + /** Get default priority for running a task */ + virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; + + /** Notify called after GameplayTask finishes initialization (not active yet) */ + virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; + + /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ + virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + + /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ + virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; + /** GameplayTaskOwnerInterface - end */ + + virtual UWorld* GetWorld() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp new file mode 100644 index 0000000..30e0213 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp @@ -0,0 +1,48 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" + +#include "../Abilities/GAAbilityBase.h" + +#include "GAEffectField.h" + +AGAEffectField::AGAEffectField(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + bReplicates = true; + SetReplicates(true); +} + +void AGAEffectField::InitializeField() +{ + //if (bIsFieldPersistent && AbilityInstigator) + //{ + + //} + //else if (!bIsFieldPersistent && AbilityInstigator) + //{ + // AbilityInstigator->OnAbilityCastEnd.AddUObject(this, &AGAEffectField::DestroyField); + //} + + //1. Automaticallt gather all collision componenets from blueprinted version. + // don't want to hardcode any kind of collision inside base class + // let designer decide what exactly he wants to do with it. + // but on other hand encapsulate this functionality so + // designer won't have to deal with binding/assiging events inside blueprint. + //2. Bind Events from them. +} + +void AGAEffectField::DestroyField() +{ + +} + +void AGAEffectField::OnAbilityExecuted_Implementation() +{ + +} + +void AGAEffectField::OnOtherFieldOverlap_Implementation() +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h new file mode 100644 index 0000000..6c02bb4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h @@ -0,0 +1,60 @@ +#pragma once +#include "GAEffectField.generated.h" + +/* + Base class for effect field. + These fields might exist in two states: + 1. As long as ability is channeled. + 2. They are persistent on their own, which means that ability only create them once + and from create tim they might exist set amount of time (including indefinetly), or + until they are manually removed or destroyed. + + Main use cases: + 1. Createing persistent level effects (fire wall, oil puddle, wall of ice etc). + 2. Spawning other actors (rain of meteors, other pawns). + + Possible functionaltity: + 1. Interacting with other fields (Wind field can extinguish fire field). + 2. Interacting with other direct damage/attribute changes (fire damage, can + ignite oil field, creating fire field). + Not sure about this. I would probabaly need to implement this functionality down the line in + GameSystem Module, or add GameAttributes dependency here. + + Fields are only created on server, and then replicated back to clients. + + Need custom K2 Node to properly spawn this actor!. Default SpawnActorFromClass is + not sufficient. +*/ + +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced) +class ABILITYFRAMEWORK_API AGAEffectField : public AActor +{ + GENERATED_UCLASS_BODY() +public: + /** + * If false, field will exist only as long as ability is channeled. + * Otherwise specific life time. + */ + UPROPERTY(BlueprintReadOnly, meta=(ExposeOnSpawn), Category = "Config") + bool bIsFieldPersistent; + + /** + * How long this field will live in world ? + * Only applicable if bIsFieldPersistent = true; + */ + UPROPERTY(BlueprintReadOnly, meta = (ExposeOnSpawn), Category = "Config") + float Lifetime; + + //UPROPERTY(BlueprintReadOnly, Category = "Owner") + //class AGASAbility* AbilityInstigator; + + void InitializeField(); + + void DestroyField(); + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Field") + void OnAbilityExecuted(); + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Field") + void OnOtherFieldOverlap(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp new file mode 100644 index 0000000..6d7f9e5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp @@ -0,0 +1,143 @@ +#pragma once +#include "../AbilityFramework.h" +#include "../GAAbilitiesComponent.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAEffectExecution.h" +#include "../IGAAbilities.h" +#include "GAGameEffect.h" +#include "GACustomCalculation.h" + + + +float FGADirectModifier::GetValue() { return Value; } +float FGADirectModifier::GetValue() const { return Value; } +float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + switch (Source) + { + case EGAAttributeSource::Instigator: + { + IIGAAbilities* AttrInt = Cast(Context.Instigator.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes(); + attr = Attributes->GetAttribute(Attribute); + //attr = Context.InstigatorComp->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Target: + { + IIGAAbilities* AttrInt = Cast(Context.Target.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; + attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Causer: + { + IIGAAbilities* AttrInt = Cast(Context.Causer.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; + attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); + break; + } + default: + return 0; + } + Result = (Coefficient * (PreMultiply + attr->GetFinalValue()) + PostMultiply) * PostCoefficient; + if (!bUseSecondaryAttribute) + return Result; + + return 0; +} +float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) const +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + + switch (Source) + { + case EGAAttributeSource::Instigator: + { + IIGAAbilities* AttrInt = Cast(Context.Instigator.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes(); + attr = Attributes->GetAttribute(Attribute); + //attr = Context.InstigatorComp->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Target: + { + IIGAAbilities* AttrInt = Cast(Context.Target.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes(); + attr = Attributes->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Causer: + { + IIGAAbilities* AttrInt = Cast(Context.Causer.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; + attr = Attributes->GetAttribute(Attribute); + break; + } + default: + return 0; + } + Result = (Coefficient * (PreMultiply + attr->GetFinalValue()) + PostMultiply) * PostCoefficient; + if (!bUseSecondaryAttribute) + return Result; + + return 0; +} + +float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + switch (Source) + { + case EGAAttributeSource::Instigator: + attr = ContextIn.InstigatorComp->GetAttribute(Attribute); + break; + case EGAAttributeSource::Target: + attr = ContextIn.TargetComp->GetAttribute(Attribute); + break; + default: + return 0; + } + FString ContextString(TEXT("Evaluating modifier value.")); + Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); + return Result; +} +float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) const +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + switch (Source) + { + case EGAAttributeSource::Instigator: + attr = ContextIn.InstigatorComp->GetAttribute(Attribute); + break; + case EGAAttributeSource::Target: + attr = ContextIn.TargetComp->GetAttribute(Attribute); + break; + default: + return 0; + } + FString ContextString(TEXT("Evaluating modifier value.")); + Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); + return Result; +} +float FGACustomCalculationModifier::GetValue(const struct FGAEffectHandle& HandleIn) +{ + if (CustomCalculation) + { + return CustomCalculation->NativeCalculateMagnitude(HandleIn); + } + return 0; +} +float FGACustomCalculationModifier::GetValue(const struct FGAEffectHandle& HandleIn) const +{ + if (CustomCalculation) + { + return CustomCalculation->NativeCalculateMagnitude(HandleIn); + } + return 0; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h new file mode 100644 index 0000000..467bc65 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h @@ -0,0 +1,155 @@ +#pragma once +#include "../AbilityFramework.h" +#include "../Attributes/GAAttributeGlobals.h" +#include "GameplayTagContainer.h" +#include "../GAGlobalTypes.h" +#include "GAEffectGlobalTypes.generated.h" + + +USTRUCT(BlueprintType) +struct FAFFunctionModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + float Additive; + UPROPERTY() + float Subtract; + UPROPERTY() + float Multiply; + UPROPERTY() + float Divide; + + FAFFunctionModifier() + {}; +}; + +/* +Base concept behind those attributes calculations (not sure if these are any good solutions +/performance firendly but: +1. Prefer getting values directly of attributes (GetBaseValue(), GetFinalValue(), GetBonus() etc), +as attributes can track their own state, we don't need any sophisticated way to access them and calculate bonuses). +2. Prefer simple and direct formulas (either evaluate from CurveTable, just plain add, Multiply various numbers, +or get value directly). +3. This system is not inteded, to calculate absolute final value on effect, before that effect is applied. +It will calculate absolute maximum value from the informations it have access to. +Further modifications like increasing specific damage type value, or reducing damage by value, are done +on AttributeComponent, by implementing approperiate functions, or by existing effects, which happen to intercept +incoming effect. +This might change in future though. But even if, I still prefer the magnitude calculations to be simple, +and we will add needed buffs/debuffs as we progress trough execution chain. +4. All calculations are linear. +*/ +//EGAMagnitudeCalculation::Direct +USTRUCT(BlueprintType) +struct FGADirectModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere) + float Value; + + float GetValue(); + float GetValue() const; +}; +//EGAMagnitudeCalculation::AttributeBased +USTRUCT(BlueprintType) +struct FGAAttributeBasedModifier +{ + /* + We also need to add concept of backing attributes, + though I'm not sure how I want to handle them at this point. + */ + GENERATED_USTRUCT_BODY() +public: + /* + Source of Attribute for this calculation. + */ + UPROPERTY(EditAnywhere) + EGAAttributeSource Source; + /* + Name of attribute Used for calculation. + */ + UPROPERTY(EditAnywhere) + FGAAttribute Attribute; + + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float Coefficient; + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float PreMultiply; + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float PostMultiply; + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float PostCoefficient; + /* + Should we use secondary attribute for this ecalculation ? + */ + UPROPERTY(EditAnywhere) + bool bUseSecondaryAttribute; + /* + Source for secondary attribute + */ + UPROPERTY(EditAnywhere) + EGAAttributeSource SecondarySource; + /* + Name of secondary attribute used in calculation. + */ + UPROPERTY(EditAnywhere) + FGAAttribute SecondaryAttribute; + + FGAAttributeBasedModifier() + : Source(EGAAttributeSource::Instigator), + Coefficient(1), + PreMultiply(0), + PostMultiply(0), + PostCoefficient(1), + bUseSecondaryAttribute(false) + {} + + float GetValue(const FGAEffectContext& Context); + float GetValue(const FGAEffectContext& Context) const; +}; +//EGAMagnitudeCalculation::CurveBased +USTRUCT(BlueprintType) +struct FGACurveBasedModifier +{ + GENERATED_USTRUCT_BODY() +public: + /* + Source of Attribute for this calculation. + */ + UPROPERTY(EditAnywhere) + EGAAttributeSource Source; + /* + Name of attribute from which we will take XValue for Curve + */ + UPROPERTY(EditAnywhere) + FGAAttribute Attribute; + /* + Curve and row from which we will take YValue. + */ + UPROPERTY(EditAnywhere) + FCurveTableRowHandle CurveTable; + + float GetValue(const FGAEffectContext& ContextIn); + float GetValue(const FGAEffectContext& ContextIn) const; +}; +//EGAMagnitudeCalculation::CustomCalculation +USTRUCT(BlueprintType) +struct FGACustomCalculationModifier +{ + GENERATED_USTRUCT_BODY() +public: + /* + Instanced, so we can setup custom properties this class might provide, per effect spec. + */ + UPROPERTY(EditAnywhere, Instanced) + class UGACustomCalculation* CustomCalculation; + + FGACustomCalculationModifier() + : CustomCalculation(nullptr) + {}; + + float GetValue(const struct FGAEffectHandle& HandleIn); + float GetValue(const struct FGAEffectHandle& HandleIn) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp new file mode 100644 index 0000000..f2fedef --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAEffectSet.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h new file mode 100644 index 0000000..dfb591f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Engine/DataAsset.h" +#include "GAEffectSet.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAEffectSet : public UDataAsset +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray> Specs; + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp new file mode 100644 index 0000000..5e3c5e1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -0,0 +1,689 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GameplayTagContainer.h" +#include "../GAAbilitiesComponent.h" +#include "../Attributes/GAAttributesBase.h" +#include "../IGAAbilities.h" + +#include "../GAAbilitiesComponent.h" +#include "GAEffectExecution.h" +#include "GAEffectExtension.h" +#include "../GAGlobalTypes.h" +#include "AFEffectApplicationRequirement.h" +#include "AFEffectCustomApplication.h" +#include "GAGameEffect.h" + +DEFINE_STAT(STAT_GatherModifiers); + +void FGAEffectProperty::Initialize() +{ + Spec = SpecClass.SpecClass->GetDefaultObject(); + ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); + Application = GetSpec()->Application.GetDefaultObject(); + Execution = GetSpec()->ExecutionType.GetDefaultObject(); +} +void FGAEffectProperty::InitializeIfNotInitialized() +{ + if (!IsInitialized()) + { + Initialize(); + } +} + +void FAFEffectRepInfo::OnApplied() +{ + +} +void FAFEffectRepInfo::OnPeriod() +{ + +} +void FAFEffectRepInfo::OnRemoved() +{ + +} + +void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) +{ + InArraySerializer.EffectInfos.Remove(Handle); + InArraySerializer.OwningComponent->OnEffectRepInfoRemoved.Broadcast(this); +} +void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) +{ + InArraySerializer.EffectInfos.Add(Handle, this); + InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); +} +void FAFEffectRepInfo::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) +{ + +} +float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) +{ + switch (CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeBased.GetValue(Context); + } + case EGAMagnitudeCalculation::CurveBased: + { + return CurveBased.GetValue(Context); + } + case EGAMagnitudeCalculation::CustomCalculation: + { + //return Custom.GetValue(*this); + } + default: + return 0; + } + + return 0; +} +FGAEffect::FGAEffect(class UGAGameEffectSpec* GameEffectIn, + const FGAEffectContext& ContextIn) + : GameEffect(GameEffectIn), + Context(ContextIn) +{ + OwnedTags = GameEffectIn->OwnedTags; + if (GameEffect->Extension) + { + Extension = NewObject(Context.Target.Get(), GameEffect->Extension); + Extension->OwningComponent = Context.TargetComp.Get(); + } + if (ContextIn.TargetComp.IsValid()) + { + TargetWorld = ContextIn.TargetComp->GetWorld(); + AppliedTime = TargetWorld->TimeSeconds; + LastTickTime = TargetWorld->TimeSeconds; + } + else if (ContextIn.InstigatorComp.IsValid()) + { + TargetWorld = ContextIn.InstigatorComp->GetWorld(); + AppliedTime = TargetWorld->TimeSeconds; + LastTickTime = TargetWorld->TimeSeconds; + } + IsActive = false; +} + +float FAFStatics::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + switch (AttributeIn.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return AttributeIn.DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeIn.AttributeBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CurveBased: + { + return AttributeIn.CurveBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return AttributeIn.Custom.GetValue(InHandle); + } + default: + break; + } + + return 0; +} +FGAEffectMod FAFStatics::GetAttributeModifier(FGAAttributeModifier& ModInfoIn + , class UGAGameEffectSpec* InSpec + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + FGAEffectMod ModOut; + if (InSpec) + { + switch (ModInfoIn.Magnitude.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.DirectModifier.GetValue(), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.AttributeBased.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + + } + case EGAMagnitudeCalculation::CurveBased: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.CurveBased.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.Custom.GetValue(InHandle), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + + } + default: + break; + } + } + return ModOut; +} +FGAEffect::~FGAEffect() +{ + if (Extension.IsValid()) + { + Extension->MarkPendingKill(); + Extension.Reset(); + } +} +void FGAEffect::SetContext(const FGAEffectContext& ContextIn) +{ + Context = ContextIn; +} + +void FGAEffect::OnApplied() +{ + IsActive = true; + AppliedTime = TargetWorld->TimeSeconds; + if (Extension.IsValid()) + { + Extension->NativeOnEffectApplied(); + } +} +void FGAEffect::OnDuration() +{ + +} +void FGAEffect::OnExecuted() +{ + OnEffectPeriod.Broadcast(Handle); + if (Extension.IsValid()) + { + Extension->NativeOnEffectExecuted(); + } +} +void FGAEffect::OnExpired() +{ + OnEffectExpired.Broadcast(Handle); + IsActive = false; + if (Extension.IsValid()) + { + Extension->NativeOnEffectExpired(); + } +} +void FGAEffect::OnRemoved() +{ + OnEffectRemoved.Broadcast(Handle); + IsActive = false; + if (Extension.IsValid()) + { + Extension->NativeOnEffectRemoved(); + } +} +void FGAEffect::DurationExpired() +{ + +} + +float FGAEffect::GetDurationTime() const +{ + return GetFloatFromAttributeMagnitude(GameEffect->Duration); +} +float FGAEffect::GetPeriodTime() const +{ + return GetFloatFromAttributeMagnitude(GameEffect->Period); +} +float FGAEffect::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const +{ + switch (AttributeIn.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return AttributeIn.DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeIn.AttributeBased.GetValue(Context); + } + case EGAMagnitudeCalculation::CurveBased: + { + return AttributeIn.CurveBased.GetValue(Context); + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return AttributeIn.Custom.GetValue(Handle); + } + default: + break; + } + + return 0; +} +float FGAEffect::GetCurrentActivationTime() +{ + float CurrentTime = TargetWorld->TimeSeconds; + return CurrentTime - AppliedTime; +} + +float FGAEffect::GetCurrentActivationTime() const +{ + float CurrentTime = TargetWorld->TimeSeconds; + return CurrentTime - AppliedTime; +} + +float FGAEffect::GetCurrentTickTime() +{ + float CurrentTime = TargetWorld->TimeSeconds; + return CurrentTime - LastTickTime; +} + +void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams) +{ + /*if (!EffectCue) + { + return; + } + AActor* Instigator = EffectHandle.GetContext().Instigator.Get(); + UGAEffectCue* NewCue = NewObject(Instigator, EffectCue); + if (NewCue && Instigator) + { + NewCue->SetParameters(Instigator, CueParams); + NewCue->Context = EffectHandle.GetContext(); + NewCue->BeginCue(); + }*/ +} + +FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty + , const FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + FGAEffectHandle Handle; + bool bHasDuration = InProperty.Duration > 0; + bool bHasPeriod = InProperty.Period > 0; + + if (bHasDuration || bHasPeriod) + { + Handle = FGAEffectHandle::GenerateHandle(EffectIn); + } + if (InProperty.ApplicationRequirement->CanApply(EffectIn, InProperty, this, InContext, Handle)) + { + if(!bHasDuration && !bHasPeriod) + { + if (InProperty.Handle.IsValid()) + { + if (InProperty.Application->ApplyEffect(InProperty.Handle, + EffectIn, InProperty, this, InContext)) + { + InProperty.Application->ExecuteEffect(InProperty.Handle, InProperty, InContext, Modifier); + // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); + } + } + else + { + Handle = FGAEffectHandle::GenerateHandle(EffectIn); + EffectIn->Handle = Handle; + InProperty.Handle = Handle; + if (InProperty.Application->ApplyEffect(Handle, + EffectIn, InProperty, this, InContext)) + { + InProperty.Application->ExecuteEffect(Handle, InProperty, InContext, Modifier); + // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); + } + } + } + else + { + EffectIn->Handle = Handle; + if (InProperty.Application->ApplyEffect(Handle, + EffectIn, InProperty, this, InContext)) + { + InProperty.Application->ExecuteEffect(Handle, InProperty, InContext, Modifier); + // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); + } + } + + } + EffectIn->OnApplied(); + return Handle; + //ApplyReplicationInfo(HandleIn); + //apply additonal effect applied with this effect. + //for (TSubclassOf Spec : EffectIn.GameEffect->OnAppliedEffects) + //{ + // FGAEffectHandle Handle = EffectIn.Context.TargetComp->MakeGameEffect(Spec, EffectIn.Context); + + // EffectIn.Context.InstigatorComp->ApplyEffectToTarget(Handle.GetEffect(), Handle, InProperty); + //} +} + +void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& HandleIn) +{ + //TSharedPtr EffectPtr = HandleIn.GetEffectPtr(); + //UGAGameEffectSpec* EffectSpec = HandleIn.GetEffectSpec(); + //if (EffectPtr.IsValid() && EffectSpec && EffectSpec->EffectCue) + //{ + // FGAEffectRepInfo RepInfo(0, EffectSpec->Period, EffectSpec->Duration, 0); + //// RepInfo.EffectCueClass = EffectSpec->EffectCue; + // MarkItemDirty(RepInfo); + //} +} +EGAEffectAggregation FGAEffectContainer::GetEffectAggregation(const FGAEffectHandle& HandleIn) const +{ + UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); + return Spec->EffectAggregation; +} + +TSet FGAEffectContainer::GetHandlesByAttribute(const FGAEffectHandle& HandleIn) +{ + TSet Handles; + if (TSet* ptr = EffectByAttribute.Find(HandleIn.GetAttribute())) + { + Handles = *ptr; + } + return Handles; +} + +TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectProperty& InProperty +, const FGAEffectContext& InContext) +{ + TSet Handles; + UGAGameEffectSpec* Spec = InProperty.Spec; + EGAEffectAggregation Aggregation = Spec->EffectAggregation; + UClass* EffectClass = Spec->GetClass(); + + switch (Aggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + UGAAbilitiesComponent* Instigator = InContext.InstigatorComp.Get(); + TMap>* EffectByClassMap = InstigatorEffectByClass.Find(Instigator); + //TSet* EffectByClass; + if (EffectByClassMap) + { + return EffectByClassMap->FindRef(EffectClass); + } + + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + UGAAbilitiesComponent* Target = InContext.TargetComp.Get(); + TSet* TargetEffect = TargetEffectByClass.Find(EffectClass); + if (TargetEffect) + { + return *TargetEffect; + } + break; + } + default: + break; + } + return Handles; +} + +void FGAEffectContainer::AddEffect(const FGAEffectHandle& HandleIn, bool bInfinite) +{ + TSet& AttributeEffect = EffectByAttribute.FindOrAdd(HandleIn.GetAttribute()); + AttributeEffect.Add(HandleIn); + ActiveEffectHandles.Add(HandleIn); + AddEffectByClass(HandleIn); + UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); + FObjectKey key(HandleIn.GetEffectSpec()->GetClass()); + TArray& handles = EffectByClass.FindOrAdd(key); + handles.Add(HandleIn); + if (bInfinite) + { + InfiniteEffects.Add(HandleIn); + } +} +void FGAEffectContainer::AddEffectByClass(const FGAEffectHandle& HandleIn) +{ + UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); + EGAEffectAggregation Aggregation = Spec->EffectAggregation; + UClass* EffectClass = Spec->GetClass(); + TSet Handles; + UGAAbilitiesComponent* Target = HandleIn.GetContextRef().TargetComp.Get(); + switch (Aggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + UGAAbilitiesComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); + + + TMap>& EffectByClassMap = InstigatorEffectByClass.FindOrAdd(Instigator); + TSet& instigatorEffect = EffectByClassMap.FindOrAdd(EffectClass); + instigatorEffect.Add(HandleIn); + if (Target) + { + Target->AddTagContainer(Spec->ApplyTags); + } + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + TSet& TargetEffects = TargetEffectByClass.FindOrAdd(EffectClass); + TargetEffects.Add(HandleIn); + if (Target) + { + Target->AddTagContainer(Spec->ApplyTags); + } + break; + } + default: + break; + } +} +void FGAEffectContainer::RemoveFromAttribute(const FGAEffectHandle& HandleIn) +{ + TSet* AttributeEffect = EffectByAttribute.Find(HandleIn.GetAttribute()); + IIGAAbilities* Target = HandleIn.GetContextRef().TargetInterface; + if (AttributeEffect) + { + AttributeEffect->Remove(HandleIn); + if (AttributeEffect->Num() <= 0) + { + EffectByAttribute.Remove(HandleIn.GetAttribute()); + } + } + + //UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::RemoveFromAttribute %s = %f"), *HandleIn.GetAttribute().ToString(), Target->GetAttributeValue(HandleIn.GetAttribute())); + Target->RemoveBonus(HandleIn.GetAttribute(), HandleIn, HandleIn.GetAttributeMod()); + //UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::RemoveFromAttribute %s = %f"), *HandleIn.GetAttribute().ToString(), Target->GetAttributeValue(HandleIn.GetAttribute())); +} +void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn + , const FGAEffectProperty& InProperty) +{ + RemoveFromAttribute(HandleIn); + ActiveEffectHandles.Remove(HandleIn); + InfiniteEffects.Remove(HandleIn); + TArray* handles = EffectByClass.Find(FObjectKey(InProperty.GetClass())); + if (handles && handles->Num() > 0) + { + handles->Remove(HandleIn); + if (handles->Num() <= 0) + { + EffectByClass.Remove(FObjectKey(InProperty.GetClass())); + } + } +} +void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn + , const FGAEffectProperty& InProperty) +{ + UGAAbilitiesComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); + UClass* EffectClass = HandleIn.GetEffectSpec()->GetClass(); + TMap>* InstigatorEffect = InstigatorEffectByClass.Find(Instigator); + TSet* HandlesToRemove = InstigatorEffect->Find(EffectClass); + IIGAAbilities* Target = HandleIn.GetContextRef().TargetInterface; + TSharedPtr Effect = HandleIn.GetEffectPtr(); + if (HandlesToRemove) + { + HandlesToRemove->Remove(HandleIn); + if (HandlesToRemove->Num() <= 0) + { + InstigatorEffect->Remove(EffectClass); + } + } + if (Effect.IsValid()) + { + Effect->OnEffectRemoved.Broadcast(Effect->Handle); + Target->RemoveTagContainer(Effect->ApplyTags); + FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); + DurationTimer.ClearTimer(Effect->DurationTimerHandle); + DurationTimer.ClearTimer(Effect->PeriodTimerHandle); + } + RemoveEffectProtected(HandleIn, InProperty); + +} + +void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) +{ + UGAGameEffectSpec* Spec = InProperty.Spec; + EGAEffectAggregation Aggregation = Spec->EffectAggregation; + //TSet* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); + + if (!ActiveEffectHandles.Contains(InHandle)) + { + UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *InHandle.GetEffectRef().ToString()); + return; + } + switch (Aggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + RemoveInstigatorEffect(InHandle, InProperty); + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + RemoveTargetEffect(InHandle, InProperty); + break; + } + default: + break; + } +} + +void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn + , const FGAEffectProperty& InProperty) +{ + UClass* EffectClass = HandleIn.GetEffectSpec()->GetClass(); + TSet* Handles = TargetEffectByClass.Find(EffectClass); + IIGAAbilities* Target = HandleIn.GetContextRef().TargetInterface; + + TSharedPtr Effect = HandleIn.GetEffectPtr(); + + if (Handles) + { + Handles->Remove(HandleIn); + if (Handles->Num() <= 0) + { + TargetEffectByClass.Remove(EffectClass); + } + } + + RemoveEffectProtected(HandleIn, InProperty); + if (Effect.IsValid()) + { + Effect->OnEffectRemoved.Broadcast(Effect->Handle); + Target->RemoveTagContainer(Effect->ApplyTags); + FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); + DurationTimer.ClearTimer(Effect->DurationTimerHandle); + DurationTimer.ClearTimer(Effect->PeriodTimerHandle); + } +} + +void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num) +{ + UGAGameEffectSpec* Spec = HandleIn.Spec; + EGAEffectAggregation Aggregation = Spec->EffectAggregation; + TArray* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); + + if (handles) + { + for (int32 idx = 0; idx < Num; idx++) + { + if (handles->IsValidIndex(0)) + { + FGAEffectHandle OutHandle = (*handles)[0]; + if (OutHandle.IsValid()) + { + if (!ActiveEffectHandles.Contains(OutHandle)) + { + UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffectRef().ToString()); + continue; + } + switch (Aggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + RemoveInstigatorEffect(OutHandle, HandleIn); + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + RemoveTargetEffect(OutHandle, HandleIn); + break; + } + default: + break; + } + } + } + } + } +} + +//FGAEffectContainer::FGAEffectContainer() +//{ +//} + +void FGAEffectContainer::ApplyEffectInstance(class UGAEffectExtension* EffectIn) +{ + +} + + +bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) +{ + if (ActiveEffectHandles.Contains(HandleIn)) + { + return true; + } + return false; +} +bool FGAEffectContainer::ContainsEffectOfClass(const FGAEffectProperty& InProperty) +{ + FObjectKey key(InProperty.GetClass()); + if (EffectByClass.Contains(key)) + { + return true; + } + return false; +} +//TSharedPtr FGAEffectContainer::GetEffectByHandle(const FGAEffectHandle& HandleIn) +//{ +// return ActiveEffects.FindRef(HandleIn); +//} +UWorld* FGAEffectContainer::GetWorld() const +{ + if (OwningComponent) + { + return OwningComponent->GetWorld(); + } + return nullptr; +} + +UGAGameEffectSpec::UGAGameEffectSpec() +{ + ExecutionType = UGAEffectExecution::StaticClass(); + ApplicationRequirement = UAFEffectApplicationRequirement::StaticClass(); + Application = UAFEffectCustomApplication::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h new file mode 100644 index 0000000..1b47bf2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -0,0 +1,753 @@ +#pragma once +//#include "GAGlobalTypes.h" +#include "GAEffectGlobalTypes.h" +#include "GameplayTagContainer.h" +//#include "NetSerialization.h" +#include "GAGameEffect.generated.h" + +DECLARE_STATS_GROUP(TEXT("GameEffect"), STATGROUP_GameEffect, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("GatherModifiers"), STAT_GatherModifiers, STATGROUP_GameEffect, ); + +/* + Modifier type for simple attribute operatinos. + It's only additive or subtractive due to possible race conditions with multiplicative/divide + mods. +*/ +UENUM() +enum class EGASimpleAttributeOperation : uint8 +{ + Additive, + Subtractive, + Invalid +}; + +UENUM() +enum class EGAMakeSpecResult : uint8 +{ + NewHandle, + OldHandle, + Invalid +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAMagnitude +{ + GENERATED_USTRUCT_BODY() +public: + /* + Type of calculation we want to perform for this Magnitude. + */ + UPROPERTY(EditAnywhere) + EGAMagnitudeCalculation CalculationType; + + UPROPERTY(EditAnywhere) + FGADirectModifier DirectModifier; + /* + Simple calculation based on attribute: + (Coefficient * (PreMultiply + AttributeValue) + PostMultiply) * PostCoefficient + + There is no any magic manipulation, it straight off pull attribute from selected source, + and make this operation on it. + */ + UPROPERTY(EditAnywhere) + FGAAttributeBasedModifier AttributeBased; + /* + Get value from selected CurveTable, based on selected attribute value. + */ + UPROPERTY(EditAnywhere) + FGACurveBasedModifier CurveBased; + /* + Provide custom calculation class. + */ + UPROPERTY(EditAnywhere) + FGACustomCalculationModifier Custom; + + float GetFloatValue(const FGAEffectContext& Context); +}; +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAAttributeModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Instant Spec") + FGAAttribute Attribute; + + UPROPERTY(EditAnywhere, Category = "Instant Spec") + EGAAttributeMod AttributeMod; + + /* + Who will be target of this attribute change. + Instigator - pawn which applied effect (regardless of to whom). + Target - targeted pawn (regardless of who applied). + */ + UPROPERTY(EditAnywhere) + EGAModifierTarget ModifierTarget; + /* + How modifier will be executed on target. + */ + //UPROPERTY(EditAnywhere, Category = "Execution Type") + // TSubclassOf ExecutionType; + + /* + Modifier value applied to attribute + */ + UPROPERTY(EditAnywhere) + FGAMagnitude Magnitude; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAttributeModifierContainer +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Modifiers; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFCueContainer +{ + GENERATED_BODY() +public: + /* Cues to apply */ + UPROPERTY(EditAnywhere) + FGameplayTagContainer CueTags; +}; + +/* + Base effect class. You can derive your own specialized classes from it + with preset customizations and values. You should never directly inherit blueprints from it. +*/ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject +{ + GENERATED_BODY() +public: + /* + Individual Tag descrbing effect type. + ie. Condition.Burning + */ + UPROPERTY(EditAnywhere, Category = "Effect Info") + FGameplayTag EffectTag; + + UPROPERTY(EditAnywhere, meta=(UseDisplayName), Category = "Effect Info") + TSubclassOf ApplicationRequirement; + /* + How effect should stack. Only relevelant for periodic effects + and modifiers applied on period. + */ + UPROPERTY(EditAnywhere, meta = (UseDisplayName), Category = "Effect Info") + TSubclassOf Application; + + UPROPERTY(EditAnywhere, Category = "Stacking") + int32 MaxStacks; + + /* + Who should aggregate this effect. Relevelant for stacking type + and by this only relevelant for periodic effects. + */ + UPROPERTY(EditAnywhere, Category = "Stacking") + EGAEffectAggregation EffectAggregation; + + /* Total duration of effect (if applicable) */ + UPROPERTY(EditAnywhere, Category = "Duration") + FGAMagnitude Duration; + /* Duration of single period. */ + UPROPERTY(EditAnywhere, Category = "Period") + FGAMagnitude Period; + /* Total duration of effect (if applicable) */ + UPROPERTY(EditAnywhere, Category = "Duration") + float MaxStackedDuration; + + /* IF true, effect will tick instantly upon application. */ + UPROPERTY(EditAnywhere, Category = "Duration") + bool bTickOnApplication; + UPROPERTY(EditAnywhere, Category = "Duration") + bool bExecuteOnApplication; + + + /* + Modifier applied to attribute + */ + UPROPERTY(EditAnywhere, Category = "Attribute Modifiers") + FGAAttributeModifier AtributeModifier; + UPROPERTY(EditAnywhere, Category = "Attribute Modifiers") + FAFAttributeModifierContainer Modifiers; + + UPROPERTY(EditAnywhere, Category = "Execution Type") + TSubclassOf ExecutionType; + + UPROPERTY(EditAnywhere, Category = "Modifiers") + TSubclassOf Extension; + + /* Cues to apply by this effect. */ + UPROPERTY(EditAnywhere, Category = "Cues") + FAFCueContainer Cues; + /* + Effects applied when this effect is applied. + These effects will be applied with the same context and the same target as + effect, which stores them. + */ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> OnAppliedEffects; + + /* Effects applied when this effect expire*/ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> OnExpiredEffects; + + /* Effects applied when this effect is removed. */ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> OnRemovedEffects; + + /* + Effects applied only when certain criteria are met. + Just dumbed here it needs it's own structure that will actually alow to setup those conditions. + */ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> ConditonalEffects; + + + /* Remove effects with these tags. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer RemoveEffectWithTags; + + /* + Tags descrbing what this effect does. + */ + /* Tags I own and I don't apply. New tags can be added here as the effect is applied. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer OwnedTags; + /* Tags owned by this effect and not applied. Describe the type of this effect. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer EffectTags; + + /* + When effect is appied trigger events with these tags. + */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer AppliedEventTags; + /* + When effect is executed trigger events with these tags. + */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ExecuteEventTags; + + /* + Tags applied to attribute when effect is applying non-instant effect. + Owned tags of another effect are checked against these tags to calculate + modifier. + Also it's checked when tag is applied to determine effect stacking, + when stacking is set to Override or StrongerOverride. + + Use only single tag here, with proper hierarchy. + Using multiple tags should be reserved only for special cases. + */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer AttributeTags; + + /* If Target have these tags I will not be applied to it. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DenyTags; + + /* Applied immunity tags. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer AppliedImmunityTags; + + /* Tags, which are applied to Target when effect is Duration/Periodic based. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ApplyTags; + + /* Tags, required for this effect to be applied. If these tags are not present, effect will be ignored. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer RequiredTags; + + /* Tags, required for this effect to be executed. If these tags are not present, effect will be ignored. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ExecutionRequiredTags; +public: + UGAGameEffectSpec(); +}; +/* + Base effect class to extend from when creating effect blueprints. +*/ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFEffectSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: +}; +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectSpec +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, Instanced, Category = "Effect") + UGAGameEffectSpec* Spec; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectClass +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Effect") + TSubclassOf SpecClass; + + const bool operator==(const FGAEffectClass& Other) const + { + return SpecClass == Other.SpecClass; + } + const bool operator==(const TSubclassOf& OtherClass) const + { + return SpecClass == OtherClass; + } + void operator=(const FGAEffectClass& Other) + { + SpecClass = Other.SpecClass; + } + void operator=(const TSubclassOf& Other) + { + SpecClass = Other; + } + void operator=(UGAGameEffectSpec* Other) + { + SpecClass = Other->GetClass(); + } +}; + +/* + Special effect container, which contains Effect class and Handle to already instanced effect + from this class. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectProperty +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Effect") + FGAEffectClass SpecClass; + + UPROPERTY() + class UAFEffectApplicationRequirement* ApplicationRequirement; + UPROPERTY() + class UAFEffectCustomApplication* Application; + UPROPERTY() + class UGAEffectExecution* Execution; + UPROPERTY() + class UGAGameEffectSpec* Spec; + + UPROPERTY() + float Duration; + UPROPERTY() + float Period; + /* + Handle to effect created from SpecClass + This handle is only created and kept for instant effects, + so we don't create new object every time instant effect is created + as potentially there can be quite a lot of allocations. + */ + FGAEffectHandle Handle; + //target of handle, handle to effect. + //only used for duration effcts, and cleared after effect is removed. + TMap Handles; + FGAEffectProperty() + : ApplicationRequirement(nullptr), + Application(nullptr), + Execution(nullptr), + Spec(nullptr) + {}; + + TSubclassOf GetClass() const { return SpecClass.SpecClass; } + const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } + UGAGameEffectSpec* GetSpec() const { return Spec; } + + //intentionally non const. + FGAEffectHandle& GetHandleRef() { return Handle; } + void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; + void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} + + void Initialize(); + void InitializeIfNotInitialized(); + + FGAAttributeModifier& GetAttributeModifier() + { + return Spec->AtributeModifier; + } + + FObjectKey GetClassKey() const + { + return FObjectKey(GetClass()); + } + + const bool IsValid() const + { + return SpecClass.SpecClass ? true : false; + } + const bool IsInitialized() const + { + return ApplicationRequirement && Application && Execution && Spec; + } + const bool IsValidHandle() const + { + return Handle.IsValid(); + } + const bool operator==(const FGAEffectProperty& Other) const + { + return SpecClass == Other.SpecClass; + } + const bool operator==(const TSubclassOf& OtherClass) const + { + return SpecClass == OtherClass; + } + void operator=(const FGAEffectProperty& Other) + { + SpecClass = Other.SpecClass; + Handle = Other.Handle; + } + void operator=(const TSubclassOf& Other) + { + SpecClass = Other; + } + void operator=(UGAGameEffectSpec* Other) + { + SpecClass = Other->GetClass(); + } +}; + + +struct FAFStatics +{ + static float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle); + static FGAEffectMod GetAttributeModifier(FGAAttributeModifier& ModInfoIn + , class UGAGameEffectSpec* InSpec, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle); +}; + +/* + Calculcated magnitudes, captured attributes and tags, set duration. + Final effect which then is used to apply custom calculations and attribute changes. +*/ +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectMulicastDelegate, const FGAEffectHandle&); + +struct ABILITYFRAMEWORK_API FGAEffect : public TSharedFromThis +{ + /* Cached pointer to original effect spec. */ + + TWeakObjectPtr Extension; + UWorld* TargetWorld; + /* + Calculated mods ready to be applied. + These are perlimenarly calculcated mods, + which can be furhter modified by Calculation object. + */ + + + /* Contains all tags gathered on the way to application ? */ + + bool IsActive; +public: + //pointer ? Acces trough handle ? + class UGAGameEffectSpec* GameEffect; + FGAEffectContext Context; + FGameplayTagContainer OwnedTags; + FGameplayTagContainer ApplyTags; + FGameplayTagContainer RequiredTags; + + FGAEffectHandle Handle; + + mutable FTimerHandle PeriodTimerHandle; + mutable FTimerHandle DurationTimerHandle; + + FGAEffectMod AttributeMod; +//because I'm fancy like that and like to make spearate public for fields and functions. +public: + //Simple delegates to make sure they are bound only to one object. + FAFEffectMulicastDelegate OnEffectPeriod; + FAFEffectMulicastDelegate OnEffectExpired; + FAFEffectMulicastDelegate OnEffectRemoved; + + float AppliedTime; + float LastTickTime; +public: + void SetContext(const FGAEffectContext& ContextIn); + + class UGAAbilitiesComponent* GetInstigatorComp() { return Context.InstigatorComp.Get(); } + class UGAAbilitiesComponent* GetTargetComp() { return Context.TargetComp.Get(); } + inline void AddOwnedTags(const FGameplayTagContainer& TagsIn) { OwnedTags.AppendTags(TagsIn); } + inline void AddApplyTags(const FGameplayTagContainer& TagsIn) { ApplyTags.AppendTags(TagsIn); } + void OnApplied(); + void OnDuration(); + void OnExpired(); + void OnRemoved(); + void OnExecuted(); + void DurationExpired(); + + float GetDurationTime() const; + float GetPeriodTime() const; + float GetCurrentActivationTime(); + float GetCurrentActivationTime() const; + float GetCurrentTickTime(); + float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const; + bool IsValid() const + { + return GameEffect != nullptr; + } + FString ToString() + { + if (GameEffect) + { + return GameEffect->GetName(); + } + return FString(); + } + FGAEffect() + : GameEffect(nullptr) + {} + FGAEffect(class UGAGameEffectSpec* GameEffectIn, + const FGAEffectContext& ContextIn); + + ~FGAEffect(); +}; + +/* + Minimum replicated info about applied info, so we don't replicate full effect if not needed. + Also provide callbacks for cues assigned to this Effect, so they can be predictevly, + executed on clients. + + Add replication optimization. +*/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectAttributeModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere) + FGAAttribute Attribute; + UPROPERTY(EditAnywhere) + float Value; +}; +USTRUCT(BlueprintType) +struct FGAEffectDuration +{ + GENERATED_USTRUCT_BODY() +public: + /* + -1 infinite duration, 0-no duration >0 - set duration + */ + UPROPERTY(EditAnywhere, Category = "Duration") + float Duration; + /* + <=0 - no period >0 - set period + */ + UPROPERTY(EditAnywhere, Category = "Duration") + float Period; + /* + If PeriodNum > 0 and Period > 0, then duration of + effect is PeriodNum * Period + */ + UPROPERTY(EditAnywhere, Category = "Duration") + float PeriodNum; +}; +/* + Effect spec struct, which can be used to create effect specs directly inside abitrary classes ? +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectSpecDefinition +{ + GENERATED_USTRUCT_BODY() +}; + +struct FGAActiveGameEffect +{ + FGAActiveGameEffect(); +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer +{ + GENERATED_USTRUCT_BODY() + + UPROPERTY() + TArray Effects; +}; + +/* + Contains all active effects (which have duration, period or are infinite). + + The only reason this is USTRUCT() is because we need to hold hard references somewhere to instanced + effects. +*/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem +{ + GENERATED_USTRUCT_BODY() + +public: + //Handle to effect, which is using this info. + UPROPERTY() + FGAEffectHandle Handle; + UPROPERTY() + float AppliedTime; + UPROPERTY() + float PeriodTime; + UPROPERTY() + float Duration; + UPROPERTY() + float ReplicationTime; + + FSimpleDelegate OnAppliedDelegate; + + //UPROPERTY() + // FGAEffectContext Context; + + void OnApplied(); + void OnPeriod(); + void OnRemoved(); + + void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); + void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); + void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); + + + FAFEffectRepInfo() + {}; + + const bool operator==(const FAFEffectRepInfo& Other) const + { + return Handle == Other.Handle; + } + + FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn) + : AppliedTime(AppliedTimeIn), + PeriodTime(PeriodTimeIn), + Duration(DurationIn), + ReplicationTime(ReplicationTimeIn) + {}; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGAGameCue +{ + GENERATED_USTRUCT_BODY() + + + //Handle to effect, which spawned this cue. + UPROPERTY() + FGAEffectHandle EffectHandle; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGameCueContainer +{ + GENERATED_USTRUCT_BODY() + + TWeakObjectPtr OwningComp; +public: + void AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams); +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + TArray ActiveEffectInfos; + //IDK might be actually easier to map Handles to active effects on clients + //as Handle should be synced between client and server. + //that's why handle should only be created on server (and by that, effects). + mutable TMap EffectInfos; + + + + TMap> EffectByAttribute; + + TMap> EffectByClass; + + //TQueue dupa; + /* All effects. */ + TSet ActiveEffectHandles; + /* + Contains effects with infinite duration. + Infinite effects are considred to be special case, where they can only be self spplied + and must be manually removed. + */ + TSet InfiniteEffects; + + //not really sure if we really need set.\ + // it could be usefull, for effects which stack in add. + /* + UObject* - Instigator + FName = Effect class name + FGAEffectHandle = handle to effect of class. + */ + TMap>> InstigatorEffectByClass; + + /* + FName = Effect class name + FGAEffectHandle = handle to effect of class. + */ + TMap> TargetEffectByClass; + + /* Keeps effects instanced per target actor. */ + UPROPERTY(NotReplicated) + TArray TargetInstancedEffects; + + UPROPERTY(NotReplicated) + class UGAAbilitiesComponent* OwningComponent; +public: + //FGAEffectContainer(); + FGAEffectHandle ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty + , const FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ + void RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); + /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ + void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); + /* Remove given number of effects of the same type */ + void ApplyReplicationInfo(const FGAEffectHandle& HandleIn); + inline int32 GetEffectsNum() const { return ActiveEffectHandles.Num(); }; + + EGAEffectAggregation GetEffectAggregation(const FGAEffectHandle& HandleIn) const; + + TSet GetHandlesByAttribute(const FGAEffectHandle& HandleIn); + + TSet GetHandlesByClass(const FGAEffectProperty& InProperty, + const FGAEffectContext& InContext); + + void AddEffect(const FGAEffectHandle& HandleIn, bool bInfinite = false); + void AddEffectByClass(const FGAEffectHandle& HandleIn); + + void RemoveFromAttribute(const FGAEffectHandle& HandleIn); + void RemoveEffectProtected(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); + void RemoveInstigatorEffect(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); + void RemoveTargetEffect(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); + void ApplyEffectInstance(class UGAEffectExtension* EffectIn); + //modifiers + void ApplyEffectsFromMods() {}; + void DoesQualify() {}; + bool IsEffectActive(const FGAEffectHandle& HandleIn); + bool ContainsEffectOfClass(const FGAEffectProperty& InProperty); + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + //return FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); + return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); + } + UWorld* GetWorld() const; + +}; +template<> +struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + WithCopy = false + }; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp new file mode 100644 index 0000000..b8c2e84 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp @@ -0,0 +1,790 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" + +#include "Abilities/GAAbilityBase.h" +#include "IAbilityFramework.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" +#include "Animation/AnimInstance.h" +#include "Animation/AnimMontage.h" +#include "GAGlobals.h" +#include "Abilities/GAAbilitySet.h" +#include "Attributes/GAAttributesBase.h" +#include "IGAAbilities.h" +#include "Effects/GAEffectExecution.h" +#include "Effects/GAGameEffect.h" +#include "MessageEndpoint.h" +#include "MessageEndpointBuilder.h" +#include "Effects/GAEffectExtension.h" +#include "Effects/GAEffectCue.h" +#include "AFCueSet.h" +#include "AFCueManager.h" +#include "GAAbilitiesComponent.h" + + + +DEFINE_STAT(STAT_ApplyEffect); +DEFINE_STAT(STAT_ModifyAttribute); + +UGAAbilitiesComponent::UGAAbilitiesComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bWantsInitializeComponent = true; + bIsAnyAbilityActive = false; + bAutoActivate = true; + bAutoRegister = true; + PrimaryComponentTick.bCanEverTick = true; + PrimaryComponentTick.bStartWithTickEnabled = true; + PrimaryComponentTick.bRunOnAnyThread = false; + PrimaryComponentTick.bAllowTickOnDedicatedServer = true; + PrimaryComponentTick.TickGroup = ETickingGroup::TG_DuringPhysics; + +} + +void UGAAbilitiesComponent::BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData) +{ + FAFAttributeChangedDelegate* Delegate = AttributeChanged.Find(InAttribute); + if (Delegate) + { + Delegate->Broadcast(InData); + } +} + +bool UGAAbilitiesComponent::GetShouldTick() const +{ + return true; +} + +void UGAAbilitiesComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn + ,FGAEffectProperty& InProperty) +{ + //OnAttributePreModifed.Broadcast(ModIn, 0); + //Add log. + float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); + FAFAttributeChangedData Data; + FGAEffectContext& Context = HandleIn.GetContextRef(); + Data.Mod = ModIn; + Data.Target = Context.Target; + Data.Location = Context.HitResult.Location; + OnAttributeModifed.Broadcast(Data); + NotifyInstigatorTargetAttributeChanged(Data, Context); +}; +void UGAAbilitiesComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext) +{ + InContext.InstigatorComp->OnTargetAttributeModifed.Broadcast(InData); +} +void UGAAbilitiesComponent::GetAttributeStructTest(FGAAttribute Name) +{ + DefaultAttributes->GetAttribute(Name); +} + +void UGAAbilitiesComponent::OnRep_GameEffectContainer() +{ + float test = 0; +} +void UGAAbilitiesComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + UActorComponent::TickComponent(DeltaTime, TickType, ThisTickFunction); + if (DefaultAttributes) + { + DefaultAttributes->Tick(DeltaTime); + } +} +void UGAAbilitiesComponent::Update() +{ + +} +void UGAAbilitiesComponent::BeginPlay() +{ + Super::BeginPlay(); +} +void UGAAbilitiesComponent::DestroyComponent(bool bPromoteChildren) +{ + Super::DestroyComponent(bPromoteChildren); +} + +FGAEffectHandle UGAAbilitiesComponent::ApplyEffectToSelf(FGAEffect* EffectIn + ,FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; + FAFEventData Data; + for (const FGameplayTag& Tag : AppliedEventTags) + { + if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + { + Event->Broadcast(Data); + } + } + + //OnEffectApplyToSelf.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); + GameEffectContainer.MarkArrayDirty(); + return Handle; + //FGAEffectCueParams CueParams; + //CueParams.HitResult = EffectIn.Context.HitResult; + //OnEffectApplied.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); +} +FGAEffectHandle UGAAbilitiesComponent::ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + //broadcast cues first ? + //Probabaly because effect might not always apply. Or relegate cue + //application to object which was hit ? + + + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + } + else if (mode == ENetMode::NM_DedicatedServer) + { + prefix = FString::Printf(TEXT("DedicatedServer: ")); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), + *prefix, + *GetOwner()->GetName(), + *InContext.Instigator->GetName() + ); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams; + CueParams.Instigator = InContext.Instigator; + CueParams.Causer = InContext.Causer; + CueParams.HitResult = InContext.HitResult; + CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; + if (mode == ENetMode::NM_Standalone + || role >= ENetRole::ROLE_Authority) + { + MulticastApplyEffectCue(CueParams); + } + + } + //execute cue from effect regardless if we have target object or not. + if(InContext.TargetComp.IsValid()) + return InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + + return FGAEffectHandle(); + +// if (EffectIn.IsValid() && EffectIn.Context.TargetComp.IsValid()) +// { + //OnEffectApplyToTarget.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); + // return EffectIn.Context.TargetComp->ApplyEffectToSelf(EffectIn, HandleIn); +// } +} + +void UGAAbilitiesComponent::OnAttributeModified(const FGAEffectMod& InMod, + const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) +{ + +} +void UGAAbilitiesComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty + ,FAFFunctionModifier Modifier, FGAEffectContext InContex) +{ + /* + this patth will give effects chance to do any replicated events, like applying cues. + WE do not make any replication at the ApplyEffect because some effect might want to apply cues + on periods on expiration etc, and all those will go trouch ExecuteEffect path. + */ + const FGameplayTagContainer& RequiredTags = InProperty.GetSpec()->RequiredTags; + if (RequiredTags.Num() > 0) + { + if (!HasAll(RequiredTags)) + { + UE_LOG(GameAttributesEffects, Log, TEXT("UGAAbilitiesComponent:: Effect %s not executed, require tags: %s"), *HandleIn.GetEffectSpec()->GetName(), *RequiredTags.ToString()); + return; + } + } + + //apply execution events: + const FGameplayTagContainer& ExecuteEventTags = InProperty.GetSpec()->ExecuteEventTags; + FAFEventData Data; + for (const FGameplayTag& Tag : ExecuteEventTags) + { + if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + { + Event->Broadcast(Data); + } + } + + OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + UE_LOG(GameAttributesEffects, Log, TEXT("UGAAbilitiesComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); + FGAEffect& Effect = HandleIn.GetEffectRef(); + FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() + , InProperty.GetSpec() + , InContex + , HandleIn); + + //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? + + Effect.OnExecuted(); + MulticastExecuteEffectCue(HandleIn); + InProperty.Execution->ExecuteEffect(HandleIn, Mod, HandleIn.GetContextRef(), InProperty, Modifier); + PostExecuteEffect(); +} +void UGAAbilitiesComponent::PostExecuteEffect() +{ + +} +void UGAAbilitiesComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty) +{ + //call effect internal delegate: + HandleIn.GetEffectPtr()->OnExpired(); + //InternalRemoveEffect(HandleIn); + //OnEffectExpired.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + GameEffectContainer.RemoveEffectByHandle(HandleIn, InProperty); +} +void UGAAbilitiesComponent::RemoveEffect(const FGAEffectProperty& InProperty) +{ + InternalRemoveEffect(InProperty); + //OnEffectRemoved.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); +} +void UGAAbilitiesComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty) +{ + UE_LOG(GameAttributesEffects, Log, TEXT("UGAAbilitiesComponent:: Reset Timers and Remove Effect")); + + //MulticastRemoveEffectCue(HandleIn); + + GameEffectContainer.RemoveEffect(InProperty); +} + +TArray UGAAbilitiesComponent::GetEffectUIData() +{ + TArray dataReturn; + return dataReturn; +} + +int32 UGAAbilitiesComponent::GetEffectUIIndex() +{ + return 1; +} +FGAEffectUIData UGAAbilitiesComponent::GetEffectUIDataByIndex(int32 IndexIn) +{ + FGAEffectUIData data; + return data; +} + +void UGAAbilitiesComponent::MulticastApplyEffectCue_Implementation( FGAEffectCueParams CueParams) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if(mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : MulticastApplyEffectCue Owner: %s, Instigator: %s" ), + *prefix, + *GetOwner()->GetName(), + *CueParams.Instigator->GetName() + ); + + //for (const FGameplayTag& Tag : CueParams.CueTags) + //{ + // TSubclassOf CueClass = TestCueSet->Cues.FindRef(Tag); + // if (!CueClass) + // continue; + + // FActorSpawnParameters SpawnParams; + // FVector Location = CueParams.HitResult.Location; + // FRotator Rotation = FRotator::ZeroRotator; + // AGAEffectCue* actor = nullptr; + // + // actor = GetWorld()->SpawnActor(CueClass, Location, Rotation, SpawnParams); + // actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), + // CueParams.Causer.Get(), CueParams.HitResult); + + //} + + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams); + } +} + +void UGAAbilitiesComponent::MulticastExecuteEffectCue_Implementation(FGAEffectHandle EffectHandle) +{ + // ActiveCues.ExecuteCue(EffectHandle); +} + +void UGAAbilitiesComponent::MulticastRemoveEffectCue_Implementation(FGAEffectHandle EffectHandle) +{ + // ActiveCues.RemoveCue(EffectHandle); +} + +void UGAAbilitiesComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} +void UGAAbilitiesComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) +{ + +} +void UGAAbilitiesComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) +{ + +} +void UGAAbilitiesComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} + +void UGAAbilitiesComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly replicate it to everyone + //to allow prediction for UI. + DOREPLIFETIME(UGAAbilitiesComponent, DefaultAttributes); + DOREPLIFETIME(UGAAbilitiesComponent, ModifiedAttribute); + DOREPLIFETIME(UGAAbilitiesComponent, GameEffectContainer); + + DOREPLIFETIME(UGAAbilitiesComponent, ActiveCues); + + DOREPLIFETIME_CONDITION(UGAAbilitiesComponent, AbilityContainer, COND_OwnerOnly); + DOREPLIFETIME_CONDITION(UGAAbilitiesComponent, RepMontage, COND_SkipOwner); + //DOREPLIFETIME(UGAAbilitiesComponent, RepMontage); +} +void UGAAbilitiesComponent::OnRep_ActiveEffects() +{ + +} +void UGAAbilitiesComponent::OnRep_ActiveCues() +{ + +} + +void UGAAbilitiesComponent::OnRep_AttributeChanged() +{ + //for (FGAModifiedAttribute& attr : ModifiedAttribute.Mods) + //{ + // attr.Causer->OnAttributeModifed.Broadcast(attr); + //} +} +bool UGAAbilitiesComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) +{ + bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); + + if (DefaultAttributes) + { + WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); + } + for (const FGASAbilityItem& Ability : AbilityContainer.AbilitiesItems) + { + //if (Set.InputOverride) + // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); + + if (Ability.Ability) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); + } + return WroteSomething; +} +void UGAAbilitiesComponent::GetSubobjectsWithStableNamesForNetworking(TArray& Objs) +{ + if (DefaultAttributes && DefaultAttributes->IsNameStableForNetworking()) + { + Objs.Add(const_cast(DefaultAttributes)); + } +} + + +FAFEventDelegate& UGAAbilitiesComponent::GetTagEvent(FGameplayTag TagIn) +{ + FAFEventDelegate& Delegate = EffectEvents.FindChecked(TagIn); + return Delegate; +} +void UGAAbilitiesComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + FAFEventDelegate* Delegate = EffectEvents.Find(TagIn); + if (Delegate) + { + if (Delegate->IsBound()) + { + Delegate->Broadcast(InEventData); + } + } +} +void UGAAbilitiesComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const +{ + TagContainer = AppliedTags.AllTags; +} +bool UGAAbilitiesComponent::HasMatchingGameplayTag(FGameplayTag TagToCheck) const +{ + return AppliedTags.HasTag(TagToCheck); +} + +bool UGAAbilitiesComponent::HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const +{ + return AppliedTags.HasAll(TagContainer); +} + +bool UGAAbilitiesComponent::HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const +{ + return AppliedTags.HasAny(TagContainer); +} + +bool UGAAbilitiesComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) +{ + bool bDenyApplication = false; + if (InTags.Num() > 0) + { + bDenyApplication = HasAll(InTags); + } + return bDenyApplication; +} + +bool UGAAbilitiesComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) +{ + bool bAllowApplication = true; + if (InTags.Num() > 0) + { + bAllowApplication = HasAll(InTags); + } + return bAllowApplication; +} +void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer) +{ + +} +void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) +{ + if (InArraySerializer.AbilitiesComp.IsValid()) + { + //should be safe, since we only modify the non replicated part of struct. + FGASAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); + //if (InArraySerializer.AbilitiesComp->PawnInterface) + //{ + // Ability->POwner = InArraySerializer.AbilitiesComp->PawnInterface->GetGamePawn(); + // Ability->PCOwner = InArraySerializer.AbilitiesComp->PawnInterface->GetGamePlayerController(); + // Ability->OwnerCamera = InArraySerializer.AbilitiesComp->PawnInterface->GetPawnCamera(); + // //ability->AIOwner = PawnInterface->GetGameController(); + //} + Ability->InitAbility(); + + InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); + } +} +void FGASAbilityItem::PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer) +{ + +} + +UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn, FGameplayTag ActionName) +{ + //if (AbilityIn && AbilitiesComp.IsValid()) + //{ + // UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); + // ability->AbilityComponent = AbilitiesComp.Get(); + // if (AbilitiesComp->PawnInterface) + // { + // ability->POwner = AbilitiesComp->PawnInterface->GetGamePawn(); + // ability->PCOwner = AbilitiesComp->PawnInterface->GetGamePlayerController(); + // ability->OwnerCamera = AbilitiesComp->PawnInterface->GetPawnCamera(); + // //ability->AIOwner = PawnInterface->GetGameController(); + // } + // ability->InitAbility(); + // FGameplayTag Tag = ability->AbilityTag; + + // AbilitiesInputs.Add(Tag, ability); + // FGASAbilityItem AbilityItem; + // AbilityItem.Ability = ability; + // AbilitiesItems.Add(AbilityItem); + ///* if (ActionName.IsValid()) + // { + // UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); + // AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); + // }*/ + // return ability; + //} + return nullptr; +} +UGAAbilityBase* FGASAbilityContainer::GetAbility(FGameplayTag TagIn) +{ + return AbilitiesInputs.FindRef(TagIn); +} +void FGASAbilityContainer::HandleInputPressed(FGameplayTag TagIn, FGameplayTag ActionName) +{ + UGAAbilityBase* ability = AbilitiesInputs.FindRef(TagIn); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + ability->OnNativeInputPressed(ActionName); + } +} +void FGASAbilityContainer::HandleInputReleased(FGameplayTag TagIn, FGameplayTag ActionName) +{ + UGAAbilityBase* ability = AbilitiesInputs.FindRef(TagIn); + if (ability) + { + ability->OnNativeInputReleased(ActionName); + } +} + +void FGASAbilityContainer::TriggerAbylityByTag(FGameplayTag InTag) +{ + UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + ability->OnNativeInputPressed(FGameplayTag()); + } +} + +void UGAAbilitiesComponent::InitializeComponent() +{ + Super::InitializeComponent(); + //PawnInterface = Cast(GetOwner()); + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + AbilityContainer.AbilitiesComp = this; + + if (DefaultAttributes) + { + DefaultAttributes->InitializeAttributes(this); + DefaultAttributes->InitializeAttributesFromTable(); + } + GameEffectContainer.OwningComponent = this; + ActiveCues.OwningComp = this; + //ActiveCues.OwningComponent = this; + AppliedTags.AddTagContainer(DefaultTags); + //TestRunnable = new FAsyncUObjectRunnable(this); + //TEstAsyncUObject = NewObject(this, UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); + //TEstAsyncUObject->AddToRoot(); + //RouterThread = FRunnableThread::Create(TEstAsyncUObject, TEXT("AsyncUObject.Test"), 128 * 1024, TPri_Normal, FPlatformAffinity::GetPoolThreadMask()); + InitializeInstancedAbilities(); +} +void UGAAbilitiesComponent::UninitializeComponent() +{ + Super::UninitializeComponent(); + //GameEffectContainer +} +void UGAAbilitiesComponent::BP_BindAbilityToAction(FGameplayTag ActionName, FGameplayTag AbilityTag) +{ + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + BindAbilityToAction(InputComponent, ActionName, AbilityTag); +} +void UGAAbilitiesComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName, FGameplayTag AbilityTag) +{ + if (!InputComponent) + return; + { + FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UGAAbilitiesComponent::NativeInputPressed, AbilityTag, ActionName); + InputComponent->AddActionBinding(AB); + } + + // Released event + { + FInputActionBinding AB(ActionName.GetTagName(), IE_Released); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UGAAbilitiesComponent::NativeInputReleased, AbilityTag, ActionName); + InputComponent->AddActionBinding(AB); + } +} +void UGAAbilitiesComponent::BP_InputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + NativeInputPressed(AbilityTag, ActionName); +} +void UGAAbilitiesComponent::NativeInputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeInputPressed(AbilityTag, ActionName); + UE_LOG(AbilityFramework, Log, TEXT("Client UGAAbilitiesComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); + //naive needs better qynchornization to what going on where. + if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + { + if (Ability->AbilityComponent == this) + { + AbilityContainer.HandleInputPressed(AbilityTag, ActionName); + } + } + } + else + { + UE_LOG(AbilityFramework, Log, TEXT("Server UGAAbilitiesComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); + if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + { + if (Ability->AbilityComponent == this) + { + AbilityContainer.HandleInputPressed(AbilityTag, ActionName); + } + } + } +} + +void UGAAbilitiesComponent::ServerNativeInputPressed_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + NativeInputPressed(AbilityTag, FGameplayTag()); +} +bool UGAAbilitiesComponent::ServerNativeInputPressed_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + return true; +} + +void UGAAbilitiesComponent::BP_InputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + NativeInputReleased(AbilityTag, ActionName); +} + +void UGAAbilitiesComponent::NativeInputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + { + if (Ability->AbilityComponent == this) + { + AbilityContainer.HandleInputReleased(AbilityTag, ActionName); + } + } + ServerNativeInputReleased(AbilityTag, ActionName); + } + else + { + UE_LOG(AbilityFramework, Log, TEXT("UGAAbilitiesComponent::NativeInputReleased: %s"), *AbilityTag.GetTagName().ToString()); + + AbilityContainer.HandleInputReleased(AbilityTag, ActionName); + } +} + +void UGAAbilitiesComponent::ServerNativeInputReleased_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + NativeInputReleased(AbilityTag, FGameplayTag()); +} +bool UGAAbilitiesComponent::ServerNativeInputReleased_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName) +{ + return true; +} + +void UGAAbilitiesComponent::BP_AddAbility(TSubclassOf AbilityClass, + FGameplayTag ActionName, bool bAutoBind) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + return; + } + else + { + NativeAddAbility(AbilityClass, ActionName, bAutoBind); + } + +} + +void UGAAbilitiesComponent::NativeAddAbility(TSubclassOf AbilityClass, + FGameplayTag ActionName, bool bAutoBind) +{ + InstanceAbility(AbilityClass, ActionName); + if (bAutoBind) + ClientOnAbilityAdded(AbilityClass->GetDefaultObject()->AbilityTag, ActionName); +} + +void UGAAbilitiesComponent::ClientOnAbilityAdded_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionTag) +{ + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + BindAbilityToAction(InputComponent, ActionTag, AbilityTag); +} +void UGAAbilitiesComponent::BP_RemoveAbility(FGameplayTag TagIn) +{ + +} +UGAAbilityBase* UGAAbilitiesComponent::BP_GetAbilityByTag(FGameplayTag TagIn) +{ + return AbilityContainer.GetAbility(TagIn); +} +UGAAbilityBase* UGAAbilitiesComponent::InstanceAbility(TSubclassOf AbilityClass, FGameplayTag ActionName) +{ + if (AbilityClass) + { + UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, ActionName); + AbilityContainer.MarkArrayDirty(); + return ability; + } + return nullptr; +} + +void UGAAbilitiesComponent::NativeAddAbilitiesFromSet(TSubclassOf AbilitySet) +{ + //do not let add abilities on non authority. + if (GetOwnerRole() < ENetRole::ROLE_Authority) + return; + + UGAAbilitySet* Set = AbilitySet.GetDefaultObject(); + int32 Index = 0; + for (const FGASAbilitySetItem& Item : Set->AbilitySet.Abilities) + { + InstanceAbility(Item.AbilityClass, Item.Binding); + Index++; + } +} + +void UGAAbilitiesComponent::BP_AddAbilitiesFromSet(TSubclassOf AbilitySet) +{ + NativeAddAbilitiesFromSet(AbilitySet); +} + +void UGAAbilitiesComponent::OnRep_InstancedAbilities() +{ +} + +void UGAAbilitiesComponent::InitializeInstancedAbilities() +{ +} + +void UGAAbilitiesComponent::OnRep_PlayMontage() +{ + ACharacter* MyChar = Cast(GetOwner()); + if (MyChar) + { + UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); + AnimInst->Montage_Play(RepMontage.CurrentMontage); + if (RepMontage.SectionName != NAME_None) + { + AnimInst->Montage_JumpToSection(RepMontage.SectionName, RepMontage.CurrentMontage); + } + UE_LOG(AbilityFramework, Log, TEXT("OnRep_PlayMontage MontageName: %s SectionNAme: %s ForceRep: %s"), *RepMontage.CurrentMontage->GetName(), *RepMontage.SectionName.ToString(), *FString::FormatAsNumber(RepMontage.ForceRep)); + } +} + +void UGAAbilitiesComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) +{ + //if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + //Probabaly want to do something different here for client non authority montage plays. + //return; + } + ACharacter* MyChar = Cast(GetOwner()); + if (MyChar) + { + UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); + AnimInst->Montage_Play(MontageIn, Speed); + if (SectionName != NAME_None) + { + AnimInst->Montage_JumpToSection(SectionName, MontageIn); + } + + UE_LOG(AbilityFramework, Log, TEXT("PlayMontage MontageName: %s SectionNAme: %s Where: %s"), *MontageIn->GetName(), *SectionName.ToString(), (GetOwnerRole() < ENetRole::ROLE_Authority ? TEXT("Client") : TEXT("Server"))); + RepMontage.SectionName = SectionName; + RepMontage.CurrentMontage = MontageIn; + RepMontage.ForceRep++; + } +} +void UGAAbilitiesComponent::MulticastPlayMontage_Implementation(UAnimMontage* MontageIn, FName SectionName, float Speed = 1) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h new file mode 100644 index 0000000..ebe5e9e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h @@ -0,0 +1,595 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "GameplayTaskOwnerInterface.h" +#include "GameplayTaskTypes.h" +#include "GameplayTask.h" +#include "GameplayTasksComponent.h" +#include "GameplayTags.h" +#include "GAGlobals.h" +#include "Attributes/GAAttributeBase.h" +#include "Attributes/GAAttributesBase.h" +#include "Effects/GAEffectCueGlobals.h" + +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Messaging.h" +#include "GameplayTagAssetInterface.h" +#include "IGAAbilities.h" + +//tests +#include "Async/AsyncUObjectImpl.h" +#include "Async/AsyncUObject.h" +#include "HAL/RunnableThread.h" + +#include "GAAbilitiesComponent.generated.h" + +DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGAGenericEffectDelegate, const FGAEffectHandle&, Handle, const FGameplayTagContainer&, Tags); + +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate , FAFEventData); +DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); + +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectRepInfoDelegate, FAFEffectRepInfo*); + +USTRUCT() +struct FGAModifiedAttributeData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + TArray Mods; + UPROPERTY() + int32 ForceUpdate; + + FGAModifiedAttributeData() + : ForceUpdate(0) + {} +}; + +USTRUCT(BlueprintType) +struct FGAEffectUIData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "UI") + float RemainingTime; + + FGAEffectUIData() + : RemainingTime(0) + {}; +}; +struct FGAContextSetup +{ +public: + UGAAttributesBase* IntigatorAttributes; + UGAAttributesBase* TargetAttributes; + UGAAbilitiesComponent* InstigatorComp; + UGAAbilitiesComponent* TargetComp; + + FGAContextSetup() + {}; + FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, + UGAAbilitiesComponent* InstigatorCompIn, UGAAbilitiesComponent* TargetCompIn) + : IntigatorAttributes(IntigatorAttributesIn), + TargetAttributes(TargetAttributesIn), + InstigatorComp(InstigatorCompIn), + TargetComp(TargetCompIn) + {}; +}; +DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); +DECLARE_DELEGATE_ThreeParams(FAFMontageGenericDelegate, const FAFAbilityNotifyData&, const FGameplayTag&, const FName&); +/* TODO:: Implement fast serialization for structs. */ +/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ +/**/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASMontageRepData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + UAnimMontage* CurrentMontage; + + UPROPERTY() + FName SectionName; + + UPROPERTY() + uint8 ForceRep; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem +{ + GENERATED_BODY() + +public: + UPROPERTY() + UGAAbilityBase* Ability; + + void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); + void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); + void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); +}; +USTRUCT() +struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + + UPROPERTY() + TArray AbilitiesItems; + + TWeakObjectPtr AbilitiesComp; + + TMap AbilitiesInputs; + + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, FGameplayTag ActionName); + UGAAbilityBase* GetAbility(FGameplayTag TagIn); + + void HandleInputPressed(FGameplayTag TagIn, FGameplayTag ActionName); + void HandleInputReleased(FGameplayTag TagIn, FGameplayTag ActionName); + + void TriggerAbylityByTag(FGameplayTag InTag); + + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + +UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) +class ABILITYFRAMEWORK_API UGAAbilitiesComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface +{ + GENERATED_BODY() + /* Attributes handling */ +public: + friend struct FAFMessageTick; + //Only for base testing and prototyping cue application. + //will be removed when Cue Manager will be more functional. + UPROPERTY(EditAnywhere) + class UAFCueSet* TestCueSet; + UPROPERTY(EditAnywhere, Category = "Test") + FGameplayTag TagTest; + /* + Set attribute which will be considered for indicating whether or not actor is dead. + */ + UPROPERTY(EditAnywhere, Category = "Config") + FGAAttribute DeathAttribute; + + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DefaultTags; + + UPROPERTY() + FGACountedTagContainer AppliedTags; + + UPROPERTY() + FGACountedTagContainer ImmunityTags; + + UFUNCTION() + void OnRep_ActiveEffects(); + + UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) + FGameCueContainer ActiveCues; + UFUNCTION() + void OnRep_ActiveCues(); + /* + Could make it array. But realistically. How many times do you really need more, than one + attribute set for actor ? + + Of course array of attributes would allow to compose attributes from small discreete + attribute sets. On the other hand similiar funcionality can be achieved by using + inheritance. + + And I think that using inheritance in this case will be easier. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) + class UGAAttributesBase* DefaultAttributes; + + //probabaly replace FGameplayTag with FObjectKey + TMap AdditionalAttributes; + + UPROPERTY(ReplicatedUsing = OnRep_AttributeChanged) + FGAModifiedAttributeData ModifiedAttribute; + UFUNCTION() + void OnRep_AttributeChanged(); + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnAttributeModifed; + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnTargetAttributeModifed; + /* Effect/Attribute System Delegates */ + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectApplied; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectApplyToTarget; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectApplyToSelf; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectExecuted; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectExpired; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectRemoved; + + /* NEW EFFECT SYSTEM */ + UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) + FGAEffectContainer GameEffectContainer; + + FAFEffectRepInfoDelegate OnEffectRepInfoApplied; + FAFEffectRepInfoDelegate OnEffectRepInfoRemoved; + /* + Default effects applied when character spawns. + Can contain things like attribute regen, racial bonuses + racial debuffs etc. + */ + UPROPERTY(EditAnywhere, Category = "Effects") + TArray> DefaultEffects; + + TMap EffectEvents; + TMap AttributeChanged; + + void BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData); + + virtual bool GetShouldTick() const override; + + UFUNCTION() + void OnRep_GameEffectContainer(); + + template + T* GetAttributes() + { + return CastChecked(DefaultAttributes); + } + + template + T* GetAttributeSet(FGameplayTag InOwner) + { + UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); + return Cast(AttributeSet); + } + void AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) + { + bool bExists = AdditionalAttributes.Contains(InOwner); + if (bExists) + { + return; + } + AdditionalAttributes.Add(InOwner, InAttributes); + } + UFUNCTION(BlueprintCallable, Category = "Test") + void GetAttributeStructTest(FGAAttribute Name); + + virtual void BeginPlay() override; + virtual void DestroyComponent(bool bPromoteChildren = false) override; + + virtual void InitializeComponent() override; + + virtual void UninitializeComponent() override; + + +public: + ///////////////////////////////////////////////// + //////////// EFFECTS HANDLING + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + void Update(); + FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + void ApplyEffectToTarget(TSubclassOf InSpecClass, + const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); + + + /* Have to to copy handle around, because timer delegates do not support references. */ + void ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty + ,FAFFunctionModifier Modifier, FGAEffectContext InContext); + virtual void PostExecuteEffect(); + /* ExpireEffect is used to remove existing effect naturally when their time expires. */ + void ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty); + /* RemoveEffect is used to remove effect by force. */ + void RemoveEffect(const FGAEffectProperty& InProperty); + void InternalRemoveEffect(const FGAEffectProperty& InProperty); + + + /* Never call it directly. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes|UI") + TArray GetEffectUIData(); + + /* + Get Last Index of effect for UI display. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes|UI") + int32 GetEffectUIIndex(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes|UI") + FGAEffectUIData GetEffectUIDataByIndex(int32 IndexIn); + /* + Need prediction for spawning effects on client, + and then on updateing them predicitvely on all other clients. + */ + /* + + */ + UFUNCTION(NetMulticast, Unreliable) + void MulticastApplyEffectCue(FGAEffectCueParams CueParams); + virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExecuteEffectCue(FGAEffectHandle EffectHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastRemoveEffectCue(FGAEffectHandle EffectHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + + //////////// EFFECTS HANDLING + ///////////////////////////////////////////////// + +public: + ///////////////////////////////////////////////// + //////////// ATTRIBUTES HANDLING + + /* + Two functions, They will allow to apply any static numerical mods from player who + initiated attribute change, and from player who will be affected by change. + + Mods will be appiled by small objects, and changed against tags. + For example there might be physical armor mod, which will apply changes only + to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. + */ + + inline float GetFinalAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetFinalAttributeValue(Name); + } + inline float GetCurrentAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetCurrentAttributeValue(Name); + } + //////////// ATTRIBUTES HANDLING + ///////////////////////////////////////////////// + /* + Attribute replication. + */ + void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); + + FAFEventDelegate& GetTagEvent(FGameplayTag TagIn); + void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + //Helper functions: +public: + /* + IGameplayTagAssetInterface Start + */ + /** + * Get any owned gameplay tags on the asset + * + * @param OutTags [OUT] Set of tags on the asset + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; + + /** + * Check if the asset has a gameplay tag that matches against the specified tag (expands to include parents of asset tags) + * + * @param TagToCheck Tag to check for a match + * + * @return True if the asset has a gameplay tag that matches, false if not + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual bool HasMatchingGameplayTag(FGameplayTag TagToCheck) const override; + + /** + * Check if the asset has gameplay tags that matches against all of the specified tags (expands to include parents of asset tags) + * + * @param TagContainer Tag container to check for a match + * + * @return True if the asset has matches all of the gameplay tags, will be true if container is empty + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual bool HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; + + /** + * Check if the asset has gameplay tags that matches against any of the specified tags (expands to include parents of asset tags) + * + * @param TagContainer Tag container to check for a match + * + * @return True if the asset has matches any of the gameplay tags, will be false if container is empty + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual bool HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; + /* + IGameplayTagAssetInterface End + */ + + bool DenyEffectApplication(const FGameplayTagContainer& InTags); + bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); + /* + Effect Container Wrapp Start + */ + /* + */ + inline bool IsEffectActive(const FGAEffectHandle& HandleIn) { return GameEffectContainer.IsEffectActive(HandleIn); }; + /* + Effect Container Wrapp End + */ + + /* Counted Tag Container Wrapper Start */ + inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; + inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; + inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; + inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; + inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } + inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; + inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; + inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; + inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; + inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; + inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } + /* Counted Tag Container Wrapper Start */ + + /* Active Effects Wrapper Start */ + inline int32 GetEffectsNum() const { return GameEffectContainer.GetEffectsNum(); }; + /* Active Effects Wrapper End */ + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; + + void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext); + FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; + float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + +private: + class IIGAAbilities* AttributeInterface; + +public: + UGAAbilitiesComponent(const FObjectInitializer& ObjectInitializer); + + UFUNCTION() + void OnRep_InstancedAbilities(); + UPROPERTY(Replicated) + FGASAbilityContainer AbilityContainer; + UPROPERTY() + TArray AbilitiesRefs; + + UPROPERTY() + APlayerController* PCOwner; + + /* Ability which is currently being executed. */ + UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") + class UGAAbilityBase* ExecutingAbility; + + TMap AbilitiesToConfirm; + + /* + True if player is currently casting/channeling/activating(?) + any ability. + */ + bool bIsAnyAbilityActive; + + FAFMontageGenericDelegate OnAbilityNotifyBegin; + FAFMontageGenericDelegate OnAbilityNotifyTick; + FAFMontageGenericDelegate OnAbilityNotifyEnd; + + //class IIGIPawn* PawnInterface; +private: + + + UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) + FGASMontageRepData RepMontage; + UFUNCTION() + void OnRep_PlayMontage(); + +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + UFUNCTION(NetMulticast, Unreliable) + void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); +public: + inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) + { + return nullptr; + } + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") + void BP_BindAbilityToAction(FGameplayTag ActionName, FGameplayTag AbilityTag); + void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName, FGameplayTag AbilityTag); + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") + void BP_InputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName); + + void NativeInputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName); + virtual void ServerNativeInputPressed_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName); + virtual bool ServerNativeInputPressed_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName); + + + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") + void BP_InputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName); + + void NativeInputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName); + virtual void ServerNativeInputReleased_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName); + virtual bool ServerNativeInputReleased_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability"), Category = "AbilityFramework|Abilities") + void BP_AddAbility(TSubclassOf AbilityClass, + FGameplayTag ActionName, bool bAutoBind = true); + + void NativeAddAbility(TSubclassOf AbilityClass, + FGameplayTag ActionName, bool bAutoBind = true); + + /* Callback from server, after ability has been added. */ + UFUNCTION(Client, Reliable) + void ClientOnAbilityAdded(FGameplayTag AbilityTag, FGameplayTag ActionTag); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") + void BP_RemoveAbility(FGameplayTag TagIn); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") + UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); + /* + Should be called on server. + Adds new ability to ActiveAbilities; + */ + void NativeAddAbilitiesFromSet(TSubclassOf AbilitySet); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Abilities From Set"), Category = "AbilityFramework|Abilities") + void BP_AddAbilitiesFromSet(TSubclassOf AbilitySet); + + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; + void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; +protected: + void InitializeInstancedAbilities(); + UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, FGameplayTag ActionName = FGameplayTag()); + /* + Messagin implementation for applying effects from multiple threads (in case + at some beatyfull day UObject will be able to exist on any thread), and from single thread. + + Implementation is based on FMessageEndpoint. + */ + +}; + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp new file mode 100644 index 0000000..632d0a5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -0,0 +1,312 @@ +#pragma once +#include "AbilityFramework.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "GameplayTagContainer.h" +#include "GAAbilitiesComponent.h" +#include "Attributes/GAAttributeBase.h" +#include "Effects/GAEffectExecution.h" +#include "IGAAbilities.h" +#include "Effects/GACustomCalculation.h" +FGAEffectContext::FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, + const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, + TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, + TWeakObjectPtr TargetCompIn, + TWeakObjectPtr InstigatorCompIn) + : TargetAttributes(TargetAttributesIn), + InstigatorAttributes(InstigatorAttributesIn), + TargetHitLocation(TargetHitLocationIn), + Target(TargetIn), + Causer(CauserIn), + Instigator(InstigatorIn), + TargetComp(TargetCompIn), + InstigatorComp(InstigatorCompIn) +{ + TargetInterface = Cast(TargetIn.Get()); + InstigatorInterface = Cast(Instigator.Get()); + IIGAAbilities* CauserInterface = Cast(Causer.Get()); +} +FGAEffectHandle::FGAEffectHandle(uint32 HandleIn, FGAEffect* EffectIn) + : Handle(HandleIn), + EffectPtr(EffectIn) +{ +} + +FGAEffectHandle::~FGAEffectHandle() +{ + Reset(); +} +FGAEffectContext& FGAEffectHandle::GetContextRef() { return EffectPtr->Context; } +FGAEffectContext& FGAEffectHandle::GetContextRef() const { return EffectPtr->Context; } + +UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() { return EffectPtr->GameEffect; } +UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() const { return EffectPtr->GameEffect; } + +uint32 FGAEffectHandle::GetHandle() const { return Handle; } + +FGAEffect FGAEffectHandle::GetEffect() { return *EffectPtr.Get(); } +FGAEffect FGAEffectHandle::GetEffect() const { return *EffectPtr.Get(); } + +FGAEffect& FGAEffectHandle::GetEffectRef() { return EffectPtr.ToSharedRef().Get(); } +FGAEffect& FGAEffectHandle::GetEffectRef() const { return EffectPtr.ToSharedRef().Get(); }; + +TSharedPtr FGAEffectHandle::GetEffectPtr() { return EffectPtr; }; +TSharedPtr FGAEffectHandle::GetEffectPtr() const { return EffectPtr; }; + +void FGAEffectHandle::SetContext(const FGAEffectContext& ContextIn) { EffectPtr->SetContext(ContextIn); } +void FGAEffectHandle::SetContext(const FGAEffectContext& ContextIn) const { EffectPtr->SetContext(ContextIn); } + +FGAEffectContext& FGAEffectHandle::GetContext() { return EffectPtr->Context; } +FGAEffectContext& FGAEffectHandle::GetContext() const { return EffectPtr->Context; } + +/* Executes effect trough provided execution class. */ + +FGAEffectHandle FGAEffectHandle::GenerateHandle(FGAEffect* EffectIn) +{ + static uint32 Handle; + Handle++; + return FGAEffectHandle(Handle, EffectIn); +} +void FGAEffectHandle::AppendOwnedTags(const FGameplayTagContainer& TagsIn) +{ + GetEffectPtr()->OwnedTags.AppendTags(TagsIn); +} +void FGAEffectHandle::AppendOwnedTags(const FGameplayTagContainer& TagsIn) const +{ + GetEffectPtr()->OwnedTags.AppendTags(TagsIn); +} + +bool FGAEffectHandle::HasAllTags(const FGameplayTagContainer& TagsIn) const +{ + return EffectPtr->OwnedTags.HasAll(TagsIn); +} +bool FGAEffectHandle::HasAllTagsExact(const FGameplayTagContainer& TagsIn) const +{ + return EffectPtr->OwnedTags.HasAllExact(TagsIn); +} +bool FGAEffectHandle::HasAllAttributeTags(const FGAEffectHandle& HandleIn) const +{ + return GetEffectSpec()->AttributeTags.HasAll(HandleIn.GetEffectSpec()->AttributeTags); +} +bool FGAEffectHandle::HasAllAttributeTagsExact(const FGAEffectHandle& HandleIn) const +{ + return GetEffectSpec()->AttributeTags.HasAllExact(HandleIn.GetEffectSpec()->AttributeTags); +} +FGameplayTagContainer& FGAEffectHandle::GetOwnedTags() const +{ + return EffectPtr->OwnedTags; +} +FGAEffectMod FGAEffectHandle::GetAttributeModifier() const +{ + return FGAEffectMod();// EffectPtr->GetAttributeModifier(); +} + +FGAAttribute FGAEffectHandle::GetAttribute() const +{ + return GetEffectSpec()->AtributeModifier.Attribute; +} +EGAAttributeMod FGAEffectHandle::GetAttributeMod() const +{ + return GetEffectSpec()->AtributeModifier.AttributeMod; +} + +bool FGAEffectHandle::IsValid() const +{ + return (Handle != INDEX_NONE) && EffectPtr.IsValid();// && EffectPtr->Context.IsValid(); +} +//void FGAEffectHandle::operator=(const FGAEffectHandle& Other) +//{ +// Handle = Other.Handle; +// //EffectPtr = Other.EffectPtr; +//} +void FGAEffectHandle::Reset() +{ + Handle = 0; + EffectPtr.Reset(); +} +FGAHashedGameplayTagContainer::FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn) + : Tags(TagsIn) +{ + GenerateFNameKey(); +} +void FGAHashedGameplayTagContainer::GenerateFNameKey() +{ + FString RetString; + for (const FGameplayTag& tag : Tags) + { + RetString += TEXT("."); + RetString += tag.ToString(); + RetString += TEXT("."); + } + Key = *RetString; +} + +void FGAEffectContext::Reset() +{ + Target.Reset(); + Causer.Reset(); + Instigator.Reset(); + TargetComp.Reset(); + InstigatorComp.Reset(); +} +class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() +{ + if (TargetAttributes.IsValid()) + return TargetAttributes.Get(); + else + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() +{ + if(InstigatorComp.IsValid()) + return InstigatorComp->DefaultAttributes; + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() +{ + IIGAAbilities* AttrInt = Cast(Causer.Get()); + if (AttrInt) + { + return AttrInt->GetAttributes(); + } + return nullptr; +} + +class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() const +{ + if (TargetAttributes.IsValid()) + return TargetAttributes.Get(); + else + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() const +{ + if (InstigatorComp.IsValid()) + return InstigatorComp->DefaultAttributes; + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() const +{ + IIGAAbilities* AttrInt = Cast(Causer.Get()); + if (AttrInt) + { + return AttrInt->GetAttributes(); + } + return nullptr; +} + +FGAEffectContext::~FGAEffectContext() +{ + Target.Reset(); + Causer.Reset(); + Instigator.Reset(); + TargetComp.Reset(); + InstigatorComp.Reset(); +} + +void FGACountedTagContainer::AddTag(const FGameplayTag& TagIn) +{ + int32& count = CountedTags.FindOrAdd(TagIn); + //if (count) + //{ + // *count += 1; + // return; + //} + count++; + //CountedTags.Add(TagIn, 1); + AllTags.AddTag(TagIn); +} +void FGACountedTagContainer::AddTagContainer(const FGameplayTagContainer& TagsIn) +{ + for (auto TagIt = TagsIn.CreateConstIterator(); TagIt; ++TagIt) + { + int32* count = CountedTags.Find(*TagIt); + if (count) + { + *count += 1; + } + else + { + CountedTags.Add(*TagIt, 1); + AllTags.AddTag(*TagIt); + } + } +} +void FGACountedTagContainer::RemoveTag(const FGameplayTag& TagIn) +{ + int32* count = CountedTags.Find(TagIn); + if (count) + { + *count -= 1; + if (*count <= 0) + { + CountedTags.Remove(TagIn); + AllTags.RemoveTag(TagIn); + } + } +} +void FGACountedTagContainer::RemoveTagContainer(const FGameplayTagContainer& TagsIn) +{ + for (auto TagIt = TagsIn.CreateConstIterator(); TagIt; ++TagIt) + { + int32* count = CountedTags.Find(*TagIt); + if (count) + { + *count -= 1; + } + if (*count <= 0) + { + CountedTags.Remove(*TagIt); + AllTags.RemoveTag(*TagIt); + } + } +} +bool FGACountedTagContainer::HasTag(const FGameplayTag& TagIn) +{ + return AllTags.HasTag(TagIn); +} +bool FGACountedTagContainer::HasTagExact(const FGameplayTag TagIn) +{ + return AllTags.HasTagExact(TagIn); +} +bool FGACountedTagContainer::HasAny(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAny(TagsIn); +} +bool FGACountedTagContainer::HasAnyExact(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAnyExact(TagsIn); +} +bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAll(TagsIn); +} +bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAllExact(TagsIn); +} + +bool FGACountedTagContainer::HasTag(const FGameplayTag& TagIn) const +{ + return AllTags.HasTag(TagIn); +} +bool FGACountedTagContainer::HasTagExact(const FGameplayTag TagIn) const +{ + return AllTags.HasTagExact(TagIn); +} +bool FGACountedTagContainer::HasAny(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAny(TagsIn); +} +bool FGACountedTagContainer::HasAnyExact(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAnyExact(TagsIn); +} +bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAll(TagsIn); +} +bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAllExact(TagsIn); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h new file mode 100644 index 0000000..1c3dcd9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -0,0 +1,834 @@ +#pragma once +#include "AbilityFramework.h" +#include "GameplayTagsModule.h" +#include "GameplayTagContainer.h" +#include "Messaging.h" +#include "GAGlobalTypes.generated.h" + +/* + Explanation of tags from Fred K, on forums: + https://forums.unrealengine.com/showthread.php?57988-GameplayAbilities-questions&p=220315#post220315 + Here are some examples to illustrate the possible results. Let's assume that our + tag container contains exactly one tag, "A.B.C". + + HasTag("A.B.C", Explicit, Explicit) returns true. + HasTag("A.B", Explicit, Explicit) returns false. + HasTag("A.B.C.D", Explicit, Explicit) returns false. + HasTag("E.B.C", Explicit, Explicit) returns false. + HasTag("A.B.C", IncludeParentTags, IncludeParentTags) returns true. + HasTag("A.B", IncludeParentTags, IncludeParentTags) returns true. + HasTag("A.B.C.D", IncludeParentTags, IncludeParentTags) returns true. + HasTag("E.B.C", IncludeParentTags, IncludeParentTags) returns false. + HasTag("A.B.C", IncludeParentTags, Explicit) returns true. + HasTag("A.B", IncludeParentTags, Explicit) returns true. + HasTag("A.B.C.D", IncludeParentTags, Explicit) returns false. + HasTag("E.B.C", IncludeParentTags, Explicit) returns false. + HasTag("A.B.C", Explicit, IncludeParentTags) returns true. + HasTag("A.B", Explicit, IncludeParentTags) returns false. + HasTag("A.B.C.D", Explicit, IncludeParentTags) returns true. + HasTag("E.B.C", Explicit, IncludeParentTags) returns false. +*/ + +/* + I seriosuly need to clean this shit up. +*/ +/* + TODO:: I probabaly need to change it to normal enum. + So I can use it as array indexes. +*/ +UENUM() +enum class EGAAttributeMod : int32 +{ + Add = 0, //Value = Value + X + Subtract = 1, //Value = Value - X + Multiply = 2, //Value = Value * X + Divide = 3,//Value = Value * X - ok its's not really divide. + Set = 4, //Value = X + PercentageAdd = 5, + PercentageSubtract = 6, + Invalid = 7 +}; + +UENUM() +enum class EGAAttributeSource : uint8 +{ + Instigator, + Target, + Causer, + Ability +}; + +UENUM() +enum class EGAModifierTarget : uint8 +{ + Instigator, + Target +}; + +UENUM() +enum class EGAAttributeValue : uint8 +{ + Base, + Current, + Final, + Bonus +}; + +UENUM() +enum class EGAEffectType : uint8 +{ + Instant = 0, + Duration = 1, + Infinite = 2, +}; + +/* How applied effects should stack on Attribute */ +UENUM() +enum class EGAAttributeStacking : uint8 +{ + Add, + Intensity, + Override, + Stronger +}; +UENUM() +enum class EAFAttributeStacking : uint8 +{ + Add, + Override, + StrongerOverride +}; +/* + + StrongetOverride - Does not check for effect type/tags. It will just check if modified + attribute, is already modified, and if incoming effect is stronger it will override + all modifiers affecting this attribute, and remove all weaker ones. + + Override - does not check if it is stronger/weaker, it will simply override any existing modifiers + and effects with the same name. + + Duration - Will add duration to existing effect of EXACTLY the same type. + + Intensity - Undefined. It will either add new effects to stack, + or it will simply sum modifiers, from all effects of the same types, for the same attributes + and refresh duration to the latest applied effect. + + Add - no checks, simply add new effect to stack. +*/ +UENUM() +enum class EGAEffectStacking : uint8 +{ + Add = 0, + Duration = 1, + Override = 2, //override existing effect of the same type, and all other effects which have override the same attribute and have same AttributeTags + Intensity = 3, + //will add duration to existing effect + //will simply add new effect +}; + +UENUM() +enum class EGAMagnitudeCalculation : uint8 +{ + Direct, //straight float value, no calculations. + AttributeBased, //calculate based on attribute Attribute * RestOfEquationToBeDecided + CurveBased, //Takes value of attribute, and then gets value from curve based on this attribute. + CustomCalculation,//uses custom object to calculate magnitude. + Invalid +}; + + +/* +Rules for where we should aggregate effects. +Concept might look bit muddy at first look, but it is actually very simple. + +Let's say we have additive effect which modify Health by 50 points, and effect which modify health by 100. +We want, to only the highest one, affect target (positive bonus). Regardless of who applied this effect. + +To do it we need to tell this effect, that it should be aggregated by target and set effect stacking rule to +HighestOverride. + +Now say we have effect which reduce Health by 30 points, and second which reduce by 20 points. +We might want negative effects from diffrent source to stack. +To do this we need to aggregate those effects by Instigator. +And then we can decide how those effects will stack within single Instigator. +*/ +UENUM() +enum class EGAEffectAggregation : uint8 +{ + /* + Effect will be stacked/aggregated by Instigator who applied it. + Checking for stacking rules will be done only against other effects from the same Instigator. + */ + AggregateByInstigator, + /* + Effects will be stacked/aggregated by Target. + Checking for stacking rules, will be done only for effects, with the same target. + */ + AggregateByTarget +}; +UENUM() +enum class EGAStackingChannel : uint8 +{ + Channel001, + Channel002, + Channel003, + Channel004, + Channel005, + Channel006, + Channel007, + Channel008, + Channel009, + Channel010, + Channel011, + Channel012, + Channel013, + Channel014, + Channel015, + Channel016, + Channel017, + Channel018, + Channel019, + Channel020, + Channel021, + Channel022, + Channel023, + Channel024, + Channel025, + Channel026, + Channel027, + Channel028, + Channel029, + Channel030, + Channel031, + Channel032, +}; +USTRUCT() +struct FAFEventData +{ + GENERATED_USTRUCT_BODY() +}; + +USTRUCT() +struct FAFAtributeRowData : public FTableRowBase +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float BaseValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float MinValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float MaxValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + TSubclassOf Extension; +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectContext +{ + GENERATED_USTRUCT_BODY() +public: + /* + Just copy entire hit result struct. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + FHitResult HitResult; + /** + * Where exactly we hit target. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + FVector TargetHitLocation; + + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr TargetAttributes; + + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr InstigatorAttributes; + + /** + * Direct Reference to TargetActor (I will possibly remove FHitResult Target! + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Target; + /** + * Object which caused this effect. Might be ability, weapon, projectile etc. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Causer; + /** + * Pawn, which originally instigated effect (an owned AttributeComponent). + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Instigator; + /** + * Attribute component of Target. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr TargetComp; + /** + * Attribute component of Intigator + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr InstigatorComp; + + class IIGAAbilities* TargetInterface; + class IIGAAbilities* InstigatorInterface; + template + inline T* GetTarget() + { + return Cast(Target); + } + + inline bool IsValid() const + { + /*if (Target.IsValid() && Causer.IsValid() && Instigator.IsValid() && TargetComp.IsValid() && InstigatorComp.IsValid()) + return true;*/ + if (Causer.IsValid() && Instigator.IsValid() && InstigatorComp.IsValid() && TargetInterface) + return true; + //UE_LOG(GameAttributesEffects, Error, TEXT("Effect Context Is Not Valid")); + return false; + } + + inline FString ToString() + { + if (!IsValid()) + { + //UE_LOG(GameAttributesEffects, Error, TEXT("Effect Context Is Not Valid")); + return FString("Context Is not valid"); + } + FString ret; + ret = "TargetHitLocation: "; + ret += TargetHitLocation.ToString(); + ret += "\n"; + ret += "Target: "; + ret += Target->GetName(); + ret += "\n"; + ret += "Causer: "; + ret += Causer->GetName(); + ret += "\n"; + ret += "Instigator: "; + ret += Instigator->GetName(); + ret += "\n"; + ret += "TargetComp: "; + return ret; + } + + + + void Reset(); + + class UGAAttributesBase* GetTargetAttributes(); + class UGAAttributesBase* GetInstigatorAttributes(); + class UGAAttributesBase* GetCauserAttributes(); + + class UGAAttributesBase* GetTargetAttributes() const; + class UGAAttributesBase* GetInstigatorAttributes() const; + class UGAAttributesBase* GetCauserAttributes() const; + + FGAEffectContext() + {} + + FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, + const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, + TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, + TWeakObjectPtr TargetCompIn, + TWeakObjectPtr InstigatorCompIn); + + ~FGAEffectContext(); +}; + +struct FGAEffect; +class UGAGameEffectSpec; +struct FGAEffectMod; +struct FGAAttribute; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectHandle +{ + GENERATED_BODY() +protected: + //just to be safe we don't run out of numbers.. + UPROPERTY() + uint32 Handle; //Fname Guid ? + + TSharedPtr EffectPtr; +public: + + FGAEffectContext& GetContextRef(); + FGAEffectContext& GetContextRef() const; + + UGAGameEffectSpec* GetEffectSpec(); + UGAGameEffectSpec* GetEffectSpec() const; + + uint32 GetHandle() const; + + FGAEffect GetEffect(); + FGAEffect GetEffect() const; + + FGAEffect& GetEffectRef(); + FGAEffect& GetEffectRef() const; + + TSharedPtr GetEffectPtr(); + TSharedPtr GetEffectPtr() const; + + void SetContext(const FGAEffectContext& ContextIn); + void SetContext(const FGAEffectContext& ContextIn) const; + + FGAEffectContext& GetContext(); + FGAEffectContext& GetContext() const; + + void AppendOwnedTags(const FGameplayTagContainer& TagsIn); + void AppendOwnedTags(const FGameplayTagContainer& TagsIn) const; + struct FGAEffectMod GetAttributeModifier() const; + FGAAttribute GetAttribute() const; + EGAAttributeMod GetAttributeMod() const; + + static FGAEffectHandle GenerateHandle(FGAEffect* EffectIn); + bool HasAllTags(const FGameplayTagContainer& TagsIn) const; + bool HasAllTagsExact(const FGameplayTagContainer& TagsIn) const; + bool HasAllAttributeTags(const FGAEffectHandle& HandleIn) const; + bool HasAllAttributeTagsExact(const FGAEffectHandle& HandleIn) const; + FGameplayTagContainer& GetOwnedTags() const; + bool operator==(const FGAEffectHandle& Other) const + { + return Handle == Other.Handle; + } + bool operator!=(const FGAEffectHandle& Other) const + { + return Handle != Other.Handle; + } + void operator=(const FGAEffectHandle& Other) + { + Handle = Other.Handle; + EffectPtr = Other.EffectPtr; + } + + //FGAEffectHandle& operator=(const FGAEffectHandle& Other) + //{ + // Handle = Other.Handle; + // EffectPtr = Other.EffectPtr; + // return *this; + //} + + void Reset(); + bool IsValid() const; + friend uint32 GetTypeHash(const FGAEffectHandle& InHandle) + { + return InHandle.Handle; + } + + FGAEffectHandle() + : Handle(INDEX_NONE) + {} + + FGAEffectHandle(uint32 HandleIn, FGAEffect* EffectIn); +public: + ~FGAEffectHandle(); +}; +// +//template<> +//struct TStructOpsTypeTraits< FGAEffectHandle > : public TStructOpsTypeTraitsBase2 +//{ +// enum +// { +// WithCopy = true, +// }; +//}; + +DECLARE_MULTICAST_DELEGATE(FGAGenericDelegate); + +struct ABILITYFRAMEWORK_API EnumToString +{ + static FString GetStatckingAsString(EGAEffectStacking Stacking) + { + switch (Stacking) + { + case EGAEffectStacking::Override: + return FString("Override"); + case EGAEffectStacking::Intensity: + return FString("Intensity"); + case EGAEffectStacking::Duration: + return FString("Duration"); + case EGAEffectStacking::Add: + return FString("Add"); + } + return FString(""); + } +}; + +/* + Special struct, which allows to use FGameplayTagContainer as key, for TSet and TMap. + Bear in mind slower inserts/remove, but allow for complex keys. +*/ +struct ABILITYFRAMEWORK_API FGAHashedGameplayTagContainer +{ +public: + FGameplayTagContainer Tags; + +private: + FName Key; + void GenerateFNameKey(); + +public: + FGAHashedGameplayTagContainer() + {}; + FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn); + + friend uint32 GetTypeHash(const FGAHashedGameplayTagContainer& InHandle) + { + return ::GetTypeHash(InHandle.Key); + } +}; + +USTRUCT(BlueprintType) +struct FGAIndividualMods +{ + GENERATED_BODY() +public: + UPROPERTY() + float Additive; + UPROPERTY() + float Subtractive; + UPROPERTY() + float Multiplicative; + UPROPERTY() + float Divide; + UPROPERTY() + float PercentageAdd; + UPROPERTY() + float PercentageSubtract; + + FGAIndividualMods() + : Additive(0.0f), + Subtractive(0.0f), + Multiplicative(0.0f), + Divide(0.0f), + PercentageAdd(0.0f), + PercentageSubtract(0.0f) + {}; + FGAIndividualMods(float AdditiveIn, + float SubtractiveIn, + float MultiplicativeIn, + float DivideIn, + float PercentageAddIn, + float PercentageSubtractIn + ) + : Additive(AdditiveIn), + Subtractive(SubtractiveIn), + Multiplicative(MultiplicativeIn), + Divide(DivideIn), + PercentageAdd(PercentageAddIn), + PercentageSubtract(PercentageSubtractIn) + {} +}; +/** +* Struct representing single attribute. Needed for Pin customization. +* What we really need is to use this struct for making "complex" attributes. +* Which means attributes, which needs to track their own state. +* Bonuses applied to them, types of bonues, and who applied those bonuses +* so we can properly remove them, get them, track them, and controll order +* in which theyare added. +* we will two have attributes types. Staless (transient), auxiallry attttributes +* and staefull attributes, which are going to track their state. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAAttribute +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly) + FName AttributeName; + + inline bool operator== (const FGAAttribute& OtherAttribute) const + { + return (OtherAttribute.AttributeName == AttributeName); + } + + inline bool operator!= (const FGAAttribute& OtherAttribute) const + { + return (OtherAttribute.AttributeName != AttributeName); + } + + inline bool IsValid() const + { + return !AttributeName.IsNone(); + } + + inline FString ToString() + { + return AttributeName.ToString(); + } + + FGAAttribute() + { + AttributeName = NAME_None; + }; + FGAAttribute(const FName& AttributeNameIn) + { + AttributeName = AttributeNameIn; + }; + friend uint32 GetTypeHash(const FGAAttribute& InAttribute) + { + return GetTypeHash(InAttribute.AttributeName); + } + //FGAAttribute(const FString& AttributeNameIn) + //{ + // AttributeName = *AttributeNameIn; + //}; +}; + +/* Final calculcated mod from effect, which can be modified by Calculation object. */ +USTRUCT() +struct FGAEffectMod +{ + GENERATED_BODY() + FGAAttribute Attribute; + float Value; + EGAAttributeMod AttributeMod; + struct FGAEffectHandle Handle; + FGameplayTagContainer AttributeTags; + /* + Spec from which this mod has been derived. + Used to do not copy to much heavy data around. + */ + inline bool CompareMods(const FGAEffectMod& OtherMod) const + { + return AttributeMod == OtherMod.AttributeMod; + } + inline bool HasAllTags(const FGameplayTagContainer& TagsIn) const + { + return AttributeTags.HasAll(TagsIn); + } + inline bool HasAllTagsExact(const FGAEffectMod& OtherMod) const + { + return AttributeTags.HasAllExact(OtherMod.AttributeTags); + } + inline bool HasAllTagsExact(const FGameplayTagContainer& TagsIn) const + { + return AttributeTags.HasAllExact(TagsIn); + } + inline bool HasAllTagsIncludingChildren(const FGameplayTagContainer& TagsIn) const + { + return TagsIn.HasAll(AttributeTags); +// bool has = true; +// TArray GameplayTags; +// AttributeTags.GetGameplayTagArray(GameplayTags); +// for (const FGameplayTag& OtherTag : TagsIn) +// { +// /*for (const FGameplayTag& ChildTag : AttributeTags) +// { +// FGameplayTagContainer test = UGameplayTagsManager::Get().RequestGameplayTagChildren(ChildTag); +//*/ +// if (!ChildTags.HasAnyExact(TagsIn)) +// { +// if (!GameplayTags.Contains(OtherTag)) +// { +// has = false; +// } +// } +// //} +// } +// return has; + } + const bool operator==(const FGAEffectMod& Other) const + { + return Value == Other.Value && AttributeMod == Other.AttributeMod; + } + const bool operator!=(const FGAEffectMod& Other) const + { + return Value != Other.Value && AttributeMod == Other.AttributeMod; + } + + const bool operator>(const FGAEffectMod& Other) const + { + return Value > Other.Value && AttributeMod == Other.AttributeMod; + } + + const bool operator<(const FGAEffectMod& Other) const + { + return Value < Other.Value && AttributeMod == Other.AttributeMod; + } + const bool operator>=(const FGAEffectMod& Other) const + { + return Value >= Other.Value && AttributeMod == Other.AttributeMod; + } + + const bool operator<=(const FGAEffectMod& Other) const + { + return Value <= Other.Value && AttributeMod == Other.AttributeMod; + } + + + FGAEffectMod() + : Attribute(NAME_None), + Value(0), + AttributeMod(EGAAttributeMod::Invalid) + {}; + + FGAEffectMod(const FGAAttribute& AttributeIn, float ValueIn, + EGAAttributeMod AttributeModIn, FGAEffectHandle HandleIn, FGameplayTagContainer AttributeTagsIn) + : Attribute(AttributeIn), + Value(ValueIn), + AttributeMod(AttributeModIn), + Handle(HandleIn), + AttributeTags(AttributeTagsIn) + { + }; +}; + +USTRUCT(BlueprintType) +struct FAFAttributeChangedData +{ + GENERATED_BODY() +public: + FGAEffectMod Mod; + UPROPERTY() + TWeakObjectPtr Target; + //HitLocation of applicable; + FVector Location; + float NewValue; +}; + +/* +Struct representing final modifier applied to attribute. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + EGAAttributeMod AttributeMod; + UPROPERTY() + float Value; + + FGameplayTagContainer Tags; + /* + Weak pointer to effect, which added this modifier. + Useful because, while effect exist it have lots of useful informations. + */ + struct FGAEffectHandle Handle; + + FGAModifier() + {}; + FGAModifier(EGAAttributeMod ModIn, float ValueIn) + : AttributeMod(ModIn), + Value(ValueIn) + {}; + FGAModifier(EGAAttributeMod ModIn, float ValueIn, FGAEffectHandle HandleIn) + : AttributeMod(ModIn), + Value(ValueIn), + Handle(HandleIn) + {}; + + FGAModifier(const FGAEffectMod& ModIn) + : AttributeMod(ModIn.AttributeMod), + Value(ModIn.Value), + Handle(ModIn.Handle) + {}; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGACountedTagContainer +{ + GENERATED_USTRUCT_BODY() +protected: + /* + Here we will store counted GamaplayTags. + If tag is already in map, we just incremement count. + */ + TMap CountedTags; + + /* + Here we store all currently posesd tags. + It is equivalent of CountedTags, except this does not track count of tags, but we need it + to have something against which we can perform queries. + */ +public: + UPROPERTY() + FGameplayTagContainer AllTags; +public: + + inline FGameplayTagContainer GetTags() { return AllTags; }; + + void AddTag(const FGameplayTag& TagIn); + void AddTagContainer(const FGameplayTagContainer& TagsIn); + void RemoveTag(const FGameplayTag& TagIn); + void RemoveTagContainer(const FGameplayTagContainer& TagsIn); + + bool HasTag(const FGameplayTag& TagIn); + bool HasTagExact(const FGameplayTag TagIn); + bool HasAny(const FGameplayTagContainer& TagsIn); + bool HasAnyExact(const FGameplayTagContainer& TagsIn); + bool HasAll(const FGameplayTagContainer& TagsIn); + bool HasAllExact(const FGameplayTagContainer& TagsIn); + + bool HasTag(const FGameplayTag& TagIn) const; + bool HasTagExact(const FGameplayTag TagIn) const; + bool HasAny(const FGameplayTagContainer& TagsIn) const; + bool HasAnyExact(const FGameplayTagContainer& TagsIn) const; + bool HasAll(const FGameplayTagContainer& TagsIn) const; + bool HasAllExact(const FGameplayTagContainer& TagsIn) const; + + inline FGameplayTagContainer& GetAllTags() + { + return AllTags; + } + + inline int32 GetTagCount(const FGameplayTag& TagIn) const + { + return CountedTags.FindRef(TagIn); + } +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFContextHandle +{ + GENERATED_BODY() +protected: + TSharedPtr Data; +public: + FAFContextHandle() + { + + } +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectCueParams +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "Gameplay Cue") + FHitResult HitResult; + + /** Instigator actor, the actor that owns the ability system component */ + UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") + TWeakObjectPtr Instigator; + + /** The physical actor that actually did the damage, can be a weapon or projectile */ + UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") + TWeakObjectPtr Causer; + /* Which ability spawned (if applicable) */ + UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") + TWeakObjectPtr Ability; + + /* Tick interval for periodic effects */ + UPROPERTY(BlueprintReadOnly, Category = "GameplayCue") + float Period; + UPROPERTY(BlueprintReadOnly, Category = "GameplayCue") + float Duration; + + UPROPERTY(BlueprintReadOnly) + FGameplayTagContainer CueTags; + FGAEffectCueParams() + {}; + FGAEffectCueParams(const FHitResult& InHitResult, AActor* InstigatorIn, UObject* CauserIn) + : HitResult(InHitResult), + Instigator(InstigatorIn), + Causer(CauserIn) + {}; + //bool NetSerialize(FArchive& Ar, class UPackageMap* Map, bool& bOutSuccess); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp new file mode 100644 index 0000000..c7e7b6d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp @@ -0,0 +1,5 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAGlobals.h" + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h new file mode 100644 index 0000000..b011d8d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h @@ -0,0 +1,88 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "GAGlobals.generated.h" +/** + * + */ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASAbilitySetItem +{ + GENERATED_USTRUCT_BODY() +public: + /* Index in this array coresponds directly FGASActiveAbility::ActiveAbilities Index*/ + UPROPERTY(EditAnywhere) + TSubclassOf AbilityClass; + + UPROPERTY(EditAnywhere) + FGameplayTag Binding; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASAbilitySetContainer +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Abilities; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAbilityNotifyData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere) + float TEMP; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASAbilityHit : public FFastArraySerializerItem +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + FHitResult Hit; + + FGASAbilityHit() + {} + + FGASAbilityHit(const FHitResult& HitIn) + : Hit(HitIn) + {}; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASAbilityHitArray : public FFastArraySerializer +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + TArray Hits; + + inline void AddHit(const FHitResult& HitIn) + { + Hits.Add(FGASAbilityHit(HitIn)); + } + + inline void Empty() + { + Hits.Empty(); + } + + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(Hits, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FGASAbilityHitArray > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp new file mode 100644 index 0000000..0451e0e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp @@ -0,0 +1,5 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAHelperTemplates.h" + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h new file mode 100644 index 0000000..279614c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h @@ -0,0 +1,59 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "GAAbilitiesComponent.h" +#include "GAHelperTemplates.generated.h" + +USTRUCT(BlueprintType) +struct FGAAttributeSource +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + EGAAttributeSource Source; + /* Class which is source for attribute set. */ + UPROPERTY(EditAnywhere)//, meta = (MustImplement = "IGAAbilities")) + FGameplayTag AttributeSource; +}; + +USTRUCT(BlueprintType) +struct FGAAttributeCapture +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FGAAttributeSource Source; + + UPROPERTY(EditAnywhere) + FGameplayTagContainer RequiredTags; + UPROPERTY(EditAnywhere) + FGameplayTagContainer DenyTags; + + template + T* GetAttributeSet(const FGAEffectContext& ContextIn) + { + UGAAbilitiesComponent* TargetComp = ContextIn.TargetComp.Get(); + UGAAbilitiesComponent* InstigatorComp = ContextIn.InstigatorComp.Get(); + T* AttributeSet = nullptr; + switch (Source.Source) + { + case EGAAttributeSource::Causer: + { + break; + } + case EGAAttributeSource::Target: + { + AttributeSet = TargetComp->GetAttributeSet(Source.AttributeSource); + break; + } + case EGAAttributeSource::Instigator: + { + AttributeSet = InstigatorComp->GetAttributeSet(Source.AttributeSource); + break; + } + } + return AttributeSet; + } +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp new file mode 100644 index 0000000..05718f4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAPhysicalMaterial.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h new file mode 100644 index 0000000..429f1bd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "PhysicalMaterials/PhysicalMaterial.h" +#include "GAPhysicalMaterial.generated.h" + +/** + * + */ +UCLASS(Blueprintable) +class ABILITYFRAMEWORK_API UGAPhysicalMaterial : public UPhysicalMaterial +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Fx") + UParticleEmitter* SurfaceHitFX; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp new file mode 100644 index 0000000..6e90d29 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAUIData.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h new file mode 100644 index 0000000..bc6d205 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Object.h" +#include "GAUIData.generated.h" + +/** + * Base class for UI data for effect. + * Do not instance it. Just use CDO, to get data from it. + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAUIData : public UObject +{ + GENERATED_BODY() +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h new file mode 100644 index 0000000..3b4bce0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h @@ -0,0 +1,37 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "ModuleManager.h" + + +/** + * The public interface to this module. In most cases, this interface is only public to sibling modules + * within this plugin. + */ +class IAbilityFramework : public IModuleInterface +{ + +public: + /** + * Singleton-like access to this module's interface. This is just for convenience! + * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. + * + * @return Returns singleton instance, loading the module on demand if needed + */ + static inline IAbilityFramework& Get() + { + return FModuleManager::LoadModuleChecked< IAbilityFramework >( "AbilityFramework" ); + } + + /** + * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. + * + * @return True if the module is loaded and ready to use + */ + static inline bool IsAvailable() + { + return FModuleManager::Get().IsModuleLoaded( "AbilityFramework" ); + } +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp new file mode 100644 index 0000000..119e97a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp @@ -0,0 +1,10 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "IGAAbilities.h" + +UIGAAbilities::UIGAAbilities(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h b/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h new file mode 100644 index 0000000..5643918 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h @@ -0,0 +1,48 @@ +#pragma once +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypes.h" +#include "Messaging.h" +#include "IGAAbilities.generated.h" + + +struct FAFAttributeBase; +struct FGAEffectHandle; +UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) +class ABILITYFRAMEWORK_API UIGAAbilities : public UInterface +{ + GENERATED_UINTERFACE_BODY() +}; + +class IIGAAbilities +{ + GENERATED_IINTERFACE_BODY() +public: + virtual FVector GetSocketLocation(FName SocketNameIn){ return FVector::ZeroVector; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UGAAttributesBase* GetAttributes() = 0; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UGAAbilitiesComponent* GetAbilityComp() { return nullptr; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; + + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) {}; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; + + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) { return FGAEffectHandle(); }; + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) {}; + //override to allow gathering tags from causer + //those tags will be merged into effect owned tags. + virtual FGameplayTagContainer GetCauserTags() { return FGameplayTagContainer(); } + + virtual void Died() {}; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp new file mode 100644 index 0000000..9c9ce07 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp @@ -0,0 +1,71 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GALatentFunctionBase.h" + +void FGALatentFunctionTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) +{ + if (Target && !Target->IsPendingKillOrUnreachable()) + { + FScopeCycleCounterUObject ActorScope(Target); + Target->TickAction(DeltaTime, TickType, *this); + } +} + +FString FGALatentFunctionTick::DiagnosticMessage() +{ + return Target->GetFullName() + TEXT("[TickAction]"); +} + +UGALatentFunctionBase::UGALatentFunctionBase(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + TickFunction.TickGroup = TG_PrePhysics; + // Default to no tick function, but if we set 'never ticks' to false (so there is a tick function) it is enabled by default + TickFunction.bCanEverTick = false; + TickFunction.bStartWithTickEnabled = true; + TickFunction.bAllowTickOnDedicatedServer = true; + TickFunction.bRunOnAnyThread = true; + + TickFunction.SetTickFunctionEnable(true); + SetFlags(RF_StrongRefOnFrame); +} + +void UGALatentFunctionBase::Initialize() +{ + if (GetWorld()) + { + TickFunction.Target = this; + ULevel* level = GetWorld()->GetCurrentLevel(); + if (level) + { + TickFunction.RegisterTickFunction(level); + } + } +} +void UGALatentFunctionBase::EndTask() +{ + if (TickFunction.bCanEverTick && TickFunction.IsTickFunctionRegistered()) + { + TickFunction.UnRegisterTickFunction(); + TickFunction.SetTickFunctionEnable(false); + } + MarkPendingKill(); +} +void UGALatentFunctionBase::BeginDestroy() +{ + Super::BeginDestroy(); + if (Endpoint.IsValid()) + { + FMessageEndpoint::SafeRelease(Endpoint); + Endpoint.Reset(); + } +} +UWorld* UGALatentFunctionBase::GetWorld() const +{ + if (TaskOwner) + { + return TaskOwner->GetWorld(); + } + return nullptr; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h new file mode 100644 index 0000000..7c5c16e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h @@ -0,0 +1,55 @@ +#pragma once +#include "CoreMinimal.h" +#include "Engine/EngineBaseTypes.h" +#include "Messaging.h" +#include "GALatentFunctionBase.generated.h" + +struct FGALatentFunctionTick: public FTickFunction +{ + /** AActor that is the target of this tick **/ + class UGALatentFunctionBase* Target; + + /** + * Abstract function actually execute the tick. + * @param DeltaTime - frame time to advance, in seconds + * @param TickType - kind of tick for this frame + * @param CurrentThread - thread we are executing on, useful to pass along as new tasks are created + * @param MyCompletionGraphEvent - completion event for this task. Useful for holding the completetion of this task until certain child tasks are complete. + **/ + virtual void ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) override; + /** Abstract function to describe this tick. Used to print messages about illegal cycles in the dependency graph **/ + virtual FString DiagnosticMessage() override; +}; + +UCLASS(meta = (ExposedAsyncProxy = "true")) +class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject +{ + GENERATED_BODY() + //never access internals of these classes directly. Use messages instead. +protected: + UPROPERTY() + UObject* TaskOwner; + friend struct FGALatentFunctionTick; + FGALatentFunctionTick TickFunction; + + TSharedPtr Endpoint; + UGALatentFunctionBase(const FObjectInitializer& ObjectInitializer); + virtual UWorld* GetWorld() const override; + + //virtual void Tick(float DeltaSecondsIn); + virtual void TickAction(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) {}; + virtual void Initialize(); + virtual void ReadyForActivation() {}; + virtual void Activate() {}; + virtual void EndTask(); + virtual void BeginDestroy() override; + + template + FORCEINLINE static T* NewTask(UObject* WorldContextObject, UObject* InTaskOwner, FName InstanceName = FName()) + { + T* MyObj = NewObject(WorldContextObject); + MyObj->TaskOwner = InTaskOwner; + MyObj->Initialize(); + return MyObj; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp new file mode 100644 index 0000000..b3e128d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp @@ -0,0 +1,55 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAWaitAction.h" + +UGAWaitAction::UGAWaitAction(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + TickFunction.bCanEverTick = true; + TickFunction.bStartWithTickEnabled = true; + TickFunction.bAllowTickOnDedicatedServer = true; + TickFunction.bRunOnAnyThread = true; + SetFlags(RF_StrongRefOnFrame); +} + +UGAWaitAction* UGAWaitAction::NewGAWaitAction(UObject* InTaskOwner, float Time) +{ + UGAWaitAction* MyTask = NewTask(InTaskOwner, InTaskOwner); + if (MyTask) + { + MyTask->Time = Time; + //MyTask->TaskOwner = InTaskOwner; + //MyTask->Initialize(); + MyTask->Activate(); + + } + return MyTask; +} + +void UGAWaitAction::Activate() +{ + OnInitialized.Broadcast(); + if (GEngine) + { + GEngine->AddOnScreenDebugMessage(0, 1, FColor::Red, FString("ObjectName: ") + GetName()); + } + if (TaskOwner && TaskOwner->GetWorld()) + { + UWorld* World = TaskOwner->GetWorld(); + TimeStarted = World->GetTimeSeconds(); + + // Use a dummy timer handle as we don't need to store it for later but we don't need to look for something to clear + FTimerHandle TimerHandle; + World->GetTimerManager().SetTimer(TimerHandle, this, &UGAWaitAction::OnTimeFinish, Time, false); + } +} +void UGAWaitAction::TickAction(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) +{ + OnTick.Broadcast(); +}; +void UGAWaitAction::OnTimeFinish() +{ + OnFinish.Broadcast(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h new file mode 100644 index 0000000..0c4b147 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h @@ -0,0 +1,42 @@ +#pragma once +#include "GALatentFunctionBase.h" +#include "GAWaitAction.generated.h" +/* + AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and + the should be activated from ability. + Then can perform tasks, like spawn tagetting helpers (splines, circles), spawn actors, + gather targeting data etc. + + Should they be activated automatically after ability is initialized, (it'e ability enterted in + active state, which means it's ready to be fired and display helpers, but did not yet received input, + or should designer in blueprint decide when to launch actions ?). +*/ +UCLASS(meta = (ExposedAsyncProxy = "true") ) +class ABILITYFRAMEWORK_API UGAWaitAction : public UGALatentFunctionBase +{ + GENERATED_BODY() + +public: + UGAWaitAction(const FObjectInitializer& ObjectInitializer); + float Time; + float TimeStarted; + + DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAWaitActionDelegate); + UPROPERTY(BlueprintAssignable) + FGAWaitActionDelegate OnInitialized; + UPROPERTY(BlueprintAssignable) + FGAWaitActionDelegate OnFinish; + + UPROPERTY(BlueprintAssignable) + FGAWaitActionDelegate OnTick; + + //virtual void Tick(float DeltaSecondsIn); + + virtual void Activate() override; + virtual void TickAction(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; + UFUNCTION(BlueprintCallable, Category = "Latent Actions", meta = (AdvancedDisplay = "InTaskOwner, Priority", DefaultToSelf = "InTaskOwner", BlueprintInternalUseOnly = "TRUE")) + static UGAWaitAction* NewGAWaitAction(UObject* InTaskOwner, float Time); + + void OnTimeFinish(); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp new file mode 100644 index 0000000..8069c17 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp @@ -0,0 +1,11 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "GAGlobalTypes.h" +#include "GAAttributeMod.h" + +UGAAttributeMod::UGAAttributeMod(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h b/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h new file mode 100644 index 0000000..1363965 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h @@ -0,0 +1,32 @@ +#pragma once +#include "GAGlobalTypes.h" +#include "GameplayTagContainer.h" +#include "GAAttributeMod.generated.h" +/* + Using this class you can perform actions, when change to attribute is instigated. + Outcoming are modifiers appiled by instigator. + Incoming are modifiers appiled by target. + + Common applications are generic mods like damage reduction by armor or other attribute. + Increasing damage. + + Fireing other actions, when certain critera has been meet. + + This system is actually similiar to Effects from GameEffectSystem module. + + The main difference is that, attribute mods, cannot be appiled by other objects. You can add or remove + them on runtime, by providing set of classes, that can be added to component and the constructed. + + But you can't apply those mods by means like weapons or abilities. + They are always passive (as they are listening for events), they are always infinite + (their duration is for the entire lifetime of pawn/controller/game) + and they can't affect other attribute mods. They can only affect attributes, and trigger actions + based on them. This might include launching effects. + + As per usual using GameplayTags is recommened for defining behaviour. +*/ +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInlineNew) +class ABILITYFRAMEWORK_API UGAAttributeMod : public UObject +{ + GENERATED_UCLASS_BODY() +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp new file mode 100644 index 0000000..f645ed8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../Abilities/GAAbilityBase.h" +#include "GASAbilityTargetingObject.h" + +FHitResult UGASAbilityTargetingObject::GetTarget() +{ + FHitResult HitOut; + APlayerController* PC = AbilityOwner->PCOwner; + APawn* P = AbilityOwner->POwner; + FVector TraceStart = PC->PlayerCameraManager->GetCameraLocation(); // P->GetPawnViewLocation(); + FRotator UnusedRot = P->GetBaseAimRotation(); + PC->GetActorEyesViewPoint(TraceStart, UnusedRot); + FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; + UWorld* World = GetWorld(); + FCollisionQueryParams ColParams; + ColParams.AddIgnoredActor(P); + FCollisionResponseParams ColResp; + + World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + if (HitOut.bBlockingHit) + { + DrawDebugLine(GetWorld(), TraceStart, HitOut.ImpactPoint, FColor::Red, true, 4); + } + DrawDebugLine(GetWorld(), TraceStart, TraceEnd, FColor::Green, true, 4); + + return HitOut; +} + +class UWorld* UGASAbilityTargetingObject::GetWorld() const +{ + if (AbilityOwner.IsValid()) + return AbilityOwner->GetWorld(); + return nullptr; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h new file mode 100644 index 0000000..05e6f28 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Object.h" +#include "GASAbilityTargetingObject.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGASAbilityTargetingObject : public UObject +{ + GENERATED_BODY() +public: + TWeakObjectPtr AbilityOwner; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, meta = (ExposeOnSpawn = "true"), Category = "Config") + bool bDebugDraw; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, meta = (ExposeOnSpawn = "true"), Category = "Config") + float Range; + + virtual FHitResult GetTarget(); + + virtual class UWorld* GetWorld() const; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp new file mode 100644 index 0000000..c377965 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GATargetingActor.h" + + +// Sets default values +AGATargetingActor::AGATargetingActor() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AGATargetingActor::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AGATargetingActor::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h new file mode 100644 index 0000000..c48049e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Actor.h" +#include "GATargetingActor.generated.h" + +UCLASS() +class ABILITYFRAMEWORK_API AGATargetingActor : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + AGATargetingActor(); + + // Called when the game starts or when spawned + virtual void BeginPlay() override; + + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp new file mode 100644 index 0000000..5b45dcb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp @@ -0,0 +1,13 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAAttributesTest.h" + + + + +void UGAAttributesTest::InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp) +{ + + Super::InitializeAttributes(InOwningAttributeComp); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h new file mode 100644 index 0000000..aa3632b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h @@ -0,0 +1,49 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "../Attributes/GAAttributesBase.h" +#include "GAAttributesTest.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAttributesTest : public UGAAttributesBase +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase Health; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase Energy; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase Stamina; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase Magic; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase Inteligence; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase MagicDamageBonus; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase MagicDamageMultiplayer; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase Armor; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase MagicDefensePercentage; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase MagicDefenseFlat; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase MagicalBonus; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase PhysicalBonus; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") + FAFAttributeBase MagicResistance; +public: + virtual void InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp) override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp new file mode 100644 index 0000000..09255d3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp @@ -0,0 +1,1646 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "AutomationTest.h" +#include "GameplayTagsModule.h" +#include "../GAGlobalTypes.h" +#include "../Attributes/GAAttributeBase.h" +#include "../Effects/GAGameEffect.h" +#include "../GAAbilitiesComponent.h" +#include "../Attributes/GAAttributesBase.h" +#include "../Effects/GAEffectExecution.h" +#include "../Effects/GABlueprintLibrary.h" +#include "GAAttributesTest.h" +#include "GASpellExecutionTest.h" +#include "GACharacterAttributeTest.h" +#include "GACustomCalculationTest.h" +#include "GAffectSpecTestOne.h" +#include "../Effects/ApplicationRequirement/AFAttributeStongerOverride.h" +#include "../Effects/CustomApplications/AFAttributeDurationOverride.h" +#include "../Effects/CustomApplications/AFPeriodApplicationOverride.h" +#include "../Effects/CustomApplications/AFAtributeDurationAdd.h" +#include "../Effects/CustomApplications/AFPeriodApplicationAdd.h" +#include "../Effects/CustomApplications/AFAttributeDurationInfinite.h" +#include "../Effects/CustomApplications/AFPeriodApplicationExtend.h" + +#if WITH_EDITOR + +static UDataTable* CreateGameplayDataTable() +{ + FString CSV(TEXT(",Tag,CategoryText,")); + CSV.Append(TEXT("\r\n0,Damage")); + CSV.Append(TEXT("\r\n1,Damage.Basic")); + CSV.Append(TEXT("\r\n2,Damage.Type1")); + CSV.Append(TEXT("\r\n3,Damage.Type2")); + CSV.Append(TEXT("\r\n4,Damage.Reduce")); + CSV.Append(TEXT("\r\n5,Damage.Buffable")); + CSV.Append(TEXT("\r\n6,Damage.Buff")); + CSV.Append(TEXT("\r\n7,Damage.Physical")); + CSV.Append(TEXT("\r\n8,Damage.Fire")); + CSV.Append(TEXT("\r\n9,Damage.Buffed.FireBuff")); + CSV.Append(TEXT("\r\n10,Damage.Mitigated.Armor")); + CSV.Append(TEXT("\r\n11,Lifesteal")); + CSV.Append(TEXT("\r\n12,Shield")); + CSV.Append(TEXT("\r\n13,Buff")); + CSV.Append(TEXT("\r\n14,Immune")); + CSV.Append(TEXT("\r\n15,FireDamage")); + CSV.Append(TEXT("\r\n16,ShieldAbsorb")); + CSV.Append(TEXT("\r\n17,Stackable")); + CSV.Append(TEXT("\r\n18,Stack")); + CSV.Append(TEXT("\r\n19,Stack.CappedNumber")); + CSV.Append(TEXT("\r\n20,Stack.DiminishingReturns")); + CSV.Append(TEXT("\r\n21,Protect.Damage")); + CSV.Append(TEXT("\r\n22,SpellDmg.Buff")); + CSV.Append(TEXT("\r\n23,GameplayCue.Burning")); + CSV.Append(TEXT("\r\n24,Damage.Fire")); + CSV.Append(TEXT("\r\n25,Damage.Ice")); + CSV.Append(TEXT("\r\n26,Damage.Acid")); + CSV.Append(TEXT("\r\n27,Damage.Earth")); + CSV.Append(TEXT("\r\n28,Damage.Electricity")); + CSV.Append(TEXT("\r\n29,Damage.Darkness")); + CSV.Append(TEXT("\r\n30,Damage.Necrotic")); + CSV.Append(TEXT("\r\n31,Damage.Radiant")); + CSV.Append(TEXT("\r\n32,Damage.Water")); + + auto DataTable = NewObject(GetTransientPackage(), FName(TEXT("TempDataTable"))); + DataTable->RowStruct = FGameplayTagTableRow::StaticStruct(); + DataTable->CreateTableFromCSVString(CSV); + + FGameplayTagTableRow * Row = (FGameplayTagTableRow*)DataTable->RowMap["0"]; + if (Row) + { + check(Row->Tag == TEXT("Damage")); + } + return DataTable; +}; + +struct FTagsInput +{ + FGameplayTagContainer OwnedTags; + FGameplayTagContainer EffectTags; + FGameplayTagContainer AttributeTags; + FGameplayTagContainer DenyTags; + FGameplayTagContainer AppliedImmunityTags; + FGameplayTagContainer ApplyTags; + FGameplayTagContainer RequiredTags; + FGameplayTagContainer OngoingRequiredTags; +}; +#define CONSTRUCT_CLASS(Class, Name) Class* Name = NewObject(GetTransientPackage(), FName(TEXT(#Name))) +class GameEffectsTestSuite +{ + UWorld* World; + FAutomationTestBase* Test; + + AGACharacterAttributeTest* SourceActor; + UGAAbilitiesComponent* SourceComponent; + + AGACharacterAttributeTest* DestActor; + UGAAbilitiesComponent* DestComponent; + + AGACharacterAttributeTest* TargetOne; + UGAAbilitiesComponent* TargetCompOne; + + AGACharacterAttributeTest* TargetTwo; + UGAAbilitiesComponent* TargetCompTwo; + +public: + GameEffectsTestSuite(UWorld* WorldIn, FAutomationTestBase* TestIn) + : World(WorldIn), + Test(TestIn) + { + SourceActor = World->SpawnActor(); + SourceComponent = SourceActor->Attributes; + SourceComponent->DefaultAttributes = NewObject(SourceActor->Attributes); + SourceComponent->GetAttributes()->Health.SetBaseValue(100); + SourceComponent->GetAttributes()->Energy.SetBaseValue(100); + SourceComponent->GetAttributes()->Stamina.SetBaseValue(100); + SourceComponent->GetAttributes()->Health.SetMaxValue(500); + SourceComponent->GetAttributes()->Energy.SetMaxValue(500); + SourceComponent->GetAttributes()->Stamina.SetMaxValue(500); + /*SourceComponent->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; + SourceComponent->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; + SourceComponent->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add; +*/ + SourceComponent->GetAttributes()->MagicalBonus.SetMaxValue(500); + SourceComponent->GetAttributes()->PhysicalBonus.SetMaxValue(500); + SourceComponent->GetAttributes()->MagicResistance.SetMaxValue(500); + + //SourceComponent->GetAttributes()->MagicalBonus.Stacking = EAFAttributeStacking::Override; + //SourceComponent->GetAttributes()->PhysicalBonus.Stacking = EAFAttributeStacking::Add; + //SourceComponent->GetAttributes()->MagicResistance.Stacking = EAFAttributeStacking::Override; + + SourceComponent->GetAttributes()->Health.InitializeAttribute(); + SourceComponent->GetAttributes()->Energy.InitializeAttribute(); + SourceComponent->GetAttributes()->Stamina.InitializeAttribute(); + + SourceComponent->GetAttributes()->MagicalBonus.InitializeAttribute(); + SourceComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(); + SourceComponent->GetAttributes()->MagicResistance.InitializeAttribute(); + SourceComponent->DefaultAttributes->InitializeAttributes(SourceComponent); + + DestActor = World->SpawnActor(); + DestComponent = DestActor->Attributes; + DestComponent->DefaultAttributes = NewObject(DestActor->Attributes); + DestComponent->GetAttributes()->Health.SetBaseValue(100); + DestComponent->GetAttributes()->Energy.SetBaseValue(100); + DestComponent->GetAttributes()->Stamina.SetBaseValue(100); + DestComponent->GetAttributes()->Health.SetMaxValue(500); + DestComponent->GetAttributes()->Energy.SetMaxValue(500); + DestComponent->GetAttributes()->Stamina.SetMaxValue(500); + /*DestComponent->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; + DestComponent->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; + DestComponent->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add;*/ + DestComponent->GetAttributes()->MagicalBonus.SetMaxValue(500); + DestComponent->GetAttributes()->PhysicalBonus.SetMaxValue(500); + DestComponent->GetAttributes()->MagicResistance.SetMaxValue(500); + + DestComponent->GetAttributes()->Health.InitializeAttribute(); + DestComponent->GetAttributes()->Energy.InitializeAttribute(); + DestComponent->GetAttributes()->Stamina.InitializeAttribute(); + + DestComponent->GetAttributes()->MagicalBonus.InitializeAttribute(); + DestComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(); + DestComponent->GetAttributes()->MagicResistance.InitializeAttribute(); + DestComponent->DefaultAttributes->InitializeAttributes(DestComponent); + + TargetOne = World->SpawnActor(); + TargetCompOne = TargetOne->Attributes; + TargetCompOne->DefaultAttributes = NewObject(TargetOne->Attributes); + TargetCompOne->GetAttributes()->Health.SetBaseValue(100); + TargetCompOne->GetAttributes()->Energy.SetBaseValue(100); + TargetCompOne->GetAttributes()->Stamina.SetBaseValue(100); + TargetCompOne->GetAttributes()->Health.SetMaxValue(500); + TargetCompOne->GetAttributes()->Energy.SetMaxValue(500); + TargetCompOne->GetAttributes()->Stamina.SetMaxValue(500); + //TargetCompOne->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; + //TargetCompOne->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; + //TargetCompOne->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add; + TargetCompOne->GetAttributes()->MagicalBonus.SetMaxValue(500); + TargetCompOne->GetAttributes()->PhysicalBonus.SetMaxValue(500); + TargetCompOne->GetAttributes()->MagicResistance.SetMaxValue(500); + + TargetCompOne->GetAttributes()->Health.InitializeAttribute(); + TargetCompOne->GetAttributes()->Energy.InitializeAttribute(); + TargetCompOne->GetAttributes()->Stamina.InitializeAttribute(); + + TargetCompOne->GetAttributes()->MagicalBonus.InitializeAttribute(); + TargetCompOne->GetAttributes()->PhysicalBonus.InitializeAttribute(); + TargetCompOne->GetAttributes()->MagicResistance.InitializeAttribute(); + TargetCompOne->DefaultAttributes->InitializeAttributes(TargetCompOne); + + + TargetTwo = World->SpawnActor(); + TargetCompTwo = TargetTwo->Attributes; + TargetCompTwo->DefaultAttributes = NewObject(TargetTwo->Attributes); + TargetCompTwo->GetAttributes()->Health.SetBaseValue(100); + TargetCompTwo->GetAttributes()->Energy.SetBaseValue(100); + TargetCompTwo->GetAttributes()->Stamina.SetBaseValue(100); + TargetCompTwo->GetAttributes()->Health.SetMaxValue(500); + TargetCompTwo->GetAttributes()->Energy.SetMaxValue(500); + TargetCompTwo->GetAttributes()->Stamina.SetMaxValue(500); + //TargetCompTwo->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; + //TargetCompTwo->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; + //TargetCompTwo->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add; + TargetCompTwo->GetAttributes()->MagicalBonus.SetMaxValue(500); + TargetCompTwo->GetAttributes()->PhysicalBonus.SetMaxValue(500); + TargetCompTwo->GetAttributes()->MagicResistance.SetMaxValue(500); + + TargetCompTwo->GetAttributes()->Health.InitializeAttribute(); + TargetCompTwo->GetAttributes()->Energy.InitializeAttribute(); + TargetCompTwo->GetAttributes()->Stamina.InitializeAttribute(); + + TargetCompTwo->GetAttributes()->MagicalBonus.InitializeAttribute(); + TargetCompTwo->GetAttributes()->PhysicalBonus.InitializeAttribute(); + TargetCompTwo->GetAttributes()->MagicResistance.InitializeAttribute(); + TargetCompTwo->DefaultAttributes->InitializeAttributes(TargetCompTwo); + + //DestActor->BeginPlay(); + //SourceActor->BeginPlay(); + } + + ~GameEffectsTestSuite() + { + // run after each test + + // destroy the actors + if (SourceActor) + { + World->EditorDestroyActor(SourceActor, false); + } + if (DestActor) + { + World->EditorDestroyActor(DestActor, false); + } + } + void TickWorld(float Time) + { + const float step = 0.01f; + while (Time > 0.f) + { + World->Tick(ELevelTick::LEVELTICK_All, FMath::Min(Time, step)); + Time -= step; + + // This is terrible but required for subticking like this. + // we could always cache the real GFrameCounter at the start of our tests and restore it when finished. + GFrameCounter++; + } + } + FGameplayTag RequestTag(const FName& TagIn) + { + return UGameplayTagsManager::Get().RequestGameplayTag(TagIn); + } + + FGameplayTagContainer CreateTags(const TArray& TagsIn) + { + FGameplayTagContainer OutTags; + TArray Tags; + for (const FName& Tag : TagsIn) + { + FGameplayTag ReqTeg = UGameplayTagsManager::Get().RequestGameplayTag(Tag); + if (ReqTeg.IsValid()) + { + Tags.Add(ReqTeg); + } + } + OutTags = FGameplayTagContainer::CreateFromArray(Tags); + //OutTags.FillParentTags(); + return OutTags; + } + + void TestEqual(const FString& TestText, float Actual, float Expected) + { + Test->TestEqual(FString::Printf(TEXT("%s: %f (actual) != %f (expected)"), *TestText, Actual, Expected), Actual, Expected); + } + void TestEqual(const FString& TestText, int32 Actual, int32 Expected) + { + Test->TestEqual(FString::Printf(TEXT("%s: %f (actual) != %f (expected)"), *TestText, Actual, Expected), Actual, Expected); + } + void TestEqualTags(const FString& TestText, FName Actual, FName Expected) + { + Test->TestEqual(FString::Printf(TEXT("%s: %s (actual) != %s (expected)"), *TestText, *Actual.ToString(), *Expected.ToString()), Actual, Expected); + } + void TestEqualTags(const FString& TestText, FGameplayTag Actual, FGameplayTag Expected) + { + Test->TestEqual(FString::Printf(TEXT("%s: %s (actual) != %s (expected)"), *TestText, *Actual.ToString(), *Expected.ToString()), Actual, Expected); + } + FGAAttributeModifier CreateAttributeModifer(const TArray& OwnedTags, float ModValue, + EGAAttributeMod ModType, const FName& Attribute) + { + FGAAttributeModifier AttributeModifier; + AttributeModifier.Attribute = FGAAttribute(Attribute); + AttributeModifier.AttributeMod = ModType; + AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; + AttributeModifier.Magnitude.DirectModifier.Value = ModValue; + + return AttributeModifier; + } + + FGAEffectProperty CreateEffectSpec(const TArray& OwnedTags, float ModValue, + EGAAttributeMod ModType, const FName& Attribute, TSubclassOf CDO) + { + TSubclassOf c = CDO; + FGAEffectProperty Spec; + //UGAGameEffectSpec* Effect = NewObject(GetTransientPackage()); + Spec = c; + //Spec = Effect; + UGAGameEffectSpec* cds = Spec.GetClass().GetDefaultObject(); + cds->ExecutionType = UGASpellExecutionTest::StaticClass(); + cds->ApplicationRequirement = UAFEffectApplicationRequirement::StaticClass(); + cds->Application = UAFEffectCustomApplication::StaticClass(); + FGAAttributeModifier AttributeModifier; + AttributeModifier.Attribute = FGAAttribute(Attribute); + AttributeModifier.AttributeMod = ModType; + AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; + AttributeModifier.Magnitude.DirectModifier.Value = ModValue; + cds->OwnedTags = CreateTags(OwnedTags); + cds->AtributeModifier = AttributeModifier; + FGAMagnitude DurationMag; + DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; + DurationMag.DirectModifier.Value = 0; + cds->Duration = DurationMag; + FGAMagnitude PeriodMag; + PeriodMag.CalculationType = EGAMagnitudeCalculation::Direct; + PeriodMag.DirectModifier.Value = 0; + cds->Period = PeriodMag; + return Spec; + } + FGAEffectProperty CreateEffectDurationSpec(const TArray& OwnedTags, float ModValue, + EGAAttributeMod ModType, const FName& Attribute, EGAEffectStacking Stacking, + const TArray& AttributeTags = TArray(), + const TArray& ApplyTags = TArray(), + const FTagsInput& TagsIn = FTagsInput(), + TSubclassOf ApplReq = UAFEffectApplicationRequirement::StaticClass(), + TSubclassOf Appl = UAFEffectCustomApplication::StaticClass(), + TSubclassOf CDO = UGAGameEffectSpec::StaticClass() + ) + { + const float Duration = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + FGAEffectProperty Spec; + Spec = CDO; + UGAGameEffectSpec* cdo = Spec.GetClass().GetDefaultObject(); + + //UClass* clas = DuplicateObject(UGAGameEffectSpec::StaticClass()); + //Spec.Spec = + cdo->ExecutionType = UGAEffectExecution::StaticClass(); + cdo->ApplicationRequirement = ApplReq; + cdo->Application = Appl; + cdo->OwnedTags = CreateTags(OwnedTags); + cdo->bExecuteOnApplication = true; + if (AttributeTags.Num() > 0) + cdo->AttributeTags = CreateTags(AttributeTags); + if (ApplyTags.Num() > 0) + cdo->ApplyTags = CreateTags(ApplyTags); + + cdo->RequiredTags = TagsIn.RequiredTags; + cdo->DenyTags = TagsIn.DenyTags; + cdo->ExecutionRequiredTags = TagsIn.OngoingRequiredTags; + + FGAAttributeModifier AttributeModifier; + AttributeModifier.Attribute = FGAAttribute(Attribute); + AttributeModifier.AttributeMod = ModType; + AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; + AttributeModifier.Magnitude.DirectModifier.Value = ModValue; + cdo->AtributeModifier = AttributeModifier; + FGAMagnitude DurationMag; + DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; + DurationMag.DirectModifier.Value = Duration; + cdo->Duration = DurationMag; + FGAMagnitude PeriodMag; + PeriodMag.CalculationType = EGAMagnitudeCalculation::Direct; + PeriodMag.DirectModifier.Value = 0; + cdo->Period = PeriodMag; + return Spec; + } + + FGAEffectProperty CreateEffectPeriodicSpec(const TArray& OwnedTags, float ModValue, + EGAAttributeMod ModType, const FName& Attribute, EGAEffectStacking Stacking, + const TArray& AttributeTags = TArray(), + const TArray& ApplyTags = TArray(), + const FTagsInput& TagsIn = FTagsInput(), + TSubclassOf CDO = UGAGameEffectSpec::StaticClass(), + TSubclassOf Appl = UAFEffectCustomApplication::StaticClass(), + bool InExecuteOnApplication = false + ) + { + const float Duration = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + FGAEffectProperty Spec; + Spec = CDO; + UGAGameEffectSpec* cdo = Spec.GetClass().GetDefaultObject(); + + cdo->ExecutionType = UGAEffectExecution::StaticClass(); + cdo->ApplicationRequirement = UAFAttributeStongerOverride::StaticClass(); + cdo->Application = Appl; + + cdo->OwnedTags = CreateTags(OwnedTags); + if (AttributeTags.Num() > 0) + cdo->AttributeTags = CreateTags(AttributeTags); + if (ApplyTags.Num() > 0) + cdo->ApplyTags = CreateTags(ApplyTags); + + cdo->RequiredTags = TagsIn.RequiredTags; + cdo->DenyTags = TagsIn.DenyTags; + cdo->ExecutionRequiredTags = TagsIn.OngoingRequiredTags; + cdo->bExecuteOnApplication = InExecuteOnApplication; + FGAAttributeModifier AttributeModifier; + AttributeModifier.Attribute = FGAAttribute(Attribute); + AttributeModifier.AttributeMod = ModType; + AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; + AttributeModifier.Magnitude.DirectModifier.Value = ModValue; + cdo->AtributeModifier = AttributeModifier; + FGAMagnitude DurationMag; + DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; + DurationMag.DirectModifier.Value = Duration; + cdo->Duration = DurationMag; + FGAMagnitude PeriodMag; + PeriodMag.CalculationType = EGAMagnitudeCalculation::Direct; + PeriodMag.DirectModifier.Value = PeriodSecs; + cdo->Period = PeriodMag; + return Spec; + } + + FGAEffectProperty CreateEffectInfiniteSpec(const TArray& OwnedTags, float ModValue, + EGAAttributeMod ModType, const FName& Attribute, EGAEffectStacking Stacking, + const TArray& AttributeTags = TArray(), + const TArray& ApplyTags = TArray(), + const FTagsInput& TagsIn = FTagsInput(), + TSubclassOf CDO = UGAGameEffectSpec::StaticClass(), + TSubclassOf ApplReq = UAFEffectApplicationRequirement::StaticClass(), + TSubclassOf Appl = UAFEffectCustomApplication::StaticClass() + ) + { + const float Duration = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + FGAEffectProperty Spec; + Spec = CDO; + UGAGameEffectSpec* cdo = Spec.GetClass().GetDefaultObject(); + + //UClass* clas = DuplicateObject(UGAGameEffectSpec::StaticClass()); + //Spec.Spec = + cdo->ApplicationRequirement = ApplReq; + cdo->Application = Appl; + cdo->ExecutionType = UGAEffectExecution::StaticClass(); + cdo->OwnedTags = CreateTags(OwnedTags); + cdo->bExecuteOnApplication = true; + if (AttributeTags.Num() > 0) + cdo->AttributeTags = CreateTags(AttributeTags); + if (ApplyTags.Num() > 0) + cdo->ApplyTags = CreateTags(ApplyTags); + + cdo->RequiredTags = TagsIn.RequiredTags; + cdo->DenyTags = TagsIn.DenyTags; + cdo->ExecutionRequiredTags = TagsIn.OngoingRequiredTags; + + FGAAttributeModifier AttributeModifier; + AttributeModifier.Attribute = FGAAttribute(Attribute); + AttributeModifier.AttributeMod = ModType; + AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; + AttributeModifier.Magnitude.DirectModifier.Value = ModValue; + cdo->AtributeModifier = AttributeModifier; + FGAMagnitude DurationMag; + DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; + DurationMag.DirectModifier.Value = Duration; + cdo->Duration = DurationMag; + + return Spec; + } + + void ApplyEffectModifiers() + { + + } + void Test_CompareTagContainers() + { + TArray OwnedTags1; + OwnedTags1.Add(TEXT("Damage.Ice")); + OwnedTags1.Add(TEXT("Damage.Spell")); + FGameplayTagContainer A = CreateTags(OwnedTags1); + + TArray OwnedTags2; + OwnedTags2.Add(TEXT("Damage")); + FGameplayTagContainer B = CreateTags(OwnedTags2); + + TArray OwnedTags3; + OwnedTags3.Add(TEXT("Damage.Spell")); + FGameplayTagContainer C = CreateTags(OwnedTags3); + + TArray OwnedTags4; + OwnedTags4.Add(TEXT("Damage.Ice")); + OwnedTags4.Add(TEXT("Damage.Spell")); + OwnedTags4.Add(TEXT("Ability.Fireball")); + + FGameplayTagContainer Ability = CreateTags(OwnedTags4); + + bool A_Ability = A.HasAll(Ability); //false + bool B_Ability = B.HasAll(Ability); //false + bool C_Ability = C.HasAll(Ability); //false + + Test->TestFalse("A_ABility: ", A_Ability); + Test->TestFalse("B_ABility: ", B_Ability); + Test->TestFalse("C_ABility: ", C_Ability); + + bool Ability_A = Ability.HasAll(A); //true + bool Ability_B = Ability.HasAll(B); //true + bool Ability_C = Ability.HasAll(C); //true + Test->TestTrue("Ability_A: ", Ability_A); + Test->TestTrue("Ability_B: ", Ability_B); + Test->TestTrue("Ability_C: ", Ability_C); + } + + void Test_InstantEffectApplication() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + FGAEffectProperty Effect = CreateEffectSpec(OwnedTags, 10, + EGAAttributeMod::Subtract, "Health", UGAGameEffectSpec::StaticClass()); + + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Post: ", PostVal, 90.0f); + } + //Damage.Fire + //Damage.Basic + //Damage.Buffed.FireBuff + //Damage.Acid + //Buff + //Immune + //Item + //Item.Rune + //Spell + //Stackable + //Attribute.Health + //Condition.Burning + void Test_PeriodicDamageEffect() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + AttributeTags.Add(TEXT("Buff")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Buff")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 5, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + ++NumApplications; + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Post: ", PostVal, 100.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + + ++NumApplications; + + // check that health has been reduced + + } + TickWorld(PeriodSecs); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 55.0f); + } + + void Test_DurationBuffEffect() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 5, + EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass()); + + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + + ++NumApplications; + + // check that health has been reduced + + } + TickWorld(PeriodSecs); + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Post: ", PostVal, 55.0f); + } + + void Test_AtttributeStatckingOverride() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Energy"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), + UAFAttributeDurationOverride::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + + + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Energy")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Energy")); + TestEqual("Source Health PPost: ", PostVal, 150.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, + EGAAttributeMod::Add, TEXT("Energy"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), + UAFAttributeDurationOverride::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Energy")); + TestEqual("Source Health Post2: ", PostVal2, 130.0f); + } + + // check that health has been reduced + + } + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Energy")); + TestEqual("Source Health Finished: ", FinishedVal, 100.0f); + } + + void Test_AtttributeStatckingStrongerOverride() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), + UAFAttributeDurationOverride::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 150.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, + EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), + UAFAttributeDurationOverride::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + //for (int32 i = 0; i < NumPeriods; ++i) + //{ + // // advance time by one period + // TickWorld(PeriodSecs); + //} + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 100.0f); + } + + void Test_AtttributeStatckingStrongerOverrideReversed() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 30, + EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), + UAFAttributeDurationOverride::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 130.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), + UAFAttributeDurationOverride::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 100.0f); + } + + void Test_AtttributeStatckingeAdd() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), + UAFAtributeDurationAdd::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PPost: ", PostVal, 150.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, + EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), + UAFAtributeDurationAdd::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Post2: ", PostVal2, 180.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PreFinished: ", PreFinishedVal, 130.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Finished: ", FinishedVal, 100.0f); + } + void Test_AtttributeStatckingeAddSameProp() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), + UAFAtributeDurationAdd::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PPost: ", PostVal, 150.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Post2: ", PostVal2, 200.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PreFinished: ", PreFinishedVal, 150.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Finished: ", FinishedVal, 100.0f); + } + + void Test_AtttributeStatckingeAddSamePropDifferentTargets() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), + UAFAtributeDurationAdd::StaticClass(), + UGAGameEffectSpec::StaticClass() + ); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PPost: ", PostVal, 150.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, TargetOne, SourceActor, SourceActor, FuncMod); + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = TargetCompOne->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("TargetCompOne Stamina PreFinished: ", PreFinishedVal, 150.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Finished: ", FinishedVal, 100.0f); + + float TargetOneFinish = TargetCompOne->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("TargetCompOne Stamina PreFinished: ", TargetOneFinish, 100.0f); + } + + void Test_AtttributeStatckingeAddInfinite() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectInfiniteSpec(OwnedTags, 50, + EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFEffectApplicationRequirement::StaticClass(), + UAFAttributeDurationInfinite::StaticClass() + ); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PPost: ", PostVal, 150.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + //if (i == 5) + //{ + // FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, + // EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, + // AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass()); + // UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + // float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + // TestEqual("Source Stamina Post2: ", PostVal2, 180.0f); + //} + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina PreFinished: ", PreFinishedVal, 150.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Finished: ", FinishedVal, 150.0f); + DestComponent->RemoveEffect(Effect); + float PostRemovedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); + TestEqual("Source Stamina Finished: ", PostRemovedVal, 100.0f); + } + + void Test_EffectStatckingOverride() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 5, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost2: ", PostVal2, 70.0f); + FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 32.0f); + } + + void Test_EffectStatckingOverrideSameClass() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 5, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost2: ", PostVal2, 70.0f); + FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, + AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 32.0f); + } + + void Test_EffectStatckingAdd() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationAdd::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost2: ", PostVal2, 88.0f); + FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, + AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), + UAFPeriodApplicationAdd::StaticClass()); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 74.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 62.0f); + } + + void Test_EffectStatckingAddSameHandle() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationAdd::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost2: ", PostVal2, 88.0f); + /*FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, + AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), + UAFPeriodApplicationAdd::StaticClass());*/ + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 74.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 62.0f); + } + + void Test_EffectStatckingAddSameHandleDifferentTargets() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationAdd::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + //TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("DestComponent Health PPost2: ", PostVal2, 88.0f); + + /*FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, + AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), + UAFPeriodApplicationAdd::StaticClass());*/ + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, TargetOne, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + UE_LOG(AbilityFramework, Log, TEXT("Val: %d"), i * 2); + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("DestComponent Health PreFinishedVal: ", PreFinishedVal, 80.0f);; + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = TargetCompOne->GetAttributeValue(FGAAttribute("Health")); + TestEqual("TargetCompOne Health Finished: ", FinishedVal, 82.0f); + } + + + void Test_EffectStatckingDurationDifferentEffects() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 1, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost2: ", PostVal2, 94.0f); + FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, + AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), + UAFPeriodApplicationOverride::StaticClass()); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 84.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 72.0f); + } + + void Test_EffectStatckingDurationSameEffects() + { + TArray OwnedTags; + OwnedTags.Add("Ability.Fireball"); + TArray AttributeTags; + AttributeTags.Add(TEXT("Damage.Fire")); + + TArray ApplyTags; + ApplyTags.Add(TEXT("Damage.Fire")); + ApplyTags.Add(TEXT("Ability.Fireball")); + + FTagsInput TagsIn; + + FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationExtend::StaticClass()); + + int32 NumApplications = 0; + float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Pre: ", PreVal, 100.0f); + FAFFunctionModifier FuncMod; + UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); + + TickWorld(SMALL_NUMBER); + //++NumApplications; + float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost: ", PostVal, 100.0f); + const int32 NumPeriods = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + TickWorld(PeriodSecs * .1f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + if (i == 5) + { + float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PPost2: ", PostVal2, 88.0f); + FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, + EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, + AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), + UAFPeriodApplicationExtend::StaticClass()); + UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); + //TestEqual("Source Health Post2: ", PostVal2, 150.0f); + } + + // check that health has been reduced + + } + float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 80.0f); + for (int32 i = 0; i < NumPeriods; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + } + TickWorld(PeriodSecs * 0.1f); + float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); + TestEqual("Source Health Finished: ", FinishedVal, 60.0f); + } + + void Test_StrongerOverrideNonStackingHealthBonus() + { + const float Duration = 10; + const float PeriodSecs = 1.0f; + const float DamagePerPeriod = 5.f; + for (int32 i = 0; i < 9; ++i) + { + // advance time by one period + TickWorld(PeriodSecs); + //++NumApplications;; + } + + // advance time by one extra period + TickWorld(PeriodSecs); + } + +}; +#define ADD_TEST(Name) \ + TestFunctions.Add(&GameEffectsTestSuite::Name); \ + TestFunctionNames.Add(TEXT(#Name)) + + + +class FGAAttributesTests : public FAutomationTestBase +{ +public: + typedef void (GameEffectsTestSuite::*TestFunc)(); + TArray TestFunctions; + TArray TestFunctionNames; + + FGAAttributesTests(const FString& InName) + : FAutomationTestBase(InName, false) + { + ADD_TEST(Test_CompareTagContainers); + ADD_TEST(Test_InstantEffectApplication); + ADD_TEST(Test_PeriodicDamageEffect); + ADD_TEST(Test_AtttributeStatckingOverride); + ADD_TEST(Test_AtttributeStatckingStrongerOverride); + ADD_TEST(Test_AtttributeStatckingStrongerOverrideReversed); + ADD_TEST(Test_AtttributeStatckingeAdd); + ADD_TEST(Test_AtttributeStatckingeAddSameProp); + ADD_TEST(Test_AtttributeStatckingeAddSamePropDifferentTargets); + ADD_TEST(Test_AtttributeStatckingeAddInfinite); + ADD_TEST(Test_EffectStatckingOverride); + ADD_TEST(Test_EffectStatckingOverrideSameClass); + ADD_TEST(Test_EffectStatckingAdd); + ADD_TEST(Test_EffectStatckingAddSameHandle); + ADD_TEST(Test_EffectStatckingAddSameHandleDifferentTargets); + ADD_TEST(Test_EffectStatckingDurationDifferentEffects); + ADD_TEST(Test_EffectStatckingDurationSameEffects); + ADD_TEST(Test_StrongerOverrideNonStackingHealthBonus); + }; + virtual uint32 GetTestFlags() const override + { + //EAutomationTestFlags::Type::EditorContext | + return (EAutomationTestFlags::Type::EngineFilter); + }//EAutomationTestFlags::EditorContext | EAutomationTestFlags::SmokeFilter; } + virtual bool IsStressTest() const { return false; } + virtual uint32 GetRequiredDeviceNum() const override { return 1; } + + virtual FString GetBeautifiedTestName() const override { return TEXT("GameAttributes.Attributes"); } + virtual void GetTests(TArray& OutBeautifiedNames, TArray & OutTestCommands) const override + { + for (const FString& TestFunctionName : TestFunctionNames) + { + OutBeautifiedNames.Add(TestFunctionName); + OutTestCommands.Add(TestFunctionName); + } + } + bool RunTest(const FString& Parameters) + { + TestFunc TestFunction = nullptr; + for (int32 i = 0; i < TestFunctionNames.Num(); ++i) + { + if (TestFunctionNames[i] == Parameters) + { + TestFunction = TestFunctions[i]; + break; + } + } + if (TestFunction == nullptr) + { + return false; + } + //UDataTable* TagTable = CreateGameplayDataTable(); + + //IGameplayTagsModule::Get().GetGameplayTagsManager().PopulateTreeFromDataTable(TagTable); + IGameplayTagsModule& GameplayTagsModule = IGameplayTagsModule::Get(); + TArray TagsList; + + FString ItemTags = "/Game/Data/GameplayTags/DamageStatusTags.DamageStatusTags"; + TagsList.Add(ItemTags); + + UGameplayTagsManager::Get().DestroyGameplayTagTree(); + //UGameplayTagsManager::Get().LoadGameplayTagTables(); + UGameplayTagsManager::Get().ConstructGameplayTagTree(); + + UWorld *World = UWorld::CreateWorld(EWorldType::Game, false); + FWorldContext &WorldContext = GEngine->CreateNewWorldContext(EWorldType::Game); + WorldContext.SetCurrentWorld(World); + + FURL URL; + World->InitializeActorsForPlay(URL); + World->BeginPlay(); + + // run the matching test + uint64 InitialFrameCounter = GFrameCounter; + { + GameEffectsTestSuite Tester(World, this); + (Tester.*TestFunction)(); + } + GFrameCounter = InitialFrameCounter; + + GEngine->DestroyWorldContext(World); + World->DestroyWorld(false); + return true; + } +}; + +namespace AbilityFrameworkTests +{ + FGAAttributesTests FGAAttributesTestsAutomationTestInstance(TEXT("FGAAttributesTests")); +} + +#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp new file mode 100644 index 0000000..a5f345f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp @@ -0,0 +1,71 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAAbilitiesComponent.h" +#include "GACharacterAttributeTest.h" + + +// Sets default values +AGACharacterAttributeTest::AGACharacterAttributeTest() +{ + // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + Attributes = CreateDefaultSubobject(TEXT("Attributes")); +} + +// Called when the game starts or when spawned +void AGACharacterAttributeTest::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AGACharacterAttributeTest::Tick( float DeltaTime ) +{ + Super::Tick( DeltaTime ); + +} + +// Called to bind functionality to input +void AGACharacterAttributeTest::SetupPlayerInputComponent(class UInputComponent* InInputComponent) +{ + Super::SetupPlayerInputComponent(InputComponent); + +} + +class UGAAttributesBase* AGACharacterAttributeTest::GetAttributes() +{ + return Attributes->DefaultAttributes; +} +class UGAAbilitiesComponent* AGACharacterAttributeTest::GetAbilityComp() +{ + return Attributes; +} +void AGACharacterAttributeTest::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + FGAEffectProperty& InProperty) +{ + GetAttributes()->ModifyAttribute(ModIn, HandleIn, InProperty); +} + +FAFAttributeBase* AGACharacterAttributeTest::GetAttribute(FGAAttribute AttributeIn) +{ + return GetAttributes()->GetAttribute(AttributeIn); +} +void AGACharacterAttributeTest::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) +{ + GetAttribute(AttributeIn)->RemoveBonus(HandleIn, InMod); +} +FGAEffectHandle AGACharacterAttributeTest::ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) +{ + return GetAbilityComp()->ApplyEffectToTarget(EffectIn, InProperty, InContext); +}; +void AGACharacterAttributeTest::RemoveTagContainer(const FGameplayTagContainer& TagsIn) +{ + GetAbilityComp()->RemoveTagContainer(TagsIn); +} +float AGACharacterAttributeTest::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return 0; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h new file mode 100644 index 0000000..fbf06e4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h @@ -0,0 +1,41 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Character.h" +#include "../IGAAbilities.h" +#include "GACharacterAttributeTest.generated.h" + +UCLASS() +class ABILITYFRAMEWORK_API AGACharacterAttributeTest : public ACharacter, public IIGAAbilities +{ + GENERATED_BODY() +public: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Attributes") + class UGAAbilitiesComponent* Attributes; +public: + // Sets default values for this character's properties + AGACharacterAttributeTest(); + + // Called when the game starts or when spawned + virtual void BeginPlay() override; + + // Called every frame + virtual void Tick( float DeltaSeconds ) override; + + // Called to bind functionality to input + virtual void SetupPlayerInputComponent(class UInputComponent* InInputComponent) override; + + + virtual class UGAAttributesBase* GetAttributes() override; + virtual class UGAAbilitiesComponent* GetAbilityComp() override; + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override { return 0; }; + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// override { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn);// override { return DefaultAttributes->GetAttribute(AttributeIn); }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty, FGAEffectContext& InContext) override;// { return ApplyEffectToTarget(EffectIn, HandleIn); }; + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const;// override { return 0; }; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp new file mode 100644 index 0000000..e0c66ba --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAAttributesTest.h" +#include "GACustomCalculationTest.h" + + + + +float UGACustomCalculationTest::NativeCalculateMagnitude(const FGAEffectHandle& HandleIn) +{ + UGAAttributesTest* InstAttr = Cast(HandleIn.GetContext().GetInstigatorAttributes()); + UGAAttributesTest* TargetAttr = Cast(HandleIn.GetContext().GetTargetAttributes()); + if (InstAttr && TargetAttr) + { + FGAIndividualMods ModsOut; + /*float MagicBonus = InstAttr->MagicalBonus.GetFinalValueByTags(HandleIn.GetOwnedTags(), ModsOut); + float MagicResistance = TargetAttr->MagicResistance.GetFinalValueByTags(HandleIn.GetOwnedTags(), ModsOut); + return MagicBonus - MagicResistance;*/ + } + return 0; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h new file mode 100644 index 0000000..3e212b2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "../Effects/GACustomCalculation.h" +#include "GACustomCalculationTest.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGACustomCalculationTest : public UGACustomCalculation +{ + GENERATED_BODY() + +public: + virtual float NativeCalculateMagnitude(const FGAEffectHandle& HandleIn) override; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp new file mode 100644 index 0000000..dca71e3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp @@ -0,0 +1,15 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GameplayTagContainer.h" +#include "../GAAbilitiesComponent.h" +#include "../Attributes/GAAttributesBase.h" +#include "GASpellExecutionTest.h" + +#include "Effects/GAGameEffect.h" + +UGASpellExecutionTest::UGASpellExecutionTest(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h new file mode 100644 index 0000000..04efdee --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h @@ -0,0 +1,15 @@ +#pragma once +#include "../Effects/GAEffectExecution.h" +#include "../Effects/GAGameEffect.h" +#include "GASpellExecutionTest.generated.h" + +/* + +*/ +UCLASS(BlueprintType, Blueprintable) +class UGASpellExecutionTest : public UGAEffectExecution +{ + GENERATED_BODY() +public: + UGASpellExecutionTest(const FObjectInitializer& ObjectInitializer); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp new file mode 100644 index 0000000..2f65d91 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAffectSpecTestOne.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h new file mode 100644 index 0000000..afa2a74 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "GAffectSpecTestOne.generated.h" + +/** + * + */ +UCLASS(NotBlueprintType, NotBlueprintable) +class ABILITYFRAMEWORK_API UGAffectSpecTestOne : public UGAGameEffectSpec +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp new file mode 100644 index 0000000..02f483d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp @@ -0,0 +1,75 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityActivationSpec.h" +#include "AFAbilityActionSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityActivationSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityActivationSpecDetails); +} + +void FAFAbilityActivationSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityActivationSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityActivationSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityActivationSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h new file mode 100644 index 0000000..75a6c49 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityActivationSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + FSimpleDelegate UpdateEffectTypeyDelegate; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp new file mode 100644 index 0000000..217ee21 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp @@ -0,0 +1,75 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityCooldownSpec.h" +#include "AFAbilityCooldownSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityCooldownSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityCooldownSpecDetails); +} + +void FAFAbilityCooldownSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityCooldownSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityCooldownSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityCooldownSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h new file mode 100644 index 0000000..be653a3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h @@ -0,0 +1,30 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityCooldownSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp new file mode 100644 index 0000000..9119b69 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp @@ -0,0 +1,81 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityPeriodSpec.h" +#include "AFAbilityPeriodSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityPeriodSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityPeriodSpecDetails); +} + +void FAFAbilityPeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityPeriodSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityPeriodSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); + + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityPeriodSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h new file mode 100644 index 0000000..b5e4527 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityPeriodSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + TSharedPtr PeriodCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp new file mode 100644 index 0000000..b8105cb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp @@ -0,0 +1,89 @@ + +#include "AbilityFrameworkEditor.h" +#include "Kismet/KismetMathLibrary.h" +#include "Kismet/KismetArrayLibrary.h" +#include "GameplayTask.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "Abilities/AFBlueprintFunctionLibrary.h" +#include "Effects/GAEffectExtension.h" +#include "KismetCompiler.h" +#include "BlueprintEditorUtils.h" +#include "AFEK2Node_AsyncEffectTaskCall.h" +#include "K2Node_EnumLiteral.h" +#include "BlueprintFunctionNodeSpawner.h" +#include "BlueprintActionDatabaseRegistrar.h" + +#define LOCTEXT_NAMESPACE "K2Node" + +UAFEK2Node_AsyncEffectTaskCall::UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + if (HasAnyFlags(RF_ClassDefaultObject) == true) + { + UK2Node_LatentGameplayTaskCall::RegisterSpecializedTaskNodeClass(GetClass()); + } +} + +bool UAFEK2Node_AsyncEffectTaskCall::IsHandling(TSubclassOf TaskClass) const +{ + bool isChilldOf = TaskClass && TaskClass->IsChildOf(UAFEffectTask::StaticClass()); + return isChilldOf; +} + +bool UAFEK2Node_AsyncEffectTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const +{ + bool bIsCompatible = false; + + EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); + bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); + + if (bAllowLatentFuncs) + { + UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); + if (MyBlueprint && MyBlueprint->GeneratedClass) + { + if (MyBlueprint->GeneratedClass->IsChildOf(UGAEffectExtension::StaticClass())) + { + bIsCompatible = true; + } + } + } + return bIsCompatible; +} + + +void UAFEK2Node_AsyncEffectTaskCall::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const +{ + //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); + struct GetMenuActions_Utils + { + static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) + { + UAFEK2Node_AsyncEffectTaskCall* AsyncTaskNode = CastChecked(NewNode); + if (FunctionPtr.IsValid()) + { + UFunction* Func = FunctionPtr.Get(); + UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); + + AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); + AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); + AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; + } + } + }; + + UClass* NodeClass = GetClass(); + //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + { + UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); + check(NodeSpawner != nullptr); + NodeSpawner->NodeClass = NodeClass; + + TWeakObjectPtr FunctionPtr = FactoryFunc; + NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); + return NodeSpawner; + })); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h new file mode 100644 index 0000000..0762b9c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h @@ -0,0 +1,23 @@ + +#pragma once +#include "EdGraph/EdGraphPin.h" +#include "EdGraphSchema_K2.h" +#include "K2Node_BaseAsyncTask.h" +#include "K2Node_LatentGameplayTaskCall.h" +#include "AFEK2Node_AsyncEffectTaskCall.generated.h" + +UCLASS() +class UAFEK2Node_AsyncEffectTaskCall : public UK2Node_LatentGameplayTaskCall +{ + GENERATED_BODY() + +public: + UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer); + + // UEdGraphNode interface + virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; + virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; + // End of UEdGraphNode interface +protected: + virtual bool IsHandling(TSubclassOf TaskClass) const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp new file mode 100644 index 0000000..4fb874d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp @@ -0,0 +1,109 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFrameworkEditor.h" +#include "Effects/GAGameEffect.h" +#include "DetailLayoutBuilder.h" +#include "DetailCategoryBuilder.h" +#include "AFEffectCustomizationCommon.h" + +FAFEffectCustomizationCommon::FAFEffectCustomizationCommon() +{ +} + +FAFEffectCustomizationCommon::~FAFEffectCustomizationCommon() +{ +} +void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, + TSharedPtr& InProperty, FName InCategory) +{ + + IDetailCategoryBuilder& DurationCategory = DetailLayout.EditCategory(InCategory); + TSharedPtr DurationCalcTypeProp = InProperty->GetChildHandle("CalculationType"); + + uint8 CalcType = 0; + DurationCalcTypeProp->GetValue(CalcType); + + TSharedPtr DirectModifier = InProperty->GetChildHandle("DirectModifier"); + TSharedPtr AttributeBased = InProperty->GetChildHandle("AttributeBased"); + TSharedPtr CurveBased = InProperty->GetChildHandle("CurveBased"); + TSharedPtr Custom = InProperty->GetChildHandle("Custom"); + + DurationCategory.AddProperty(DurationCalcTypeProp.ToSharedRef()); + switch (CalcType) + { + case 0: //Direct + { + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Value = DirectModifier->GetChildHandle("Value"); + DurationCategory.AddProperty(Value.ToSharedRef()); + break; + } + case 1: //AttributeBased + { + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Source = AttributeBased->GetChildHandle("Source"); + TSharedPtr Attribute = AttributeBased->GetChildHandle("Attribute"); + TSharedPtr Coefficient = AttributeBased->GetChildHandle("Coefficient"); + TSharedPtr PreMultiply = AttributeBased->GetChildHandle("PreMultiply"); + TSharedPtr PostMultiply = AttributeBased->GetChildHandle("PostMultiply"); + TSharedPtr PostCoefficient = AttributeBased->GetChildHandle("PostCoefficient"); + TSharedPtr bUseSecondaryAttribute = AttributeBased->GetChildHandle("bUseSecondaryAttribute"); + TSharedPtr SecondarySource = AttributeBased->GetChildHandle("SecondarySource"); + TSharedPtr SecondaryAttribute = AttributeBased->GetChildHandle("SecondaryAttribute"); + + DurationCategory.AddProperty(Source.ToSharedRef()); + DurationCategory.AddProperty(Attribute.ToSharedRef()); + DurationCategory.AddProperty(Coefficient.ToSharedRef()); + DurationCategory.AddProperty(PreMultiply.ToSharedRef()); + DurationCategory.AddProperty(PostMultiply.ToSharedRef()); + DurationCategory.AddProperty(PostCoefficient.ToSharedRef()); + DurationCategory.AddProperty(bUseSecondaryAttribute.ToSharedRef()); + DurationCategory.AddProperty(SecondarySource.ToSharedRef()); + DurationCategory.AddProperty(SecondaryAttribute.ToSharedRef()); + + break; + } + case 2: //CurveBased + { + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Source = CurveBased->GetChildHandle("Source"); + TSharedPtr Attribute = CurveBased->GetChildHandle("Attribute"); + TSharedPtr CurveTable = CurveBased->GetChildHandle("CurveTable"); + + DurationCategory.AddProperty(Source.ToSharedRef()); + DurationCategory.AddProperty(Attribute.ToSharedRef()); + DurationCategory.AddProperty(CurveTable.ToSharedRef()); + break; + } + case 3: //CustomCalculation + { + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(Custom); + + TSharedPtr CustomCalculation = Custom->GetChildHandle("CustomCalculation"); + DurationCategory.AddProperty(CustomCalculation.ToSharedRef()); + break; + } + } +} +void FAFEffectCustomizationCommon::HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName) +{ + UProperty* prop = UGAGameEffectSpec::StaticClass()->FindPropertyByName(InName); + + TSharedPtr Property = DetailLayout.GetProperty(InName, UGAGameEffectSpec::StaticClass()); + DetailLayout.HideProperty(Property); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h new file mode 100644 index 0000000..2c495a7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IDetailCustomization.h" +#include "PropertyHandle.h" +/** + * + */ +class ABILITYFRAMEWORKEDITOR_API FAFEffectCustomizationCommon +{ +public: + FAFEffectCustomizationCommon(); + ~FAFEffectCustomizationCommon(); + static void CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, + TSharedPtr& InProperty, FName InCategory); + static void HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp new file mode 100644 index 0000000..0e2b42a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "AssetTypeActions_GAAbilityBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "GAAbilityEditor.h" +#include "Abilities/GAAbilityBlueprint.h" +#include "Abilities/GAAbilityBase.h" +#include "GAAbilityBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_GAAbilityBlueprint::GetName() const +{ + return FText::FromString("Ability"); +} +UClass* FAssetTypeActions_GAAbilityBlueprint::GetSupportedClass() const +{ + return UGAAbilityBlueprint::StaticClass(); +} + +void FAssetTypeActions_GAAbilityBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FGAAbilityEditor > NewEditor(new FGAAbilityEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitAbilitiesEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_GAAbilityBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return false; +} + +UFactory* FAssetTypeActions_GAAbilityBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UGAAbilityBlueprintFactory* AbilityBlueprintFactory = NewObject(); + AbilityBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return AbilityBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h new file mode 100644 index 0000000..b1762c2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" +//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" +#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_GAAbilityBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp new file mode 100644 index 0000000..ca4698b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp @@ -0,0 +1,334 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityBlueprintFactory.h" +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Effects/GAGameEffect.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "Abilities/GAAbilityBlueprint.h" +#include "Abilities/GAAbilityBase.h" +#include "GAAbilityGraph.h" +#include "GAAbilityGraphSchema.h" + +#include "ClassViewerFilter.h" + +#include "SlateOptMacros.h" + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SAbilityBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAbilityBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UGAAbilityBase::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SAbilityBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SAbilityBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied AbilitiesBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InAbilitiesBlueprintFactory) + { + AbilitiesBlueprintFactory = InAbilitiesBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Ability Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + AbilitiesBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FAbilityBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FAbilityBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FAbilityBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(UGAAbilityBase::StaticClass()); + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SAbilityBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (AbilitiesBlueprintFactory.IsValid()) + { + AbilitiesBlueprintFactory->BlueprintType = BPTYPE_Normal; + AbilitiesBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr AbilitiesBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UAbilitiesBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UGAAbilityBlueprintFactory::UGAAbilityBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UGAAbilityBlueprint::StaticClass(); + ParentClass = UGAAbilityBase::StaticClass(); +} + +bool UGAAbilityBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SAbilityBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UGAAbilityBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(UGAAbilityBase::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UGAAbilityBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAAbilityBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { + UGAAbilityBlueprint* AbilityBP = UGAAbilityBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + if (AbilityBP == NULL) + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + + // Only allow a gameplay ability graph if there isn't one in a parent blueprint + UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAAbilityGraph::StaticClass(), UGAAbilityGraphSchema::StaticClass()); +#if WITH_EDITORONLY_DATA + if (NewBP->UbergraphPages.Num()) + { + FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); + } +#endif + FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); + NewBP->LastEditedDocuments.Add(NewGraph); + NewGraph->bAllowDeletion = false; + + UBlueprintEditorSettings* Settings = GetMutableDefault(); + if(Settings && Settings->bSpawnDefaultBlueprintNodes) + { + int32 NodePositionY = 0; + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + } + } + } + + return NewBP; + } +} + +UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h new file mode 100644 index 0000000..ec61b23 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "GAAbilityBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UGAAbilityBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp new file mode 100644 index 0000000..ef34e13 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp @@ -0,0 +1,142 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityEditor.h" +#include "EditorReimportHandler.h" + +#if WITH_EDITOR +#include "Editor.h" +#endif +#include "ISequencerModule.h" +#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" +#include "Toolkits/ToolkitManager.h" +#include "Toolkits/GlobalEditorCommonCommands.h" + +#include "Abilities/GAAbilityBlueprint.h" +#include "GAAbilityBlueprintFactory.h" +#include "GAAbilityGraphSchema.h" +#include "Kismet2/BlueprintEditorUtils.h" + +#define LOCTEXT_NAMESPACE "FGAAbilityEditor" + + +///////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +FGAAbilityEditor::FGAAbilityEditor() +{ + +} + +FGAAbilityEditor::~FGAAbilityEditor() +{ + FEditorDelegates::OnAssetPostImport.RemoveAll(this); + FReimportManager::Instance()->OnPostReimport().RemoveAll(this); + + // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor +} +void FGAAbilityEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) +{ + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, ObjectsToEdit, bInIsToolbarFocusable); +} +void FGAAbilityEditor::InitAbilitiesEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) +{ + InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); + + for (auto Blueprint : InBlueprints) + { + EnsureAbilityBlueprintIsUpToDate(Blueprint); + } +} + +void FGAAbilityEditor::EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint) +{ +#if WITH_EDITORONLY_DATA + int32 Count = Blueprint->UbergraphPages.Num(); + for (auto Graph : Blueprint->UbergraphPages) + { + // remove the default event graph, if it exists, from existing Gameplay Ability Blueprints + if (Graph->GetName() == "EventGraph" && Graph->Nodes.Num() == 0) + { + check(!Graph->Schema->GetClass()->IsChildOf(UGAAbilityGraphSchema::StaticClass())); + FBlueprintEditorUtils::RemoveGraph(Blueprint, Graph); + break; + } + } +#endif +} +bool FGAAbilityEditor::IsBlueprintEditor() const +{ + return true; +} +// FRED_TODO: don't merge this back +// FName FGameplayAbilitiesEditor::GetToolkitContextFName() const +// { +// return GetToolkitFName(); +// } + +FName FGAAbilityEditor::GetToolkitFName() const +{ + return FName("GameAbilityEditor"); +} + +FText FGAAbilityEditor::GetBaseToolkitName() const +{ + return FText::FromString("Game Ability Editor"); +} + +FText FGAAbilityEditor::GetToolkitName() const +{ + const TArray& EditingObjs = GetEditingObjects(); + + check(EditingObjs.Num() > 0); + + FFormatNamedArguments Args; + + const UObject* EditingObject = EditingObjs[0]; + + const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); + + Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(FText::FromString("{ObjectName}{DirtyState}"), Args); +} + +FText FGAAbilityEditor::GetToolkitToolTipText() const +{ + const UObject* EditingObject = GetEditingObject(); + + check (EditingObject != NULL); + + return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); +} + +FString FGAAbilityEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("AbilityEditor"); +} + +FLinearColor FGAAbilityEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +UBlueprint* FGAAbilityEditor::GetBlueprintObj() const +{ + const TArray& EditingObjs = GetEditingObjects(); + for (int32 i = 0; i < EditingObjs.Num(); ++i) + { + if (EditingObjs[i]->IsA()) + { + return (UBlueprint*)EditingObjs[i]; + } + } + return nullptr; +} + +FString FGAAbilityEditor::GetDocumentationLink() const +{ + return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h new file mode 100644 index 0000000..cfd9ffa --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h @@ -0,0 +1,64 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Framework/Commands/UICommandList.h" +#include "Framework/MultiBox/MultiBoxExtender.h" +#include "GraphEditor.h" +#include "ISequencer.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" + +////////////////////////////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +/** + * Gameplay abilities asset editor (extends Blueprint editor) + */ +class FGAAbilityEditor : public FBlueprintEditor +{ +public: + virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; + /** + * Edits the specified gameplay ability asset(s) + * + * @param Mode Asset editing mode for this editor (standalone or world-centric) + * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within + * @param InBlueprints The blueprints to edit + * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode + */ + + void InitAbilitiesEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); + +private: + /** + * Updates existing gameplay ability blueprints to make sure that they are up to date + * + * @param Blueprint The blueprint to be updated + */ + void EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint); + +public: + FGAAbilityEditor(); + + virtual ~FGAAbilityEditor(); + +public: + // IToolkit interface + // FRED_TODO: don't merge this back +// virtual FName GetToolkitContextFName() const override; + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual bool IsBlueprintEditor() const override; + // End of IToolkit interface + + /** @return the documentation location for this editor */ + virtual FString GetDocumentationLink() const override; + + /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ + virtual UBlueprint* GetBlueprintObj() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp new file mode 100644 index 0000000..da482a3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityGraph.h" + +#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" + +///////////////////////////////////////////////////// +// UGameplayAbilityGraph + +UGAAbilityGraph::UGAAbilityGraph(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h new file mode 100644 index 0000000..dcc6890 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraph/EdGraph.h" +#include "GAAbilityGraph.generated.h" + +UCLASS(MinimalAPI) +class UGAAbilityGraph : public UEdGraph +{ + GENERATED_UCLASS_BODY() +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp new file mode 100644 index 0000000..f51d3ff --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityGraphSchema.h" +#include "EdGraphSchema_K2_Actions.h" +#include "Effects/GAGameEffect.h" +#include "Kismet2/BlueprintEditorUtils.h" + +UGAAbilityGraphSchema::UGAAbilityGraphSchema(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UK2Node_VariableGet* UGAAbilityGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); +} + +UK2Node_VariableSet* UGAAbilityGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h new file mode 100644 index 0000000..1c099f8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h @@ -0,0 +1,38 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraphSchema_K2.h" +#include "GAAbilityGraphSchema.generated.h" + +UCLASS(MinimalAPI) +class UGAAbilityGraphSchema : public UEdGraphSchema_K2 +{ + GENERATED_UCLASS_BODY() + + /** + * Creates a new variable getter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + /** + * Creates a new variable setter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs new file mode 100644 index 0000000..80e2c53 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs @@ -0,0 +1,94 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +using UnrealBuildTool; +using System.IO; +namespace UnrealBuildTool.Rules +{ + public class AbilityFrameworkEditor : ModuleRules + { + public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) + { + var EngineDir = Path.GetFullPath(BuildConfiguration.RelativeEnginePath); + PublicIncludePaths.AddRange( + new string[] { + "AbilityFramework", + "AbilityFramework/Public", + // "GameAttributesEditor", + "AbilityFramework/Public" + // ... add public include paths required here ... + } + ); + + PrivateIncludePaths.AddRange( + new string[] { + "AbilityFrameworkEditor/Private", + Path.Combine(EngineDir, @"Source/Editor/GraphEditor/Private"), + Path.Combine(EngineDir, @"Source/Editor/Kismet/Private"), + Path.Combine(EngineDir, @"Source/Editor/PropertyEditor/Private"), + Path.Combine(EngineDir, @"Source/Developer/AssetTools/Private") + // ... add other private include paths required here ... + } + ); + PrivateIncludePathModuleNames.AddRange( + new string[] { + "UnrealEd", + "AssetTools", + "PropertyEditor", + "MovieScene", + "MovieSceneTools", + "MovieSceneTracks", + "Sequencer", + "ActorSequence" + }); + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + "Engine", + "CoreUObject", + "AssetTools", + "UnrealEd", + "BlueprintGraph", + "GraphEditor", + "PropertyEditor", + "SlateCore", + "Slate", + "EditorStyle", + "Kismet", + "KismetCompiler", + "AssetTools", + "MainFrame", + "InputCore", + "GameplayTasks", + "GameplayTasksEditor", + "AbilityFramework", + "MovieScene", + "MovieSceneTools", + "MovieSceneTracks", + "Sequencer", + "ActorSequence" + // ... add other public dependencies that you statically link with here ... + } + ); + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "Core", + "Engine", + "CoreUObject", + "AssetTools", + "UnrealEd", + "PropertyEditor", + // ... add private dependencies that you statically link with here ... + } + ); + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp new file mode 100644 index 0000000..fb4592b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp @@ -0,0 +1,134 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "AbilityFrameworkEditor.h" +#include "GAAttributePin.h" +#include "Attributes/GAAttributeGlobals.h" +#include "Effects/GAEffectCue.h" +#include "GAAttributePanelGraphPinFactory.h" +#include "GAAttributeDetailCustomization.h" + +#include "GAEffectDetails.h" +//#include "GAEffectSpecStructCustomization.h" +#include "GAEffectPropertyStructCustomization.h" +#include "AFAbilityActionSpecDetails.h" +#include "AFAbilityPeriodSpecDetails.h" +#include "AFAbilityCooldownSpecDetails.h" + +#include "EffectEditor/AssetTypeActions_GAEffectBlueprint.h" +#include "AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h" +#include "EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h" + + +#include "BlueprintEditorModule.h" +#include "BlueprintEditorTabs.h" +#include "LayoutExtender.h" +#include "LevelEditor.h" +#include "MovieSceneToolsProjectSettings.h" +#include "PropertyEditorModule.h" +#include "Styling/SlateStyle.h" +#include "WorkflowTabManager.h" +#include "Modules/ModuleManager.h" +#include "Widgets/Docking/SDockTab.h" + +#include "ISettingsModule.h" + +#include "AFCueManager.h" + +TSet FAbilityFrameworkEditor::EffectClasses = TSet(); + +void FAbilityFrameworkEditor::RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action) +{ + AssetTools.RegisterAssetTypeActions(Action); + CreatedAssetTypeActions.Add(Action); +} +void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequence) +{ + auto* ProjectSettings = GetDefault(); + AGAEffectCue* Cue = Cast(Sequence->GetOuter()); + if (Cue) + { + Sequence->GetMovieScene()->SetPlaybackRange(Cue->StartTime, Cue->EndTime); + } + else + { + Sequence->GetMovieScene()->SetPlaybackRange(ProjectSettings->DefaultStartTime, ProjectSettings->DefaultStartTime + ProjectSettings->DefaultDuration); + } +} + /** IModuleInterface implementation */ +void FAbilityFrameworkEditor::StartupModule() +{ + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); + PropertyModule.RegisterCustomPropertyTypeLayout("GAAttribute", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAAttributeDetailCustomization::MakeInstance)); + PropertyModule.RegisterCustomPropertyTypeLayout("GAEffectProperty", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); + + TSharedPtr GAAttributePanelGraphPinFactory = MakeShareable(new FGAAttributePanelGraphPinFactory()); + FEdGraphUtilities::RegisterVisualPinFactory(GAAttributePanelGraphPinFactory); + + PropertyModule.RegisterCustomClassLayout("AFEffectSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityActivationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityCooldownSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); + + + IAssetTools& AssetTools = FModuleManager::LoadModuleChecked("AssetTools").Get(); + TSharedRef GABAction = MakeShareable(new FAssetTypeActions_GAEffectBlueprint()); + RegisterAssetTypeAction(AssetTools, GABAction); + TSharedRef GAAbilityAction = MakeShareable(new FAssetTypeActions_GAAbilityBlueprint()); + RegisterAssetTypeAction(AssetTools, GAAbilityAction); + TSharedRef GAEffectCueAction = MakeShareable(new FAssetTypeActions_GAEffectCueBlueprint()); + RegisterAssetTypeAction(AssetTools, GAEffectCueAction); + + //BlueprintEditorTabBinding = MakeShared(); + OnInitializeSequenceHandle = UGAEffectCueSequence::OnInitializeSequence().AddStatic(FAbilityFrameworkEditor::OnInitializeSequence); + + if (ISettingsModule* SettingsModule = FModuleManager::GetModulePtr("Settings")) + { + SettingsModule->RegisterSettings("Project", "Game", "Cue Manager", + FText::FromString("Cue Manager"), + FText::FromString("Cue Manager Settings"), + GetMutableDefault() + ); + } +} +void FAbilityFrameworkEditor::ShutdownModule() +{ + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); + //PropertyModule.UnregisterCustomClassLayout("GAGameEffectSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityActivationSpec"); + //PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodSpec"); + //PropertyModule.UnregisterCustomClassLayout("AFAbilityCooldownSpec"); + + PropertyModule.UnregisterCustomPropertyTypeLayout("GAAttribute"); + PropertyModule.UnregisterCustomPropertyTypeLayout("GAEffectProperty"); + + UGAEffectCueSequence::OnInitializeSequence().Remove(OnInitializeSequenceHandle); + BlueprintEditorTabBinding = nullptr; + if (FModuleManager::Get().IsModuleLoaded("AssetTools")) + { + IAssetTools& AssetToolsModule = FModuleManager::GetModuleChecked("AssetTools").Get(); + for (auto& AssetTypeAction : CreatedAssetTypeActions) + { + if (AssetTypeAction.IsValid()) + { + AssetToolsModule.UnregisterAssetTypeActions(AssetTypeAction.ToSharedRef()); + } + } + } +} + +IMPLEMENT_GAME_MODULE(FAbilityFrameworkEditor, AbilityFrameworkEditor); + + +//void FGameAttributesEditor::StartupModule() +//{ +// +//} +// +// +//void FGameAttributesEditor::ShutdownModule() +//{ +// +//} + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h new file mode 100644 index 0000000..db82698 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h @@ -0,0 +1,58 @@ +#pragma once +#include "Engine.h" +#include "AbilityFramework.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "EditorStyle.h" +#include "Effects/GAEffectCueSequence.h" +#include "EffectCueEditor/GAEffectCueEditor.h" + +#include "UnrealEd.h" +#include "AssetToolsModule.h" +#include "IAssetTypeActions.h" +#include "IAbilityFrameworkEditor.h" +class FEffectCueSequenceEditorTabBinding + : public TSharedFromThis +{ +public: + + FEffectCueSequenceEditorTabBinding() + { + + } + + + ~FEffectCueSequenceEditorTabBinding() + { + /*FBlueprintEditorModule* BlueprintEditorModule = FModuleManager::GetModulePtr("Kismet"); + if (BlueprintEditorModule) + { + BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); + BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); + }*/ + } + +private: + + /** Delegate binding handle for FBlueprintEditorModule::OnRegisterTabsForEditor */ + FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; + + FDelegateHandle LevelEditorTabSpawnerHandle, LevelEditorLayoutExtensionHandle; +}; +//add static list of registered custom derived effcts. Will be used to specify, from which classes +//new effect blueprints can be created, and which classes are allowed to pick (if not specified +//in metaData. +class FAbilityFrameworkEditor : public IAbilityFrameworkEditor +{ + TArray< TSharedPtr > CreatedAssetTypeActions; + TSharedPtr BlueprintEditorTabBinding; + FDelegateHandle OnInitializeSequenceHandle; + + static TSet EffectClasses; + + void RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action); + static void OnInitializeSequence(UGAEffectCueSequence* Sequence); + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp new file mode 100644 index 0000000..5840655 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp @@ -0,0 +1,28 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "GACurveTableDetailCustomization.h" + +TSharedRef FGACurveTableDetailCustomization::MakeInstance() +{ + return MakeShareable(new FGACurveTableDetailCustomization); +} + +FGACurveTableDetailCustomization::~FGACurveTableDetailCustomization() +{ + +} + +void FGACurveTableDetailCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} +void FGACurveTableDetailCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h new file mode 100644 index 0000000..2b09d86 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h @@ -0,0 +1,23 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "../GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FGACurveTableDetailCustomization : public IPropertyTypeCustomization +{ +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FGACurveTableDetailCustomization(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + + + +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp new file mode 100644 index 0000000..326f96c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "AssetTypeActions_GAEffectCueBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "GAEffectCueEditor.h" +#include "GAEffectCueBlueprint.h" +#include "Effects/GAEffectCue.h" +#include "GAEffectCueBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_GAEffectCueBlueprint::GetName() const +{ + return FText::FromString("Effect Cue"); +} +UClass* FAssetTypeActions_GAEffectCueBlueprint::GetSupportedClass() const +{ + return UGAEffectCueBlueprint::StaticClass(); +} + +void FAssetTypeActions_GAEffectCueBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FGAEffectCueEditor > NewEditor(new FGAEffectCueEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitEffectCueEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_GAEffectCueBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return false; +} + +UFactory* FAssetTypeActions_GAEffectCueBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UGAEffectCueBlueprintFactory* EffectCueBlueprintFactory = NewObject(); + EffectCueBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return EffectCueBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h new file mode 100644 index 0000000..d0b4f17 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" +//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" +#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_GAEffectCueBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp new file mode 100644 index 0000000..dcbb00a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAEffectCueBlueprint* UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint) +{ + UGAEffectCueBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAEffectCueBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h new file mode 100644 index 0000000..e3a7eaf --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAEffectCueBlueprint.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORKEDITOR_API UGAEffectCueBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() +UPROPERTY() + class UGAEffectCueSequence* Animation; +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAEffectCueBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint); + +#endif +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp new file mode 100644 index 0000000..f37eefc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp @@ -0,0 +1,334 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueBlueprintFactory.h" +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Effects/GAGameEffect.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "GAEffectCueBlueprint.h" +#include "Effects/GAEffectCue.h" +#include "GAEffectCueGraph.h" +#include "GAEffectCueGraphSchema.h" + +#include "ClassViewerFilter.h" + +#include "SlateOptMacros.h" + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SEffectCueBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectCueBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = AGAEffectCue::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCueBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCueBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied AbilitiesBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InEffectCueBlueprintFactory) + { + EffectCueBlueprintFactory = InEffectCueBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Ability Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + EffectCueBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FEffectCueBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FEffectCueBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FEffectCueBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(AGAEffectCue::StaticClass()); + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCueBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (EffectCueBlueprintFactory.IsValid()) + { + EffectCueBlueprintFactory->BlueprintType = BPTYPE_Normal; + EffectCueBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr EffectCueBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UAbilitiesBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UGAEffectCueBlueprintFactory::UGAEffectCueBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UGAEffectCueBlueprint::StaticClass(); + ParentClass = AGAEffectCue::StaticClass(); +} + +bool UGAEffectCueBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SEffectCueBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UGAEffectCueBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(AGAEffectCue::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UGAEffectCueBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectCueBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { + UGAEffectCueBlueprint* AbilityBP = UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + if (AbilityBP == NULL) + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + + // Only allow a gameplay ability graph if there isn't one in a parent blueprint + UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAEffectCueGraph::StaticClass(), UGAEffectCueGraphSchema::StaticClass()); +#if WITH_EDITORONLY_DATA + if (NewBP->UbergraphPages.Num()) + { + FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); + } +#endif + FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); + NewBP->LastEditedDocuments.Add(NewGraph); + NewGraph->bAllowDeletion = false; + + UBlueprintEditorSettings* Settings = GetMutableDefault(); + if(Settings && Settings->bSpawnDefaultBlueprintNodes) + { + int32 NodePositionY = 0; + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + } + } + } + + return NewBP; + } +} + +UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h new file mode 100644 index 0000000..1c78872 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "GAEffectCueBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UGAEffectCueBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp new file mode 100644 index 0000000..b1c35e9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp @@ -0,0 +1,315 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "Effects/GAEffectCue.h" +#include "GAEffectCueEditor.h" +#include "Effects/GAEffectCueSequence.h" +#include "EditorReimportHandler.h" +#include "MovieScene.h" +#include "Tracks/MovieScenePropertyTrack.h" +#if WITH_EDITOR +#include "Editor.h" +#endif +#include "ISequencerModule.h" +#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" +#include "Toolkits/ToolkitManager.h" +#include "Toolkits/GlobalEditorCommonCommands.h" + +#include "GAEffectCueBlueprint.h" +#include "GAEffectCueBlueprintFactory.h" +#include "GAEffectCueGraphSchema.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "SDockTab.h" +#include "BlueprintEditorTabs.h" +#include "LayoutExtender.h" +#include "BlueprintEditorModes.h" +#include "BlueprintEditorTabs.h" + +#define LOCTEXT_NAMESPACE "FGAEffectCueEditor" + +FEffectCueSequenceEditorSummoner::FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor) + : FWorkflowTabFactory("EmbeddedEffectCueSequenceID", BlueprintEditor) + , WeakBlueprintEditor(BlueprintEditor) +{ + bIsSingleton = true; + + TabLabel = LOCTEXT("SequencerTabName", "Cue Sequencer"); +} + +TSharedRef FEffectCueSequenceEditorSummoner::CreateTabBody(const FWorkflowTabSpawnInfo& Info) const +{ + return SNew(SBox); +} +//TSharedRef FEffectCueSequenceEditorSummoner::SpawnTab(const FWorkflowTabSpawnInfo& Info) const +//{ +// TSharedRef Tab = FWorkflowTabFactory::SpawnTab(Info); +// +// TSharedPtr BlueprintEditorPtr = StaticCastSharedPtr(HostingApp.Pin()); +// BlueprintEditorPtr->GetInspector()->SetOwnerTab(Tab); +// +// BlueprintEditorPtr->GetInspector()->GetPropertyView()->SetHostTabManager(Info.TabManager); +// +// return Tab; +//} + +///////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +FGAEffectCueEditor::FGAEffectCueEditor() +{ + EditedCue = nullptr; + FBlueprintEditorModule& BlueprintEditorModule = FModuleManager::LoadModuleChecked("Kismet"); + BlueprintEditorTabSpawnerHandle = BlueprintEditorModule.OnRegisterTabsForEditor().AddRaw(this, &FGAEffectCueEditor::RegisterBlueprintEditorTab); + BlueprintEditorLayoutExtensionHandle = BlueprintEditorModule.OnRegisterLayoutExtensions().AddRaw(this, &FGAEffectCueEditor::RegisterBlueprintEditorLayout); +} + +void FGAEffectCueEditor::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) +{ + Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); +} + +void FGAEffectCueEditor::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) +{ + TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); +} +TArray FGAEffectCueEditor::GetAnimationEventContexts() const +{ + TArray EventContexts; + return EventContexts; +} +void FGAEffectCueEditor::SetSequencer(UGAEffectCueSequence* NewSequence) +{ + if (UGAEffectCueSequence* OldSequence = EditedSequence.Get()) + { + if (OnSequenceChangedHandle.IsValid()) + { + OldSequence->OnSignatureChanged().Remove(OnSequenceChangedHandle); + } + } + + EditedSequence = NewSequence; + + if (NewSequence) + { + OnSequenceChangedHandle = NewSequence->OnSignatureChanged().AddSP(this, &FGAEffectCueEditor::OnSequenceChanged); + } + + // If we already have a sequencer open, just assign the sequence + if (Sequencer.IsValid() && NewSequence) + { + if (Sequencer->GetRootMovieSceneSequence() != NewSequence) + { + Sequencer->ResetToNewRootSequence(*NewSequence); + } + return; + } + + // If we're setting the sequence to none, destroy sequencer + if (!NewSequence) + { + return; + } + + // We need to initialize a new sequencer instance + FSequencerInitParams SequencerInitParams; + { + TWeakObjectPtr LocalWeakSequence = NewSequence; + SequencerInitParams.RootSequence = NewSequence; + auto GetPlaybackContext = + [LocalWeakSequence]() -> UObject* + { + UGAEffectCueSequence* LocalActorSequence = LocalWeakSequence.Get(); + if (LocalActorSequence) + { + if (AGAEffectCue* Actor = LocalActorSequence->GetTypedOuter()) + { + return Actor; + } + } + return nullptr; + }; + + + SequencerInitParams.EventContexts = TAttribute>::Create(TAttribute>::FGetter::CreateLambda( + [GetPlaybackContext] { + TArray Contexts; + if (auto* Context = GetPlaybackContext()) + { + Contexts.Add(Context); + } + return Contexts; + } + )); + SequencerInitParams.PlaybackContext = TAttribute::Create(TAttribute::FGetter::CreateLambda(GetPlaybackContext)); + + SequencerInitParams.ViewParams.bReadOnly = false; // !WeakBlueprintEditor.IsValid() && !NewSequence->IsEditable(); + SequencerInitParams.bEditWithinLevelEditor = false; + SequencerInitParams.ViewParams.UniqueName = "EffectCueSequenceEditor"; + //SequencerInitParams.ViewParams.OnReceivedFocus.BindRaw(this, &SActorSequenceEditorWidgetImpl::OnSequencerReceivedFocus); + } + + Sequencer = FModuleManager::LoadModuleChecked("Sequencer").CreateSequencer(SequencerInitParams); + //FLevelEditorSequencerIntegrationOptions Options; + //Options.bRequiresLevelEvents = true; + //Options.bRequiresActorEvents = false; + //Options.bCanRecord = false; + + Sequencer->SetViewRange(TRange(0, 5)); +} +void FGAEffectCueEditor::OnSequenceChanged() +{ + UBlueprint* Blueprint = GetBlueprintObj(); + + if (Blueprint) + { + FBlueprintEditorUtils::MarkBlueprintAsModified(Blueprint); + } +} +void FGAEffectCueEditor::OnMovieSceneDataChanged() +{ +} +void FGAEffectCueEditor::ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView) +{ +} +FGAEffectCueEditor::~FGAEffectCueEditor() +{ + FEditorDelegates::OnAssetPostImport.RemoveAll(this); + FReimportManager::Instance()->OnPostReimport().RemoveAll(this); + FBlueprintEditorModule* BlueprintEditorModule = &FModuleManager::LoadModuleChecked("Kismet"); + BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); + BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); + BlueprintEditorTabSpawnerHandle.Reset(); + BlueprintEditorLayoutExtensionHandle.Reset(); + TabManager.Pin()->UnregisterTabSpawner(FName("EmbeddedEffectCueSequenceID")); + if (Sequencer.IsValid()) + { + Sequencer->OnMovieSceneDataChanged().RemoveAll(this); + Sequencer->Close(); + Sequencer.Reset(); + } + // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor +} + +void FGAEffectCueEditor::RegisterTabSpawners(const TSharedRef& InTabManager) +{ + TabManager = InTabManager; + FBlueprintEditor::RegisterTabSpawners(InTabManager); +} +void FGAEffectCueEditor::UnregisterTabSpawners(const TSharedRef& InTabManager) +{ + FAssetEditorToolkit::RegisterTabSpawners(InTabManager); +} + +void FGAEffectCueEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) +{ + + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, ObjectsToEdit, bInIsToolbarFocusable); +} +void FGAEffectCueEditor::InitEffectCueEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) +{ + InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); + UBlueprint* BP = InBlueprints[0]; + EditedCue = BP->GeneratedClass->GetDefaultObject(); + CueClass = BP->GeneratedClass; + UObjectPropertyBase* Prop = FindField(CueClass, TEXT("Sequence")); + //Cast( + UObject* Anim = Prop->GetObjectPropertyValue_InContainer(CueClass); + bool test2 = Prop->ContainsInstancedObjectProperty(); + + SetSequencer(EditedCue->Sequence); + //TabManager.Pin()->InvokeTab(FName("EmbeddedEffectCueSequenceID"))->SetContent(Sequencer->GetSequencerWidget()); + + TabManager.Pin()->InvokeTab(FName("EmbeddedEffectCueSequenceID"))->SetContent(Sequencer->GetSequencerWidget()); + //TabLayout = GetDefaltEditorLayout(InBlueprintEditor); + for (auto Blueprint : InBlueprints) + { + EnsureAbilityBlueprintIsUpToDate(Blueprint); + } +} + +void FGAEffectCueEditor::EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint) +{ +#if WITH_EDITORONLY_DATA + int32 Count = Blueprint->UbergraphPages.Num(); + for (auto Graph : Blueprint->UbergraphPages) + { + // remove the default event graph, if it exists, from existing Gameplay Ability Blueprints + if (Graph->GetName() == "EventGraph" && Graph->Nodes.Num() == 0) + { + check(!Graph->Schema->GetClass()->IsChildOf(UGAEffectCueGraphSchema::StaticClass())); + FBlueprintEditorUtils::RemoveGraph(Blueprint, Graph); + break; + } + } +#endif +} +bool FGAEffectCueEditor::IsBlueprintEditor() const +{ + return true; +} + +FName FGAEffectCueEditor::GetToolkitFName() const +{ + return FName("EffectCueEditor"); +} + +FText FGAEffectCueEditor::GetBaseToolkitName() const +{ + return FText::FromString("Game Effect Cue"); +} + +FText FGAEffectCueEditor::GetToolkitName() const +{ + const TArray& EditingObjs = GetEditingObjects(); + + check(EditingObjs.Num() > 0); + + FFormatNamedArguments Args; + + const UObject* EditingObject = EditingObjs[0]; + + const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); + + Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(FText::FromString("{ObjectName}{DirtyState}"), Args); +} + +FText FGAEffectCueEditor::GetToolkitToolTipText() const +{ + const UObject* EditingObject = GetEditingObject(); + + check (EditingObject != NULL); + + return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); +} + +FString FGAEffectCueEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("EffectCueEditor"); +} + +FLinearColor FGAEffectCueEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +UBlueprint* FGAEffectCueEditor::GetBlueprintObj() const +{ + const TArray& EditingObjs = GetEditingObjects(); + for (int32 i = 0; i < EditingObjs.Num(); ++i) + { + if (EditingObjs[i]->IsA()) + { + return (UBlueprint*)EditingObjs[i]; + } + } + return nullptr; +} + +FString FGAEffectCueEditor::GetDocumentationLink() const +{ + return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h new file mode 100644 index 0000000..45ad3e6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h @@ -0,0 +1,90 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Framework/Commands/UICommandList.h" +#include "Framework/MultiBox/MultiBoxExtender.h" +#include "GraphEditor.h" +#include "ISequencer.h" +#include "Effects/GAEffectCueSequence.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" +#include "WorkflowTabFactory.h" +////////////////////////////////////////////////////////////////////////// +// FGameplayAbilitiesEditor +class UGAEffectCueSequence; +/** + * Gameplay abilities asset editor (extends Blueprint editor) + */ +struct FEffectCueSequenceEditorSummoner + : public FWorkflowTabFactory +{ + FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor); + + virtual TSharedRef CreateTabBody(const FWorkflowTabSpawnInfo& Info) const override; + /*virtual TSharedRef SpawnTab(const FWorkflowTabSpawnInfo& Info) const override;*/ +protected: + TWeakPtr WeakBlueprintEditor; +}; +class FGAEffectCueEditor : public FBlueprintEditor +{ + TSharedPtr Sequencer; + void SetSequencer(UGAEffectCueSequence* NewSequence); + TWeakPtr TabManager; + FDelegateHandle OnSequenceChangedHandle; + + TArray GetAnimationEventContexts() const; + FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; + class AGAEffectCue* EditedCue; + TSubclassOf CueClass; + TWeakObjectPtr EditedSequence; + void ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView); + void OnMovieSceneDataChanged(); + void OnSequenceChanged(); + void RegisterBlueprintEditorLayout(FLayoutExtender& Extender); + void RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor); +public: + virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; + /** + * Edits the specified gameplay ability asset(s) + * + * @param Mode Asset editing mode for this editor (standalone or world-centric) + * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within + * @param InBlueprints The blueprints to edit + * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode + */ + + void InitEffectCueEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); +private: + /** + * Updates existing gameplay ability blueprints to make sure that they are up to date + * + * @param Blueprint The blueprint to be updated + */ + void EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint); + +public: + FGAEffectCueEditor(); + + virtual ~FGAEffectCueEditor(); + +public: + // IToolkit interface + // FRED_TODO: don't merge this back + virtual void RegisterTabSpawners(const TSharedRef& InTabManager) override; + virtual void UnregisterTabSpawners(const TSharedRef& InTabManager) override; + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual bool IsBlueprintEditor() const override; + // End of IToolkit interface + + /** @return the documentation location for this editor */ + virtual FString GetDocumentationLink() const override; + + /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ + virtual UBlueprint* GetBlueprintObj() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp new file mode 100644 index 0000000..1487984 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueGraph.h" + +#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" + +///////////////////////////////////////////////////// +// UGameplayAbilityGraph + +UGAEffectCueGraph::UGAEffectCueGraph(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h new file mode 100644 index 0000000..5a3bfe0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraph/EdGraph.h" +#include "GAEffectCueGraph.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectCueGraph : public UEdGraph +{ + GENERATED_UCLASS_BODY() +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp new file mode 100644 index 0000000..bae2670 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueGraphSchema.h" +#include "EdGraphSchema_K2_Actions.h" +#include "Effects/GAGameEffect.h" +#include "Kismet2/BlueprintEditorUtils.h" + +UGAEffectCueGraphSchema::UGAEffectCueGraphSchema(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UK2Node_VariableGet* UGAEffectCueGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); +} + +UK2Node_VariableSet* UGAEffectCueGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h new file mode 100644 index 0000000..1f9b8cc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h @@ -0,0 +1,38 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraphSchema_K2.h" +#include "GAEffectCueGraphSchema.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectCueGraphSchema : public UEdGraphSchema_K2 +{ + GENERATED_UCLASS_BODY() + + /** + * Creates a new variable getter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + /** + * Creates a new variable setter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp new file mode 100644 index 0000000..44ef642 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "AssetTypeActions_GAEffectBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "GAEffectEditor.h" +#include "Effects/GAEffectBlueprint.h" +#include "Effects/GAGameEffect.h" +#include "GAEffectBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_GAEffectBlueprint::GetName() const +{ + return FText::FromString("Effect Data"); +} +UClass* FAssetTypeActions_GAEffectBlueprint::GetSupportedClass() const +{ + return UGAEffectBlueprint::StaticClass(); +} + +void FAssetTypeActions_GAEffectBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FGAEffectEditor > NewEditor(new FGAEffectEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitEffectEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Gameplay Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_GAEffectBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return true; +} + +UFactory* FAssetTypeActions_GAEffectBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UGAEffectBlueprintFactory* EffectBlueprintFactory = NewObject(); + EffectBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return EffectBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h new file mode 100644 index 0000000..7f507b8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" +//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" +#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_GAEffectBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp new file mode 100644 index 0000000..ccfc252 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp @@ -0,0 +1,347 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAEffectBlueprintFactory.h" +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Effects/GAGameEffect.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "Effects/GAEffectBlueprint.h" +#include "GAEffectGraph.h" +#include "GAEffectGraphSchema.h" +#include "Abilities/AFAbilityActivationSpec.h" +#include "Abilities/AFAbilityCooldownSpec.h" +#include "Abilities/AFAbilityPeriodSpec.h" +#include "Abilities/AFAbilityInfiniteDurationSpec.h" + +#include "ClassViewerFilter.h" + +#include "SlateOptMacros.h" + +#define LOCTEXT_NAMESPACE "UEffectBlueprintFactory" + + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SEffectBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UGAGameEffectSpec::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied EffectBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InEffectlueprintFactory) + { + EffectBlueprintFactory = InEffectlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Game Effect Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + EffectBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FEffectBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FEffectBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FEffectBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(UAFEffectSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityActivationSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityCooldownSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityPeriodSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityInfiniteDurationSpec::StaticClass()); + + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (EffectBlueprintFactory.IsValid()) + { + EffectBlueprintFactory->BlueprintType = BPTYPE_Normal; + EffectBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr EffectBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UEffectBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UGAEffectBlueprintFactory::UGAEffectBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UGAEffectBlueprint::StaticClass(); + ParentClass = UGAGameEffectSpec::StaticClass(); +} + +bool UGAEffectBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SEffectBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UGAEffectBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UGAEffectBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : LOCTEXT("Null", "(null)") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Effect Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UGAEffectBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { + UGAEffectBlueprint* AbilityBP = UGAEffectBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + if (AbilityBP == NULL) + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + + // Only allow a gameplay ability graph if there isn't one in a parent blueprint + //UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Not Used Effect Graph"), UGAEffectGraph::StaticClass(), UGAEffectGraphSchema::StaticClass()); +#if WITH_EDITORONLY_DATA + if (NewBP->UbergraphPages.Num()) + { + FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); + } +#endif + //FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); + //NewBP->LastEditedDocuments.Add(NewGraph); + //NewGraph->bAllowDeletion = false; + + UBlueprintEditorSettings* Settings = GetMutableDefault(); + if(Settings && Settings->bSpawnDefaultBlueprintNodes) + { + int32 NodePositionY = 0; + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAGameEffectSpec::StaticClass(), NodePositionY); + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAGameEffectSpec::StaticClass(), NodePositionY); + } + } + } + + return NewBP; + } +} + +UObject* UGAEffectBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h new file mode 100644 index 0000000..8a9b850 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "GAEffectBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UGAEffectBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp new file mode 100644 index 0000000..5559a8d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp @@ -0,0 +1,124 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAEffectEditor.h" +#include "EditorReimportHandler.h" + +#if WITH_EDITOR +#include "Editor.h" +#endif +//Editor\UnrealEd\Public\Toolkits\ToolkitManager.h +//\Editor\UnrealEd\Private\Toolkits\SStandaloneAssetEditorToolkitHost.h +#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" +#include "Toolkits/ToolkitManager.h" +//#include "Toolkits/AssetEditorCommonCommands.h" +#include "Toolkits/GlobalEditorCommonCommands.h" + +#include "Effects/GAEffectBlueprint.h" +#include "GAEffectBlueprintFactory.h" +#include "GAEffectGraphSchema.h" +#include "Kismet2/BlueprintEditorUtils.h" + +#define LOCTEXT_NAMESPACE "FGAEffectEditor" + + +///////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +FGAEffectEditor::FGAEffectEditor() +{ + // todo: Do we need to register a callback for when properties are changed? + //bCreateMenuExtenders = true; + //bCreateDefaultStandaloneMenu = false; + //bCreateDefaultToolbar = false; +} + +FGAEffectEditor::~FGAEffectEditor() +{ + FEditorDelegates::OnAssetPostImport.RemoveAll(this); + FReimportManager::Instance()->OnPostReimport().RemoveAll(this); + + // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor +} +void FGAEffectEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) +{ + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, true, true, ObjectsToEdit, true); +} +void FGAEffectEditor::InitEffectEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) +{ + InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); + RemoveAllToolbarWidgets(); +} + + +// FRED_TODO: don't merge this back +// FName FGameplayAbilitiesEditor::GetToolkitContextFName() const +// { +// return GetToolkitFName(); +// } + +FName FGAEffectEditor::GetToolkitFName() const +{ + return FName("GameEffectEditor"); +} + +FText FGAEffectEditor::GetBaseToolkitName() const +{ + return FText::FromString("Game Effect Editor"); +} + +FText FGAEffectEditor::GetToolkitName() const +{ + const TArray& EditingObjs = GetEditingObjects(); + + check(EditingObjs.Num() > 0); + + FFormatNamedArguments Args; + + const UObject* EditingObject = EditingObjs[0]; + + const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); + + Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(LOCTEXT("GameplayAbilitiesToolkitName", "{ObjectName}{DirtyState}"), Args); +} + +FText FGAEffectEditor::GetToolkitToolTipText() const +{ + const UObject* EditingObject = GetEditingObject(); + + check(EditingObject != NULL); + + return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); +} + +FString FGAEffectEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("EffectEditor"); +} + +FLinearColor FGAEffectEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +UBlueprint* FGAEffectEditor::GetBlueprintObj() const +{ + const TArray& EditingObjs = GetEditingObjects(); + for (int32 i = 0; i < EditingObjs.Num(); ++i) + { + if (EditingObjs[i]->IsA()) + { + return (UBlueprint*)EditingObjs[i]; + } + } + return nullptr; +} + +FString FGAEffectEditor::GetDocumentationLink() const +{ + return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h new file mode 100644 index 0000000..e0dd625 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h @@ -0,0 +1,53 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" + +////////////////////////////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +/** + * Gameplay abilities asset editor (extends Blueprint editor) + */ +class FGAEffectEditor : public FBlueprintEditor +{ +public: + virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; + /** + * Edits the specified gameplay ability asset(s) + * + * @param Mode Asset editing mode for this editor (standalone or world-centric) + * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within + * @param InBlueprints The blueprints to edit + * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode + */ + + void InitEffectEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); +public: + FGAEffectEditor(); + + virtual ~FGAEffectEditor(); + +public: + // IToolkit interface + // FRED_TODO: don't merge this back +// virtual FName GetToolkitContextFName() const override; + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual bool IsAssetEditor() const override { return true; } + virtual bool IsBlueprintEditor() const override { return false; }; + virtual void PostRegenerateMenusAndToolbars() override { RemoveAllToolbarWidgets(); }; + // End of IToolkit interface + + /** @return the documentation location for this editor */ + virtual FString GetDocumentationLink() const override; + + /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ + virtual UBlueprint* GetBlueprintObj() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp new file mode 100644 index 0000000..a802167 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectGraph.h" + +#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" + +///////////////////////////////////////////////////// +// UGameplayAbilityGraph + +UGAEffectGraph::UGAEffectGraph(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h new file mode 100644 index 0000000..3492fc2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraph/EdGraph.h" +#include "GAEffectGraph.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectGraph : public UEdGraph +{ + GENERATED_UCLASS_BODY() +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp new file mode 100644 index 0000000..1404740 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectGraphSchema.h" +#include "EdGraphSchema_K2_Actions.h" +#include "Effects/GAGameEffect.h" +#include "Kismet2/BlueprintEditorUtils.h" + +UGAEffectGraphSchema::UGAEffectGraphSchema(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UK2Node_VariableGet* UGAEffectGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); +} + +UK2Node_VariableSet* UGAEffectGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h new file mode 100644 index 0000000..d435fae --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h @@ -0,0 +1,38 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraphSchema_K2.h" +#include "GAEffectGraphSchema.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectGraphSchema : public UEdGraphSchema_K2 +{ + GENERATED_UCLASS_BODY() + + /** + * Creates a new variable getter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + /** + * Creates a new variable setter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp new file mode 100644 index 0000000..81cbfa0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp @@ -0,0 +1,90 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "SGAAttributeWidget.h" + +#include "GAAttributeDetailCustomization.h" + +TSharedRef FGAAttributeDetailCustomization::MakeInstance() +{ + return MakeShareable(new FGAAttributeDetailCustomization); +} + +FGAAttributeDetailCustomization::~FGAAttributeDetailCustomization() +{ + +} + +void FGAAttributeDetailCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + SocketNameHandle = InStructPropertyHandle->GetChildHandle(GET_MEMBER_NAME_CHECKED(FGAAttribute, AttributeName)); + check(SocketNameHandle.IsValid()); + + HeaderRow + .NameContent() + [ + InStructPropertyHandle->CreatePropertyNameWidget() + ] + .ValueContent() + .MaxDesiredWidth(512) + [ + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .AutoWidth() + .VAlign(VAlign_Center) + [ + SNew(SComboButton) + .OnGetMenuContent(this, &FGAAttributeDetailCustomization::GetSocketTree) + .ContentPadding(FMargin(0.4)) + .ButtonContent() + [ + SNew(STextBlock) + .Margin(FMargin(0.6)) + .Text(this, &FGAAttributeDetailCustomization::GetAttributeName) + ] + ] + ]; +} +void FGAAttributeDetailCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} + +FText FGAAttributeDetailCustomization::GetAttributeName() const +{ + FName attributeName; + if (SocketNameHandle.IsValid()) + { + SocketNameHandle->GetValue(attributeName); + return FText::FromName(attributeName); + } + return FText::FromName(attributeName); +} + +TSharedRef FGAAttributeDetailCustomization::GetSocketTree() +{ + return SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(400) + [ + SNew(SGAAttributeWidget) + .OnAttributeSelectedIn(this, &FGAAttributeDetailCustomization::SetSocketName) + ]; +} + +void FGAAttributeDetailCustomization::SetSocketName(FString AttributeNameIn) +{ + FName name; + FName nameToSet = *AttributeNameIn; + SocketNameHandle->GetValue(name); + if (name != nameToSet) + { + SocketNameHandle->SetValue(nameToSet); + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h new file mode 100644 index 0000000..7b28395 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h @@ -0,0 +1,33 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FGAAttributeDetailCustomization : public IPropertyTypeCustomization +{ +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FGAAttributeDetailCustomization(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + + +protected: + /** Cached Property Handle */ + TSharedPtr SocketNameHandle; + + /** Used with Combobox, show up socket tree widget. */ + TSharedRef GetSocketTree(); + + FText GetAttributeName() const; + + void SetSocketName(FString AttributeNameIn); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp new file mode 100644 index 0000000..347b0d0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" + + + +//TSharedPtr FGAAttributePanelGraphPinFactory::CreatePin(class UEdGraphPin* InPin) const +//{ +// const UEdGraphSchema_K2* K2Schema = GetDefault(); +// if (InPin->PinType.PinCategory == K2Schema->PC_Struct) +// //&& InPin->PinType.PinSubCategoryObject == FGAAttribute::StaticStruct()) +// { +// +// } +// return nullptr; +//} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h new file mode 100644 index 0000000..047dc24 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h @@ -0,0 +1,23 @@ +#pragma once +#include "SlateBasics.h" +#include "Attributes/GAAttributeGlobals.h" +#include "EdGraph/EdGraphPin.h" +#include "EdGraph/EdGraphSchema.h" +#include "EdGraphSchema_K2.h" +#include "GAAttributePanelGraphPinFactory.h" +#include "GAAttributePin.h" +#include "EdGraphUtilities.h" + +class FGAAttributePanelGraphPinFactory : public FGraphPanelPinFactory +{ + virtual TSharedPtr CreatePin(class UEdGraphPin* InPin) const override + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + if (InPin->PinType.PinCategory == K2Schema->PC_Struct + && InPin->PinType.PinSubCategoryObject == FGAAttribute::StaticStruct()) + { + return SNew(SGAAttributePin, InPin); + } + return nullptr; + } +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp new file mode 100644 index 0000000..51b9723 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp @@ -0,0 +1,105 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" + +#include "KismetEditorUtilities.h" + +#include "STextComboBox.h" +#include "EdGraph/EdGraphPin.h" +#include "EdGraph/EdGraphSchema.h" + +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Attributes/GAAttributesBase.h" +#include "SGAAttributeWidget.h" +#include "GAAttributePin.h" + +void SGAAttributePin::Construct(const FArguments& InArgs, UEdGraphPin* InGraphPinObj) +{ + AttributesList.Empty(); + + SelectedAttribute = InGraphPinObj->GetDefaultAsString(); + SelectedAttribute.RemoveFromStart("(AttributeName=\""); + SelectedAttribute.RemoveFromEnd("\")"); + + for (TObjectIterator ClassIt; ClassIt; ++ClassIt) + { + UClass* Class = *ClassIt; + if (Class->IsChildOf(UGAAttributesBase::StaticClass()) + && !FKismetEditorUtilities::IsClassABlueprintSkeleton(Class)) + { + for (TFieldIterator PropertyIt(Class, EFieldIteratorFlags::ExcludeSuper); PropertyIt; ++PropertyIt) + { + UProperty* Prop = *PropertyIt; + //I need array within array, one for list of attributes, and one for class names. + TSharedPtr attribute = MakeShareable(new FString(Prop->GetName())); + AttributesList.Add(attribute); + } + } + } + SGraphPin::Construct(SGraphPin::FArguments(), InGraphPinObj); +} +TSharedRef SGAAttributePin::GetDefaultValueWidget() +{ + //AttributesList.Empty(); + return SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + [ + SAssignNew(AttributeComboButton, SComboButton) + .OnGetMenuContent(this, &SGAAttributePin::GetAttributesMenu) + .ButtonContent() + [ + SNew(STextBlock) + .Text(this, &SGAAttributePin::GetSelectedAttributeText) + ] + ]; + //return SNew(STextComboBox) + // .OptionsSource(&AttributesList) + // .OnSelectionChanged(this, &SGAAttributePin::OnAttributeSelected); + //return AttributeComboButton.ToSharedRef(); + +} + +TSharedRef SGAAttributePin::GetAttributesMenu() +{ + return SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(400) + [ + SNew(SGAAttributeWidget) + .OnAttributeSelectedIn(this, &SGAAttributePin::OnAttributeSelected) + ]; +} + +FText SGAAttributePin::GetSelectedAttributeText() const +{ + return FText::FromString(SelectedAttribute); +} +void SGAAttributePin::OnAttributeSelected(FString ItemSelected) +{ + SelectedAttribute = ItemSelected; + //FString CurrentValue = GraphPinObj->GetDefaultAsString(); + FString CurrentDefaultValue = GraphPinObj->GetDefaultAsString(); + FString attribute = ItemSelected; + if (CurrentDefaultValue.IsEmpty()) + { + CurrentDefaultValue = FString(TEXT("()")); + } + FString AttributeString = TEXT("("); + if (!attribute.IsEmpty()) + { + AttributeString += TEXT("AttributeName=\""); + AttributeString += attribute; + AttributeString += TEXT("\""); + } + AttributeString += TEXT(")"); + + if (!CurrentDefaultValue.Equals(AttributeString)) + { + GraphPinObj->GetSchema()->TrySetDefaultValue(*GraphPinObj, AttributeString); + } + + //if () +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h new file mode 100644 index 0000000..74aeb68 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h @@ -0,0 +1,27 @@ +#pragma once +#include "SlateBasics.h" +#include "SGraphPin.h" + +class SGAAttributePin : public SGraphPin +{ +public: + SLATE_BEGIN_ARGS(SGAAttributePin) {} + SLATE_END_ARGS() + +public: + void Construct(const FArguments& InArgs, UEdGraphPin* InGraphPinObj); + + virtual TSharedRef GetDefaultValueWidget() override; + void OnAttributeSelected(FString ItemSelected); +private: + TArray> AttributesList; + + TSharedPtr AttributeComboButton; + + TSharedRef GetAttributesMenu(); + + FText GetSelectedAttributeText() const; + + FString SelectedAttribute; + +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp new file mode 100644 index 0000000..1f7dde8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -0,0 +1,89 @@ + +#include "AbilityFrameworkEditor.h" +#include "Kismet/KismetMathLibrary.h" +#include "Kismet/KismetArrayLibrary.h" +#include "GameplayTask.h" +#include "Abilities/Tasks/GAAbilityTask.h" +#include "Abilities/AFBlueprintFunctionLibrary.h" +#include "Abilities/GAAbilityBase.h" +#include "KismetCompiler.h" +#include "BlueprintEditorUtils.h" +#include "GAEK2Node_LatentAbilityTaskCall.h" +#include "K2Node_EnumLiteral.h" +#include "BlueprintFunctionNodeSpawner.h" +#include "BlueprintActionDatabaseRegistrar.h" + +#define LOCTEXT_NAMESPACE "K2Node" + +UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + if (HasAnyFlags(RF_ClassDefaultObject) == true) + { + UK2Node_LatentGameplayTaskCall::RegisterSpecializedTaskNodeClass(GetClass()); + } +} + +bool UGAEK2Node_LatentAbilityTaskCall::IsHandling(TSubclassOf TaskClass) const +{ + bool isChilldOf = TaskClass && TaskClass->IsChildOf(UGAAbilityTask::StaticClass()); + return isChilldOf; +} + +bool UGAEK2Node_LatentAbilityTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const +{ + bool bIsCompatible = false; + + EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); + bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); + + if (bAllowLatentFuncs) + { + UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); + if (MyBlueprint && MyBlueprint->GeneratedClass) + { + if (MyBlueprint->GeneratedClass->IsChildOf(UGAAbilityBase::StaticClass())) + { + bIsCompatible = true; + } + } + } + return bIsCompatible; +} + + +void UGAEK2Node_LatentAbilityTaskCall::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const +{ + //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); + struct GetMenuActions_Utils + { + static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) + { + UGAEK2Node_LatentAbilityTaskCall* AsyncTaskNode = CastChecked(NewNode); + if (FunctionPtr.IsValid()) + { + UFunction* Func = FunctionPtr.Get(); + UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); + + AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); + AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); + AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; + } + } + }; + + UClass* NodeClass = GetClass(); + //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + { + UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); + check(NodeSpawner != nullptr); + NodeSpawner->NodeClass = NodeClass; + + TWeakObjectPtr FunctionPtr = FactoryFunc; + NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); + return NodeSpawner; + })); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h new file mode 100644 index 0000000..f8ba9c0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h @@ -0,0 +1,23 @@ + +#pragma once +#include "EdGraph/EdGraphPin.h" +#include "EdGraphSchema_K2.h" +#include "K2Node_BaseAsyncTask.h" +#include "K2Node_LatentGameplayTaskCall.h" +#include "GAEK2Node_LatentAbilityTaskCall.generated.h" + +UCLASS() +class UGAEK2Node_LatentAbilityTaskCall : public UK2Node_LatentGameplayTaskCall +{ + GENERATED_BODY() + +public: + UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer); + + // UEdGraphNode interface + virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; + virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; + // End of UEdGraphNode interface +protected: + virtual bool IsHandling(TSubclassOf TaskClass) const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp new file mode 100644 index 0000000..0519e76 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp @@ -0,0 +1,76 @@ + +#include "AbilityFrameworkEditor.h" +#include "Kismet/KismetMathLibrary.h" +#include "Kismet/KismetArrayLibrary.h" +#include "KismetCompiler.h" +#include "BlueprintEditorUtils.h" +#include "GAEK2Node_LatentAction.h" +#include "K2Node_EnumLiteral.h" +#include "BlueprintFunctionNodeSpawner.h" +#include "BlueprintActionDatabaseRegistrar.h" +#include "LatentActions/GALatentFunctionBase.h" +#define LOCTEXT_NAMESPACE "K2Node" + +UGAEK2Node_LatentAction::UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + //ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentActionBase, ReadyForActivation); +} + +bool UGAEK2Node_LatentAction::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const +{ + bool bIsCompatible = true; + + //EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); + //bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); + + //if (bAllowLatentFuncs) + //{ + // UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); + // if (MyBlueprint && MyBlueprint->GeneratedClass) + // { + // if (MyBlueprint->GeneratedClass->IsChildOf(UGAAbilityBase::StaticClass())) + // { + // bIsCompatible = true; + // } + // } + //} + return bIsCompatible; +} + + +void UGAEK2Node_LatentAction::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const +{ + //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); + struct GetMenuActions_Utils + { + static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) + { + UGAEK2Node_LatentAction* AsyncTaskNode = CastChecked(NewNode); + if (FunctionPtr.IsValid()) + { + UFunction* Func = FunctionPtr.Get(); + UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); + + AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); + AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); + AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; + } + } + }; + + UClass* NodeClass = GetClass(); + //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + { + UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); + check(NodeSpawner != nullptr); + NodeSpawner->NodeClass = NodeClass; + + TWeakObjectPtr FunctionPtr = FactoryFunc; + NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); + return NodeSpawner; + })); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h new file mode 100644 index 0000000..5e88133 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h @@ -0,0 +1,19 @@ + +#pragma once +#include "EdGraph/EdGraphPin.h" +#include "EdGraphSchema_K2.h" +#include "K2Node_BaseAsyncTask.h" +#include "GAEK2Node_LatentAction.generated.h" + +UCLASS() +class UGAEK2Node_LatentAction : public UK2Node_BaseAsyncTask +{ + GENERATED_BODY() + +public: + UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer); + + // UEdGraphNode interface + virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; + virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp new file mode 100644 index 0000000..d8dbbe5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp @@ -0,0 +1,833 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "IDetailsView.h" +#include "PropertyEditorModule.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" +#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" +#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" +#include "Editor/PropertyEditor/Private/SDetailsView.h" + +#include "STextCombobox.h" +#include "STreeView.h" +#include "SButton.h" +#include "STextBlock.h" + +#include "ClassViewerModule.h" +#include "ClassViewerFilter.h" + +#include "EditorClassUtils.h" +#include "IAssetTools.h" +#include "AssetRegistryModule.h" +#include "Dialogs/DlgPickAssetPath.h" +#include "AssetToolsModule.h" +#include "KismetCompilerModule.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "Kismet2/CompilerResultsLog.h" +#include "EffectEditor/GAEffectEditor.h" +#include "SMyBlueprint.h" +#include "SKismetInspector.h" + +#include "SGAAttributeWidget.h" +#include "Effects/GAGameEffect.h" +#include "Effects/GAEffectBlueprint.h" +#include "EffectEditor/GAEffectBlueprintFactory.h" +#include "GAEffectClassStructWidget.h" +#include "GAEffectDetails.h" +#include "AFAbilityActionSpecDetails.h" +#include "AFAbilityPeriodSpecDetails.h" +#include "AFAbilityCooldownSpecDetails.h" +#include "Abilities/AFAbilityActivationSpec.h" +#include "Abilities/AFAbilityPeriodSpec.h" +#include "Abilities/AFAbilityCooldownSpec.h" + +class SEffectCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectCreateDialog) {} + SLATE_ARGUMENT(TSet, MetaClass); + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UGAGameEffectSpec::StaticClass(); + MetaClass = InArgs._MetaClass; + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied GameplayAbilitiesBlueprintFactory */ + bool ConfigureProperties(FGAEffectClassStructWidget* InGameplayAbilitiesBlueprintFactory) + { + GameplayAbilitiesBlueprintFactory = InGameplayAbilitiesBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Game Effect Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + GameplayAbilitiesBlueprintFactory = nullptr; + + return bOkClicked; + } + +private: + class FGameplayAbilityBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FGameplayAbilityBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FGameplayAbilityBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses = MetaClass; + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (GameplayAbilitiesBlueprintFactory) + { + GameplayAbilitiesBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + FGAEffectClassStructWidget* GameplayAbilitiesBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + TSet MetaClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; +class FPropertyEditorClassFilter : public IClassViewerFilter +{ +public: + /** The meta class for the property that classes must be a child-of. */ + const UClass* ClassPropertyMetaClass; + + /** The interface that must be implemented. */ + const UClass* InterfaceThatMustBeImplemented; + + /** Whether or not abstract classes are allowed. */ + bool bAllowAbstract; + + bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + bool bMatchesFlags = !InClass->HasAnyClassFlags(CLASS_Hidden | CLASS_HideDropDown | CLASS_Deprecated) && + (bAllowAbstract || !InClass->HasAnyClassFlags(CLASS_Abstract)); + + if (bMatchesFlags && InClass->IsChildOf(ClassPropertyMetaClass) + && (!InterfaceThatMustBeImplemented || InClass->ImplementsInterface(InterfaceThatMustBeImplemented))) + { + return true; + } + + return false; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + bool bMatchesFlags = !InClass->HasAnyClassFlags(CLASS_Hidden | CLASS_HideDropDown | CLASS_Deprecated) && + (bAllowAbstract || !InClass->HasAnyClassFlags(CLASS_Abstract)); + + if (bMatchesFlags && InClass->IsChildOf(ClassPropertyMetaClass) + && (!InterfaceThatMustBeImplemented || InClass->ImplementsInterface(InterfaceThatMustBeImplemented))) + { + return true; + } + + return false; + } +}; + +FGAEffectClassStructWidget::~FGAEffectClassStructWidget() +{ + +} + +TSharedRef FGAEffectClassStructWidget::CreateEffectClassWidget() +{ + //TAttribute EffectName;// (); + //EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectClassStructWidget::GetClassName)); + return SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .AutoWidth() + [ + SAssignNew(ComboButton, SComboButton) + .OnGetMenuContent(this, &FGAEffectClassStructWidget::GenerateClassPicker) + .ContentPadding(FMargin(2.0f, 2.0f)) + .ToolTipText(this, &FGAEffectClassStructWidget::GetDisplayValueAsString) + .ButtonContent() + [ + SNew(STextBlock) + .Text(this, &FGAEffectClassStructWidget::GetDisplayValueAsString) + //.Font(InArgs._Font) + ] + ] + +SHorizontalBox::Slot() + .AutoWidth() + [ + MakeNewBlueprintButton() + ] + +SHorizontalBox::Slot() + .AutoWidth() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnEditButtonClicked) + [ + SNew(STextBlock) + .Text(FText::FromString("Edit")) + ] + ]; +} + +FText FGAEffectClassStructWidget::GetClassName() const +{ + if (StructPropertyHandle.IsValid()) + { + return StructPropertyHandle->GetPropertyDisplayName(); + } + return FText::FromString("No Effect Selected"); +} +static FString GetClassDisplayName(const UObject* Object) +{ + const UClass* Class = Cast(Object); + if (Class != NULL) + { + UBlueprint* BP = UBlueprint::GetBlueprintFromClass(Class); + if (BP != NULL) + { + return BP->GetName(); + } + } + return (Object) ? Object->GetName() : "None"; +} +FText FGAEffectClassStructWidget::GetDisplayValueAsString() const +{ + static bool bIsReentrant = false; + + // Guard against re-entrancy which can happen if the delegate executed below (SelectedClass.Get()) forces a slow task dialog to open, thus causing this to lose context and regain focus later starting the loop over again + if (!bIsReentrant) + { + TGuardValue(bIsReentrant, true); + if (EffectPropertyHandle.IsValid()) + { + UObject* ObjectValue = NULL; + FPropertyAccess::Result Result = EffectPropertyHandle->GetValue(ObjectValue); + + if (Result == FPropertyAccess::Success && ObjectValue != NULL) + { + return FText::FromString(GetClassDisplayName(ObjectValue)); + } + + return FText::FromString("None"); + } + + return FText::FromString("None"); + } + else + { + return FText::FromString("None"); + } + +} +UClass* FGAEffectClassStructWidget::GetClassFromString(const FString& ClassName) +{ + if (ClassName.IsEmpty() || ClassName == "None") + { + return nullptr; + } + + UClass* Class = FindObject(ANY_PACKAGE, *ClassName); + if (!Class) + { + Class = LoadObject(nullptr, *ClassName); + } + return Class; +} +TSharedRef FGAEffectClassStructWidget::GenerateClassPicker() +{ + FClassViewerInitializationOptions Options; + Options.bShowUnloadedBlueprints = true; + Options.bShowNoneOption = true; + + if (EffectPropertyHandle.IsValid()) + { + Options.PropertyHandle = EffectPropertyHandle; + } + + + class FGameplayAbilityBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + bool bAllowAbstract; + FGameplayAbilityBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + if (!bAllowAbstract) + { + return !InClass->HasAnyClassFlags(CLASS_Abstract) && InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + TSharedPtr ClassFilter = MakeShareable(new FGameplayAbilityBlueprintParentFilter); + + TSet MetaClass; + TSharedPtr EffectPropertyHandleLocal = StructPropertyHandle->GetParentHandle(); + if (EffectPropertyHandleLocal.IsValid()) + { + FString ClassName = EffectPropertyHandleLocal->GetMetaData("AllowedClass"); + TArray ClassNames; + //ClassName.Pars + ClassName.ParseIntoArray(ClassNames, TEXT(",")); + if (ClassNames.Num() > 0) + { + for (const FString& name : ClassNames) + { + UClass* temp = GetClassFromString(name); + if (temp) + { + MetaClass.Add(temp); + } + } + } + else + { + MetaClass.Add(UGAGameEffectSpec::StaticClass()); + } + } + ClassFilter->AllowedChildrenOfClasses = MetaClass; + Options.ClassFilter = ClassFilter; + //ClassFilter->ClassPropertyMetaClass = MetaClass; + //ClassFilter->InterfaceThatMustBeImplemented = nullptr;// UInterface::StaticClass(); + ClassFilter->bAllowAbstract = false; + Options.bIsBlueprintBaseOnly = true; + Options.bIsPlaceableOnly = false; + Options.DisplayMode = EClassViewerDisplayMode::TreeView;// : EClassViewerDisplayMode::ListView; + Options.bAllowViewOptions = true; + Options.bShowDisplayNames = true; + + FOnClassPicked OnPicked(FOnClassPicked::CreateRaw(this, &FGAEffectClassStructWidget::OnClassPicked)); + + return SNew(SBox) + .WidthOverride(280) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(500) + [ + FModuleManager::LoadModuleChecked("ClassViewer").CreateClassViewer(Options, OnPicked) + ] + ]; +} + +void FGAEffectClassStructWidget::OnClassPicked(UClass* InClass) +{ + if (!InClass) + { + SendToObjects(TEXT("None")); + } + else + { + SendToObjects(InClass->GetPathName()); + } + + ComboButton->SetIsOpen(false); +} + +void FGAEffectClassStructWidget::SendToObjects(const FString& NewValue) +{ + if (EffectPropertyHandle.IsValid()) + { + EffectPropertyHandle->SetValueFromFormattedString(NewValue); + } + else + { + UClass* NewClass = FindObject(ANY_PACKAGE, *NewValue); + if (!NewClass) + { + NewClass = LoadObject(nullptr, *NewValue); + } + //OnSetClass.Execute(NewClass); + } +} + +TSharedRef FGAEffectClassStructWidget::MakeNewBlueprintButton() +{ + return + SNew(SButton) + .Text(FText::FromString("New Blueprint")) + //.ToolTipText(OptionalToolTipText.Get().IsEmpty() ? LOCTEXT("NewBlueprintButtonToolTipText", "Create New Blueprint") : OptionalToolTipText) + .OnClicked(this, &FGAEffectClassStructWidget::MakeNewBlueprint) + .IsEnabled(true) + .IsFocusable(false) + .ButtonColorAndOpacity(FSlateColor::UseForeground()) + [ + SNew(SImage) + .Image(FEditorStyle::GetBrush("PropertyWindow.Button_CreateNewBlueprint")) + ]; +} + +FReply FGAEffectClassStructWidget::MakeNewBlueprint() +{ + TSet MetaClass; + TSharedPtr EffectPropertyHandleLocal = StructPropertyHandle->GetParentHandle(); + FString ClassName = EffectPropertyHandleLocal->GetMetaData("AllowedClass"); + TArray ClassNames; + //ClassName.Pars + ClassName.ParseIntoArray(ClassNames, TEXT(",")); + if (ClassNames.Num() > 0) + { + for (const FString& name : ClassNames) + { + UClass* temp = GetClassFromString(name); + if (temp) + { + MetaClass.Add(temp); + } + } + } + else + { + MetaClass.Add(UAFEffectSpec::StaticClass()); + } + TSharedRef Dialog = SNew(SEffectCreateDialog).MetaClass(MetaClass); + Dialog->ConfigureProperties(this); + if (ParentClass) + { + check(FKismetEditorUtilities::CanCreateBlueprintOfClass(UGAGameEffectSpec::StaticClass())); + + // Pre-generate a unique asset name to fill out the path picker dialog with. + FString OuterName; + if (StructPropertyHandle.IsValid()) + { + UProperty* prop = StructPropertyHandle->GetProperty(); + OuterName = prop->GetOuter()->GetName(); + OuterName = prop->GetPathName(); + } + FString NewNameSuggestion = FString::Printf(TEXT("AFE_%s_"), *OuterName); + + + UClass* BlueprintClass = UGAGameEffectSpec::StaticClass(); + UClass* BlueprintGeneratedClass = UGAEffectBlueprint::StaticClass(); + + IKismetCompilerInterface& KismetCompilerModule = FModuleManager::LoadModuleChecked("KismetCompiler"); + KismetCompilerModule.GetBlueprintTypesForClass(UGAGameEffectSpec::StaticClass(), BlueprintClass, BlueprintGeneratedClass); + + FString PackageName = FString(TEXT("/Game/Blueprints/")) + NewNameSuggestion; + FString Name; + FAssetToolsModule& AssetToolsModule = FModuleManager::LoadModuleChecked("AssetTools"); + AssetToolsModule.Get().CreateUniqueAssetName(PackageName, TEXT(""), PackageName, Name); + + + + TSharedPtr PickAssetPathWidget = + SNew(SDlgPickAssetPath) + .Title(FText::FromString("Create New Effect")) + .DefaultAssetPath(FText::FromString(PackageName)); + UBlueprint* Blueprint = nullptr; + if (EAppReturnType::Ok == PickAssetPathWidget->ShowModal()) + { + // Get the full name of where we want to create the physics asset. + FString UserPackageName = PickAssetPathWidget->GetFullAssetPath().ToString(); + FName BPName(*FPackageName::GetLongPackageAssetName(UserPackageName)); + + // Check if the user inputed a valid asset name, if they did not, give it the generated default name + if (BPName == NAME_None) + { + // Use the defaults that were already generated. + UserPackageName = PackageName; + BPName = *Name; + } + + // Then find/create it. + UPackage* Package = CreatePackage(NULL, *UserPackageName); + check(Package); + + // Create and init a new Blueprint + Blueprint = FKismetEditorUtilities::CreateBlueprint(ParentClass, Package, BPName, BPTYPE_Normal, UGAEffectBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), FName("LevelEditorActions")); + if (Blueprint) + { + // Notify the asset registry + FAssetRegistryModule::AssetCreated(Blueprint); + + // Mark the package dirty... + Package->MarkPackageDirty(); + } + } + if (Blueprint != NULL && Blueprint->GeneratedClass ) + { + UGAEffectBlueprint* eff = Cast(Blueprint); + if (eff) + { + EffectPropertyHandle->SetValueFromFormattedString(eff->GeneratedClass->GetPathName()); + + FAssetEditorManager::Get().OpenEditorForAsset(eff); + return FReply::Handled(); + } + } + } + return FReply::Unhandled(); +} + +FReply FGAEffectClassStructWidget::OnEditButtonClicked() +{ + if (EffectEditorWindow.IsValid()) + { + //EffectEditorWindow->RequestDestroyWindow(); + EffectEditorWindow->DestroyWindowImmediately(); + EffectEditorWindow.Reset(); + // already open, just show it + //EffectEditorWindow->BringToFront(true); + } + + { + UObject* OutVal = nullptr; + UGAEffectBlueprint* Blueprint = nullptr; + UProperty* Prop; + UBlueprintGeneratedClass* Class = nullptr; + if (EffectPropertyHandle.IsValid()) + { + EffectPropertyHandle->GetValue(OutVal); + EffectPropertyHandle->CreatePropertyValueWidget(); + Prop = EffectPropertyHandle->GetProperty(); + + if (OutVal) + { + Class = Cast(OutVal); + if (Class && Class->ClassGeneratedBy && Class->ClassGeneratedBy->IsA(UGAEffectBlueprint::StaticClass())) + { + Blueprint = Cast(Class->ClassGeneratedBy); + } + } + } + + FDetailsViewArgs Args; + Args.bHideSelectionTip = true; + Args.bLockable = false; + FPropertyEditorModule& PropertyEditorModule = FModuleManager::GetModuleChecked("PropertyEditor"); + TSharedRef DetailView = PropertyEditorModule.CreateDetailView(Args); + TArray InObjects; + if (Blueprint) + { + EditedBlueprint = Blueprint; + if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityActivationSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityActivationSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); + } + else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityPeriodSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityPeriodSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); + } + else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityCooldownSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityCooldownSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); + } + else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + } + } + if(!Class) + { + return FReply::Unhandled(); + } + if (!Class->ClassDefaultObject) + { + return FReply::Unhandled(); + } + //DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + InObjects.Add(Class->ClassDefaultObject); + DetailView->SetObjects(InObjects); + FString WindowTitle = "Effect Editor: "; + WindowTitle += Blueprint->GetName(); + EffectEditorWindow = SNew(SWindow) + .Title(FText::FromString(WindowTitle)) + .HasCloseButton(true) + .ClientSize(FVector2D(600, 400)); + EffectEditorWindow->SetContent( + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush(TEXT("PropertyWindow.WindowBorder"))) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(24.0f) + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnSaveButtonClicked) + [ + SNew(STextBlock) + .Text(FText::FromString("Save")) + ] + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnSaveCloseButtonClicked) + [ + SNew(STextBlock) + .Text(FText::FromString("Save/Close")) + ] + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnCloseButtonClicked) + .IsEnabled(true) + .IsFocusable(false) + [ + SNew(STextBlock) + .Text(FText::FromString("Close")) + ] + ] + ] + +SVerticalBox::Slot() + .FillHeight(1) + [ + DetailView + ] + ] + ); + + if (FGlobalTabmanager::Get()->GetRootWindow().IsValid()) + { + FSlateApplication::Get().AddWindowAsNativeChild(EffectEditorWindow.ToSharedRef(), FGlobalTabmanager::Get()->GetRootWindow().ToSharedRef()); + } + else + { + FSlateApplication::Get().AddWindow(EffectEditorWindow.ToSharedRef()); + } + } + + return FReply::Handled(); +} +FReply FGAEffectClassStructWidget::OnSaveButtonClicked() +{ + if (EditedBlueprint) + { + FCompilerResultsLog LogResults; + LogResults.BeginEvent(TEXT("Compile")); + LogResults.bLogDetailedResults = false; + LogResults.EventDisplayThresholdMs = 0.1; + EBlueprintCompileOptions CompileOptions = EBlueprintCompileOptions::None; + CompileOptions |= EBlueprintCompileOptions::SaveIntermediateProducts; + + FKismetEditorUtilities::CompileBlueprint(EditedBlueprint, CompileOptions, &LogResults); + TArray PackagesToSave; + check((EditedBlueprint != nullptr) && EditedBlueprint->IsAsset()); + PackagesToSave.Add(EditedBlueprint->GetOutermost()); + + FEditorFileUtils::PromptForCheckoutAndSave(PackagesToSave, true, /*bPromptToSave=*/ false); + //EditedBlueprint = nullptr; + } + return FReply::Unhandled(); +} +FReply FGAEffectClassStructWidget::OnSaveCloseButtonClicked() +{ + if (EditedBlueprint) + { + FCompilerResultsLog LogResults; + LogResults.BeginEvent(TEXT("Compile")); + LogResults.bLogDetailedResults = false; + LogResults.EventDisplayThresholdMs = 0.1; + EBlueprintCompileOptions CompileOptions = EBlueprintCompileOptions::None; + CompileOptions |= EBlueprintCompileOptions::SaveIntermediateProducts; + + FKismetEditorUtilities::CompileBlueprint(EditedBlueprint, CompileOptions, &LogResults); + TArray PackagesToSave; + check((EditedBlueprint != nullptr) && EditedBlueprint->IsAsset()); + PackagesToSave.Add(EditedBlueprint->GetOutermost()); + + FEditorFileUtils::PromptForCheckoutAndSave(PackagesToSave, true, /*bPromptToSave=*/ false); + + EditedBlueprint = nullptr; + + if (EffectEditorWindow.IsValid()) + { + EffectEditorWindow->RequestDestroyWindow(); + EffectEditorWindow = nullptr; + + return FReply::Handled(); + } + } + + return FReply::Unhandled(); +} +FReply FGAEffectClassStructWidget::OnCloseButtonClicked() +{ + if (EffectEditorWindow.IsValid()) + { + EffectEditorWindow->RequestDestroyWindow(); + EffectEditorWindow = nullptr; + return FReply::Handled(); + } + return FReply::Unhandled(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h new file mode 100644 index 0000000..b7666ed --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FGAEffectClassStructWidget : public TSharedFromThis +{ +protected: + /* Handle to FGAEffectClass*/ + TSharedPtr StructPropertyHandle; + + /* Handle to TSubclassOf SpecClass */ + TSharedPtr EffectPropertyHandle; + + TSharedPtr ComboButton; + + TSharedPtr EffectEditorWindow; + UBlueprint* EditedBlueprint; +public: + FGAEffectClassStructWidget() {}; + FGAEffectClassStructWidget(TSharedPtr InStructPropertyHandle, + TSharedPtr InEffectPropertyHandle) + : StructPropertyHandle(InStructPropertyHandle), + EffectPropertyHandle(InEffectPropertyHandle) + {}; + + TSubclassOf ParentClass; + TSharedRef CreateEffectClassWidget(); + void SetHandles(TSharedPtr InStructPropertyHandle, + TSharedPtr InEffectPropertyHandle) + { + StructPropertyHandle = InStructPropertyHandle; + EffectPropertyHandle = InEffectPropertyHandle; + } + + /** + * Destructor + */ + virtual ~FGAEffectClassStructWidget(); + + FText GetClassName() const; + FText GetDisplayValueAsString() const; + UClass* GetClassFromString(const FString& ClassName); + TSharedRef GenerateClassPicker(); + void OnClassPicked(UClass* InClass); + void SendToObjects(const FString& NewValue); + //FReply OnDrop(const FGeometry& MyGeometry, const FDragDropEvent& DragDropEvent); + TSharedRef MakeNewBlueprintButton(); + FReply MakeNewBlueprint(); + FReply OnEditButtonClicked(); + FReply OnSaveButtonClicked(); + FReply OnSaveCloseButtonClicked(); + FReply OnCloseButtonClicked(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp new file mode 100644 index 0000000..0841a9e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp @@ -0,0 +1,111 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Effects/GAGameEffect.h" +#include "GAEffectDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +#include "Abilities/AFAbilityActivationSpec.h" +#include "Abilities/AFAbilityPeriodSpec.h" +#include "Abilities/AFAbilityCooldownSpec.h" +TSharedRef FGAEffectDetails::MakeInstance() +{ + return MakeShareable(new FGAEffectDetails); +} + +void FGAEffectDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FGAEffectDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + DurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + DurationHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + DurationCalcTypeHandle = DurationHandle->GetChildHandle("CalculationType"); + PeriodCalcTypeHandle = PeriodHandle->GetChildHandle("CalculationType"); + + DurationCalcTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFEffectSpec* Spec = Cast(obj.Get())) + { + /*if (!Spec->IsA(UAFAbilityActivationSpec::StaticClass()) + && !Spec->IsA(UAFAbilityPeriodSpec::StaticClass()) + && !Spec->IsA(UAFAbilityCooldownSpec::StaticClass()) + )*/ + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + if (bIsPeriodic && bIsDuration) + { + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(DurationHandle); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationHandle, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodHandle, "Period"); + } + else if (!bIsPeriodic && bIsDuration) + { + TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); + TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(MaxStacksProp); + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(DurationHandle); + DetailLayout.HideProperty(MaxStackedDurationHandle); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationHandle, "Duration"); + } + else if (bIsPeriodic && !bIsDuration) + { + TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); + TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(MaxStacksProp); + DetailLayout.HideProperty(DurationHandle); + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(MaxStackedDurationHandle); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodHandle, "Period"); + } + else if (!bIsPeriodic && !bIsDuration) + { + TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); + TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(MaxStacksProp); + DetailLayout.HideProperty(DurationHandle); + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(MaxStackedDurationHandle); + DetailLayout.HideCategory("Duration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplyTags"); + + } + } + } + } +} +void FGAEffectDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h new file mode 100644 index 0000000..8280469 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h @@ -0,0 +1,32 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FGAEffectDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationHandle; + TSharedPtr PeriodHandle; + TSharedPtr DurationCalcTypeHandle; + TSharedPtr PeriodCalcTypeHandle; + IDetailLayoutBuilder* MyDetailLayout; + FSimpleDelegate UpdateEffectTypeyDelegate; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp new file mode 100644 index 0000000..5d81d1f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp @@ -0,0 +1,89 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "IDetailsView.h" +#include "PropertyEditorModule.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" +#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" +#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" +#include "Editor/PropertyEditor/Private/SDetailsView.h" +//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h +#include "STextCombobox.h" +#include "STreeView.h" +#include "SButton.h" +#include "STextBlock.h" + +#include "ClassViewerModule.h" +#include "ClassViewerFilter.h" + +#include "EditorClassUtils.h" +#include "IAssetTools.h" +#include "AssetRegistryModule.h" +#include "Dialogs/DlgPickAssetPath.h" +#include "AssetToolsModule.h" +#include "KismetCompilerModule.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "EffectEditor/GAEffectEditor.h" +#include "SMyBlueprint.h" +#include "SKismetInspector.h" + +#include "SGAAttributeWidget.h" +#include "Effects/GAGameEffect.h" +#include "Effects/GAEffectBlueprint.h" +#include "EffectEditor/GAEffectBlueprintFactory.h" +#include "GAEffectPropertyStructCustomization.h" +#include "GAEffectDetails.h" + +TSharedRef FGAEffectPropertyStructCustomization::MakeInstance() +{ + return MakeShareable(new FGAEffectPropertyStructCustomization); +} + +FGAEffectPropertyStructCustomization::~FGAEffectPropertyStructCustomization() +{ + +} + +void FGAEffectPropertyStructCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + StructPropertyHandle = InStructPropertyHandle; + TAttribute EffectName;// (); + EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectPropertyStructCustomization::GetClassName)); + /*SNew(SVerticalBox) + + SVerticalBox::Slot() + [ + SNew(STextBlock) + .Text(EffectName) + ]*/ + EffectPropertyHandle = InStructPropertyHandle->GetChildHandle(TEXT("SpecClass")); //struct + TSharedPtr ClassInStruct = EffectPropertyHandle->GetChildHandle(TEXT("SpecClass")); + EffectClassWidget = MakeShareable(new FGAEffectClassStructWidget()); + EffectClassWidget->SetHandles(EffectPropertyHandle, ClassInStruct); + HeaderRow + .NameContent() + [ + InStructPropertyHandle->CreatePropertyNameWidget() + ] + .ValueContent() + .HAlign(HAlign_Fill) + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + .AutoWidth() + [ + EffectClassWidget->CreateEffectClassWidget() + ] + ]; +} +void FGAEffectPropertyStructCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} +FText FGAEffectPropertyStructCustomization::GetClassName() const +{ + if (StructPropertyHandle.IsValid()) + { + return StructPropertyHandle->GetPropertyDisplayName(); + } + return FText::FromString("No Effect Selected"); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h new file mode 100644 index 0000000..4ed717c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h @@ -0,0 +1,28 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +#include "GAEffectClassStructWidget.h" +class FGAEffectPropertyStructCustomization : public IPropertyTypeCustomization +{ +protected: + TSharedPtr StructPropertyHandle; + TSharedPtr EffectPropertyHandle; + TSharedPtr EffectClassWidget; +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FGAEffectPropertyStructCustomization(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + + FText GetClassName() const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h new file mode 100644 index 0000000..3f87d07 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h @@ -0,0 +1,35 @@ + +#pragma once + +#include "GAGlobalTypesEditor.generated.h" + +USTRUCT() +struct FGAAttributeNode +{ + GENERATED_USTRUCT_BODY() +public: + //Name of current node, like class, category, attribute etc. + FString NodeName; + + FString ParentClassName; + + //current attribute for this node); + FString Attribute; + + TWeakPtr ParentNode; + + TArray > ChildNodes; + + /* + List of attributes containe within selected class (ParentClassName) + */ + TArray AttributeNames; + TArray CategoryNames; + FGAAttributeNode() {}; + ~FGAAttributeNode() + { + ParentClassName.Empty(); + Attribute.Empty(); + AttributeNames.Empty(); + }; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h new file mode 100644 index 0000000..6b825c2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h @@ -0,0 +1,36 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "ModuleManager.h" + + +/** + * The public interface to this module. In most cases, this interface is only public to sibling modules + * within this plugin. + */ +class IAbilityFrameworkEditor : public IModuleInterface +{ +public: + + /** + * Singleton-like access to this module's interface. This is just for convenience! + * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. + * + * @return Returns singleton instance, loading the module on demand if needed + */ + static inline IAbilityFrameworkEditor& Get() + { + return FModuleManager::LoadModuleChecked< IAbilityFrameworkEditor >("AbilityFrameworkEditor"); + } + + /** + * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. + * + * @return True if the module is loaded and ready to use + */ + static inline bool IsAvailable() + { + return FModuleManager::Get().IsModuleLoaded( "AbilityFrameworkEditor" ); + } +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h new file mode 100644 index 0000000..f4402fa --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h @@ -0,0 +1,39 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "Developer/AssetTools/Public/AssetToolsModule.h" +#include "IAssetTypeActions.h" +#include "ModuleManager.h" + + +/** + * The public interface to this module. In most cases, this interface is only public to sibling modules + * within this plugin. + */ +class IGameAttributesEditor : public IModuleInterface +{ + TArray< TSharedPtr > CreatedAssetTypeActions; +public: + + /** + * Singleton-like access to this module's interface. This is just for convenience! + * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. + * + * @return Returns singleton instance, loading the module on demand if needed + */ + static inline IGameAttributesEditor& Get() + { + return FModuleManager::LoadModuleChecked< IGameAttributesEditor >("GameAttributesEditor"); + } + + /** + * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. + * + * @return True if the module is loaded and ready to use + */ + static inline bool IsAvailable() + { + return FModuleManager::Get().IsModuleLoaded( "GameAttributesEditor" ); + } +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp new file mode 100644 index 0000000..95453df --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp @@ -0,0 +1,151 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "AbilityFrameworkEditor.h" + +#include "KismetEditorUtilities.h" + +#include "STextComboBox.h" +#include "STreeView.h" +#include "GAGlobalTypesEditor.h" + +#include "Attributes/GAAttributesBase.h" +#include "SGAAttributeWidget.h" + +void SGAAttributeWidget::Construct(const FArguments& InArgs) +{ + AttributesList.Empty(); + AttributesNodes.Empty(); + OnAttributeSelected = InArgs._OnAttributeSelectedIn; + + /* + Intended look: + ClassName + --CategoryName + ----AttributeName + + Or: + ClassName + --CategoryName + ----AttributeType + ------AttributeName + + + search. We really need search! + */ + for (TObjectIterator ClassIt; ClassIt; ++ClassIt) + { + UClass* Class = *ClassIt; + if (Class->IsChildOf(UGAAttributesBase::StaticClass()) + && !FKismetEditorUtilities::IsClassABlueprintSkeleton(Class)) + { + FString className = Class->GetName(); + if (!className.Contains(TEXT("REINST_"))) + { + TSharedPtr classRootNode = MakeShareable(new FGAAttributeNode()); + classRootNode->Attribute = className; + //first let's find root of tree, which is class name + classRootNode->NodeName = className; + FString Category; + //now let's categories as childs + for (TFieldIterator PropertyIt(Class, EFieldIteratorFlags::ExcludeSuper); PropertyIt; ++PropertyIt) + { + UProperty* Prop = *PropertyIt; + Category = Prop->GetMetaData("Category"); + + //check if we already have this category added.. + bool bFoundExistingCategory = false; + if (!Category.IsEmpty()) + { + for (TSharedPtr childNode : classRootNode->ChildNodes) + { + if (childNode->NodeName == Category) + { + bFoundExistingCategory = true; + TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); + attrNode->NodeName = Prop->GetName(); + attrNode->ParentNode = childNode; + childNode->ChildNodes.Add(attrNode); + } + } + if (!bFoundExistingCategory) + { + TSharedPtr categoryNode = MakeShareable(new FGAAttributeNode()); + categoryNode->NodeName = Category; + categoryNode->ParentNode = classRootNode; + classRootNode->ChildNodes.Add(categoryNode); + + TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); + attrNode->NodeName = Prop->GetName(); + attrNode->ParentNode = categoryNode; + categoryNode->ChildNodes.Add(attrNode); + } + } + } + AttributesNodes.Add(classRootNode); + } + } + } + + ChildSlot + [ + SAssignNew(AttributeTreeWidget, STreeView>) + .OnSelectionChanged(this, &SGAAttributeWidget::OnItemSelected) + .TreeItemsSource(&AttributesNodes) + .OnGenerateRow(this, &SGAAttributeWidget::OnGenerateRow) + .OnGetChildren(this, &SGAAttributeWidget::OnGetChildren) + .OnExpansionChanged(this, &SGAAttributeWidget::OnExpansionChanged) + .SelectionMode(ESelectionMode::Single) + ]; +} +SGAAttributeWidget::~SGAAttributeWidget() +{ + AttributesNodes.Empty(); +} + +void SGAAttributeWidget::OnItemSelected(TSharedPtr SelectedItem, ESelectInfo::Type SelectInfo) +{ + if (SelectedItem.IsValid()) + { + if (OnAttributeSelected.IsBound()) + { + OnAttributeSelected.Execute(SelectedItem->NodeName); + } + } +} + +TSharedRef SGAAttributeWidget::OnGenerateRow(TSharedPtr InItem, const TSharedRef& OwnerTable) +{ + return SNew(STableRow< TSharedPtr >, OwnerTable) + [ + SNew(STextBlock) + .Text(FText::FromString(InItem->NodeName)) + ]; +} + +void SGAAttributeWidget::OnGetChildren(TSharedPtr InItem, TArray< TSharedPtr >& OutChildren) +{ + TArray> Children; + + TArray> Children2; + + for (const FString& attribute : InItem->AttributeNames) + { + TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); + attrNode->Attribute = attribute; + Children.Add(attrNode); + } + + for (TSharedPtr childs : InItem->ChildNodes) + { + Children2.Add(childs); + } + + OutChildren += Children2; +} + + +void SGAAttributeWidget::OnExpansionChanged(TSharedPtr InItem, bool bIsExpanded) +{ + +} + + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h new file mode 100644 index 0000000..9ff94f5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h @@ -0,0 +1,64 @@ + +#pragma once + +#include "SlateBasics.h" +#include "GAGlobalTypesEditor.h" + +DECLARE_DELEGATE_OneParam(FGAOnAttributeSelected, FString); + +class FAFAttributeNode +{ + FString NodeName; + + FString Attribute; + + TWeakPtr ParentNode; + + TArray > ChildNodes; +}; + +class FAFAttributeTree +{ + +}; + +class SGAAttributeWidget : public SCompoundWidget +{ + SLATE_BEGIN_ARGS(SGAAttributeWidget) + {} + SLATE_EVENT(FGAOnAttributeSelected, OnAttributeSelectedIn) + SLATE_END_ARGS(); + + void Construct(const FArguments& InArgs); + ~SGAAttributeWidget(); +private: + TArray> AttributesList; + + TArray > AttributesNodes; + + TSharedPtr > > AttributeTreeWidget; + + FGAOnAttributeSelected OnAttributeSelected; + + void OnItemSelected(TSharedPtr SelectedItem, ESelectInfo::Type SelectInfo); + /** + * Generate a row widget for the specified item node and table + * + * @param InItem Tag node to generate a row widget for + * @param OwnerTable Table that owns the row + * + * @return Generated row widget for the item node + */ + TSharedRef OnGenerateRow(TSharedPtr InItem, const TSharedRef& OwnerTable); + + /** + * Get children nodes of the specified node + * + * @param InItem Node to get children of + * @param OutChildren [OUT] Array of children nodes, if any + */ + void OnGetChildren(TSharedPtr InItem, TArray< TSharedPtr >& OutChildren); + + + void OnExpansionChanged(TSharedPtr InItem, bool bIsExpanded); +}; \ No newline at end of file diff --git a/Source/ActionRPGGame.Target.cs b/Source/ActionRPGGame.Target.cs new file mode 100644 index 0000000..dac994a --- /dev/null +++ b/Source/ActionRPGGame.Target.cs @@ -0,0 +1,13 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; +using System.Collections.Generic; + +public class ActionRPGGameTarget : TargetRules +{ + public ActionRPGGameTarget(TargetInfo Target) : base(Target) + { + Type = TargetType.Game; + ExtraModuleNames.Add("ActionRPGGame"); + } +} diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs new file mode 100644 index 0000000..384db7a --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -0,0 +1,13 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class ActionRPGGame : ModuleRules +{ + public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", "HeadMountedDisplay" }); + } +} diff --git a/Source/ActionRPGGame/ActionRPGGame.cpp b/Source/ActionRPGGame/ActionRPGGame.cpp new file mode 100644 index 0000000..173c45d --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGame.cpp @@ -0,0 +1,7 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "ActionRPGGame.h" +#include "Modules/ModuleManager.h" + +IMPLEMENT_PRIMARY_GAME_MODULE( FDefaultGameModuleImpl, ActionRPGGame, "ActionRPGGame" ); + \ No newline at end of file diff --git a/Source/ActionRPGGame/ActionRPGGame.h b/Source/ActionRPGGame/ActionRPGGame.h new file mode 100644 index 0000000..25b0d29 --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGame.h @@ -0,0 +1,5 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" diff --git a/Source/ActionRPGGame/ActionRPGGameCharacter.cpp b/Source/ActionRPGGame/ActionRPGGameCharacter.cpp new file mode 100644 index 0000000..d82ab6f --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGameCharacter.cpp @@ -0,0 +1,134 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "ActionRPGGameCharacter.h" +#include "HeadMountedDisplayFunctionLibrary.h" +#include "Camera/CameraComponent.h" +#include "Components/CapsuleComponent.h" +#include "Components/InputComponent.h" +#include "GameFramework/CharacterMovementComponent.h" +#include "GameFramework/Controller.h" +#include "GameFramework/SpringArmComponent.h" + +////////////////////////////////////////////////////////////////////////// +// AActionRPGGameCharacter + +AActionRPGGameCharacter::AActionRPGGameCharacter() +{ + // Set size for collision capsule + GetCapsuleComponent()->InitCapsuleSize(42.f, 96.0f); + + // set our turn rates for input + BaseTurnRate = 45.f; + BaseLookUpRate = 45.f; + + // Don't rotate when the controller rotates. Let that just affect the camera. + bUseControllerRotationPitch = false; + bUseControllerRotationYaw = false; + bUseControllerRotationRoll = false; + + // Configure character movement + GetCharacterMovement()->bOrientRotationToMovement = true; // Character moves in the direction of input... + GetCharacterMovement()->RotationRate = FRotator(0.0f, 540.0f, 0.0f); // ...at this rotation rate + GetCharacterMovement()->JumpZVelocity = 600.f; + GetCharacterMovement()->AirControl = 0.2f; + + // Create a camera boom (pulls in towards the player if there is a collision) + CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); + CameraBoom->SetupAttachment(RootComponent); + CameraBoom->TargetArmLength = 300.0f; // The camera follows at this distance behind the character + CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller + + // Create a follow camera + FollowCamera = CreateDefaultSubobject(TEXT("FollowCamera")); + FollowCamera->SetupAttachment(CameraBoom, USpringArmComponent::SocketName); // Attach the camera to the end of the boom and let the boom adjust to match the controller orientation + FollowCamera->bUsePawnControlRotation = false; // Camera does not rotate relative to arm + + // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) + // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) +} + +////////////////////////////////////////////////////////////////////////// +// Input + +void AActionRPGGameCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) +{ + // Set up gameplay key bindings + check(PlayerInputComponent); + PlayerInputComponent->BindAction("Jump", IE_Pressed, this, &ACharacter::Jump); + PlayerInputComponent->BindAction("Jump", IE_Released, this, &ACharacter::StopJumping); + + PlayerInputComponent->BindAxis("MoveForward", this, &AActionRPGGameCharacter::MoveForward); + PlayerInputComponent->BindAxis("MoveRight", this, &AActionRPGGameCharacter::MoveRight); + + // We have 2 versions of the rotation bindings to handle different kinds of devices differently + // "turn" handles devices that provide an absolute delta, such as a mouse. + // "turnrate" is for devices that we choose to treat as a rate of change, such as an analog joystick + PlayerInputComponent->BindAxis("Turn", this, &APawn::AddControllerYawInput); + PlayerInputComponent->BindAxis("TurnRate", this, &AActionRPGGameCharacter::TurnAtRate); + PlayerInputComponent->BindAxis("LookUp", this, &APawn::AddControllerPitchInput); + PlayerInputComponent->BindAxis("LookUpRate", this, &AActionRPGGameCharacter::LookUpAtRate); + + // handle touch devices + PlayerInputComponent->BindTouch(IE_Pressed, this, &AActionRPGGameCharacter::TouchStarted); + PlayerInputComponent->BindTouch(IE_Released, this, &AActionRPGGameCharacter::TouchStopped); + + // VR headset functionality + PlayerInputComponent->BindAction("ResetVR", IE_Pressed, this, &AActionRPGGameCharacter::OnResetVR); +} + + +void AActionRPGGameCharacter::OnResetVR() +{ + UHeadMountedDisplayFunctionLibrary::ResetOrientationAndPosition(); +} + +void AActionRPGGameCharacter::TouchStarted(ETouchIndex::Type FingerIndex, FVector Location) +{ + Jump(); +} + +void AActionRPGGameCharacter::TouchStopped(ETouchIndex::Type FingerIndex, FVector Location) +{ + StopJumping(); +} + +void AActionRPGGameCharacter::TurnAtRate(float Rate) +{ + // calculate delta for this frame from the rate information + AddControllerYawInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds()); +} + +void AActionRPGGameCharacter::LookUpAtRate(float Rate) +{ + // calculate delta for this frame from the rate information + AddControllerPitchInput(Rate * BaseLookUpRate * GetWorld()->GetDeltaSeconds()); +} + +void AActionRPGGameCharacter::MoveForward(float Value) +{ + if ((Controller != NULL) && (Value != 0.0f)) + { + // find out which way is forward + const FRotator Rotation = Controller->GetControlRotation(); + const FRotator YawRotation(0, Rotation.Yaw, 0); + + // get forward vector + const FVector Direction = FRotationMatrix(YawRotation).GetUnitAxis(EAxis::X); + AddMovementInput(Direction, Value); + } +} + +void AActionRPGGameCharacter::MoveRight(float Value) +{ + if ( (Controller != NULL) && (Value != 0.0f) ) + { + // find out which way is right + const FRotator Rotation = Controller->GetControlRotation(); + const FRotator YawRotation(0, Rotation.Yaw, 0); + + // get right vector + const FVector Direction = FRotationMatrix(YawRotation).GetUnitAxis(EAxis::Y); + // add movement in that direction + AddMovementInput(Direction, Value); + } +} diff --git a/Source/ActionRPGGame/ActionRPGGameCharacter.h b/Source/ActionRPGGame/ActionRPGGameCharacter.h new file mode 100644 index 0000000..767000c --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGameCharacter.h @@ -0,0 +1,72 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Character.h" +#include "ActionRPGGameCharacter.generated.h" + +UCLASS(config=Game) +class AActionRPGGameCharacter : public ACharacter +{ + GENERATED_BODY() + + /** Camera boom positioning the camera behind the character */ + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class USpringArmComponent* CameraBoom; + + /** Follow camera */ + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class UCameraComponent* FollowCamera; +public: + AActionRPGGameCharacter(); + + /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) + float BaseTurnRate; + + /** Base look up/down rate, in deg/sec. Other scaling may affect final rate. */ + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) + float BaseLookUpRate; + +protected: + + /** Resets HMD orientation in VR. */ + void OnResetVR(); + + /** Called for forwards/backward input */ + void MoveForward(float Value); + + /** Called for side to side input */ + void MoveRight(float Value); + + /** + * Called via input to turn at a given rate. + * @param Rate This is a normalized rate, i.e. 1.0 means 100% of desired turn rate + */ + void TurnAtRate(float Rate); + + /** + * Called via input to turn look up/down at a given rate. + * @param Rate This is a normalized rate, i.e. 1.0 means 100% of desired turn rate + */ + void LookUpAtRate(float Rate); + + /** Handler for when a touch input begins. */ + void TouchStarted(ETouchIndex::Type FingerIndex, FVector Location); + + /** Handler for when a touch input stops. */ + void TouchStopped(ETouchIndex::Type FingerIndex, FVector Location); + +protected: + // APawn interface + virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; + // End of APawn interface + +public: + /** Returns CameraBoom subobject **/ + FORCEINLINE class USpringArmComponent* GetCameraBoom() const { return CameraBoom; } + /** Returns FollowCamera subobject **/ + FORCEINLINE class UCameraComponent* GetFollowCamera() const { return FollowCamera; } +}; + diff --git a/Source/ActionRPGGame/ActionRPGGameGameMode.cpp b/Source/ActionRPGGame/ActionRPGGameGameMode.cpp new file mode 100644 index 0000000..c5fa84c --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGameGameMode.cpp @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "ActionRPGGameGameMode.h" +#include "ActionRPGGameCharacter.h" +#include "UObject/ConstructorHelpers.h" + +AActionRPGGameGameMode::AActionRPGGameGameMode() +{ + // set default pawn class to our Blueprinted character + static ConstructorHelpers::FClassFinder PlayerPawnBPClass(TEXT("/Game/ThirdPersonCPP/Blueprints/ThirdPersonCharacter")); + if (PlayerPawnBPClass.Class != NULL) + { + DefaultPawnClass = PlayerPawnBPClass.Class; + } +} diff --git a/Source/ActionRPGGame/ActionRPGGameGameMode.h b/Source/ActionRPGGame/ActionRPGGameGameMode.h new file mode 100644 index 0000000..fb828e8 --- /dev/null +++ b/Source/ActionRPGGame/ActionRPGGameGameMode.h @@ -0,0 +1,19 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/GameModeBase.h" +#include "ActionRPGGameGameMode.generated.h" + +UCLASS(minimalapi) +class AActionRPGGameGameMode : public AGameModeBase +{ + GENERATED_BODY() + +public: + AActionRPGGameGameMode(); +}; + + + diff --git a/Source/ActionRPGGameClient.Target.cs b/Source/ActionRPGGameClient.Target.cs new file mode 100644 index 0000000..a64ca18 --- /dev/null +++ b/Source/ActionRPGGameClient.Target.cs @@ -0,0 +1,13 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; +using System.Collections.Generic; + +public class ActionRPGGameClientTarget : TargetRules +{ + public ActionRPGGameClientTarget(TargetInfo Target) : base(Target) + { + Type = TargetType.Client; + ExtraModuleNames.Add("ActionRPGGame"); + } +} diff --git a/Source/ActionRPGGameEditor.Target.cs b/Source/ActionRPGGameEditor.Target.cs new file mode 100644 index 0000000..6bd6d2e --- /dev/null +++ b/Source/ActionRPGGameEditor.Target.cs @@ -0,0 +1,13 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; +using System.Collections.Generic; + +public class ActionRPGGameEditorTarget : TargetRules +{ + public ActionRPGGameEditorTarget(TargetInfo Target) : base(Target) + { + Type = TargetType.Editor; + ExtraModuleNames.Add("ActionRPGGame"); + } +} From fa26827417ece051431e885b473b741a4551bae2 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 1 Jul 2017 17:50:45 +0200 Subject: [PATCH 002/187] removing files --- .gitattributes | 2 - .gitignore | 268 ----- .vs/ProjectSettings.json | 3 - .vs/VSWorkspaceState.json | 9 - .vs/config/applicationhost.config | 1031 ----------------- .vs/slnx.sqlite | Bin 69632 -> 0 bytes ActionRPGGame.uproject | 43 - Config/DefaultEditor.ini | 23 - .../DefaultEditorPerProjectUserSettings.ini | 32 - Config/DefaultEditorUserSettings.ini | 2 - Config/DefaultEngine.ini | 240 ---- Config/DefaultGame.ini | 63 - Config/DefaultGameplayTags.ini | 112 -- Config/DefaultInput.ini | 113 -- README | 15 - Source/ActionRPGGame.Target.cs | 14 - Source/ActionRPGGame/ARCharacter.cpp | 134 --- Source/ActionRPGGame/ARCharacter.h | 75 -- Source/ActionRPGGame/ARGameMode.cpp | 9 - Source/ActionRPGGame/ARGameMode.h | 19 - Source/ActionRPGGame/ActionRPGGame.Build.cs | 13 - Source/ActionRPGGame/ActionRPGGame.cpp | 7 - Source/ActionRPGGame/ActionRPGGame.h | 5 - Source/ActionRPGGameClient.Target.cs | 14 - Source/ActionRPGGameEditor.Target.cs | 14 - Source/ActionRPGGameServer.Target.cs | 16 - 26 files changed, 2276 deletions(-) delete mode 100644 .gitattributes delete mode 100644 .gitignore delete mode 100644 .vs/ProjectSettings.json delete mode 100644 .vs/VSWorkspaceState.json delete mode 100644 .vs/config/applicationhost.config delete mode 100644 .vs/slnx.sqlite delete mode 100644 ActionRPGGame.uproject delete mode 100644 Config/DefaultEditor.ini delete mode 100644 Config/DefaultEditorPerProjectUserSettings.ini delete mode 100644 Config/DefaultEditorUserSettings.ini delete mode 100644 Config/DefaultEngine.ini delete mode 100644 Config/DefaultGame.ini delete mode 100644 Config/DefaultGameplayTags.ini delete mode 100644 Config/DefaultInput.ini delete mode 100644 README delete mode 100644 Source/ActionRPGGame.Target.cs delete mode 100644 Source/ActionRPGGame/ARCharacter.cpp delete mode 100644 Source/ActionRPGGame/ARCharacter.h delete mode 100644 Source/ActionRPGGame/ARGameMode.cpp delete mode 100644 Source/ActionRPGGame/ARGameMode.h delete mode 100644 Source/ActionRPGGame/ActionRPGGame.Build.cs delete mode 100644 Source/ActionRPGGame/ActionRPGGame.cpp delete mode 100644 Source/ActionRPGGame/ActionRPGGame.h delete mode 100644 Source/ActionRPGGameClient.Target.cs delete mode 100644 Source/ActionRPGGameEditor.Target.cs delete mode 100644 Source/ActionRPGGameServer.Target.cs diff --git a/.gitattributes b/.gitattributes deleted file mode 100644 index 82090a7..0000000 --- a/.gitattributes +++ /dev/null @@ -1,2 +0,0 @@ -.uasset filter=lfs diff=lfs merge=lfs -text -*.uasset filter=lfs diff=lfs merge=lfs -text diff --git a/.gitignore b/.gitignore deleted file mode 100644 index dbb6a2c..0000000 --- a/.gitignore +++ /dev/null @@ -1,268 +0,0 @@ -################# -## Eclipse -################# - -*.pydevproject -.project -.metadata -bin/ -tmp/ -*.tmp -*.bak -*.swp -*~.nib -local.properties -.classpath -.settings/ -.loadpath - -# External tool builders -.externalToolBuilders/ - -# Locally stored "Eclipse launch configurations" -*.launch - -# CDT-specific -.cproject - -# PDT-specific -.buildpath - - -################# -## Visual Studio -################# - -## Ignore Visual Studio temporary files, build results, and -## files generated by popular Visual Studio add-ons. - -# User-specific files -*.suo -*.user -*.sln.docstates -*.sln -*.sdf - -# Build results - -[Dd]ebug/ -[Rr]elease/ -x64/ -build/ -[Bb]in/ -[Oo]bj/ - -# MSTest test Results -[Tt]est[Rr]esult*/ -[Bb]uild[Ll]og.* - -*_i.c -*_p.c -*.ilk -*.meta -*.obj -*.pch -*.pdb -*.pgc -*.pgd -*.rsp -*.sbr -*.tlb -*.tli -*.tlh -*.tmp -*.tmp_proj -*.log -*.vspscc -*.vssscc -.builds -*.pidb -*.log -*.scc - -# Visual C++ cache files -ipch/ -*.aps -*.ncb -*.opensdf -*.sdf -*.cachefile - -# Visual Studio profiler -*.psess -*.vsp -*.vspx - -# Guidance Automation Toolkit -*.gpState - -# ReSharper is a .NET coding add-in -_ReSharper*/ -*.[Rr]e[Ss]harper - -# TeamCity is a build add-in -_TeamCity* - -# DotCover is a Code Coverage Tool -*.dotCover - -# NCrunch -*.ncrunch* -.*crunch*.local.xml - -# Installshield output folder -[Ee]xpress/ - -# DocProject is a documentation generator add-in -DocProject/buildhelp/ -DocProject/Help/*.HxT -DocProject/Help/*.HxC -DocProject/Help/*.hhc -DocProject/Help/*.hhk -DocProject/Help/*.hhp -DocProject/Help/Html2 -DocProject/Help/html - -# Click-Once directory -publish/ - -# Publish Web Output -*.Publish.xml -*.pubxml - -# NuGet Packages Directory -## TODO: If you have NuGet Package Restore enabled, uncomment the next line -#packages/ - -# Windows Azure Build Output -csx -*.build.csdef - -# Windows Store app package directory -AppPackages/ - -# Others -sql/ -*.Cache -ClientBin/ -[Ss]tyle[Cc]op.* -~$* -*~ -*.dbmdl -*.[Pp]ublish.xml -*.pfx -*.publishsettings - -# RIA/Silverlight projects -Generated_Code/ - -# Backup & report files from converting an old project file to a newer -# Visual Studio version. Backup files are not needed, because we have git ;-) -_UpgradeReport_Files/ -Backup*/ -UpgradeLog*.XML -UpgradeLog*.htm - -# SQL Server files -App_Data/*.mdf -App_Data/*.ldf - -############# -## Windows detritus -############# - -# Windows image file caches -Thumbs.db -ehthumbs.db - -# Folder config file -Desktop.ini - -# Recycle Bin used on file shares -$RECYCLE.BIN/ - -# Mac crap -.DS_Store - - -############# -## Python -############# - -*.py[co] - -# Packages -*.egg -*.egg-info -dist/ -build/ -eggs/ -parts/ -var/ -sdist/ -develop-eggs/ -.installed.cfg - -# Installer logs -pip-log.txt - -# Unit test / coverage reports -.coverage -.tox - -#Translations -*.mo - -#Mr Developer -.mr.developer.cfg - -# Compiled Object files -*.slo -*.lo -*.o -*.obj - -# Compiled Dynamic libraries -*.so -*.dylib -*.dll - -# Compiled Static libraries -*.lai -*.la -*.a -*.lib - -# Executables -*.exe -*.out -*.app - -#Unreal Engine - -Binaries/ -Plugins/ -Plugins/* -Content/* -!Content/Blueprints/ -!Plugins/GameInventorySystem/Content -!Plugins/GameInventorySystem/Source -!Plugins/GameAttributes/Content -!Plugins/GameAttributes/Source -!Plugins/TimeOfDay/Content -!Plugins/TimeOfDay/Source -DerivedDataCache/ -Intermediate/ -Saved/ -*.sln -*.sln -*.sln -*.db -.vs/ActionRPGGame/v15/Browse.VC.opendb -*.db-shm -.vs/config/applicationhost.config -*.config -.vs/ActionRPGGame/v15/Solution.VC.db-wal -CodeBackup/States/GASAbilityStateCooldown.h -*.bin -*.pak diff --git a/.vs/ProjectSettings.json b/.vs/ProjectSettings.json deleted file mode 100644 index 38c5f00..0000000 --- a/.vs/ProjectSettings.json +++ /dev/null @@ -1,3 +0,0 @@ -{ - "CurrentProjectSetting": "x86-Debug" -} \ No newline at end of file diff --git a/.vs/VSWorkspaceState.json b/.vs/VSWorkspaceState.json deleted file mode 100644 index 4fd6934..0000000 --- a/.vs/VSWorkspaceState.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "ExpandedNodes": [ - "", - "\\Content\\Blueprints", - "\\Source" - ], - "SelectedNode": "\\Content", - "PreviewInSolutionExplorer": false -} \ No newline at end of file diff --git a/.vs/config/applicationhost.config b/.vs/config/applicationhost.config deleted file mode 100644 index 4b9bf47..0000000 --- a/.vs/config/applicationhost.config +++ /dev/null @@ -1,1031 +0,0 @@ - - - - - - - -
-
-
-
-
-
-
-
- - - -
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- -
-
- -
-
-
-
-
-
- -
-
-
-
-
- -
-
-
- -
-
- -
-
- -
-
-
- - -
-
-
-
-
-
- -
-
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/.vs/slnx.sqlite b/.vs/slnx.sqlite deleted file mode 100644 index 0316013feef76d7979ede78a3e7c465fbb7bed3b..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 69632 zcmeI3OK%(36~{RiCCZd3I&mE?w8%w(z+x@R57lTIz(DEY(4Lwa(tOAkR6-b$SJD*Z zP$q}61!N<;c93+_eZD|f`3l{n%Y1=mnN1e~y67?}(0k{>nYkR=l5M#N@h41?bD!t@ z?m6ea=-PvlVNtT%>vwgFti>+IBq{cLLSnJlhwS|UdwZ`%_9gB;uum!QebUztW4Zr6 zp5=wpKl3slq<_9}xX@32H~-W8M&g^<`FMZk``C}MA0{>M7U^?~b9U_)d#OZbZB6=m zXz4p0S~NPeb~LbPw@PL$6bY?6GVURE{M#k!)^iB@LsMya$y-1aK{-l5T^{a|&k5UDCf zrK)JMQX^YlL8rIo@+g7T%sP#60m~XGC?$odBj;;!zM!nQ9Tn&SHQTyras6J~n-5{s zpP0n^b+vFiZd3}KqucQbWD1Q+NG66Tq`lZV(_c(_*YZ?!YrjeA$|GmQh+Hm}xO!Td zDLBGf*ZX_aY7%WDUzP9WtIIcU-OAcSJfVWzGcEe`G&Sl+2h_JMZat}F_V|+viOj>C zbi8huZThr!)ZOWI3Ut>n4a?}6+s;>Wk5f|H+iFyylxz5^R!|<1trNAuT){T7vC>Vl zycO=WnLWO=kjThPNI6(h;!a!tSTudf1xt#P>%?=Wx+T!y< zI6R2if!H8s1ugmnA;EQ2&(VXm&m;*wr<9w?{2Lofr=&(3CxtL&Gqi7omM~n_<6EI4>md@R++IuotZm*Es>kPZ* zcscIPpPf%+l$`Wz!FCi;`0a|$CNFE70~hm>u6Z^z^+7{nP;6foO9fjPd5l6OOHbhA-n1_&8*Jun>^U^)o_aohZ=pw+(u8D_}S z;R}koy3S@@ciOu;m&jbpdXC}=%-h@Mf4l@|)sl$x4X@0o(#X8L9Cyvb+`&t61QvqZ zD0hSQ2P_JV%{0%X*+eFrm7d?WtLT3&5ypZdqYuBiup#VPFlmhJpovrXSj_Q%T-0a ztJxb3W~`Is3hWPpTMCijyPYH1*!N}~B2%*I4>r>A$D{#=hVM z0w4eaAOHd&00JNY0w4eaAOHd&aOMO)ipOKu(kj21V~1<}3PkP=P3y+x8I~TCog*K1 zUASxP@k6RB=i;&4n%t+lMcd_mH-7i|Z*G2meeEMD9=npM zv19J8?w;1&SY2CP!3m00ck)1V8`;KmY_l00ck)zyF5~fB*=900@8p2!H?x zfB*=900@A<^b^4S|MZVBGz0+<009sH0T2KI5C8!X009sH0qp-_10VnbAOHd&00JNY z0w4eaAOHd&F#QDZ`~T@5V`vBhAOHd&00JNY0w4eaAOHd&00P+m!v;VA1V8`;KmY_l z00ck)1V8`;Kw$a_@cn;sc0QKAwfN&=|H9!yKl$DKPxBjzZ)WG?{h9A$KgNDI0}6AC zb9SpQ_EL$=+S(cP;5X^^A$>ix^qmeZ8Xa0Y8d$VjrMt9G%~n*>qFhz-b%oUPcS;J` zim22~C6`l4!d_9iifI|vk=kw&RjVs^l`5%J)%ARJliXJ}Nxo4ps~YQKUD4`9E3RF$GqRWwf08#o>Ve>{Kn(3=_Xm;3U}Jf9$#8WWMn3!94(}#cWJa}7hWTpU-Oj$@nTJ3 zAhItmCKH)lPWq~52MJMa@p&N}9>nZGY!I`87JY({;5w@3=)u}&5)m9Yg5kRHNnqv$ zk>aq^IeIYEJI1a-+ffZfd&zw^{s9yAf}pE$zSW|Gfw5zBSR9>POt7v|w2g!#Mu)Qr z7^PlI=k8YRJ((=GS4i%4hFx>K9QWqW&L=WTPI|UrJBld$c135Cm$l7-i+M@cJR6$& zprJ4*wl9mNf-Q_ZMl8f#ILc#I*z98qAXeZZ_xRF$(8t9hw#<%?i&^KxJ}zblYMxr+ z?DIy#_VJfZe<9G)O_TOzy|wQ^3_Q<=ecTo$kR9-GF)Qe$C-8A^+831#HuE<29GY}b zJs-cf&?8J~LOiG&T{^Jz?m?6A1w~z5XS1$5?OmNqWUggBNAU#a?QQcvUV^h~NksaF zS7uacWL{p5yXIl;;H5YM3&CxayFvQ{76ry;nrG5%B9qNZ&u`mS=r!gvAAXt(TVOad zV1Hgl&|pqscV2ZzA3yeAXKR*Mhkmc-NY|58W})r*QQY>#FF*A?(O!}}6hudu4Ra8) z10=+(HzX1@iM&_6NZ&g-Gz-&XH{Fdozj5jV0;$V`uqC zEz2|AGFPuko3^P99<%iX-5$`#L%#D99%n*^ zCS)#~Y^GgdHM7U}q(o+ENqV+tx9JMtew+)nvE@nU?-t#Z_h*_LdS}RN&G$`jH^N4P z@Be4#8nN`B7XPvE!})#o6)z9~0T2KI5O^~JFE6GOmvg!KzdSrN=o5ZEz|YO>wVgo+ z;-X5fpWLX{)D304OuptG#PTD@8awEe>qK0}sBMz3kvsap zJ^OVQnreH6Oj;oE^0KqUa*Fs>`0_B6ZS9j{wY)yotH1MNJMpsSKRQzS&s_4#YJ_;< zBE{P3>BSvu!WRFFFUXZYULowGvN}?e=@Hc0+V|@^`UykHOIQ3ds;04n?mw`j?J*L( zWUE06+!O7$S_jLR|$I(A(^O?WE&qNW}x@j ziF~xN5VdA+Q~!LhXz%*IS`v0V1>Mqp4E!k_UO@ScEq3+}ye@5Sd8_F^DTeeM^! Yhr_*B_@co%y!MYEgqyZs&b`InitCapsuleSize(42.f, 96.0f); - - // set our turn rates for input - BaseTurnRate = 45.f; - BaseLookUpRate = 45.f; - - // Don't rotate when the controller rotates. Let that just affect the camera. - bUseControllerRotationPitch = false; - bUseControllerRotationYaw = false; - bUseControllerRotationRoll = false; - - // Configure character movement - GetCharacterMovement()->bOrientRotationToMovement = true; // Character moves in the direction of input... - GetCharacterMovement()->RotationRate = FRotator(0.0f, 540.0f, 0.0f); // ...at this rotation rate - GetCharacterMovement()->JumpZVelocity = 600.f; - GetCharacterMovement()->AirControl = 0.2f; - - // Create a camera boom (pulls in towards the player if there is a collision) - CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); - CameraBoom->SetupAttachment(RootComponent); - CameraBoom->TargetArmLength = 300.0f; // The camera follows at this distance behind the character - CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller - - // Create a follow camera - FollowCamera = CreateDefaultSubobject(TEXT("FollowCamera")); - FollowCamera->SetupAttachment(CameraBoom, USpringArmComponent::SocketName); // Attach the camera to the end of the boom and let the boom adjust to match the controller orientation - FollowCamera->bUsePawnControlRotation = false; // Camera does not rotate relative to arm - - AbilitiesComponent = CreateDefaultSubobject(TEXT("AbilitiesComponent")); - - // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) - // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) -} - -////////////////////////////////////////////////////////////////////////// -// Input - -void AARCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) -{ - // Set up gameplay key bindings - check(PlayerInputComponent); - PlayerInputComponent->BindAction("Jump", IE_Pressed, this, &ACharacter::Jump); - PlayerInputComponent->BindAction("Jump", IE_Released, this, &ACharacter::StopJumping); - - PlayerInputComponent->BindAxis("MoveForward", this, &AARCharacter::MoveForward); - PlayerInputComponent->BindAxis("MoveRight", this, &AARCharacter::MoveRight); - - // We have 2 versions of the rotation bindings to handle different kinds of devices differently - // "turn" handles devices that provide an absolute delta, such as a mouse. - // "turnrate" is for devices that we choose to treat as a rate of change, such as an analog joystick - PlayerInputComponent->BindAxis("Turn", this, &APawn::AddControllerYawInput); - PlayerInputComponent->BindAxis("TurnRate", this, &AARCharacter::TurnAtRate); - PlayerInputComponent->BindAxis("LookUp", this, &APawn::AddControllerPitchInput); - PlayerInputComponent->BindAxis("LookUpRate", this, &AARCharacter::LookUpAtRate); - - // handle touch devices - PlayerInputComponent->BindTouch(IE_Pressed, this, &AARCharacter::TouchStarted); - PlayerInputComponent->BindTouch(IE_Released, this, &AARCharacter::TouchStopped); - - // VR headset functionality - PlayerInputComponent->BindAction("ResetVR", IE_Pressed, this, &AARCharacter::OnResetVR); -} - - -void AARCharacter::OnResetVR() -{ -} - -void AARCharacter::TouchStarted(ETouchIndex::Type FingerIndex, FVector Location) -{ - Jump(); -} - -void AARCharacter::TouchStopped(ETouchIndex::Type FingerIndex, FVector Location) -{ - StopJumping(); -} - -void AARCharacter::TurnAtRate(float Rate) -{ - // calculate delta for this frame from the rate information - AddControllerYawInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds()); -} - -void AARCharacter::LookUpAtRate(float Rate) -{ - // calculate delta for this frame from the rate information - AddControllerPitchInput(Rate * BaseLookUpRate * GetWorld()->GetDeltaSeconds()); -} - -void AARCharacter::MoveForward(float Value) -{ - if ((Controller != NULL) && (Value != 0.0f)) - { - // find out which way is forward - const FRotator Rotation = Controller->GetControlRotation(); - const FRotator YawRotation(0, Rotation.Yaw, 0); - - // get forward vector - const FVector Direction = FRotationMatrix(YawRotation).GetUnitAxis(EAxis::X); - AddMovementInput(Direction, Value); - } -} - -void AARCharacter::MoveRight(float Value) -{ - if ( (Controller != NULL) && (Value != 0.0f) ) - { - // find out which way is right - const FRotator Rotation = Controller->GetControlRotation(); - const FRotator YawRotation(0, Rotation.Yaw, 0); - - // get right vector - const FVector Direction = FRotationMatrix(YawRotation).GetUnitAxis(EAxis::Y); - // add movement in that direction - AddMovementInput(Direction, Value); - } -} diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h deleted file mode 100644 index 5c08a80..0000000 --- a/Source/ActionRPGGame/ARCharacter.h +++ /dev/null @@ -1,75 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Character.h" -#include "GAAbilitiesComponent.h" -#include "ARCharacter.generated.h" - -UCLASS(config=Game) -class AARCharacter : public ACharacter -{ - GENERATED_BODY() - - /** Camera boom positioning the camera behind the character */ - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) - class USpringArmComponent* CameraBoom; - - /** Follow camera */ - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) - class UCameraComponent* FollowCamera; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) - class UGAAbilitiesComponent* AbilitiesComponent; -public: - AARCharacter(); - - /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) - float BaseTurnRate; - - /** Base look up/down rate, in deg/sec. Other scaling may affect final rate. */ - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) - float BaseLookUpRate; - -protected: - - /** Resets HMD orientation in VR. */ - void OnResetVR(); - - /** Called for forwards/backward input */ - void MoveForward(float Value); - - /** Called for side to side input */ - void MoveRight(float Value); - - /** - * Called via input to turn at a given rate. - * @param Rate This is a normalized rate, i.e. 1.0 means 100% of desired turn rate - */ - void TurnAtRate(float Rate); - - /** - * Called via input to turn look up/down at a given rate. - * @param Rate This is a normalized rate, i.e. 1.0 means 100% of desired turn rate - */ - void LookUpAtRate(float Rate); - - /** Handler for when a touch input begins. */ - void TouchStarted(ETouchIndex::Type FingerIndex, FVector Location); - - /** Handler for when a touch input stops. */ - void TouchStopped(ETouchIndex::Type FingerIndex, FVector Location); - -protected: - // APawn interface - virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; - // End of APawn interface - -public: - /** Returns CameraBoom subobject **/ - FORCEINLINE class USpringArmComponent* GetCameraBoom() const { return CameraBoom; } - /** Returns FollowCamera subobject **/ - FORCEINLINE class UCameraComponent* GetFollowCamera() const { return FollowCamera; } -}; - diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp deleted file mode 100644 index b24ea44..0000000 --- a/Source/ActionRPGGame/ARGameMode.cpp +++ /dev/null @@ -1,9 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "ARGameMode.h" -#include "ARCharacter.h" -#include "UObject/ConstructorHelpers.h" - -AARGameMode::AARGameMode() -{ -} diff --git a/Source/ActionRPGGame/ARGameMode.h b/Source/ActionRPGGame/ARGameMode.h deleted file mode 100644 index 46e5fe9..0000000 --- a/Source/ActionRPGGame/ARGameMode.h +++ /dev/null @@ -1,19 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/GameModeBase.h" -#include "ARGameMode.generated.h" - -UCLASS(minimalapi) -class AARGameMode : public AGameModeBase -{ - GENERATED_BODY() - -public: - AARGameMode(); -}; - - - diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs deleted file mode 100644 index b004faf..0000000 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ /dev/null @@ -1,13 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; - -public class ActionRPGGame : ModuleRules -{ - public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) - { - PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; - - PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", "AbilityFramework" }); - } -} diff --git a/Source/ActionRPGGame/ActionRPGGame.cpp b/Source/ActionRPGGame/ActionRPGGame.cpp deleted file mode 100644 index 173c45d..0000000 --- a/Source/ActionRPGGame/ActionRPGGame.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "ActionRPGGame.h" -#include "Modules/ModuleManager.h" - -IMPLEMENT_PRIMARY_GAME_MODULE( FDefaultGameModuleImpl, ActionRPGGame, "ActionRPGGame" ); - \ No newline at end of file diff --git a/Source/ActionRPGGame/ActionRPGGame.h b/Source/ActionRPGGame/ActionRPGGame.h deleted file mode 100644 index 25b0d29..0000000 --- a/Source/ActionRPGGame/ActionRPGGame.h +++ /dev/null @@ -1,5 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" diff --git a/Source/ActionRPGGameClient.Target.cs b/Source/ActionRPGGameClient.Target.cs deleted file mode 100644 index fbfd4ca..0000000 --- a/Source/ActionRPGGameClient.Target.cs +++ /dev/null @@ -1,14 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; -using System.Collections.Generic; - -public class ActionRPGGameClientTarget : TargetRules -{ - public ActionRPGGameClientTarget(TargetInfo Target) : base(Target) - { - Type = TargetType.Client; - LaunchModuleName = "ActionRPGGame"; - ExtraModuleNames.Add("ActionRPGGame"); - } -} diff --git a/Source/ActionRPGGameEditor.Target.cs b/Source/ActionRPGGameEditor.Target.cs deleted file mode 100644 index 7f23780..0000000 --- a/Source/ActionRPGGameEditor.Target.cs +++ /dev/null @@ -1,14 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; -using System.Collections.Generic; - -public class ActionRPGGameEditorTarget : TargetRules -{ - public ActionRPGGameEditorTarget(TargetInfo Target) : base (Target) - { - Type = TargetType.Editor; - ExtraModuleNames.Add("ActionRPGGame"); - //ExtraModuleNames.Add("ActionRPGGameEditor"); - } -} diff --git a/Source/ActionRPGGameServer.Target.cs b/Source/ActionRPGGameServer.Target.cs deleted file mode 100644 index 81d0745..0000000 --- a/Source/ActionRPGGameServer.Target.cs +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; -using System.Collections.Generic; - -[SupportedPlatforms(UnrealPlatformClass.Server)] -public class ActionRPGGameServerTarget : TargetRules -{ - public ActionRPGGameServerTarget(TargetInfo Target) : base(Target) - { - Type = TargetType.Server; - //bUsesSlate = false; - LaunchModuleName = "ActionRPGGame"; - ExtraModuleNames.Add("ActionRPGGame"); - } -} From 615e25b388281df49e5d7e065d09cffa81fcd30f Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 1 Jul 2017 17:58:30 +0200 Subject: [PATCH 003/187] new gitignore --- .gitignore | 264 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 264 insertions(+) create mode 100644 .gitignore diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..1cd7754 --- /dev/null +++ b/.gitignore @@ -0,0 +1,264 @@ +################# +## Eclipse +################# + +*.pydevproject +.project +.metadata +bin/ +tmp/ +*.tmp +*.bak +*.swp +*~.nib +local.properties +.classpath +.settings/ +.loadpath + +# External tool builders +.externalToolBuilders/ + +# Locally stored "Eclipse launch configurations" +*.launch + +# CDT-specific +.cproject + +# PDT-specific +.buildpath + + +################# +## Visual Studio +################# + +## Ignore Visual Studio temporary files, build results, and +## files generated by popular Visual Studio add-ons. + +# User-specific files +*.suo +*.user +*.sln.docstates +*.sln +*.sdf + +# Build results + +[Dd]ebug/ +[Rr]elease/ +x64/ +build/ +[Bb]in/ +[Oo]bj/ + +# MSTest test Results +[Tt]est[Rr]esult*/ +[Bb]uild[Ll]og.* + +*_i.c +*_p.c +*.ilk +*.meta +*.obj +*.pch +*.pdb +*.pgc +*.pgd +*.rsp +*.sbr +*.tlb +*.tli +*.tlh +*.tmp +*.tmp_proj +*.log +*.vspscc +*.vssscc +.builds +*.pidb +*.log +*.scc + +# Visual C++ cache files +ipch/ +*.aps +*.ncb +*.opensdf +*.sdf +*.cachefile + +# Visual Studio profiler +*.psess +*.vsp +*.vspx + +# Guidance Automation Toolkit +*.gpState + +# ReSharper is a .NET coding add-in +_ReSharper*/ +*.[Rr]e[Ss]harper + +# TeamCity is a build add-in +_TeamCity* + +# DotCover is a Code Coverage Tool +*.dotCover + +# NCrunch +*.ncrunch* +.*crunch*.local.xml + +# Installshield output folder +[Ee]xpress/ + +# DocProject is a documentation generator add-in +DocProject/buildhelp/ +DocProject/Help/*.HxT +DocProject/Help/*.HxC +DocProject/Help/*.hhc +DocProject/Help/*.hhk +DocProject/Help/*.hhp +DocProject/Help/Html2 +DocProject/Help/html + +# Click-Once directory +publish/ + +# Publish Web Output +*.Publish.xml +*.pubxml + +# NuGet Packages Directory +## TODO: If you have NuGet Package Restore enabled, uncomment the next line +#packages/ + +# Windows Azure Build Output +csx +*.build.csdef + +# Windows Store app package directory +AppPackages/ + +# Others +sql/ +*.Cache +ClientBin/ +[Ss]tyle[Cc]op.* +~$* +*~ +*.dbmdl +*.[Pp]ublish.xml +*.pfx +*.publishsettings + +# RIA/Silverlight projects +Generated_Code/ + +# Backup & report files from converting an old project file to a newer +# Visual Studio version. Backup files are not needed, because we have git ;-) +_UpgradeReport_Files/ +Backup*/ +UpgradeLog*.XML +UpgradeLog*.htm + +# SQL Server files +App_Data/*.mdf +App_Data/*.ldf + +############# +## Windows detritus +############# + +# Windows image file caches +Thumbs.db +ehthumbs.db + +# Folder config file +Desktop.ini + +# Recycle Bin used on file shares +$RECYCLE.BIN/ + +# Mac crap +.DS_Store + + +############# +## Python +############# + +*.py[co] + +# Packages +*.egg +*.egg-info +dist/ +build/ +eggs/ +parts/ +var/ +sdist/ +develop-eggs/ +.installed.cfg + +# Installer logs +pip-log.txt + +# Unit test / coverage reports +.coverage +.tox + +#Translations +*.mo + +#Mr Developer +.mr.developer.cfg + +# Compiled Object files +*.slo +*.lo +*.o +*.obj + +# Compiled Dynamic libraries +*.so +*.dylib +*.dll + +# Compiled Static libraries +*.lai +*.la +*.a +*.lib + +# Executables +*.exe +*.out +*.app + +#Unreal Engine + +Binaries/ +Plugins/ +Plugins/* +Content/* +!Content/Blueprints/ +!Plugins/AbilityFramework/Source +!Plugins/AbilityFrameworkEditor/Source +DerivedDataCache/ +Intermediate/ +Saved/ +*.sln +*.sln +*.sln +*.db +.vs/ActionRPGGame/v15/Browse.VC.opendb +*.db-shm +.vs/config/applicationhost.config +*.config +.vs/ActionRPGGame/v15/Solution.VC.db-wal +CodeBackup/States/GASAbilityStateCooldown.h +*.bin +*.pak From 24a729ad1d488d7a5f63a926d33e8a84d729b232 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 1 Jul 2017 17:58:49 +0200 Subject: [PATCH 004/187] update gitignore --- .gitignore | 2 ++ 1 file changed, 2 insertions(+) diff --git a/.gitignore b/.gitignore index 1cd7754..891ee34 100644 --- a/.gitignore +++ b/.gitignore @@ -240,6 +240,8 @@ pip-log.txt #Unreal Engine +.vs/ +.vs/* Binaries/ Plugins/ Plugins/* From e70d6c304110afaa01765207d98bcb166d0d26d1 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 4 Jul 2017 22:04:15 +0200 Subject: [PATCH 005/187] cleaining up fallout for latest ue master, and fixed some sequencer crash --- ActionRPGGame.uproject | 19 +- Config/DefaultEditor.ini | 7 +- .../DefaultEditorPerProjectUserSettings.ini | 34 +- Config/DefaultEngine.ini | 127 ++- Config/DefaultGame.ini | 7 +- Config/DefaultGameplayTags.ini | 18 + Config/DefaultInput.ini | 121 ++- .../AbilityFramework/AbilityFramework.uplugin | 10 +- .../Source/AbilityFramework/AFCueManager.cpp | 84 +- .../Source/AbilityFramework/AFCueManager.h | 9 +- .../AFAbilityInfiniteDurationSpec.cpp | 7 +- .../Abilities/AFAbilityInfiniteDurationSpec.h | 5 +- .../Abilities/AFBlueprintFunctionLibrary.cpp | 12 +- .../Abilities/GAAbilityBase.cpp | 75 +- .../Abilities/GAAbilityBase.h | 57 +- .../Abilities/Tasks/GAAbilityTask.h | 4 +- .../Tasks/GAAbilityTask_PlayMontage.cpp | 2 +- .../Tasks/GAAbilityTask_TargetData.cpp | 9 - .../Tasks/GAAbilityTask_TargetData.h | 5 +- .../Tasks/GAAbilityTask_TargetDataCircle.cpp | 57 +- .../Tasks/GAAbilityTask_TargetDataCircle.h | 13 +- .../Tasks/GAAbilityTask_WaitTargetData.cpp | 109 ++- .../Tasks/GAAbilityTask_WaitTargetData.h | 18 +- .../AbilityCues/GAAbilityCue.cpp | 19 - .../AbilityCues/GAAbilityCue.h | 68 -- .../AbilityCues/GACueActor.cpp | 30 - .../AbilityFramework/AbilityCues/GACueActor.h | 73 -- .../AbilityFramework.Build.cs | 5 +- .../AnimNotify/AFAbilityNotifyState.cpp | 6 +- .../AnimNotify/AFAbilityNotifyState.h | 2 +- .../AnimNotify/AFAnimNotify.cpp | 8 +- .../AnimNotify/AFAnimNotifyBase.cpp | 8 +- .../AbilityFramework/Async/AsyncUObject.cpp | 12 - .../AbilityFramework/Async/AsyncUObject.h | 47 -- .../Async/AsyncUObjectImpl.cpp | 12 - .../AbilityFramework/Async/AsyncUObjectImpl.h | 61 -- .../Attributes/GAAttributeBase.cpp | 4 +- .../Attributes/GAAttributeBase.h | 2 +- .../Attributes/GAAttributesBase.cpp | 4 +- .../Attributes/GAAttributesBase.h | 4 +- .../GAAttributesBlueprintFunctionLibrary.cpp | 10 +- .../Effects/AFEffectCustomStackingRule.cpp | 2 +- .../Effects/AFEffectCustomStackingRule.h | 2 +- .../AFAttributeStongerOverride.cpp | 2 +- .../AFAtributeDurationAdd.cpp | 4 +- .../AFAttributeDurationOverride.cpp | 4 +- .../AFPeriodApplicationAdd.cpp | 6 +- .../AFPeriodApplicationExtend.cpp | 8 +- .../AFPeriodApplicationInfiniteAdd.cpp | 4 +- .../AFPeriodApplicationOverride.cpp | 6 +- .../Effects/EffectTasks/AFEffectTask.h | 4 +- .../AFEffectTask_AttributeChange.cpp | 8 +- .../AFEffectTask_AttributeChange.h | 4 +- .../EffectTasks/AFEffectTask_EffectEvent.cpp | 10 +- .../EffectTasks/AFEffectTask_EffectEvent.h | 4 +- .../Effects/GABlueprintLibrary.cpp | 34 +- .../Effects/GABlueprintLibrary.h | 7 +- .../AbilityFramework/Effects/GAEffectCue.cpp | 28 +- .../AbilityFramework/Effects/GAEffectCue.h | 16 +- .../Effects/GAEffectCueGlobals.cpp | 2 +- .../Effects/GAEffectCueGlobals.h | 2 +- .../Effects/GAEffectExecution.cpp | 2 +- .../Effects/GAEffectExtension.cpp | 2 +- .../Effects/GAEffectExtension.h | 2 +- .../Effects/GAEffectGlobalTypes.cpp | 16 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 33 +- .../AbilityFramework/Effects/GAGameEffect.h | 8 +- .../AbilityFramework/GAAbilitiesComponent.cpp | 790 ------------------ .../AbilityFramework/GAAbilitiesComponent.h | 595 ------------- .../Source/AbilityFramework/GAGlobalTypes.cpp | 22 +- .../Source/AbilityFramework/GAGlobalTypes.h | 16 +- .../AbilityFramework/GAHelperTemplates.h | 6 +- .../Source/AbilityFramework/IGAAbilities.cpp | 10 - .../Source/AbilityFramework/IGAAbilities.h | 48 -- .../Targeting/GASAbilityTargetingObject.cpp | 36 - .../Targeting/GASAbilityTargetingObject.h | 27 - .../Targeting/GATargetingActor.cpp | 28 - .../Targeting/GATargetingActor.h | 25 - .../Tests/GAAttributesTest.cpp | 2 +- .../AbilityFramework/Tests/GAAttributesTest.h | 2 +- .../Tests/GAAttributesTests.cpp | 13 +- .../Tests/GACharacterAttributeTest.cpp | 6 +- .../Tests/GACharacterAttributeTest.h | 8 +- .../Tests/GASpellExecutionTest.cpp | 2 +- .../AbilityFrameworkEditor.Build.cs | 12 +- .../AbilityFrameworkEditor.cpp | 59 +- .../AbilityFrameworkEditor.h | 40 +- .../EffectCueEditor/GAEffectCueEditor.cpp | 109 +-- .../EffectCueEditor/GAEffectCueEditor.h | 11 - .../IGameAttributesEditor.h | 39 - Source/ActionRPGGame/AI/ARAICharacter.cpp | 83 ++ Source/ActionRPGGame/AI/ARAICharacter.h | 58 ++ Source/ActionRPGGame/AI/ARAIController.cpp | 7 + Source/ActionRPGGame/AI/ARAIController.h | 20 + ...onRPGGameCharacter.cpp => ARCharacter.cpp} | 97 ++- ...ActionRPGGameCharacter.h => ARCharacter.h} | 44 +- Source/ActionRPGGame/ARGameMode.cpp | 8 + .../{ActionRPGGameGameMode.h => ARGameMode.h} | 6 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 23 +- .../ActionRPGGame/ActionRPGGameGameMode.cpp | 15 - .../Attributes/ARCharacterAttributes.cpp | 17 + .../Attributes/ARCharacterAttributes.h | 32 + .../Attributes/ARGunAttributes.cpp | 7 + .../Attributes/ARGunAttributes.h | 20 + .../Attributes/ARHealthExtension.cpp | 7 + .../Attributes/ARHealthExtension.h | 20 + Source/ActionRPGGameServer.Target.cs | 14 + 107 files changed, 1179 insertions(+), 2609 deletions(-) create mode 100644 Config/DefaultGameplayTags.ini delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h create mode 100644 Source/ActionRPGGame/AI/ARAICharacter.cpp create mode 100644 Source/ActionRPGGame/AI/ARAICharacter.h create mode 100644 Source/ActionRPGGame/AI/ARAIController.cpp create mode 100644 Source/ActionRPGGame/AI/ARAIController.h rename Source/ActionRPGGame/{ActionRPGGameCharacter.cpp => ARCharacter.cpp} (65%) rename Source/ActionRPGGame/{ActionRPGGameCharacter.h => ARCharacter.h} (55%) create mode 100644 Source/ActionRPGGame/ARGameMode.cpp rename Source/ActionRPGGame/{ActionRPGGameGameMode.h => ARGameMode.h} (61%) delete mode 100644 Source/ActionRPGGame/ActionRPGGameGameMode.cpp create mode 100644 Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp create mode 100644 Source/ActionRPGGame/Attributes/ARCharacterAttributes.h create mode 100644 Source/ActionRPGGame/Attributes/ARGunAttributes.cpp create mode 100644 Source/ActionRPGGame/Attributes/ARGunAttributes.h create mode 100644 Source/ActionRPGGame/Attributes/ARHealthExtension.cpp create mode 100644 Source/ActionRPGGame/Attributes/ARHealthExtension.h create mode 100644 Source/ActionRPGGameServer.Target.cs diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 8e4bb4d..52edb78 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -1,13 +1,28 @@ { "FileVersion": 3, - "EngineAssociation": "{A035B080-4493-F253-AA70-EF8A66B855F8}", + "EngineAssociation": "{C19309FF-49B1-44A8-E307-2B81122303E8}", "Category": "", "Description": "", "Modules": [ { "Name": "ActionRPGGame", "Type": "Runtime", - "LoadingPhase": "Default" + "LoadingPhase": "Default", + "AdditionalDependencies": [ + "AbilityFramework", + "Engine", + "AIModule" + ] + } + ], + "Plugins": [ + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true } ] } \ No newline at end of file diff --git a/Config/DefaultEditor.ini b/Config/DefaultEditor.ini index 56c4d58..68e034e 100644 --- a/Config/DefaultEditor.ini +++ b/Config/DefaultEditor.ini @@ -1,8 +1,7 @@ -[UnrealEd.SimpleMap] -SimpleMapName=/Game/ThirdPersonCPP/Maps/ThirdPersonExampleMap - [EditoronlyBP] bAllowClassAndBlueprintPinMatching=true bReplaceBlueprintWithClass= true bDontLoadBlueprintOutsideEditor= true -bBlueprintIsNotBlueprintType= true \ No newline at end of file +bBlueprintIsNotBlueprintType= true + + diff --git a/Config/DefaultEditorPerProjectUserSettings.ini b/Config/DefaultEditorPerProjectUserSettings.ini index 4dcc526..5e1c2fc 100644 --- a/Config/DefaultEditorPerProjectUserSettings.ini +++ b/Config/DefaultEditorPerProjectUserSettings.ini @@ -1,2 +1,34 @@ [ContentBrowser] -ContentBrowserTab1.SelectedPaths=/Game/ThirdPersonCPP \ No newline at end of file +ContentBrowserTab1.SelectedPaths=/Game/ThirdPersonCPP + +[/Script/UnrealEd.EditorExperimentalSettings] +bProceduralFoliage=False +bEnableLocalizationDashboard=True +bEnableTranslationPicker=False +bEnableEditorUtilityBlueprints=False +bEnableFavoriteSystem=False +bDeviceOutputLog=False +ConsoleForGamepadLabels=None +bToolbarCustomization=False +bBreakOnExceptions=False +bBlueprintPerformanceAnalysisTools=False +bEnableFindAndReplaceReferences=False +bDrawMidpointArrowsInBlueprints=False +bContextMenuChunkAssignments=False +bDisableCookInEditor=False +bSharedCookedBuilds=False +MultiProcessCooking=0 +bEQSEditor=True +bAllowLateJoinInPIE=False +bAllowVulkanPreview=False +bEnableMultithreadedLightmapEncoding=False +bEnableMultithreadedShadowmapEncoding=False +bUseOpenCLForConvexHullDecomp=False +bAllowPotentiallyUnsafePropertyEditing=False +bFacialAnimationImporter=False +bClothingTools=True +bEnableLiveRecompilationOfAnimationBlueprints=True +bMobilePIEPreviewDeviceLaunch=False +bAssetMaterialBaking=False + + diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 606de6a..1350a0c 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -1,20 +1,127 @@ -[/Script/EngineSettings.GameMapsSettings] -GameDefaultMap=/Game/ThirdPersonCPP/Maps/ThirdPersonExampleMap -EditorStartupMap=/Game/ThirdPersonCPP/Maps/ThirdPersonExampleMap -GlobalDefaultGameMode="/Script/ActionRPGGame.ActionRPGGameGameMode" - [/Script/IOSRuntimeSettings.IOSRuntimeSettings] MinimumiOSVersion=IOS_8 [/Script/HardwareTargeting.HardwareTargetingSettings] TargetedHardwareClass=Desktop +AppliedTargetedHardwareClass=Desktop DefaultGraphicsPerformance=Maximum +AppliedDefaultGraphicsPerformance=Maximum + +[/Script/EngineSettings.GameMapsSettings] +GlobalDefaultGameMode=/Game/Prototypes/ProtGameMode.ProtGameMode_C +GameDefaultMap=/Game/Maps/StartMap.StartMap +ServerDefaultMap=/Game/Maps/StartMap.StartMap +EditorStartupMap=/Game/Maps/StartMap.StartMap + +[/Script/Engine.RendererSettings] +r.AllowStaticLighting=False +r.GenerateMeshDistanceFields=True +r.DistanceFieldBuild.EightBit=True +r.SupportStationarySkylight=False +r.SupportLowQualityLightmaps=False +r.ClearCoatNormal=True + +[/Script/Engine.StreamingSettings] +s.AsyncLoadingThreadEnabled=True + +[/Script/Engine.CollisionProfile] +-Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) +-Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="OverlapAll",CollisionEnabled=QueryOnly,ObjectTypeName="WorldStatic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="BlockAllDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=,HelpMessage="WorldDynamic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="OverlapAllDynamic",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="IgnoreOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that ignores Pawn and Vehicle. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="OverlapOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that overlaps Pawn, Camera, and Vehicle. All other channels will be set to default. ",bCanModify=False) +-Profiles=(Name="Pawn",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Pawn",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object. Can be used for capsule of any playerable character or AI. ",bCanModify=False) +-Profiles=(Name="Spectator",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="WorldStatic"),(Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore),(Channel="PhysicsBody",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Destructible",Response=ECR_Ignore)),HelpMessage="Pawn object that ignores all other actors except WorldStatic.",bCanModify=False) +-Profiles=(Name="CharacterMesh",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object that is used for Character Mesh. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="PhysicsActor",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=,HelpMessage="Simulating actors",bCanModify=False) +-Profiles=(Name="Destructible",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Destructible",CustomResponses=,HelpMessage="Destructible actors",bCanModify=False) +-Profiles=(Name="InvisibleWall",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldStatic object that is invisible.",bCanModify=False) +-Profiles=(Name="InvisibleWallDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that is invisible.",bCanModify=False) +-Profiles=(Name="Trigger",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that is used for trigger. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) ++Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="OverlapAll",CollisionEnabled=QueryOnly,ObjectTypeName="WorldStatic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="BlockAllDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=,HelpMessage="WorldDynamic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="OverlapAllDynamic",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="IgnoreOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that ignores Pawn and Vehicle. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="OverlapOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that overlaps Pawn, Camera, and Vehicle. All other channels will be set to default. ",bCanModify=False) ++Profiles=(Name="Pawn",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Pawn",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object. Can be used for capsule of any playerable character or AI. ",bCanModify=False) ++Profiles=(Name="Spectator",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="WorldStatic"),(Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore),(Channel="PhysicsBody",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Destructible",Response=ECR_Ignore)),HelpMessage="Pawn object that ignores all other actors except WorldStatic.",bCanModify=False) ++Profiles=(Name="CharacterMesh",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object that is used for Character Mesh. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="PhysicsActor",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=,HelpMessage="Simulating actors",bCanModify=False) ++Profiles=(Name="Destructible",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Destructible",CustomResponses=,HelpMessage="Destructible actors",bCanModify=False) ++Profiles=(Name="InvisibleWall",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldStatic object that is invisible.",bCanModify=False) ++Profiles=(Name="InvisibleWallDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that is invisible.",bCanModify=False) ++Profiles=(Name="Trigger",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that is used for trigger. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Block,bTraceType=True,bStaticObject=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Ignore,bTraceType=True,bStaticObject=False) +-ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") +-ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") +-ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") +-ProfileRedirects=(OldName="SkeletalMeshActor",NewName="PhysicsActor") +-ProfileRedirects=(OldName="InvisibleActor",NewName="InvisibleWallDynamic") ++ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") ++ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") ++ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") ++ProfileRedirects=(OldName="SkeletalMeshActor",NewName="PhysicsActor") ++ProfileRedirects=(OldName="InvisibleActor",NewName="InvisibleWallDynamic") +-CollisionChannelRedirects=(OldName="Static",NewName="WorldStatic") +-CollisionChannelRedirects=(OldName="Dynamic",NewName="WorldDynamic") +-CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +-CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") ++CollisionChannelRedirects=(OldName="Static",NewName="WorldStatic") ++CollisionChannelRedirects=(OldName="Dynamic",NewName="WorldDynamic") ++CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") ++CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") +[/Script/Engine.PhysicsSettings] +DefaultGravityZ=-980.000000 +DefaultTerminalVelocity=4000.000000 +DefaultFluidFriction=0.300000 +SimulateScratchMemorySize=262144 +RagdollAggregateThreshold=4 +TriangleMeshTriangleMinAreaThreshold=5.000000 +bEnableAsyncScene=False +bEnableShapeSharing=False +bEnablePCM=True +bEnableStabilization=False +bWarnMissingLocks=True +bEnable2DPhysics=False +LockedAxis=Invalid +DefaultDegreesOfFreedom=Full3D +BounceThresholdVelocity=200.000000 +FrictionCombineMode=Average +RestitutionCombineMode=Average +MaxAngularVelocity=3600.000000 +MaxDepenetrationVelocity=0.000000 +ContactOffsetMultiplier=0.020000 +MinContactOffset=2.000000 +MaxContactOffset=8.000000 +bSimulateSkeletalMeshOnDedicatedServer=True +DefaultShapeComplexity=CTF_UseSimpleAndComplex +bDefaultHasComplexCollision=True +bSuppressFaceRemapTable=False +bSupportUVFromHitResults=False +bDisableActiveActors=False +bDisableCCD=False +bEnableEnhancedDeterminism=False +MaxPhysicsDeltaTime=0.033333 +bSubstepping=False +bSubsteppingAsync=False +MaxSubstepDeltaTime=0.016667 +MaxSubsteps=6 +SyncSceneSmoothingFactor=0.000000 +AsyncSceneSmoothingFactor=0.990000 +InitialAverageFrameRate=0.016667 +PhysXTreeRebuildRate=10 -[/Script/Engine.Engine] -+ActiveGameNameRedirects=(OldGameName="TP_ThirdPerson",NewGameName="/Script/ActionRPGGame") -+ActiveGameNameRedirects=(OldGameName="/Script/TP_ThirdPerson",NewGameName="/Script/ActionRPGGame") -+ActiveClassRedirects=(OldClassName="TP_ThirdPersonGameMode",NewClassName="ActionRPGGameGameMode") -+ActiveClassRedirects=(OldClassName="TP_ThirdPersonCharacter",NewClassName="ActionRPGGameCharacter") diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index d913b55..31924c9 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -2,6 +2,7 @@ ProjectID=53E63CC7411F280A64FAD489EBFD3E33 ProjectName=Third Person Game Template -[StartupActions] -bAddPacks=True -InsertPack=(PackSource="StarterContent.upack,PackName="StarterContent") +[/Script/AbilityFramework.AFCueManager] +DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet + + diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini new file mode 100644 index 0000000..5f755a8 --- /dev/null +++ b/Config/DefaultGameplayTags.ini @@ -0,0 +1,18 @@ + +[/Script/GameplayTags.GameplayTagsSettings] +ImportTagsFromConfig=True +WarnOnInvalidTags=True +FastReplication=False +NumBitsForContainerSize=6 +NetIndexFirstBitSegment=16 +-GameplayTagList=(Tag="Ability.Rifle",DevComment="") +-GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +-GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +-GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") ++GameplayTagList=(Tag="Ability.Rifle",DevComment="") ++GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") ++GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") ++GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") ++GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") + + diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 1641e20..1a6997d 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -1,24 +1,103 @@ -[/Script/Engine.InputSettings] -+ActionMappings=(ActionName="Jump", Key=SpaceBar) -+ActionMappings=(ActionName="Jump", Key=Gamepad_FaceButton_Bottom) - -+AxisMappings=(AxisName="MoveForward", Key=W, Scale=1.f) -+AxisMappings=(AxisName="MoveForward", Key=S, Scale=-1.f) -+AxisMappings=(AxisName="MoveForward", Key=Up, Scale=1.f) -+AxisMappings=(AxisName="MoveForward", Key=Down, Scale=-1.f) -+AxisMappings=(AxisName="MoveForward", Key=Gamepad_LeftY, Scale=1.f) -+AxisMappings=(AxisName="MoveRight", Key=A, Scale=-1.f) -+AxisMappings=(AxisName="MoveRight", Key=D, Scale=1.f) -+AxisMappings=(AxisName="MoveRight", Key=Gamepad_LeftX, Scale=1.f) - -+AxisMappings=(AxisName="TurnRate", Key=Gamepad_RightX, Scale=1.f) -+AxisMappings=(AxisName="TurnRate", Key=Left, Scale=-1.f) -+AxisMappings=(AxisName="TurnRate", Key=Right, Scale=1.f) -+AxisMappings=(AxisName="Turn", Key=MouseX, Scale=1.f) +[/Script/Engine.InputSettings] +-AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MouseWheelAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_LeftTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_RightTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MouseWheelAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_LeftTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_RightTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +bAltEnterTogglesFullscreen=True +bF11TogglesFullscreen=True +bUseMouseForTouch=False +bEnableMouseSmoothing=True +bEnableFOVScaling=True +FOVScale=0.011110 +DoubleClickTime=0.200000 +bCaptureMouseOnLaunch=True +DefaultViewportMouseCaptureMode=CapturePermanently_IncludingInitialMouseDown +bDefaultViewportMouseLock=False +DefaultViewportMouseLockMode=LockOnCapture +-ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="NewActionMapping_0",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) +-AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) +-AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) +-AxisMappings=(AxisName="MoveForward",Key=Down,Scale=-1.000000) +-AxisMappings=(AxisName="MoveForward",Key=Gamepad_LeftY,Scale=1.000000) +-AxisMappings=(AxisName="MoveRight",Key=A,Scale=-1.000000) +-AxisMappings=(AxisName="MoveRight",Key=D,Scale=1.000000) +-AxisMappings=(AxisName="MoveRight",Key=Gamepad_LeftX,Scale=1.000000) +-AxisMappings=(AxisName="TurnRate",Key=Gamepad_RightX,Scale=1.000000) +-AxisMappings=(AxisName="TurnRate",Key=Left,Scale=-1.000000) +-AxisMappings=(AxisName="TurnRate",Key=Right,Scale=1.000000) +-AxisMappings=(AxisName="Turn",Key=MouseX,Scale=1.000000) +-AxisMappings=(AxisName="LookUpRate",Key=Gamepad_RightY,Scale=1.000000) +-AxisMappings=(AxisName="LookUp",Key=MouseY,Scale=-1.000000) ++AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) ++AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) ++AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) ++AxisMappings=(AxisName="MoveForward",Key=Down,Scale=-1.000000) ++AxisMappings=(AxisName="MoveForward",Key=Gamepad_LeftY,Scale=1.000000) ++AxisMappings=(AxisName="MoveRight",Key=A,Scale=-1.000000) ++AxisMappings=(AxisName="MoveRight",Key=D,Scale=1.000000) ++AxisMappings=(AxisName="MoveRight",Key=Gamepad_LeftX,Scale=1.000000) ++AxisMappings=(AxisName="TurnRate",Key=Gamepad_RightX,Scale=1.000000) ++AxisMappings=(AxisName="TurnRate",Key=Left,Scale=-1.000000) ++AxisMappings=(AxisName="TurnRate",Key=Right,Scale=1.000000) ++AxisMappings=(AxisName="Turn",Key=MouseX,Scale=1.000000) ++AxisMappings=(AxisName="LookUpRate",Key=Gamepad_RightY,Scale=1.000000) ++AxisMappings=(AxisName="LookUp",Key=MouseY,Scale=-1.000000) +bAlwaysShowTouchInterface=False +bShowConsoleOnFourFingerTap=True +DefaultTouchInterface=/Engine/MobileResources/HUD/DefaultVirtualJoysticks.DefaultVirtualJoysticks +ConsoleKey=None +-ConsoleKeys=Tilde ++ConsoleKeys=Tilde -+AxisMappings=(AxisName="LookUpRate", Key=Gamepad_RightY, Scale=1.f) -+AxisMappings=(AxisName="LookUp", Key=MouseY, Scale=-1.f) -+ActionMappings=(ActionName="ResetVR", Key=R) -+ActionMappings=(ActionName="ResetVR",Key=MotionController_Left_Grip1,bShift=False,bCtrl=False,bAlt=False,bCmd=False) diff --git a/Plugins/AbilityFramework/AbilityFramework.uplugin b/Plugins/AbilityFramework/AbilityFramework.uplugin index b2c0f8b..b301dbe 100644 --- a/Plugins/AbilityFramework/AbilityFramework.uplugin +++ b/Plugins/AbilityFramework/AbilityFramework.uplugin @@ -19,10 +19,10 @@ "Type": "Runtime", "LoadingPhase": "Default" }, - { - "Name": "AbilityFrameworkEditor", - "Type": "Editor", - "LoadingPhase": "Default" - } + { + "Name": "AbilityFrameworkEditor", + "Type": "Editor", + "LoadingPhase": "PostEngineInit" + } ] } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index 4775895..b45079e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -56,22 +56,35 @@ void UAFCueManager::HandleOnPIEEnd(bool InVal) } for (auto It = UsedCues.CreateIterator(); It; ++It) { - if (It->Value.IsValid()) + if (It->Value.Num() <= 0) { - while (!It->Value->IsEmpty()) + UsedCues.Remove(It->Key); + } + for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) + { + if (QIt->Value.IsValid()) { - AGAEffectCue* ToDestroy = nullptr; - It->Value->Dequeue(ToDestroy); - if (ToDestroy) + while (!QIt->Value->IsEmpty()) { - ToDestroy->Destroy(); + AGAEffectCue* ToDestroy = nullptr; + QIt->Value->Dequeue(ToDestroy); + if (ToDestroy) + { + ToDestroy->Destroy(); + } } } + if (It->Value.Num() <= 0) + { + UsedCues.Remove(It->Key); + } } + } } #endif //WITH_EDITOR -void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams) +void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams) { if (!CurrentWorld) CurrentWorld = CueParams.Instigator->GetWorld(); @@ -123,33 +136,74 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, const FGAEffect FVector Location = CueParams.HitResult.Location; FRotator Rotation = FRotator::ZeroRotator; AGAEffectCue* actor = nullptr; - /* TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); + TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); if (!Cues.IsValid()) { Cues = MakeUnique>(); } - TUniquePtr>& UseCues = UsedCues.FindOrAdd(Tag); - if (!UseCues.IsValid()) + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(Tag); + + if (!UseCuesQueue.IsValid()) { - UseCues = MakeUnique>(); + UseCuesQueue = MakeUnique>(); } if (Cues->IsEmpty()) { actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); Cues->Enqueue(actor); + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); } else { Cues->Dequeue(actor); - UseCues->Enqueue(actor); - }*/ + UseCuesQueue->Enqueue(actor); + } - actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); + //actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - CueParams.Causer.Get(), CueParams.HitResult); + CueParams.Causer.Get(), CueParams.HitResult, CueParams); /*UseCues->Dequeue(actor); Cues->Enqueue(actor);*/ } +} +void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams) +{ + if (!CurrentWorld) + CurrentWorld = CueParams.Instigator->GetWorld(); + for (const FGameplayTag& Tag : CueParams.CueTags) + { + TSubclassOf CueClass = CueSet->Cues.FindRef(Tag); + if (!CueClass) + continue; + + AGAEffectCue* actor = nullptr; + TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); + if (!Cues.IsValid()) + { + Cues = MakeUnique>(); + } + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(Tag); + + if (!UseCuesQueue.IsValid()) + { + UseCuesQueue = MakeUnique>(); + } + + UseCuesQueue->Dequeue(actor); + + + if (actor) + { + Cues->Enqueue(actor); + actor->NativeOnRemoved(); + } + } } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h index af0691c..777afce 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h @@ -26,10 +26,12 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject UPROPERTY() UAFCueSet* CueSet; + //store per instigator ? Causer ? or global pool ? //stores unused instanced cues. TMap>> InstancedCues; + //store per instigator ? Causer ? //stores used cues. - TMap>> UsedCues; + TMap>>> UsedCues; public: void Initialize(); void LoadCueSet(); @@ -39,5 +41,8 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject #endif //WITH_EDITOR public: static UAFCueManager* Get(); - void HandleCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams); + void HandleCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams); + void HandleRemoveCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp index 51665d7..19cf6ce 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp @@ -1,8 +1,13 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" +#include "Effects/CustomApplications/AFAttributeDurationInfinite.h" #include "AFAbilityInfiniteDurationSpec.h" - +UAFAbilityInfiniteDurationSpec::UAFAbilityInfiniteDurationSpec() + :Super() +{ + Application = UAFAttributeDurationInfinite::StaticClass(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h index cc0f2ae..89b59a2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h @@ -9,11 +9,12 @@ /** * */ -UCLASS() +UCLASS(Blueprintable, BlueprintType, Abstract) class ABILITYFRAMEWORK_API UAFAbilityInfiniteDurationSpec : public UGAGameEffectSpec { GENERATED_BODY() - +public: + UAFAbilityInfiniteDurationSpec(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp index e0d984d..68e2a65 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp @@ -4,20 +4,20 @@ #include "GAAbilityBase.h" #include "../Effects/GAEffectField.h" -#include "../IGAAbilities.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityInterface.h" +#include "../AFAbilityComponent.h" #include "AFBlueprintFunctionLibrary.h" void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag) { - IIGAAbilities* Interface = Cast(Target); + IAFAbilityInterface* Interface = Cast(Target); if (!Interface) { UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Invalid Target")); return; } - UGAAbilitiesComponent* Comp = Interface->GetAbilityComp(); + UAFAbilityComponent* Comp = Interface->GetAbilityComp(); if (!Comp) { UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Target %s InvalidComponent"), *Target->GetName()); @@ -29,13 +29,13 @@ void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag) { - IIGAAbilities* Interface = Cast(Target); + IAFAbilityInterface* Interface = Cast(Target); if (!Interface) { UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Invalid Target")); return; } - UGAAbilitiesComponent* Comp = Interface->GetAbilityComp(); + UAFAbilityComponent* Comp = Interface->GetAbilityComp(); if (!Comp) { UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Target %s InvalidComponent"), *Target->GetName()); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index f7cdf31..b0966dd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -6,13 +6,11 @@ #include "../Effects/GAGameEffect.h" #include "../GAGlobalTypes.h" #include "../Effects/GAEffectGlobalTypes.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" -#include "../AbilityCues/GACueActor.h" #include "GameplayTagContainer.h" #include "Net/UnrealNetwork.h" #include "Animation/AnimMontage.h" -#include "../AbilityCues/GAAbilityCue.h" #include "../Effects/GABlueprintLibrary.h" #include "Camera/CameraComponent.h" #include "Kismet/KismetSystemLibrary.h" @@ -58,19 +56,12 @@ void UGAAbilityBase::InitAbility() //still want to initialize, as Spec is used in multiple places. ActivationEffect.InitializeIfNotInitialized(); CooldownEffect.InitializeIfNotInitialized(); - DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, this, FHitResult(ForceInit)); + DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)); if (AbilityComponent) { World = AbilityComponent->GetWorld(); } - if (POwner && POwner->GetNetMode() != ENetMode::NM_Standalone) - { - InitAbilityCounter++; - } - else - { - OnRep_InitAbility(); - } + if (!AbilityComponent) { AbilityComponent = GetAbilityComp(); @@ -92,10 +83,7 @@ void UGAAbilityBase::InitAbility() TickFunction.RegisterTickFunction(AbilityComponent->GetWorld()->GetCurrentLevel()); TickFunction.SetTickFunctionEnable(true); } -void UGAAbilityBase::OnRep_InitAbility() -{ -} void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName) { { @@ -144,10 +132,10 @@ void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) void UGAAbilityBase::OnCooldownEffectExpired() { UE_LOG(AbilityFramework, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); - CooldownEffectExpiredCounter++; + if (CooldownEffectHandle.IsValid()) { - CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect); + CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); } } /* Functions for activation effect delegates */ @@ -172,7 +160,7 @@ void UGAAbilityBase::NativeOnAbilityActivationCancel() void UGAAbilityBase::OnActivationEffectPeriod(const FGAEffectHandle& InHandle) { UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); - AbilityPeriodCounter++; + OnPeriod(); } void UGAAbilityBase::FinishAbility() @@ -191,7 +179,7 @@ void UGAAbilityBase::NativeFinishAbility() OnConfirmDelegate.RemoveAll(this); //if (ActivationEffect.Handle.IsValid()) { - AbilityComponent->RemoveEffect(ActivationEffect); + AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext); } //remove effect. } @@ -202,10 +190,10 @@ void UGAAbilityBase::CancelActivation() } void UGAAbilityBase::NativeCancelActivation() { - UGAAbilitiesComponent* AttrComp = ActivationEffect.Handle.GetContext().InstigatorComp.Get(); + UAFAbilityComponent* AttrComp = ActivationEffect.Handle.GetContext().InstigatorComp.Get(); if (AbilityComponent) { - AbilityComponent->RemoveEffect(ActivationEffect); + AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext); } } @@ -246,7 +234,7 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) { bApplyActivationEffect = true; } - ActivationInfo.SetActivationInfo(GetWorld()->TimeSeconds, DurationCheck, PeriodCheck, bApplyActivationEffect); + if (bApplyActivationEffect) { FHitResult HitIn; @@ -382,9 +370,9 @@ class UGAAttributesBase* UGAAbilityBase::GetAttributes() { return Attributes; } -UGAAbilitiesComponent* UGAAbilityBase::GetAbilityComp() +UAFAbilityComponent* UGAAbilityBase::GetAbilityComp() { - IIGAAbilities* OwnerAttributes = Cast(POwner); + IAFAbilityInterface* OwnerAttributes = Cast(POwner); if (OwnerAttributes) { return OwnerAttributes->GetAbilityComp(); @@ -494,48 +482,15 @@ void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, flo void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const { Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly can be infered apon replication. DOREPLIFETIME(UGAAbilityBase, POwner); DOREPLIFETIME(UGAAbilityBase, Character); DOREPLIFETIME(UGAAbilityBase, PCOwner); DOREPLIFETIME(UGAAbilityBase, AICOwner); //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. - DOREPLIFETIME(UGAAbilityBase, CooldownStartedCounter); - DOREPLIFETIME(UGAAbilityBase, CooldownEffectExpiredCounter); - DOREPLIFETIME_CONDITION(UGAAbilityBase, ActivationInfo, COND_SkipOwner); - //DOREPLIFETIME(UGAAbilityBase, ActivationInfo); - DOREPLIFETIME(UGAAbilityBase, AbilityActivationStartedCounter); - DOREPLIFETIME(UGAAbilityBase, AbilityPeriodCounter); - DOREPLIFETIME(UGAAbilityBase, InitAbilityCounter); - DOREPLIFETIME(UGAAbilityBase, AbilityHits); - //DOREPLIFETIME(UGAAbilitiesComponent, RepMontage); -} -/* - Do some yet undertemined client stuff. - Call events ? -*/ -void UGAAbilityBase::OnRep_CooldownStarted() -{ - -} -void UGAAbilityBase::OnRep_CooldownExpired() -{ - -} -void UGAAbilityBase::OnRep_AbilityActivationStarted() -{ - -} -void UGAAbilityBase::OnRep_AbilityActivated() -{ - //ApplyActivationEffect(); -} -void UGAAbilityBase::OnRep_AbilityPeriod() -{ - -} -void UGAAbilityBase::OnRep_AbilityHits() -{ + DOREPLIFETIME(UGAAbilityBase, AvatarActor) + //DOREPLIFETIME(UAFAbilityComponent, RepMontage); } void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 7ae6152..801cd32 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -5,7 +5,7 @@ #include "GameplayTask.h" #include "GameplayTaskOwnerInterface.h" #include "../Attributes/GAAttributesBase.h" -#include "IGAAbilities.h" +#include "AFAbilityInterface.h" #include "AFAbilityActivationSpec.h" #include "GAAbilityBase.generated.h" @@ -114,7 +114,7 @@ enum EAFAbilityState }; UCLASS(BlueprintType, Blueprintable) -class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTaskOwnerInterface, public IIGAAbilities +class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTaskOwnerInterface, public IAFAbilityInterface { GENERATED_BODY() public: @@ -165,7 +165,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") class AAIController* AICOwner; UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") - class UGAAbilitiesComponent* AbilityComponent; + class UAFAbilityComponent* AbilityComponent; /* Physical reprsentation of ability in game world. It might be sword, gun, or character. @@ -173,7 +173,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask It will need some common interfaces for getting data out. */ - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") class AActor* AvatarActor; UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") @@ -199,7 +199,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask Add Periodic Effect ? (For abilities with period). */ - UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec"), Category = "Config") + UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") FGAEffectProperty ActivationEffect; FGAEffectHandle ActivationEffectHandle; /* @@ -213,16 +213,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask */ UPROPERTY(EditAnywhere, Category = "Config") FGAEffectProperty AbilityAttributeCost; - /* - Probably need that - as well as separate spawned actor, which takes care on it's own for - abilities effect (like lighting strike from heaves into certain hit point); - */ - /* What/Where ability hits landed. Replicated back to client ? */ - UPROPERTY(BlueprintReadOnly, ReplicatedUsing=OnRep_AbilityHits) - FGASAbilityHitArray AbilityHits; - UFUNCTION() - void OnRep_AbilityHits(); UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") FGameplayTag AbilityTag; @@ -254,37 +244,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION() void OnActivationEffectPeriod(const FGAEffectHandle& InHandle); - UFUNCTION() - void OnRep_CooldownStarted(); - UFUNCTION() - void OnRep_CooldownExpired(); - UFUNCTION() - void OnRep_AbilityActivationStarted(); - UFUNCTION() - void OnRep_AbilityActivated(); - UFUNCTION() - void OnRep_AbilityPeriod(); - /* - Do any needed client side initialization here. - Note that anything created trough this function will exist ONLY on client, this function - was called. - */ - UFUNCTION() - virtual void OnRep_InitAbility(); - /* Replication counters for above events. */ - UPROPERTY(ReplicatedUsing = OnRep_CooldownStarted) - uint8 CooldownStartedCounter; - UPROPERTY(ReplicatedUsing = OnRep_CooldownExpired) - uint8 CooldownEffectExpiredCounter; - UPROPERTY(ReplicatedUsing = OnRep_AbilityActivationStarted) - uint8 AbilityActivationStartedCounter; - UPROPERTY(ReplicatedUsing = OnRep_AbilityActivated) - FGAActiationInfo ActivationInfo; - UPROPERTY(ReplicatedUsing = OnRep_AbilityPeriod) - uint8 AbilityPeriodCounter; - UPROPERTY(ReplicatedUsing = OnRep_InitAbility) - uint8 InitAbilityCounter; + UPROPERTY(BlueprintAssignable) FGASGenericAbilityDelegate OnInputPressedDelegate; @@ -442,9 +403,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; /** GameplayTaskOwnerInterface - end */ - /** IIGAAbilities Begin */ + /** IAFAbilityInterface Begin */ virtual class UGAAttributesBase* GetAttributes() override; - virtual class UGAAbilitiesComponent* GetAbilityComp() override; + virtual class UAFAbilityComponent* GetAbilityComp() override; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; @@ -456,7 +417,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; - /* IIGAAbilities End **/ + /* IAFAbilityInterface End **/ UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") virtual float GetAttributeVal(FGAAttribute AttributeIn) const; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 97572ca..3e81f74 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -1,7 +1,7 @@ #pragma once #include "GameplayTask.h" #include "../GAAbilityBase.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" //#include "Messaging.h" #include "MessageEndpoint.h" @@ -28,7 +28,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask /* Ability owning this task */ TWeakObjectPtr Ability; /* Ability owning this task */ - TWeakObjectPtr AbilityComponent; + TWeakObjectPtr AbilityComponent; public: //virtual UWorld* GetWorld() const override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp index 4f4622c..aae1e99 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp @@ -1,7 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "../../AbilityFramework.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "GAAbilityTask_PlayMontage.h" UGAAbilityTask_PlayMontage* UGAAbilityTask_PlayMontage::AbilityPlayMontage(UObject* WorldContextObject, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp index 4e137d1..ce4a128 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp @@ -1,7 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "../../AbilityFramework.h" -#include "../../Targeting/GASAbilityTargetingObject.h" #include "../GAAbilityBase.h" #include "GAAbilityTask_TargetData.h" @@ -56,14 +55,6 @@ void UGAAbilityTask_TargetData::Activate() break; } } - if (TargetObj) - { - UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); - } - else - { - UE_LOG(AbilityFramework, Log, TEXT("TArget object is null.")); - } } // --------------------------------------------------------------------------------------- diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h index 7f023be..859b250 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h @@ -27,10 +27,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetData : public UGAAbilityTask, pu FGASOnReceiveTargetData OnConfirmed; UPROPERTY(BlueprintAssignable) FGASOnReceiveTargetData OnReceiveTargetData; - - UPROPERTY() - class UGASAbilityTargetingObject* TargetObj; - + EGASConfirmType ConfirmType; float Range; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp index a2f56eb..6a2b50a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp @@ -1,13 +1,12 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "../../AbilityFramework.h" -#include "../../Targeting/GASAbilityTargetingObject.h" #include "../GAAbilityBase.h" #include "GAAbilityTask_TargetDataCircle.h" UGAAbilityTask_TargetDataCircle* UGAAbilityTask_TargetDataCircle::TargetCircleDataTask(UObject* WorldContextObject, - FName InTaskName, TSubclassOf Class, EGASConfirmType ConfirmTypeIn) + FName InTaskName, EGASConfirmType ConfirmTypeIn) { auto MyObj = NewAbilityTask(WorldContextObject); @@ -24,7 +23,7 @@ void UGAAbilityTask_TargetDataCircle::Activate() { case EGASConfirmType::Instant: { - TargetObj2->GetTarget(); + } case EGASConfirmType::WaitForConfirm: { @@ -37,49 +36,29 @@ void UGAAbilityTask_TargetDataCircle::Activate() } } } - if (TargetObj2) - { - UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); - } - else - { - UE_LOG(AbilityFramework, Log, TEXT("TArget object is null.")); - } //EndTask(); } // --------------------------------------------------------------------------------------- -bool UGAAbilityTask_TargetDataCircle::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, UGASAbilityTargetingObject*& SpawnedActor) -{ - SpawnedActor = Class.GetDefaultObject();//NewObject(WorldContextObject, Class); - - if (SpawnedActor == nullptr) - { - //Failure.Broadcast(nullptr); - return false; - } - else - { - TargetObj2 = SpawnedActor; - SpawnedActor->AbilityOwner = Ability; - } - UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); - return true; -} - -void UGAAbilityTask_TargetDataCircle::FinishSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject* SpawnedActor) -{ - if (SpawnedActor) - { - //Success.Broadcast(SpawnedActor); - } - UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); - ReadyForActivation(); -} +//bool UGAAbilityTask_TargetDataCircle::BeginSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject*& SpawnedActor) +//{ +// SpawnedActor = Class.GetDefaultObject();//NewObject(WorldContext +// return true; +//} +// +//void UGAAbilityTask_TargetDataCircle::FinishSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject* SpawnedActor) +//{ +// if (SpawnedActor) +// { +// //Success.Broadcast(SpawnedActor); +// } +// UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); +// ReadyForActivation(); +//} void UGAAbilityTask_TargetDataCircle::OnConfirm() { - TargetObj2->GetTarget(); + //TargetObj2->GetTarget(); EndTask(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h index 39a60b7..fdb89b0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h @@ -19,23 +19,20 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataCircle : public UGAAbilityTa UPROPERTY(BlueprintAssignable) FGASOnReceiveTargetData OnReceiveTargetDataCircle; - UPROPERTY() - class UGASAbilityTargetingObject* TargetObj2; - EGASConfirmType ConfirmType; public: UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") static UGAAbilityTask_TargetDataCircle* TargetCircleDataTask(UObject* WorldContextObject, - FName InTaskName, TSubclassOf Class, EGASConfirmType ConfirmTypeIn); + FName InTaskName, EGASConfirmType ConfirmTypeIn); virtual void Activate() override; - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class UGASAbilityTargetingObject*& SpawnedActor); + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // bool BeginSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject*& SpawnedActor); - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - void FinishSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject* SpawnedActor); + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // void FinishSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject* SpawnedActor); // UFUNCTION() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp index 16f4455..71fefb5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp @@ -1,7 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "../../AbilityFramework.h" -#include "../../Targeting/GATargetingActor.h" #include "GAAbilityTask_WaitTargetData.h" @@ -12,14 +11,14 @@ UGAAbilityTask_WaitTargetData::UGAAbilityTask_WaitTargetData(const FObjectInitia } -UGAAbilityTask_WaitTargetData* UGAAbilityTask_WaitTargetData::WaitTargetData(UObject* WorldContextObject, - FName InTaskName, TSubclassOf InClass, float InRange, ETraceTypeQuery InTraceChannel) -{ - auto MyObj = NewAbilityTask(WorldContextObject, "UGAAbilityTask_WaitTargetData"); - MyObj->Range = InRange; - MyObj->TraceChannel = InTraceChannel; - return MyObj; -} +//UGAAbilityTask_WaitTargetData* UGAAbilityTask_WaitTargetData::WaitTargetData(UObject* WorldContextObject, +// FName InTaskName, TSubclassOf InClass, float InRange, ETraceTypeQuery InTraceChannel) +//{ +// auto MyObj = NewAbilityTask(WorldContextObject, "UGAAbilityTask_WaitTargetData"); +// MyObj->Range = InRange; +// MyObj->TraceChannel = InTraceChannel; +// return MyObj; +//} // --------------------------------------------------------------------------------------- void UGAAbilityTask_WaitTargetData::Activate() @@ -33,58 +32,58 @@ void UGAAbilityTask_WaitTargetData::Activate() } } -bool UGAAbilityTask_WaitTargetData::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AGATargetingActor*& SpawnedActor) -{ - UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); - if (World) - { - SpawnedActor = World->SpawnActorDeferred(Class, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); - } - - if (SpawnedActor == nullptr) - { - return false; - } - UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); - return true; -} - -void UGAAbilityTask_WaitTargetData::FinishSpawningActor(UObject* WorldContextObject, AGATargetingActor* SpawnedActor) -{ - if (SpawnedActor) - { - FTransform SpawnTransform; - SpawnedActor->FinishSpawning(SpawnTransform); - TargetActor = SpawnedActor; - } - ReadyForActivation(); - UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); -} +//bool UGAAbilityTask_WaitTargetData::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AGATargetingActor*& SpawnedActor) +//{ +// UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); +// if (World) +// { +// SpawnedActor = World->SpawnActorDeferred(Class, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); +// } +// +// if (SpawnedActor == nullptr) +// { +// return false; +// } +// UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); +// return true; +//} +// +//void UGAAbilityTask_WaitTargetData::FinishSpawningActor(UObject* WorldContextObject, AGATargetingActor* SpawnedActor) +//{ +// if (SpawnedActor) +// { +// FTransform SpawnTransform; +// SpawnedActor->FinishSpawning(SpawnTransform); +// TargetActor = SpawnedActor; +// } +// ReadyForActivation(); +// UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); +//} void UGAAbilityTask_WaitTargetData::TickTask(float DeltaTime) { - if (TargetActor && Ability.IsValid()) - { - FHitResult OutHit; - bool bHit = Ability->LineTraceSingleByChannelFromCamera(Range, TraceChannel, false, OutHit, - EDrawDebugTrace::Type::None, true, FLinearColor::Green, FLinearColor::Red, 2); - if (bHit) - { - TargetActor->SetActorLocation(OutHit.Location); - } - else - { - TargetActor->SetActorLocation(OutHit.TraceEnd); - } - } + //if (TargetActor && Ability.IsValid()) + //{ + // FHitResult OutHit; + // bool bHit = Ability->LineTraceSingleByChannelFromCamera(Range, TraceChannel, false, OutHit, + // EDrawDebugTrace::Type::None, true, FLinearColor::Green, FLinearColor::Red, 2); + // if (bHit) + // { + // TargetActor->SetActorLocation(OutHit.Location); + // } + // else + // { + // TargetActor->SetActorLocation(OutHit.TraceEnd); + // } + //} } void UGAAbilityTask_WaitTargetData::OnDestroy(bool bInOwnerFinished) { Super::OnDestroy(bInOwnerFinished); - if (TargetActor) - { - TargetActor->SetActorHiddenInGame(true); - TargetActor->Destroy(); - } + //if (TargetActor) + //{ + // TargetActor->SetActorHiddenInGame(true); + // TargetActor->Destroy(); + //} } void UGAAbilityTask_WaitTargetData::OnConfirm() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h index b39ec7f..683affa 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h @@ -20,18 +20,18 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_WaitTargetData : public UGAAbilityTask UPROPERTY() float Range; ETraceTypeQuery TraceChannel; - UPROPERTY() - class AGATargetingActor* TargetActor; + //UPROPERTY() + // class AGATargetingActor* TargetActor; - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_WaitTargetData* WaitTargetData(UObject* WorldContextObject, - FName InTaskName, TSubclassOf Class, float InRange, ETraceTypeQuery InTraceChannel); + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // static UGAAbilityTask_WaitTargetData* WaitTargetData(UObject* WorldContextObject, + // FName InTaskName, TSubclassOf Class, float InRange, ETraceTypeQuery InTraceChannel); - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class AGATargetingActor*& SpawnedActor); + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class AGATargetingActor*& SpawnedActor); - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - void FinishSpawningActor(UObject* WorldContextObject, class AGATargetingActor* SpawnedActor); + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // void FinishSpawningActor(UObject* WorldContextObject, class AGATargetingActor* SpawnedActor); virtual void Activate() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp deleted file mode 100644 index 637d50f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.cpp +++ /dev/null @@ -1,19 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "../Abilities/GAAbilityBase.h" -#include "GAAbilityCue.h" - -UGAAbilityCue::UGAAbilityCue(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} -UWorld* UGAAbilityCue::GetWorld() const -{ - return GetOuterUGAAbilityBase()->GetWorld(); -} -APawn* UGAAbilityCue::GetPawnOwner() const -{ - return GetOuterUGAAbilityBase()->POwner; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h deleted file mode 100644 index c311aea..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GAAbilityCue.h +++ /dev/null @@ -1,68 +0,0 @@ -#pragma once -#include "GAAbilityCue.generated.h" -/* - Ability cues are object, which will spawn cosmetic effects, for abilities. - - Make it actor, or make them spawn actors and/or component ? - - If the former I would need to replicate this trough ability actor, which would - own particular cue. - ///bla bla don't know if above is still relevelant. - - But. - AbilityCues will spawn only effects, sounds, etc at locations, which are available trough Pawn. - Be it socket on weapon, skeleton, or direct pawn location. - - For spawning effects at arbitrary world location, one should use GACueActor. - Though technically there is nothing stoping anyone from spawning PSC at world location, trough trace. - - Neither AbilityCue or CueActor will spawn effects on other actor/pawn, since they don't have information - about target. - - Only Effects, can spawn Cues, which will add Cues at Other Actor/Target location. -*/ -UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInLineNew, Within = GAAbilityBase) -class ABILITYFRAMEWORK_API UGAAbilityCue : public UObject -{ - GENERATED_UCLASS_BODY() -public: - virtual UWorld* GetWorld() const override; - - UFUNCTION(BlueprintPure, Category = "Game Abilities") - APawn* GetPawnOwner() const; - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnCooldownStart(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnCooldownExpired(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityActivationStart(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityActivated(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityPeriod(); - - //from ability anim notifies: - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityStartNotify(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityEndNotify(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotify(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotifyStateStart(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotifyStateTick(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotifyStateEnd(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp deleted file mode 100644 index 9fc3290..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.cpp +++ /dev/null @@ -1,30 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GACueActor.h" - - -// Sets default values -AGACueActor::AGACueActor(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - DefaultRoot = ObjectInitializer.CreateDefaultSubobject(this, TEXT("DefaultRoot")); - RootComponent = DefaultRoot; -} - -// Called when the game starts or when spawned -void AGACueActor::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AGACueActor::Tick( float DeltaTime ) -{ - Super::Tick( DeltaTime ); - -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h deleted file mode 100644 index cbb5616..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityCues/GACueActor.h +++ /dev/null @@ -1,73 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GameFramework/Actor.h" -#include "GACueActor.generated.h" - -UCLASS() -class ABILITYFRAMEWORK_API AGACueActor : public AActor -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintReadOnly, Category = "Abilities") - class UGAAbilityBase* OwningAbility; - - UPROPERTY(BlueprintReadOnly, VisibleAnywhere, Category = "Root") - USceneComponent* DefaultRoot; - -public: - // Sets default values for this actor's properties - AGACueActor(const FObjectInitializer& ObjectInitializer); - - // Called when the game starts or when spawned - virtual void BeginPlay() override; - - // Called every frame - virtual void Tick( float DeltaSeconds ) override; - - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnActivated(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnDeactivated(); - /* - Mirros what is inside Object version. - */ - /**/ - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnCooldownStart(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnCooldownExpired(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityActivationStart(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityActivated(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityPeriod(); - - //from ability anim notifies: - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityStartNotify(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityEndNotify(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotify(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotifyStateStart(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotifyStateTick(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Game Abilities") - void OnAbilityNotifyStateEnd(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index df3c7a8..22267e6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -11,7 +11,10 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) "AbilityFramework", "AbilityFramework/Abilities", "AbilityFramework/Attributes", - "AbilityFramework/Effects" + "AbilityFramework/Effects", + "AbilityFramework/Effects/ApplicationRequirement", + "AbilityFramework/Effects/CustomApplications", + "AbilityFramework/Public" // ... add public include paths required here ... } ); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp index 8582b2b..67dc98d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp @@ -1,8 +1,8 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "IGAAbilities.h" -#include "GAAbilitiesComponent.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" #include "AFAbilityNotifyState.h" @@ -10,7 +10,7 @@ void UAFAbilityNotifyState::NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) { - IIGAAbilities* IAbilities = Cast(MeshComp->GetOwner()); + IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); if (IAbilities) { CachedAbilitiesComp = IAbilities->GetAbilityComp(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h index 26b8d67..5dd37a5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h @@ -21,7 +21,7 @@ class ABILITYFRAMEWORK_API UAFAbilityNotifyState : public UAnimNotifyState UPROPERTY(EditAnywhere) FName Name; UPROPERTY() - class UGAAbilitiesComponent* CachedAbilitiesComp; + class UAFAbilityComponent* CachedAbilitiesComp; public: virtual void NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) override; virtual void NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp index 04bfe19..7282ecc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp @@ -1,8 +1,8 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "GAAbilitiesComponent.h" -#include "IGAAbilities.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" #include "AFAnimNotify.h" @@ -10,10 +10,10 @@ void UAFAnimNotify::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) { - IIGAAbilities* IAbilities = Cast(MeshComp->GetOwner()); + IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); if (!IAbilities) return; - UGAAbilitiesComponent* Comp = IAbilities->GetAbilityComp(); + UAFAbilityComponent* Comp = IAbilities->GetAbilityComp(); Comp->OnAbilityNotifyBegin.ExecuteIfBound(Data, Tag, Name); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp index c4ab571..bd90bba 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp @@ -1,8 +1,8 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "GAAbilitiesComponent.h" -#include "IGAAbilities.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" #include "AFAnimNotifyBase.h" @@ -10,9 +10,9 @@ void UAFAnimNotifyBase::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) { - IIGAAbilities* IAbilities = Cast(MeshComp->GetOwner()); + IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); if (!IAbilities) return; - UGAAbilitiesComponent* Comp = IAbilities->GetAbilityComp(); + UAFAbilityComponent* Comp = IAbilities->GetAbilityComp(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp deleted file mode 100644 index 3b3fd86..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.cpp +++ /dev/null @@ -1,12 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AsyncUObject.h" - - -void UAsyncUObject::JustTestFunction() -{ - float qwe = 0; - float vcx = 0; -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h deleted file mode 100644 index c9e61f5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObject.h +++ /dev/null @@ -1,47 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "UObject/NoExportTypes.h" -#include "HAL/Runnable.h" -#include "AsyncUObject.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAsyncUObject : public UObject, public FRunnable -{ - GENERATED_BODY() - -public: - void JustTestFunction(); - - virtual uint32 Run() override - { - /* Obj = NewObject(Outer.Get(), UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); - if (Obj.IsValid()) - { - Obj->JustTestFunction(); - }*/ - JustTestFunction(); - float somerandomcrap = 0; - return 0; - } - - /** - * Stops the runnable object. - * - * This is called if a thread is requested to terminate early. - * @see Init, Run, Exit - */ - virtual void Stop() override { } - - /** - * Exits the runnable object. - * - * Called in the context of the aggregating thread to perform any cleanup. - * @see Init, Run, Stop - */ - virtual void Exit() override { } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp deleted file mode 100644 index 64522ae..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.cpp +++ /dev/null @@ -1,12 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AsyncUObjectImpl.h" - -AsyncUObjectImpl::AsyncUObjectImpl() -{ -} - -AsyncUObjectImpl::~AsyncUObjectImpl() -{ -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h b/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h deleted file mode 100644 index a5c4c99..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Async/AsyncUObjectImpl.h +++ /dev/null @@ -1,61 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once -#include "HAL/Runnable.h" -#include "AsyncUObject.h" -class FAsyncUObjectRunnable : public FRunnable -{ -public: - FAsyncUObjectRunnable() - { - - } - FAsyncUObjectRunnable(class UObject* InOuter) - { - Outer = InOuter; - } - /*Runs the runnable object. - * - * This is where all per object thread work is done.This is only called if the initialization was successful. - * - * @return The exit code of the runnable object - * @see Init, Stop, Exit - */ - virtual uint32 Run() override - { - Obj = NewObject(Outer.Get(), UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); - if (Obj.IsValid()) - { - Obj->JustTestFunction(); - } - return 0; - } - - /** - * Stops the runnable object. - * - * This is called if a thread is requested to terminate early. - * @see Init, Run, Exit - */ - virtual void Stop() override { } - - /** - * Exits the runnable object. - * - * Called in the context of the aggregating thread to perform any cleanup. - * @see Init, Run, Stop - */ - virtual void Exit() override { } -private: - TWeakObjectPtr Obj; - TWeakObjectPtr Outer; -}; -/** - * - */ -class ABILITYFRAMEWORK_API AsyncUObjectImpl -{ -public: - AsyncUObjectImpl(); - ~AsyncUObjectImpl(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp index 80cb475..e271f71 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -2,9 +2,9 @@ #include "../AbilityFramework.h" #include "GameplayTagContainer.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAAttributesBase.h" -#include "../IGAAbilities.h" +#include "../AFAbilityInterface.h" #include "GAAttributeBase.h" DEFINE_STAT(STAT_CalculateBonus); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h index 74d2c40..f769cae 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -134,5 +134,5 @@ struct ABILITYFRAMEWORK_API FGAModifiedAttribute FVector InstigatorLocation; UPROPERTY() - TWeakObjectPtr Causer; + TWeakObjectPtr Causer; }; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp index 357f2f1..e7de1c9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -2,7 +2,7 @@ #include "../AbilityFramework.h" #include "../GAGlobalTypes.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAAttributesBase.h" UGAAttributesBase::UGAAttributesBase(const FObjectInitializer& ObjectInitializer) @@ -18,7 +18,7 @@ UGAAttributesBase::~UGAAttributesBase() CachedFloatPropety = nullptr; } -void UGAAttributesBase::InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp) +void UGAAttributesBase::InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) { OwningAttributeComp = InOwningAttributeComp; for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h index 34d9cb2..2256045 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h @@ -47,7 +47,7 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject UGAAttributesBase(const FObjectInitializer& ObjectInitializer); ~UGAAttributesBase(); - virtual void InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp); + virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp); void InitializeAttributesFromTable(); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) bool BP_InitializeAttributes(); @@ -62,7 +62,7 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject that it must be fully functional from within blueprint. */ UPROPERTY(Replicated) - class UGAAbilitiesComponent* OwningAttributeComp; + class UAFAbilityComponent* OwningAttributeComp; protected: UProperty* FindProperty(const FGAAttribute& AttributeIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp index b5bc78d..88996e2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp @@ -2,9 +2,9 @@ #include "../AbilityFramework.h" -#include "../IGAAbilities.h" +#include "../AFAbilityInterface.h" #include "GAAttributesBase.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAAttributesBlueprintFunctionLibrary.h" @@ -26,7 +26,7 @@ FName UGAAttributesBlueprintFunctionLibrary::GetAttribute(FGAAttribute Attribute } float UGAAttributesBlueprintFunctionLibrary::GetFinalAttributeValue(AActor* Target, FGAAttribute Name) { - IIGAAbilities* attributeInt = Cast(Target); + IAFAbilityInterface* attributeInt = Cast(Target); if (!attributeInt) return 0; if (!attributeInt->GetAttributes()) @@ -36,14 +36,14 @@ float UGAAttributesBlueprintFunctionLibrary::GetFinalAttributeValue(AActor* Targ } float UGAAttributesBlueprintFunctionLibrary::GetCurrentAttributeValue(AActor* Target, FGAAttribute Name) { - IIGAAbilities* attributeInt = Cast(Target); + IAFAbilityInterface* attributeInt = Cast(Target); if (!attributeInt) return 0; return attributeInt->GetAttributes()->GetCurrentAttributeValue(Name); } float UGAAttributesBlueprintFunctionLibrary::GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn) { - IIGAAbilities* attributeInt = Cast(Target); + IAFAbilityInterface* attributeInt = Cast(Target); if (!attributeInt) return 0; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp index f3736ac..bc4b54b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp @@ -6,7 +6,7 @@ -bool UAFEffectCustomStackingRule::CanStack(class UGAAbilitiesComponent* InComp, struct FGAEffectContainer* InContainer, +bool UAFEffectCustomStackingRule::CanStack(class UAFAbilityComponent* InComp, struct FGAEffectContainer* InContainer, const FGAEffectHandle& InHandle) { //InHandle.GetContext().TargetComp->ExecuteEffect(InHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h index 63e6f8e..ba364d2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h @@ -16,7 +16,7 @@ class ABILITYFRAMEWORK_API UAFEffectCustomStackingRule : public UObject GENERATED_BODY() public: - virtual bool CanStack(class UGAAbilitiesComponent* InComp, struct FGAEffectContainer* InContainer, + virtual bool CanStack(class UAFAbilityComponent* InComp, struct FGAEffectContainer* InContainer, const FGAEffectHandle& InHandle); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp index 49266af..2e1ca83 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../../Attributes/GAAttributeBase.h" -#include "../../IGAAbilities.h" +#include "../../AFAbilityInterface.h" #include "AFAttributeStongerOverride.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp index 75eb053..cafb889 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFAtributeDurationAdd.h" @@ -15,7 +15,7 @@ bool UAFAtributeDurationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct { FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp index a5a41d6..8e51b5b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFAttributeDurationOverride.h" @@ -30,7 +30,7 @@ bool UAFAttributeDurationOverride::ApplyEffect(const FGAEffectHandle& InHandle, FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp index 64ca21f..0edde1c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFPeriodApplicationAdd.h" @@ -13,13 +13,13 @@ bool UAFPeriodApplicationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struc { FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index a7c60f7..1d574ee 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFPeriodApplicationExtend.h" @@ -22,7 +22,7 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st float NewDuration = RemainingTime + Effect.GetDurationTime(); DurationTimer.ClearTimer(handle.GetEffectPtr()->DurationTimerHandle); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(handle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(handle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(handle.GetEffectPtr()->DurationTimerHandle, delDuration, NewDuration, false); } @@ -30,13 +30,13 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st { FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp index d22b228..3e973b0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFPeriodApplicationInfiniteAdd.h" @@ -13,7 +13,7 @@ bool UAFPeriodApplicationInfiniteAdd::ApplyEffect(const FGAEffectHandle& InHandl { FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); InContainer->AddEffect(InHandle, true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp index caa4116..2193360 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFPeriodApplicationOverride.h" @@ -22,13 +22,13 @@ bool UAFPeriodApplicationOverride::ApplyEffect(const FGAEffectHandle& InHandle, FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExpireEffect, InHandle, InProperty); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UGAAbilitiesComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index ccf1937..b2c66f7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -5,7 +5,7 @@ #include "GameplayTask.h" #include "../GAEffectExtension.h" #include "../../GAGlobalTypes.h" -#include "../../GAAbilitiesComponent.h" +#include "../../AFAbilityComponent.h" #include "AFEffectTask.generated.h" /** @@ -19,7 +19,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask UPROPERTY() class UGAEffectExtension* Effect; UPROPERTY() - class UGAAbilitiesComponent* AbilityComponent; + class UAFAbilityComponent* AbilityComponent; public: template static T* NewEffectTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp index 89803ea..48a75eb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp @@ -25,7 +25,7 @@ UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeCha void UAFEffectTask_AttributeChange::Activate() { - UGAAbilitiesComponent* ASC = GetTargetASC(); + UAFAbilityComponent* ASC = GetTargetASC(); if (ASC) { MyHandle = ASC->AttributeChanged.FindOrAdd(Attribute).AddUObject(this, &UAFEffectTask_AttributeChange::AttributeChangedCallback); @@ -50,7 +50,7 @@ void UAFEffectTask_AttributeChange::SetExternalTarget(AActor* Actor) { if (Actor) { - if (IIGAAbilities* interface = Cast(Actor)) + if (IAFAbilityInterface* interface = Cast(Actor)) { UseExternalTarget = true; OptionalExternalTarget = interface->GetAbilityComp(); @@ -59,7 +59,7 @@ void UAFEffectTask_AttributeChange::SetExternalTarget(AActor* Actor) } } -UGAAbilitiesComponent* UAFEffectTask_AttributeChange::GetTargetASC() +UAFAbilityComponent* UAFEffectTask_AttributeChange::GetTargetASC() { if (UseExternalTarget) { @@ -71,7 +71,7 @@ UGAAbilitiesComponent* UAFEffectTask_AttributeChange::GetTargetASC() void UAFEffectTask_AttributeChange::OnDestroy(bool AbilityEnding) { - UGAAbilitiesComponent* ASC = GetTargetASC(); + UAFAbilityComponent* ASC = GetTargetASC(); if (ASC && MyHandle.IsValid()) { ASC->AttributeChanged.FindOrAdd(Attribute).Remove(MyHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h index 1d3ed3f..4302a7f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h @@ -28,7 +28,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask void SetExternalTarget(AActor* Actor); - class UGAAbilitiesComponent* GetTargetASC(); + class UAFAbilityComponent* GetTargetASC(); virtual void Activate() override; @@ -39,7 +39,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask FGAAttribute Attribute; UPROPERTY() - UGAAbilitiesComponent* OptionalExternalTarget; + UAFAbilityComponent* OptionalExternalTarget; bool UseExternalTarget; bool OnlyTriggerOnce; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp index d924ed9..5695c16 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -1,7 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "../../IGAAbilities.h" +#include "../../AFAbilityInterface.h" #include "AFEffectTask_EffectEvent.h" @@ -25,7 +25,7 @@ UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UObject* void UAFEffectTask_EffectEvent::Activate() { - UGAAbilitiesComponent* ASC = GetTargetASC(); + UAFAbilityComponent* ASC = GetTargetASC(); if (ASC) { MyHandle = ASC->EffectEvents.FindOrAdd(Tag).AddUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); @@ -51,7 +51,7 @@ void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) if (Actor) { - if (IIGAAbilities* interface = Cast(Actor)) + if (IAFAbilityInterface* interface = Cast(Actor)) { UseExternalTarget = true; OptionalExternalTarget = interface->GetAbilityComp(); @@ -60,7 +60,7 @@ void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) } } -UGAAbilitiesComponent* UAFEffectTask_EffectEvent::GetTargetASC() +UAFAbilityComponent* UAFEffectTask_EffectEvent::GetTargetASC() { if (UseExternalTarget) { @@ -72,7 +72,7 @@ UGAAbilitiesComponent* UAFEffectTask_EffectEvent::GetTargetASC() void UAFEffectTask_EffectEvent::OnDestroy(bool AbilityEnding) { - UGAAbilitiesComponent* ASC = GetTargetASC(); + UAFAbilityComponent* ASC = GetTargetASC(); if (ASC && MyHandle.IsValid()) { ASC->EffectEvents.FindOrAdd(Tag).Remove(MyHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h index 21bdb3e..f1074c7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -27,7 +27,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask void SetExternalTarget(AActor* Actor); - class UGAAbilitiesComponent* GetTargetASC(); + class UAFAbilityComponent* GetTargetASC(); virtual void Activate() override; @@ -38,7 +38,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask FGameplayTag Tag; UPROPERTY() - UGAAbilitiesComponent* OptionalExternalTarget; + UAFAbilityComponent* OptionalExternalTarget; bool UseExternalTarget; bool OnlyTriggerOnce; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 8a7990c..2bb3311 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -1,11 +1,11 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #include "../AbilityFramework.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GABlueprintLibrary.h" -#include "../IGAAbilities.h" +#include "../AFAbilityInterface.h" #include "GAEffectExtension.h" UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) @@ -47,12 +47,12 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); return FGAEffectHandle(); } - FGAEffectContext Context = MakeContext(Target, Instigator, Causer, HitIn); + FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); /*if (!Context.IsValid()) { return FGAEffectHandle(); }*/ - UGAAbilitiesComponent* Target2 = Context.TargetComp.Get(); + UAFAbilityComponent* Target2 = Context.TargetComp.Get(); if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) { return FGAEffectHandle(); @@ -122,7 +122,7 @@ FGAEffectHandle UGABlueprintLibrary::MakeEffect(UGAGameEffectSpec* SpecIn, return FGAEffectHandle(); } - FGAEffectContext Context = MakeContext(Target, Instigator, Causer, HitIn); + FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); if (!Context.IsValid()) { //if the handle is valid (valid pointer to effect and id) @@ -154,17 +154,18 @@ FGAEffectHandle UGABlueprintLibrary::MakeEffect(UGAGameEffectSpec* SpecIn, return HandleIn; } -FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn) +FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, + AActor* InAvatar, UObject* Causer, const FHitResult& HitIn) { - IIGAAbilities* targetAttr = Cast(Target); - IIGAAbilities* instiAttr = Cast(Instigator); + IAFAbilityInterface* targetAttr = Cast(Target); + IAFAbilityInterface* instiAttr = Cast(Instigator); if (!targetAttr && !instiAttr) { - UE_LOG(GameAttributesEffects, Error, TEXT("Target and Instigator does not implement IIGAAbilities interface")); + UE_LOG(GameAttributesEffects, Error, TEXT("Target and Instigator does not implement IAFAbilityInterface interface")); return FGAEffectContext(); } - UGAAbilitiesComponent* targetComp = nullptr; - UGAAbilitiesComponent* instiComp = nullptr; + UAFAbilityComponent* targetComp = nullptr; + UAFAbilityComponent* instiComp = nullptr; if (targetAttr) { targetComp = targetAttr->GetAbilityComp(); @@ -179,7 +180,8 @@ FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class A targetAttr ? targetAttr->GetAttributes() : nullptr, instiAttr ? instiAttr->GetAttributes() : nullptr, location, Target, Causer, - Instigator, targetComp, instiComp); + Instigator, targetComp, instiComp, + InAvatar); Context.HitResult = HitIn; return Context; } @@ -198,23 +200,23 @@ FGAEffectContext& UGABlueprintLibrary::GetContext(const FGAEffectHandle& InHandl return InHandle.GetContextRef(); } -UGAAbilitiesComponent* UGABlueprintLibrary::GetTargetComponent(const FGAEffectHandle& InHandle) +UAFAbilityComponent* UGABlueprintLibrary::GetTargetComponent(const FGAEffectHandle& InHandle) { return InHandle.GetContextRef().InstigatorComp.Get(); } -UGAAbilitiesComponent* UGABlueprintLibrary::GetInstigatorComponent(const FGAEffectHandle& InHandle) +UAFAbilityComponent* UGABlueprintLibrary::GetInstigatorComponent(const FGAEffectHandle& InHandle) { return InHandle.GetContextRef().TargetComp.Get(); } void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag) { - IIGAAbilities* targetAttr = Cast(Target); + IAFAbilityInterface* targetAttr = Cast(Target); if (!targetAttr) return; - UGAAbilitiesComponent* TargetComp = targetAttr->GetAbilityComp(); + UAFAbilityComponent* TargetComp = targetAttr->GetAbilityComp(); if (!TargetComp) return; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h index ccee9e6..3655783 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h @@ -58,17 +58,18 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar UObject* Causer, const FHitResult& HitIn); - static FGAEffectContext MakeContext(class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn); + static FGAEffectContext MakeContext(class UObject* Target, class APawn* Instigator, AActor* InAvatar, + UObject* Causer, const FHitResult& HitIn); static void AddTagsToEffect(FGAEffect* EffectIn); UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") static FGAEffectContext& GetContext(const FGAEffectHandle& InHandle); UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") - static UGAAbilitiesComponent* GetTargetComponent(const FGAEffectHandle& InHandle); + static UAFAbilityComponent* GetTargetComponent(const FGAEffectHandle& InHandle); UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") - static UGAAbilitiesComponent* GetInstigatorComponent(const FGAEffectHandle& InHandle); + static UAFAbilityComponent* GetInstigatorComponent(const FGAEffectHandle& InHandle); UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") static void BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp index 5bd46db..1eb194e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp @@ -32,12 +32,7 @@ void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) void AGAEffectCue::BeginPlay() { SequencePlayer->Initialize(Sequence, PlaybackSettings); - if (Period > 0) - { - FTimerDelegate del = FTimerDelegate::CreateUObject(this, &AGAEffectCue::NativeOnPeriod); - FTimerManager& Timer = GetWorld()->GetTimerManager(); - Timer.SetTimer(PeriodTimer, del, Period, true); - } + Super::BeginPlay(); //NativeBeginCue(); } @@ -52,13 +47,28 @@ void AGAEffectCue::Tick( float DeltaTime ) } } void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, - const FHitResult& HitInfo) + const FHitResult& HitInfo, const FGAEffectCueParams& CueParams) { + if (CueParams.Period > 0) + { + FTimerDelegate del = FTimerDelegate::CreateUObject(this, &AGAEffectCue::NativeOnExecuted); + FTimerManager& Timer = GetWorld()->GetTimerManager(); + Timer.SetTimer(PeriodTimer, del, CueParams.Period, true); + } BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); SequencePlayer->Play(); } -void AGAEffectCue::NativeOnPeriod() +void AGAEffectCue::NativeOnExecuted() +{ + OnExecuted(); +} +void AGAEffectCue::NativeOnRemoved() { - OnPeriod(); + FTimerManager& Timer = GetWorld()->GetTimerManager(); + Timer.ClearTimer(PeriodTimer); + SequencePlayer->JumpToPosition(0); + SequencePlayer->Stop(); + + OnRemoved(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h index 026acb7..a47006b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h @@ -4,6 +4,7 @@ #include "GameFramework/Actor.h" #include "MovieSceneSequencePlayer.h" +#include "GAGlobalTypes.h" #include "GAEffectCue.generated.h" class UActorSequencePlayer; UCLASS() @@ -26,7 +27,7 @@ class ABILITYFRAMEWORK_API AGAEffectCue : public AActor const FHitResult& HitInfo); UFUNCTION(BlueprintImplementableEvent) - void OnPeriod(); + void OnExecuted(); UFUNCTION(BlueprintImplementableEvent) void OnExpired(); @@ -35,10 +36,10 @@ class ABILITYFRAMEWORK_API AGAEffectCue : public AActor void OnRemoved(); void NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, - const FHitResult& HitInfo); - - void NativeOnPeriod(); + const FHitResult& HitInfo, const FGAEffectCueParams& CueParams); + void NativeOnExecuted(); + void NativeOnRemoved(); UPROPERTY() float Duration; UPROPERTY() @@ -50,10 +51,11 @@ class ABILITYFRAMEWORK_API AGAEffectCue : public AActor UPROPERTY() double EndTime; /** Animation being played */ - UPROPERTY(Instanced) - class UGAEffectCueSequence* Sequence; - UPROPERTY(Instanced) + UPROPERTY(EditAnywhere, Instanced, Export, Category = Animation) + UGAEffectCueSequence* Sequence; + UPROPERTY(transient, BlueprintReadOnly, Category = Animation) UActorSequencePlayer* SequencePlayer; + UPROPERTY(EditAnywhere, Category = "Playback", meta = (ShowOnlyInnerProperties)) FMovieSceneSequencePlaybackSettings PlaybackSettings; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp index 7b2ed0a..3f57b12 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp @@ -1,6 +1,6 @@ #pragma once #include "../AbilityFramework.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAEffectCueGlobals.h" void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h index 50ffecf..bed97a4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h @@ -9,7 +9,7 @@ struct FGACueContainer { GENERATED_USTRUCT_BODY() public: - TWeakObjectPtr OwningComponent; + TWeakObjectPtr OwningComponent; void AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp index 0837a54..8de8211 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp @@ -3,7 +3,7 @@ #include "../AbilityFramework.h" #include "../GAGlobalTypes.h" #include "../Attributes/GAAttributeBase.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAEffectExecution.h" UGAEffectExecution::UGAEffectExecution(const FObjectInitializer& ObjectInitializer) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp index 29303cc..325f09d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp @@ -1,7 +1,7 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #include "../AbilityFramework.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAEffectExtension.h" UGAEffectExtension::UGAEffectExtension(const FObjectInitializer& ObjectInitializer) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h index 3ead376..344cb03 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h @@ -26,7 +26,7 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplay UPROPERTY(BlueprintReadOnly, Category = "Context") FGAEffectContext Context; UPROPERTY() - class UGAAbilitiesComponent* OwningComponent; + class UAFAbilityComponent* OwningComponent; UPROPERTY() class AActor* Avatar; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp index 6d7f9e5..facd31c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp @@ -1,9 +1,9 @@ #pragma once #include "../AbilityFramework.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "../Attributes/GAAttributeBase.h" #include "GAEffectExecution.h" -#include "../IGAAbilities.h" +#include "AFAbilityInterface.h" #include "GAGameEffect.h" #include "GACustomCalculation.h" @@ -19,7 +19,7 @@ float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) { case EGAAttributeSource::Instigator: { - IIGAAbilities* AttrInt = Cast(Context.Instigator.Get()); + IAFAbilityInterface* AttrInt = Cast(Context.Instigator.Get()); UGAAttributesBase* Attributes = AttrInt->GetAttributes(); attr = Attributes->GetAttribute(Attribute); //attr = Context.InstigatorComp->GetAttribute(Attribute); @@ -27,14 +27,14 @@ float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) } case EGAAttributeSource::Target: { - IIGAAbilities* AttrInt = Cast(Context.Target.Get()); + IAFAbilityInterface* AttrInt = Cast(Context.Target.Get()); UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); break; } case EGAAttributeSource::Causer: { - IIGAAbilities* AttrInt = Cast(Context.Causer.Get()); + IAFAbilityInterface* AttrInt = Cast(Context.Causer.Get()); UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); break; @@ -57,7 +57,7 @@ float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) const { case EGAAttributeSource::Instigator: { - IIGAAbilities* AttrInt = Cast(Context.Instigator.Get()); + IAFAbilityInterface* AttrInt = Cast(Context.Instigator.Get()); UGAAttributesBase* Attributes = AttrInt->GetAttributes(); attr = Attributes->GetAttribute(Attribute); //attr = Context.InstigatorComp->GetAttribute(Attribute); @@ -65,14 +65,14 @@ float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) const } case EGAAttributeSource::Target: { - IIGAAbilities* AttrInt = Cast(Context.Target.Get()); + IAFAbilityInterface* AttrInt = Cast(Context.Target.Get()); UGAAttributesBase* Attributes = AttrInt->GetAttributes(); attr = Attributes->GetAttribute(Attribute); break; } case EGAAttributeSource::Causer: { - IIGAAbilities* AttrInt = Cast(Context.Causer.Get()); + IAFAbilityInterface* AttrInt = Cast(Context.Causer.Get()); UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; attr = Attributes->GetAttribute(Attribute); break; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 5e3c5e1..20fbb24 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -2,11 +2,11 @@ #include "../AbilityFramework.h" #include "GameplayTagContainer.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "../Attributes/GAAttributesBase.h" -#include "../IGAAbilities.h" +#include "../AFAbilityInterface.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GAEffectExecution.h" #include "GAEffectExtension.h" #include "../GAGlobalTypes.h" @@ -18,10 +18,13 @@ DEFINE_STAT(STAT_GatherModifiers); void FGAEffectProperty::Initialize() { - Spec = SpecClass.SpecClass->GetDefaultObject(); - ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); - Application = GetSpec()->Application.GetDefaultObject(); - Execution = GetSpec()->ExecutionType.GetDefaultObject(); + if (SpecClass.SpecClass) + { + Spec = SpecClass.SpecClass->GetDefaultObject(); + ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); + Application = GetSpec()->Application.GetDefaultObject(); + Execution = GetSpec()->ExecutionType.GetDefaultObject(); + } } void FGAEffectProperty::InitializeIfNotInitialized() { @@ -403,7 +406,7 @@ TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectPrope { case EGAEffectAggregation::AggregateByInstigator: { - UGAAbilitiesComponent* Instigator = InContext.InstigatorComp.Get(); + UAFAbilityComponent* Instigator = InContext.InstigatorComp.Get(); TMap>* EffectByClassMap = InstigatorEffectByClass.Find(Instigator); //TSet* EffectByClass; if (EffectByClassMap) @@ -415,7 +418,7 @@ TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectPrope } case EGAEffectAggregation::AggregateByTarget: { - UGAAbilitiesComponent* Target = InContext.TargetComp.Get(); + UAFAbilityComponent* Target = InContext.TargetComp.Get(); TSet* TargetEffect = TargetEffectByClass.Find(EffectClass); if (TargetEffect) { @@ -450,12 +453,12 @@ void FGAEffectContainer::AddEffectByClass(const FGAEffectHandle& HandleIn) EGAEffectAggregation Aggregation = Spec->EffectAggregation; UClass* EffectClass = Spec->GetClass(); TSet Handles; - UGAAbilitiesComponent* Target = HandleIn.GetContextRef().TargetComp.Get(); + UAFAbilityComponent* Target = HandleIn.GetContextRef().TargetComp.Get(); switch (Aggregation) { case EGAEffectAggregation::AggregateByInstigator: { - UGAAbilitiesComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); + UAFAbilityComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); TMap>& EffectByClassMap = InstigatorEffectByClass.FindOrAdd(Instigator); @@ -484,7 +487,7 @@ void FGAEffectContainer::AddEffectByClass(const FGAEffectHandle& HandleIn) void FGAEffectContainer::RemoveFromAttribute(const FGAEffectHandle& HandleIn) { TSet* AttributeEffect = EffectByAttribute.Find(HandleIn.GetAttribute()); - IIGAAbilities* Target = HandleIn.GetContextRef().TargetInterface; + IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; if (AttributeEffect) { AttributeEffect->Remove(HandleIn); @@ -517,11 +520,11 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn , const FGAEffectProperty& InProperty) { - UGAAbilitiesComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); + UAFAbilityComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); UClass* EffectClass = HandleIn.GetEffectSpec()->GetClass(); TMap>* InstigatorEffect = InstigatorEffectByClass.Find(Instigator); TSet* HandlesToRemove = InstigatorEffect->Find(EffectClass); - IIGAAbilities* Target = HandleIn.GetContextRef().TargetInterface; + IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; TSharedPtr Effect = HandleIn.GetEffectPtr(); if (HandlesToRemove) { @@ -576,7 +579,7 @@ void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn { UClass* EffectClass = HandleIn.GetEffectSpec()->GetClass(); TSet* Handles = TargetEffectByClass.Find(EffectClass); - IIGAAbilities* Target = HandleIn.GetContextRef().TargetInterface; + IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; TSharedPtr Effect = HandleIn.GetEffectPtr(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 1b47bf2..625b291 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -474,8 +474,8 @@ struct ABILITYFRAMEWORK_API FGAEffect : public TSharedFromThis public: void SetContext(const FGAEffectContext& ContextIn); - class UGAAbilitiesComponent* GetInstigatorComp() { return Context.InstigatorComp.Get(); } - class UGAAbilitiesComponent* GetTargetComp() { return Context.TargetComp.Get(); } + class UAFAbilityComponent* GetInstigatorComp() { return Context.InstigatorComp.Get(); } + class UAFAbilityComponent* GetTargetComp() { return Context.TargetComp.Get(); } inline void AddOwnedTags(const FGameplayTagContainer& TagsIn) { OwnedTags.AppendTags(TagsIn); } inline void AddApplyTags(const FGameplayTagContainer& TagsIn) { ApplyTags.AppendTags(TagsIn); } void OnApplied(); @@ -646,7 +646,7 @@ struct ABILITYFRAMEWORK_API FGameCueContainer { GENERATED_USTRUCT_BODY() - TWeakObjectPtr OwningComp; + TWeakObjectPtr OwningComp; public: void AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams); }; @@ -700,7 +700,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TArray TargetInstancedEffects; UPROPERTY(NotReplicated) - class UGAAbilitiesComponent* OwningComponent; + class UAFAbilityComponent* OwningComponent; public: //FGAEffectContainer(); FGAEffectHandle ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp deleted file mode 100644 index b8c2e84..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.cpp +++ /dev/null @@ -1,790 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" - -#include "Abilities/GAAbilityBase.h" -#include "IAbilityFramework.h" - -#include "Net/UnrealNetwork.h" -#include "Engine/ActorChannel.h" -#include "Animation/AnimInstance.h" -#include "Animation/AnimMontage.h" -#include "GAGlobals.h" -#include "Abilities/GAAbilitySet.h" -#include "Attributes/GAAttributesBase.h" -#include "IGAAbilities.h" -#include "Effects/GAEffectExecution.h" -#include "Effects/GAGameEffect.h" -#include "MessageEndpoint.h" -#include "MessageEndpointBuilder.h" -#include "Effects/GAEffectExtension.h" -#include "Effects/GAEffectCue.h" -#include "AFCueSet.h" -#include "AFCueManager.h" -#include "GAAbilitiesComponent.h" - - - -DEFINE_STAT(STAT_ApplyEffect); -DEFINE_STAT(STAT_ModifyAttribute); - -UGAAbilitiesComponent::UGAAbilitiesComponent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bWantsInitializeComponent = true; - bIsAnyAbilityActive = false; - bAutoActivate = true; - bAutoRegister = true; - PrimaryComponentTick.bCanEverTick = true; - PrimaryComponentTick.bStartWithTickEnabled = true; - PrimaryComponentTick.bRunOnAnyThread = false; - PrimaryComponentTick.bAllowTickOnDedicatedServer = true; - PrimaryComponentTick.TickGroup = ETickingGroup::TG_DuringPhysics; - -} - -void UGAAbilitiesComponent::BroadcastAttributeChange(const FGAAttribute& InAttribute, - const FAFAttributeChangedData& InData) -{ - FAFAttributeChangedDelegate* Delegate = AttributeChanged.Find(InAttribute); - if (Delegate) - { - Delegate->Broadcast(InData); - } -} - -bool UGAAbilitiesComponent::GetShouldTick() const -{ - return true; -} - -void UGAAbilitiesComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - ,FGAEffectProperty& InProperty) -{ - //OnAttributePreModifed.Broadcast(ModIn, 0); - //Add log. - float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); - FAFAttributeChangedData Data; - FGAEffectContext& Context = HandleIn.GetContextRef(); - Data.Mod = ModIn; - Data.Target = Context.Target; - Data.Location = Context.HitResult.Location; - OnAttributeModifed.Broadcast(Data); - NotifyInstigatorTargetAttributeChanged(Data, Context); -}; -void UGAAbilitiesComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, - const FGAEffectContext& InContext) -{ - InContext.InstigatorComp->OnTargetAttributeModifed.Broadcast(InData); -} -void UGAAbilitiesComponent::GetAttributeStructTest(FGAAttribute Name) -{ - DefaultAttributes->GetAttribute(Name); -} - -void UGAAbilitiesComponent::OnRep_GameEffectContainer() -{ - float test = 0; -} -void UGAAbilitiesComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - UActorComponent::TickComponent(DeltaTime, TickType, ThisTickFunction); - if (DefaultAttributes) - { - DefaultAttributes->Tick(DeltaTime); - } -} -void UGAAbilitiesComponent::Update() -{ - -} -void UGAAbilitiesComponent::BeginPlay() -{ - Super::BeginPlay(); -} -void UGAAbilitiesComponent::DestroyComponent(bool bPromoteChildren) -{ - Super::DestroyComponent(bPromoteChildren); -} - -FGAEffectHandle UGAAbilitiesComponent::ApplyEffectToSelf(FGAEffect* EffectIn - ,FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier) -{ - const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; - FAFEventData Data; - for (const FGameplayTag& Tag : AppliedEventTags) - { - if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) - { - Event->Broadcast(Data); - } - } - - //OnEffectApplyToSelf.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); - FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); - GameEffectContainer.MarkArrayDirty(); - return Handle; - //FGAEffectCueParams CueParams; - //CueParams.HitResult = EffectIn.Context.HitResult; - //OnEffectApplied.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); -} -FGAEffectHandle UGAAbilitiesComponent::ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier) -{ - //broadcast cues first ? - //Probabaly because effect might not always apply. Or relegate cue - //application to object which was hit ? - - - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - } - else if (mode == ENetMode::NM_DedicatedServer) - { - prefix = FString::Printf(TEXT("DedicatedServer: ")); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), - *prefix, - *GetOwner()->GetName(), - *InContext.Instigator->GetName() - ); - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams; - CueParams.Instigator = InContext.Instigator; - CueParams.Causer = InContext.Causer; - CueParams.HitResult = InContext.HitResult; - CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - if (mode == ENetMode::NM_Standalone - || role >= ENetRole::ROLE_Authority) - { - MulticastApplyEffectCue(CueParams); - } - - } - //execute cue from effect regardless if we have target object or not. - if(InContext.TargetComp.IsValid()) - return InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); - - return FGAEffectHandle(); - -// if (EffectIn.IsValid() && EffectIn.Context.TargetComp.IsValid()) -// { - //OnEffectApplyToTarget.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); - // return EffectIn.Context.TargetComp->ApplyEffectToSelf(EffectIn, HandleIn); -// } -} - -void UGAAbilitiesComponent::OnAttributeModified(const FGAEffectMod& InMod, - const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) -{ - -} -void UGAAbilitiesComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty - ,FAFFunctionModifier Modifier, FGAEffectContext InContex) -{ - /* - this patth will give effects chance to do any replicated events, like applying cues. - WE do not make any replication at the ApplyEffect because some effect might want to apply cues - on periods on expiration etc, and all those will go trouch ExecuteEffect path. - */ - const FGameplayTagContainer& RequiredTags = InProperty.GetSpec()->RequiredTags; - if (RequiredTags.Num() > 0) - { - if (!HasAll(RequiredTags)) - { - UE_LOG(GameAttributesEffects, Log, TEXT("UGAAbilitiesComponent:: Effect %s not executed, require tags: %s"), *HandleIn.GetEffectSpec()->GetName(), *RequiredTags.ToString()); - return; - } - } - - //apply execution events: - const FGameplayTagContainer& ExecuteEventTags = InProperty.GetSpec()->ExecuteEventTags; - FAFEventData Data; - for (const FGameplayTag& Tag : ExecuteEventTags) - { - if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) - { - Event->Broadcast(Data); - } - } - - OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); - UE_LOG(GameAttributesEffects, Log, TEXT("UGAAbilitiesComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); - FGAEffect& Effect = HandleIn.GetEffectRef(); - FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() - , InProperty.GetSpec() - , InContex - , HandleIn); - - //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? - - Effect.OnExecuted(); - MulticastExecuteEffectCue(HandleIn); - InProperty.Execution->ExecuteEffect(HandleIn, Mod, HandleIn.GetContextRef(), InProperty, Modifier); - PostExecuteEffect(); -} -void UGAAbilitiesComponent::PostExecuteEffect() -{ - -} -void UGAAbilitiesComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty) -{ - //call effect internal delegate: - HandleIn.GetEffectPtr()->OnExpired(); - //InternalRemoveEffect(HandleIn); - //OnEffectExpired.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); - GameEffectContainer.RemoveEffectByHandle(HandleIn, InProperty); -} -void UGAAbilitiesComponent::RemoveEffect(const FGAEffectProperty& InProperty) -{ - InternalRemoveEffect(InProperty); - //OnEffectRemoved.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); -} -void UGAAbilitiesComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty) -{ - UE_LOG(GameAttributesEffects, Log, TEXT("UGAAbilitiesComponent:: Reset Timers and Remove Effect")); - - //MulticastRemoveEffectCue(HandleIn); - - GameEffectContainer.RemoveEffect(InProperty); -} - -TArray UGAAbilitiesComponent::GetEffectUIData() -{ - TArray dataReturn; - return dataReturn; -} - -int32 UGAAbilitiesComponent::GetEffectUIIndex() -{ - return 1; -} -FGAEffectUIData UGAAbilitiesComponent::GetEffectUIDataByIndex(int32 IndexIn) -{ - FGAEffectUIData data; - return data; -} - -void UGAAbilitiesComponent::MulticastApplyEffectCue_Implementation( FGAEffectCueParams CueParams) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if(mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : MulticastApplyEffectCue Owner: %s, Instigator: %s" ), - *prefix, - *GetOwner()->GetName(), - *CueParams.Instigator->GetName() - ); - - //for (const FGameplayTag& Tag : CueParams.CueTags) - //{ - // TSubclassOf CueClass = TestCueSet->Cues.FindRef(Tag); - // if (!CueClass) - // continue; - - // FActorSpawnParameters SpawnParams; - // FVector Location = CueParams.HitResult.Location; - // FRotator Rotation = FRotator::ZeroRotator; - // AGAEffectCue* actor = nullptr; - // - // actor = GetWorld()->SpawnActor(CueClass, Location, Rotation, SpawnParams); - // actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - // CueParams.Causer.Get(), CueParams.HitResult); - - //} - - UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams); - } -} - -void UGAAbilitiesComponent::MulticastExecuteEffectCue_Implementation(FGAEffectHandle EffectHandle) -{ - // ActiveCues.ExecuteCue(EffectHandle); -} - -void UGAAbilitiesComponent::MulticastRemoveEffectCue_Implementation(FGAEffectHandle EffectHandle) -{ - // ActiveCues.RemoveCue(EffectHandle); -} - -void UGAAbilitiesComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) -{ - -} -void UGAAbilitiesComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) -{ - -} -void UGAAbilitiesComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) -{ - -} -void UGAAbilitiesComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) -{ - -} - -void UGAAbilitiesComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly replicate it to everyone - //to allow prediction for UI. - DOREPLIFETIME(UGAAbilitiesComponent, DefaultAttributes); - DOREPLIFETIME(UGAAbilitiesComponent, ModifiedAttribute); - DOREPLIFETIME(UGAAbilitiesComponent, GameEffectContainer); - - DOREPLIFETIME(UGAAbilitiesComponent, ActiveCues); - - DOREPLIFETIME_CONDITION(UGAAbilitiesComponent, AbilityContainer, COND_OwnerOnly); - DOREPLIFETIME_CONDITION(UGAAbilitiesComponent, RepMontage, COND_SkipOwner); - //DOREPLIFETIME(UGAAbilitiesComponent, RepMontage); -} -void UGAAbilitiesComponent::OnRep_ActiveEffects() -{ - -} -void UGAAbilitiesComponent::OnRep_ActiveCues() -{ - -} - -void UGAAbilitiesComponent::OnRep_AttributeChanged() -{ - //for (FGAModifiedAttribute& attr : ModifiedAttribute.Mods) - //{ - // attr.Causer->OnAttributeModifed.Broadcast(attr); - //} -} -bool UGAAbilitiesComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) -{ - bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); - - if (DefaultAttributes) - { - WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); - } - for (const FGASAbilityItem& Ability : AbilityContainer.AbilitiesItems) - { - //if (Set.InputOverride) - // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); - - if (Ability.Ability) - WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); - } - return WroteSomething; -} -void UGAAbilitiesComponent::GetSubobjectsWithStableNamesForNetworking(TArray& Objs) -{ - if (DefaultAttributes && DefaultAttributes->IsNameStableForNetworking()) - { - Objs.Add(const_cast(DefaultAttributes)); - } -} - - -FAFEventDelegate& UGAAbilitiesComponent::GetTagEvent(FGameplayTag TagIn) -{ - FAFEventDelegate& Delegate = EffectEvents.FindChecked(TagIn); - return Delegate; -} -void UGAAbilitiesComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) -{ - FAFEventDelegate* Delegate = EffectEvents.Find(TagIn); - if (Delegate) - { - if (Delegate->IsBound()) - { - Delegate->Broadcast(InEventData); - } - } -} -void UGAAbilitiesComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const -{ - TagContainer = AppliedTags.AllTags; -} -bool UGAAbilitiesComponent::HasMatchingGameplayTag(FGameplayTag TagToCheck) const -{ - return AppliedTags.HasTag(TagToCheck); -} - -bool UGAAbilitiesComponent::HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const -{ - return AppliedTags.HasAll(TagContainer); -} - -bool UGAAbilitiesComponent::HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const -{ - return AppliedTags.HasAny(TagContainer); -} - -bool UGAAbilitiesComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) -{ - bool bDenyApplication = false; - if (InTags.Num() > 0) - { - bDenyApplication = HasAll(InTags); - } - return bDenyApplication; -} - -bool UGAAbilitiesComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) -{ - bool bAllowApplication = true; - if (InTags.Num() > 0) - { - bAllowApplication = HasAll(InTags); - } - return bAllowApplication; -} -void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer) -{ - -} -void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) -{ - if (InArraySerializer.AbilitiesComp.IsValid()) - { - //should be safe, since we only modify the non replicated part of struct. - FGASAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); - Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); - //if (InArraySerializer.AbilitiesComp->PawnInterface) - //{ - // Ability->POwner = InArraySerializer.AbilitiesComp->PawnInterface->GetGamePawn(); - // Ability->PCOwner = InArraySerializer.AbilitiesComp->PawnInterface->GetGamePlayerController(); - // Ability->OwnerCamera = InArraySerializer.AbilitiesComp->PawnInterface->GetPawnCamera(); - // //ability->AIOwner = PawnInterface->GetGameController(); - //} - Ability->InitAbility(); - - InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); - } -} -void FGASAbilityItem::PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer) -{ - -} - -UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn, FGameplayTag ActionName) -{ - //if (AbilityIn && AbilitiesComp.IsValid()) - //{ - // UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); - // ability->AbilityComponent = AbilitiesComp.Get(); - // if (AbilitiesComp->PawnInterface) - // { - // ability->POwner = AbilitiesComp->PawnInterface->GetGamePawn(); - // ability->PCOwner = AbilitiesComp->PawnInterface->GetGamePlayerController(); - // ability->OwnerCamera = AbilitiesComp->PawnInterface->GetPawnCamera(); - // //ability->AIOwner = PawnInterface->GetGameController(); - // } - // ability->InitAbility(); - // FGameplayTag Tag = ability->AbilityTag; - - // AbilitiesInputs.Add(Tag, ability); - // FGASAbilityItem AbilityItem; - // AbilityItem.Ability = ability; - // AbilitiesItems.Add(AbilityItem); - ///* if (ActionName.IsValid()) - // { - // UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); - // AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); - // }*/ - // return ability; - //} - return nullptr; -} -UGAAbilityBase* FGASAbilityContainer::GetAbility(FGameplayTag TagIn) -{ - return AbilitiesInputs.FindRef(TagIn); -} -void FGASAbilityContainer::HandleInputPressed(FGameplayTag TagIn, FGameplayTag ActionName) -{ - UGAAbilityBase* ability = AbilitiesInputs.FindRef(TagIn); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - ability->OnNativeInputPressed(ActionName); - } -} -void FGASAbilityContainer::HandleInputReleased(FGameplayTag TagIn, FGameplayTag ActionName) -{ - UGAAbilityBase* ability = AbilitiesInputs.FindRef(TagIn); - if (ability) - { - ability->OnNativeInputReleased(ActionName); - } -} - -void FGASAbilityContainer::TriggerAbylityByTag(FGameplayTag InTag) -{ - UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - ability->OnNativeInputPressed(FGameplayTag()); - } -} - -void UGAAbilitiesComponent::InitializeComponent() -{ - Super::InitializeComponent(); - //PawnInterface = Cast(GetOwner()); - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - AbilityContainer.AbilitiesComp = this; - - if (DefaultAttributes) - { - DefaultAttributes->InitializeAttributes(this); - DefaultAttributes->InitializeAttributesFromTable(); - } - GameEffectContainer.OwningComponent = this; - ActiveCues.OwningComp = this; - //ActiveCues.OwningComponent = this; - AppliedTags.AddTagContainer(DefaultTags); - //TestRunnable = new FAsyncUObjectRunnable(this); - //TEstAsyncUObject = NewObject(this, UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); - //TEstAsyncUObject->AddToRoot(); - //RouterThread = FRunnableThread::Create(TEstAsyncUObject, TEXT("AsyncUObject.Test"), 128 * 1024, TPri_Normal, FPlatformAffinity::GetPoolThreadMask()); - InitializeInstancedAbilities(); -} -void UGAAbilitiesComponent::UninitializeComponent() -{ - Super::UninitializeComponent(); - //GameEffectContainer -} -void UGAAbilitiesComponent::BP_BindAbilityToAction(FGameplayTag ActionName, FGameplayTag AbilityTag) -{ - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - BindAbilityToAction(InputComponent, ActionName, AbilityTag); -} -void UGAAbilitiesComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName, FGameplayTag AbilityTag) -{ - if (!InputComponent) - return; - { - FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); - AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UGAAbilitiesComponent::NativeInputPressed, AbilityTag, ActionName); - InputComponent->AddActionBinding(AB); - } - - // Released event - { - FInputActionBinding AB(ActionName.GetTagName(), IE_Released); - AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UGAAbilitiesComponent::NativeInputReleased, AbilityTag, ActionName); - InputComponent->AddActionBinding(AB); - } -} -void UGAAbilitiesComponent::BP_InputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - NativeInputPressed(AbilityTag, ActionName); -} -void UGAAbilitiesComponent::NativeInputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNativeInputPressed(AbilityTag, ActionName); - UE_LOG(AbilityFramework, Log, TEXT("Client UGAAbilitiesComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); - //naive needs better qynchornization to what going on where. - if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - { - if (Ability->AbilityComponent == this) - { - AbilityContainer.HandleInputPressed(AbilityTag, ActionName); - } - } - } - else - { - UE_LOG(AbilityFramework, Log, TEXT("Server UGAAbilitiesComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); - if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - { - if (Ability->AbilityComponent == this) - { - AbilityContainer.HandleInputPressed(AbilityTag, ActionName); - } - } - } -} - -void UGAAbilitiesComponent::ServerNativeInputPressed_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - NativeInputPressed(AbilityTag, FGameplayTag()); -} -bool UGAAbilitiesComponent::ServerNativeInputPressed_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - return true; -} - -void UGAAbilitiesComponent::BP_InputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - NativeInputReleased(AbilityTag, ActionName); -} - -void UGAAbilitiesComponent::NativeInputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - { - if (Ability->AbilityComponent == this) - { - AbilityContainer.HandleInputReleased(AbilityTag, ActionName); - } - } - ServerNativeInputReleased(AbilityTag, ActionName); - } - else - { - UE_LOG(AbilityFramework, Log, TEXT("UGAAbilitiesComponent::NativeInputReleased: %s"), *AbilityTag.GetTagName().ToString()); - - AbilityContainer.HandleInputReleased(AbilityTag, ActionName); - } -} - -void UGAAbilitiesComponent::ServerNativeInputReleased_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - NativeInputReleased(AbilityTag, FGameplayTag()); -} -bool UGAAbilitiesComponent::ServerNativeInputReleased_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName) -{ - return true; -} - -void UGAAbilitiesComponent::BP_AddAbility(TSubclassOf AbilityClass, - FGameplayTag ActionName, bool bAutoBind) -{ - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - return; - } - else - { - NativeAddAbility(AbilityClass, ActionName, bAutoBind); - } - -} - -void UGAAbilitiesComponent::NativeAddAbility(TSubclassOf AbilityClass, - FGameplayTag ActionName, bool bAutoBind) -{ - InstanceAbility(AbilityClass, ActionName); - if (bAutoBind) - ClientOnAbilityAdded(AbilityClass->GetDefaultObject()->AbilityTag, ActionName); -} - -void UGAAbilitiesComponent::ClientOnAbilityAdded_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionTag) -{ - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - BindAbilityToAction(InputComponent, ActionTag, AbilityTag); -} -void UGAAbilitiesComponent::BP_RemoveAbility(FGameplayTag TagIn) -{ - -} -UGAAbilityBase* UGAAbilitiesComponent::BP_GetAbilityByTag(FGameplayTag TagIn) -{ - return AbilityContainer.GetAbility(TagIn); -} -UGAAbilityBase* UGAAbilitiesComponent::InstanceAbility(TSubclassOf AbilityClass, FGameplayTag ActionName) -{ - if (AbilityClass) - { - UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, ActionName); - AbilityContainer.MarkArrayDirty(); - return ability; - } - return nullptr; -} - -void UGAAbilitiesComponent::NativeAddAbilitiesFromSet(TSubclassOf AbilitySet) -{ - //do not let add abilities on non authority. - if (GetOwnerRole() < ENetRole::ROLE_Authority) - return; - - UGAAbilitySet* Set = AbilitySet.GetDefaultObject(); - int32 Index = 0; - for (const FGASAbilitySetItem& Item : Set->AbilitySet.Abilities) - { - InstanceAbility(Item.AbilityClass, Item.Binding); - Index++; - } -} - -void UGAAbilitiesComponent::BP_AddAbilitiesFromSet(TSubclassOf AbilitySet) -{ - NativeAddAbilitiesFromSet(AbilitySet); -} - -void UGAAbilitiesComponent::OnRep_InstancedAbilities() -{ -} - -void UGAAbilitiesComponent::InitializeInstancedAbilities() -{ -} - -void UGAAbilitiesComponent::OnRep_PlayMontage() -{ - ACharacter* MyChar = Cast(GetOwner()); - if (MyChar) - { - UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); - AnimInst->Montage_Play(RepMontage.CurrentMontage); - if (RepMontage.SectionName != NAME_None) - { - AnimInst->Montage_JumpToSection(RepMontage.SectionName, RepMontage.CurrentMontage); - } - UE_LOG(AbilityFramework, Log, TEXT("OnRep_PlayMontage MontageName: %s SectionNAme: %s ForceRep: %s"), *RepMontage.CurrentMontage->GetName(), *RepMontage.SectionName.ToString(), *FString::FormatAsNumber(RepMontage.ForceRep)); - } -} - -void UGAAbilitiesComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) -{ - //if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - //Probabaly want to do something different here for client non authority montage plays. - //return; - } - ACharacter* MyChar = Cast(GetOwner()); - if (MyChar) - { - UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); - AnimInst->Montage_Play(MontageIn, Speed); - if (SectionName != NAME_None) - { - AnimInst->Montage_JumpToSection(SectionName, MontageIn); - } - - UE_LOG(AbilityFramework, Log, TEXT("PlayMontage MontageName: %s SectionNAme: %s Where: %s"), *MontageIn->GetName(), *SectionName.ToString(), (GetOwnerRole() < ENetRole::ROLE_Authority ? TEXT("Client") : TEXT("Server"))); - RepMontage.SectionName = SectionName; - RepMontage.CurrentMontage = MontageIn; - RepMontage.ForceRep++; - } -} -void UGAAbilitiesComponent::MulticastPlayMontage_Implementation(UAnimMontage* MontageIn, FName SectionName, float Speed = 1) -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h deleted file mode 100644 index ebe5e9e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAAbilitiesComponent.h +++ /dev/null @@ -1,595 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "GameplayTaskOwnerInterface.h" -#include "GameplayTaskTypes.h" -#include "GameplayTask.h" -#include "GameplayTasksComponent.h" -#include "GameplayTags.h" -#include "GAGlobals.h" -#include "Attributes/GAAttributeBase.h" -#include "Attributes/GAAttributesBase.h" -#include "Effects/GAEffectCueGlobals.h" - -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "Messaging.h" -#include "GameplayTagAssetInterface.h" -#include "IGAAbilities.h" - -//tests -#include "Async/AsyncUObjectImpl.h" -#include "Async/AsyncUObject.h" -#include "HAL/RunnableThread.h" - -#include "GAAbilitiesComponent.generated.h" - -DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); -DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); -DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGAGenericEffectDelegate, const FGAEffectHandle&, Handle, const FGameplayTagContainer&, Tags); - -DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate , FAFEventData); -DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); - -DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectRepInfoDelegate, FAFEffectRepInfo*); - -USTRUCT() -struct FGAModifiedAttributeData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - TArray Mods; - UPROPERTY() - int32 ForceUpdate; - - FGAModifiedAttributeData() - : ForceUpdate(0) - {} -}; - -USTRUCT(BlueprintType) -struct FGAEffectUIData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(BlueprintReadOnly, Category = "UI") - float RemainingTime; - - FGAEffectUIData() - : RemainingTime(0) - {}; -}; -struct FGAContextSetup -{ -public: - UGAAttributesBase* IntigatorAttributes; - UGAAttributesBase* TargetAttributes; - UGAAbilitiesComponent* InstigatorComp; - UGAAbilitiesComponent* TargetComp; - - FGAContextSetup() - {}; - FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, - UGAAbilitiesComponent* InstigatorCompIn, UGAAbilitiesComponent* TargetCompIn) - : IntigatorAttributes(IntigatorAttributesIn), - TargetAttributes(TargetAttributesIn), - InstigatorComp(InstigatorCompIn), - TargetComp(TargetCompIn) - {}; -}; -DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); -DECLARE_DELEGATE_ThreeParams(FAFMontageGenericDelegate, const FAFAbilityNotifyData&, const FGameplayTag&, const FName&); -/* TODO:: Implement fast serialization for structs. */ -/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ -/**/ - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASMontageRepData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - UAnimMontage* CurrentMontage; - - UPROPERTY() - FName SectionName; - - UPROPERTY() - uint8 ForceRep; -}; - -USTRUCT() -struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem -{ - GENERATED_BODY() - -public: - UPROPERTY() - UGAAbilityBase* Ability; - - void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); - void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); - void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); -}; -USTRUCT() -struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - - UPROPERTY() - TArray AbilitiesItems; - - TWeakObjectPtr AbilitiesComp; - - TMap AbilitiesInputs; - - UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, FGameplayTag ActionName); - UGAAbilityBase* GetAbility(FGameplayTag TagIn); - - void HandleInputPressed(FGameplayTag TagIn, FGameplayTag ActionName); - void HandleInputReleased(FGameplayTag TagIn, FGameplayTag ActionName); - - void TriggerAbylityByTag(FGameplayTag InTag); - - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; - -UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) -class ABILITYFRAMEWORK_API UGAAbilitiesComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface -{ - GENERATED_BODY() - /* Attributes handling */ -public: - friend struct FAFMessageTick; - //Only for base testing and prototyping cue application. - //will be removed when Cue Manager will be more functional. - UPROPERTY(EditAnywhere) - class UAFCueSet* TestCueSet; - UPROPERTY(EditAnywhere, Category = "Test") - FGameplayTag TagTest; - /* - Set attribute which will be considered for indicating whether or not actor is dead. - */ - UPROPERTY(EditAnywhere, Category = "Config") - FGAAttribute DeathAttribute; - - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer DefaultTags; - - UPROPERTY() - FGACountedTagContainer AppliedTags; - - UPROPERTY() - FGACountedTagContainer ImmunityTags; - - UFUNCTION() - void OnRep_ActiveEffects(); - - UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) - FGameCueContainer ActiveCues; - UFUNCTION() - void OnRep_ActiveCues(); - /* - Could make it array. But realistically. How many times do you really need more, than one - attribute set for actor ? - - Of course array of attributes would allow to compose attributes from small discreete - attribute sets. On the other hand similiar funcionality can be achieved by using - inheritance. - - And I think that using inheritance in this case will be easier. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) - class UGAAttributesBase* DefaultAttributes; - - //probabaly replace FGameplayTag with FObjectKey - TMap AdditionalAttributes; - - UPROPERTY(ReplicatedUsing = OnRep_AttributeChanged) - FGAModifiedAttributeData ModifiedAttribute; - UFUNCTION() - void OnRep_AttributeChanged(); - UPROPERTY(BlueprintAssignable, Category = "Game Attributes") - FGAOnAttributeModifed OnAttributeModifed; - UPROPERTY(BlueprintAssignable, Category = "Game Attributes") - FGAOnAttributeModifed OnTargetAttributeModifed; - /* Effect/Attribute System Delegates */ - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectApplied; - - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectApplyToTarget; - - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectApplyToSelf; - - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectExecuted; - - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectExpired; - - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectRemoved; - - /* NEW EFFECT SYSTEM */ - UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) - FGAEffectContainer GameEffectContainer; - - FAFEffectRepInfoDelegate OnEffectRepInfoApplied; - FAFEffectRepInfoDelegate OnEffectRepInfoRemoved; - /* - Default effects applied when character spawns. - Can contain things like attribute regen, racial bonuses - racial debuffs etc. - */ - UPROPERTY(EditAnywhere, Category = "Effects") - TArray> DefaultEffects; - - TMap EffectEvents; - TMap AttributeChanged; - - void BroadcastAttributeChange(const FGAAttribute& InAttribute, - const FAFAttributeChangedData& InData); - - virtual bool GetShouldTick() const override; - - UFUNCTION() - void OnRep_GameEffectContainer(); - - template - T* GetAttributes() - { - return CastChecked(DefaultAttributes); - } - - template - T* GetAttributeSet(FGameplayTag InOwner) - { - UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); - return Cast(AttributeSet); - } - void AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) - { - bool bExists = AdditionalAttributes.Contains(InOwner); - if (bExists) - { - return; - } - AdditionalAttributes.Add(InOwner, InAttributes); - } - UFUNCTION(BlueprintCallable, Category = "Test") - void GetAttributeStructTest(FGAAttribute Name); - - virtual void BeginPlay() override; - virtual void DestroyComponent(bool bPromoteChildren = false) override; - - virtual void InitializeComponent() override; - - virtual void UninitializeComponent() override; - - -public: - ///////////////////////////////////////////////// - //////////// EFFECTS HANDLING - virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - void Update(); - FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - void ApplyEffectToTarget(TSubclassOf InSpecClass, - const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); - - - /* Have to to copy handle around, because timer delegates do not support references. */ - void ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty - ,FAFFunctionModifier Modifier, FGAEffectContext InContext); - virtual void PostExecuteEffect(); - /* ExpireEffect is used to remove existing effect naturally when their time expires. */ - void ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty); - /* RemoveEffect is used to remove effect by force. */ - void RemoveEffect(const FGAEffectProperty& InProperty); - void InternalRemoveEffect(const FGAEffectProperty& InProperty); - - - /* Never call it directly. */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes|UI") - TArray GetEffectUIData(); - - /* - Get Last Index of effect for UI display. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes|UI") - int32 GetEffectUIIndex(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes|UI") - FGAEffectUIData GetEffectUIDataByIndex(int32 IndexIn); - /* - Need prediction for spawning effects on client, - and then on updateing them predicitvely on all other clients. - */ - /* - - */ - UFUNCTION(NetMulticast, Unreliable) - void MulticastApplyEffectCue(FGAEffectCueParams CueParams); - virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastExecuteEffectCue(FGAEffectHandle EffectHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastRemoveEffectCue(FGAEffectHandle EffectHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); - - //////////// EFFECTS HANDLING - ///////////////////////////////////////////////// - -public: - ///////////////////////////////////////////////// - //////////// ATTRIBUTES HANDLING - - /* - Two functions, They will allow to apply any static numerical mods from player who - initiated attribute change, and from player who will be affected by change. - - Mods will be appiled by small objects, and changed against tags. - For example there might be physical armor mod, which will apply changes only - to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. - */ - - inline float GetFinalAttributeValue(const FGAAttribute& Name) - { - return DefaultAttributes->GetFinalAttributeValue(Name); - } - inline float GetCurrentAttributeValue(const FGAAttribute& Name) - { - return DefaultAttributes->GetCurrentAttributeValue(Name); - } - //////////// ATTRIBUTES HANDLING - ///////////////////////////////////////////////// - /* - Attribute replication. - */ - void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); - - FAFEventDelegate& GetTagEvent(FGameplayTag TagIn); - void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); - //Helper functions: -public: - /* - IGameplayTagAssetInterface Start - */ - /** - * Get any owned gameplay tags on the asset - * - * @param OutTags [OUT] Set of tags on the asset - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; - - /** - * Check if the asset has a gameplay tag that matches against the specified tag (expands to include parents of asset tags) - * - * @param TagToCheck Tag to check for a match - * - * @return True if the asset has a gameplay tag that matches, false if not - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual bool HasMatchingGameplayTag(FGameplayTag TagToCheck) const override; - - /** - * Check if the asset has gameplay tags that matches against all of the specified tags (expands to include parents of asset tags) - * - * @param TagContainer Tag container to check for a match - * - * @return True if the asset has matches all of the gameplay tags, will be true if container is empty - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual bool HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; - - /** - * Check if the asset has gameplay tags that matches against any of the specified tags (expands to include parents of asset tags) - * - * @param TagContainer Tag container to check for a match - * - * @return True if the asset has matches any of the gameplay tags, will be false if container is empty - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual bool HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; - /* - IGameplayTagAssetInterface End - */ - - bool DenyEffectApplication(const FGameplayTagContainer& InTags); - bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); - /* - Effect Container Wrapp Start - */ - /* - */ - inline bool IsEffectActive(const FGAEffectHandle& HandleIn) { return GameEffectContainer.IsEffectActive(HandleIn); }; - /* - Effect Container Wrapp End - */ - - /* Counted Tag Container Wrapper Start */ - inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; - inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; - inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; - inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; - inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } - inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; - inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; - inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; - inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; - inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; - inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } - /* Counted Tag Container Wrapper Start */ - - /* Active Effects Wrapper Start */ - inline int32 GetEffectsNum() const { return GameEffectContainer.GetEffectsNum(); }; - /* Active Effects Wrapper End */ - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; - - void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; - void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, - const FGAEffectContext& InContext); - FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; - void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; - float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; - -private: - class IIGAAbilities* AttributeInterface; - -public: - UGAAbilitiesComponent(const FObjectInitializer& ObjectInitializer); - - UFUNCTION() - void OnRep_InstancedAbilities(); - UPROPERTY(Replicated) - FGASAbilityContainer AbilityContainer; - UPROPERTY() - TArray AbilitiesRefs; - - UPROPERTY() - APlayerController* PCOwner; - - /* Ability which is currently being executed. */ - UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") - class UGAAbilityBase* ExecutingAbility; - - TMap AbilitiesToConfirm; - - /* - True if player is currently casting/channeling/activating(?) - any ability. - */ - bool bIsAnyAbilityActive; - - FAFMontageGenericDelegate OnAbilityNotifyBegin; - FAFMontageGenericDelegate OnAbilityNotifyTick; - FAFMontageGenericDelegate OnAbilityNotifyEnd; - - //class IIGIPawn* PawnInterface; -private: - - - UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) - FGASMontageRepData RepMontage; - UFUNCTION() - void OnRep_PlayMontage(); - -public: - UFUNCTION(BlueprintCallable, Category = "AbilityFramework") - void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); - UFUNCTION(NetMulticast, Unreliable) - void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); -public: - inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) - { - return nullptr; - } - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") - void BP_BindAbilityToAction(FGameplayTag ActionName, FGameplayTag AbilityTag); - void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName, FGameplayTag AbilityTag); - - UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") - void BP_InputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName); - - void NativeInputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName); - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputPressed(FGameplayTag AbilityTag, FGameplayTag ActionName); - virtual void ServerNativeInputPressed_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName); - virtual bool ServerNativeInputPressed_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName); - - - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") - void BP_InputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName); - - void NativeInputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName); - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputReleased(FGameplayTag AbilityTag, FGameplayTag ActionName); - virtual void ServerNativeInputReleased_Implementation(FGameplayTag AbilityTag, FGameplayTag ActionName); - virtual bool ServerNativeInputReleased_Validate(FGameplayTag AbilityTag, FGameplayTag ActionName); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability"), Category = "AbilityFramework|Abilities") - void BP_AddAbility(TSubclassOf AbilityClass, - FGameplayTag ActionName, bool bAutoBind = true); - - void NativeAddAbility(TSubclassOf AbilityClass, - FGameplayTag ActionName, bool bAutoBind = true); - - /* Callback from server, after ability has been added. */ - UFUNCTION(Client, Reliable) - void ClientOnAbilityAdded(FGameplayTag AbilityTag, FGameplayTag ActionTag); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") - void BP_RemoveAbility(FGameplayTag TagIn); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") - UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); - /* - Should be called on server. - Adds new ability to ActiveAbilities; - */ - void NativeAddAbilitiesFromSet(TSubclassOf AbilitySet); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Abilities From Set"), Category = "AbilityFramework|Abilities") - void BP_AddAbilitiesFromSet(TSubclassOf AbilitySet); - - bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; - void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; -protected: - void InitializeInstancedAbilities(); - UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, FGameplayTag ActionName = FGameplayTag()); - /* - Messagin implementation for applying effects from multiple threads (in case - at some beatyfull day UObject will be able to exist on any thread), and from single thread. - - Implementation is based on FMessageEndpoint. - */ - -}; - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index 632d0a5..8888e3e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -3,16 +3,17 @@ #include "Effects/GAGameEffect.h" #include "GAGlobalTypes.h" #include "GameplayTagContainer.h" -#include "GAAbilitiesComponent.h" +#include "AFAbilityComponent.h" #include "Attributes/GAAttributeBase.h" #include "Effects/GAEffectExecution.h" -#include "IGAAbilities.h" +#include "AFAbilityInterface.h" #include "Effects/GACustomCalculation.h" FGAEffectContext::FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, - TWeakObjectPtr TargetCompIn, - TWeakObjectPtr InstigatorCompIn) + TWeakObjectPtr TargetCompIn, + TWeakObjectPtr InstigatorCompIn, + TWeakObjectPtr InAvatar) : TargetAttributes(TargetAttributesIn), InstigatorAttributes(InstigatorAttributesIn), TargetHitLocation(TargetHitLocationIn), @@ -20,11 +21,12 @@ FGAEffectContext::FGAEffectContext(TWeakObjectPtr Targe Causer(CauserIn), Instigator(InstigatorIn), TargetComp(TargetCompIn), - InstigatorComp(InstigatorCompIn) + InstigatorComp(InstigatorCompIn), + Avatar(InAvatar) { - TargetInterface = Cast(TargetIn.Get()); - InstigatorInterface = Cast(Instigator.Get()); - IIGAAbilities* CauserInterface = Cast(Causer.Get()); + TargetInterface = Cast(TargetIn.Get()); + InstigatorInterface = Cast(Instigator.Get()); + IAFAbilityInterface* CauserInterface = Cast(Causer.Get()); } FGAEffectHandle::FGAEffectHandle(uint32 HandleIn, FGAEffect* EffectIn) : Handle(HandleIn), @@ -164,7 +166,7 @@ class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() } class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() { - IIGAAbilities* AttrInt = Cast(Causer.Get()); + IAFAbilityInterface* AttrInt = Cast(Causer.Get()); if (AttrInt) { return AttrInt->GetAttributes(); @@ -187,7 +189,7 @@ class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() const } class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() const { - IIGAAbilities* AttrInt = Cast(Causer.Get()); + IAFAbilityInterface* AttrInt = Cast(Causer.Get()); if (AttrInt) { return AttrInt->GetAttributes(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 1c3dcd9..a0474b9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -261,19 +261,22 @@ struct ABILITYFRAMEWORK_API FGAEffectContext */ UPROPERTY(BlueprintReadOnly, Category = "Spec") TWeakObjectPtr Instigator; + + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Avatar; /** * Attribute component of Target. */ UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr TargetComp; + TWeakObjectPtr TargetComp; /** * Attribute component of Intigator */ UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr InstigatorComp; + TWeakObjectPtr InstigatorComp; - class IIGAAbilities* TargetInterface; - class IIGAAbilities* InstigatorInterface; + class IAFAbilityInterface* TargetInterface; + class IAFAbilityInterface* InstigatorInterface; template inline T* GetTarget() { @@ -332,8 +335,9 @@ struct ABILITYFRAMEWORK_API FGAEffectContext FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, - TWeakObjectPtr TargetCompIn, - TWeakObjectPtr InstigatorCompIn); + TWeakObjectPtr TargetCompIn, + TWeakObjectPtr InstigatorCompIn, + TWeakObjectPtr InAvatar); ~FGAEffectContext(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h index 279614c..34b2f98 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h @@ -3,7 +3,7 @@ #pragma once #include "Engine/NetSerialization.h" #include "GameplayTags.h" -#include "GAAbilitiesComponent.h" +#include "AFAbilityComponent.h" #include "GAHelperTemplates.generated.h" USTRUCT(BlueprintType) @@ -34,8 +34,8 @@ struct FGAAttributeCapture template T* GetAttributeSet(const FGAEffectContext& ContextIn) { - UGAAbilitiesComponent* TargetComp = ContextIn.TargetComp.Get(); - UGAAbilitiesComponent* InstigatorComp = ContextIn.InstigatorComp.Get(); + UAFAbilityComponent* TargetComp = ContextIn.TargetComp.Get(); + UAFAbilityComponent* InstigatorComp = ContextIn.InstigatorComp.Get(); T* AttributeSet = nullptr; switch (Source.Source) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp deleted file mode 100644 index 119e97a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.cpp +++ /dev/null @@ -1,10 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "IGAAbilities.h" - -UIGAAbilities::UIGAAbilities(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h b/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h deleted file mode 100644 index 5643918..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/IGAAbilities.h +++ /dev/null @@ -1,48 +0,0 @@ -#pragma once -#include "GAGlobalTypes.h" -#include "Effects/GAGameEffect.h" -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypes.h" -#include "Messaging.h" -#include "IGAAbilities.generated.h" - - -struct FAFAttributeBase; -struct FGAEffectHandle; -UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) -class ABILITYFRAMEWORK_API UIGAAbilities : public UInterface -{ - GENERATED_UINTERFACE_BODY() -}; - -class IIGAAbilities -{ - GENERATED_IINTERFACE_BODY() -public: - virtual FVector GetSocketLocation(FName SocketNameIn){ return FVector::ZeroVector; }; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UGAAttributesBase* GetAttributes() = 0; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UGAAbilitiesComponent* GetAbilityComp() { return nullptr; }; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; - - virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) {}; - virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; - - virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; - - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) { return FGAEffectHandle(); }; - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) {}; - //override to allow gathering tags from causer - //those tags will be merged into effect owned tags. - virtual FGameplayTagContainer GetCauserTags() { return FGameplayTagContainer(); } - - virtual void Died() {}; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp deleted file mode 100644 index f645ed8..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.cpp +++ /dev/null @@ -1,36 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../Abilities/GAAbilityBase.h" -#include "GASAbilityTargetingObject.h" - -FHitResult UGASAbilityTargetingObject::GetTarget() -{ - FHitResult HitOut; - APlayerController* PC = AbilityOwner->PCOwner; - APawn* P = AbilityOwner->POwner; - FVector TraceStart = PC->PlayerCameraManager->GetCameraLocation(); // P->GetPawnViewLocation(); - FRotator UnusedRot = P->GetBaseAimRotation(); - PC->GetActorEyesViewPoint(TraceStart, UnusedRot); - FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; - UWorld* World = GetWorld(); - FCollisionQueryParams ColParams; - ColParams.AddIgnoredActor(P); - FCollisionResponseParams ColResp; - - World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); - if (HitOut.bBlockingHit) - { - DrawDebugLine(GetWorld(), TraceStart, HitOut.ImpactPoint, FColor::Red, true, 4); - } - DrawDebugLine(GetWorld(), TraceStart, TraceEnd, FColor::Green, true, 4); - - return HitOut; -} - -class UWorld* UGASAbilityTargetingObject::GetWorld() const -{ - if (AbilityOwner.IsValid()) - return AbilityOwner->GetWorld(); - return nullptr; -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h deleted file mode 100644 index 05e6f28..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GASAbilityTargetingObject.h +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Object.h" -#include "GASAbilityTargetingObject.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGASAbilityTargetingObject : public UObject -{ - GENERATED_BODY() -public: - TWeakObjectPtr AbilityOwner; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, meta = (ExposeOnSpawn = "true"), Category = "Config") - bool bDebugDraw; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, meta = (ExposeOnSpawn = "true"), Category = "Config") - float Range; - - virtual FHitResult GetTarget(); - - virtual class UWorld* GetWorld() const; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp deleted file mode 100644 index c377965..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.cpp +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GATargetingActor.h" - - -// Sets default values -AGATargetingActor::AGATargetingActor() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void AGATargetingActor::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AGATargetingActor::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h deleted file mode 100644 index c48049e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Targeting/GATargetingActor.h +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GameFramework/Actor.h" -#include "GATargetingActor.generated.h" - -UCLASS() -class ABILITYFRAMEWORK_API AGATargetingActor : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - AGATargetingActor(); - - // Called when the game starts or when spawned - virtual void BeginPlay() override; - - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp index 5b45dcb..adcb2e0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp @@ -6,7 +6,7 @@ -void UGAAttributesTest::InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp) +void UGAAttributesTest::InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) { Super::InitializeAttributes(InOwningAttributeComp); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h index aa3632b..4553dc4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h @@ -45,5 +45,5 @@ class ABILITYFRAMEWORK_API UGAAttributesTest : public UGAAttributesBase UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") FAFAttributeBase MagicResistance; public: - virtual void InitializeAttributes(UGAAbilitiesComponent* InOwningAttributeComp) override; + virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) override; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp index 09255d3..50d3a1a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp @@ -6,7 +6,7 @@ #include "../GAGlobalTypes.h" #include "../Attributes/GAAttributeBase.h" #include "../Effects/GAGameEffect.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "../Attributes/GAAttributesBase.h" #include "../Effects/GAEffectExecution.h" #include "../Effects/GABlueprintLibrary.h" @@ -92,16 +92,16 @@ class GameEffectsTestSuite FAutomationTestBase* Test; AGACharacterAttributeTest* SourceActor; - UGAAbilitiesComponent* SourceComponent; + UAFAbilityComponent* SourceComponent; AGACharacterAttributeTest* DestActor; - UGAAbilitiesComponent* DestComponent; + UAFAbilityComponent* DestComponent; AGACharacterAttributeTest* TargetOne; - UGAAbilitiesComponent* TargetCompOne; + UAFAbilityComponent* TargetCompOne; AGACharacterAttributeTest* TargetTwo; - UGAAbilitiesComponent* TargetCompTwo; + UAFAbilityComponent* TargetCompTwo; public: GameEffectsTestSuite(UWorld* WorldIn, FAutomationTestBase* TestIn) @@ -1075,7 +1075,8 @@ class GameEffectsTestSuite TickWorld(PeriodSecs * 0.1f); float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); TestEqual("Source Stamina Finished: ", FinishedVal, 150.0f); - DestComponent->RemoveEffect(Effect); + FGAEffectContext Context = UGABlueprintLibrary::MakeContext(DestActor, SourceActor, DestActor, SourceActor, FHitResult(ForceInit)); + DestComponent->RemoveEffect(Effect, Context); float PostRemovedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); TestEqual("Source Stamina Finished: ", PostRemovedVal, 100.0f); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp index a5f345f..882246c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp @@ -1,7 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "GACharacterAttributeTest.h" @@ -10,7 +10,7 @@ AGACharacterAttributeTest::AGACharacterAttributeTest() { // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. PrimaryActorTick.bCanEverTick = true; - Attributes = CreateDefaultSubobject(TEXT("Attributes")); + Attributes = CreateDefaultSubobject(TEXT("Attributes")); } // Called when the game starts or when spawned @@ -38,7 +38,7 @@ class UGAAttributesBase* AGACharacterAttributeTest::GetAttributes() { return Attributes->DefaultAttributes; } -class UGAAbilitiesComponent* AGACharacterAttributeTest::GetAbilityComp() +class UAFAbilityComponent* AGACharacterAttributeTest::GetAbilityComp() { return Attributes; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h index fbf06e4..a772172 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h @@ -3,16 +3,16 @@ #pragma once #include "GameFramework/Character.h" -#include "../IGAAbilities.h" +#include "../AFAbilityInterface.h" #include "GACharacterAttributeTest.generated.h" UCLASS() -class ABILITYFRAMEWORK_API AGACharacterAttributeTest : public ACharacter, public IIGAAbilities +class ABILITYFRAMEWORK_API AGACharacterAttributeTest : public ACharacter, public IAFAbilityInterface { GENERATED_BODY() public: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Attributes") - class UGAAbilitiesComponent* Attributes; + class UAFAbilityComponent* Attributes; public: // Sets default values for this character's properties AGACharacterAttributeTest(); @@ -28,7 +28,7 @@ class ABILITYFRAMEWORK_API AGACharacterAttributeTest : public ACharacter, public virtual class UGAAttributesBase* GetAttributes() override; - virtual class UGAAbilitiesComponent* GetAbilityComp() override; + virtual class UAFAbilityComponent* GetAbilityComp() override; virtual float GetAttributeValue(FGAAttribute AttributeIn) const override { return 0; }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// override { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp index dca71e3..408549d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp @@ -2,7 +2,7 @@ #include "../AbilityFramework.h" #include "GameplayTagContainer.h" -#include "../GAAbilitiesComponent.h" +#include "../AFAbilityComponent.h" #include "../Attributes/GAAttributesBase.h" #include "GASpellExecutionTest.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs index 80e2c53..03137c6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs @@ -11,8 +11,9 @@ public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) PublicIncludePaths.AddRange( new string[] { "AbilityFramework", - "AbilityFramework/Public", - // "GameAttributesEditor", + "AbilityFramework/Abilities", + "AbilityFramework/Attributes", + "AbilityFramework/Effects", "AbilityFramework/Public" // ... add public include paths required here ... } @@ -24,7 +25,12 @@ public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) Path.Combine(EngineDir, @"Source/Editor/GraphEditor/Private"), Path.Combine(EngineDir, @"Source/Editor/Kismet/Private"), Path.Combine(EngineDir, @"Source/Editor/PropertyEditor/Private"), - Path.Combine(EngineDir, @"Source/Developer/AssetTools/Private") + Path.Combine(EngineDir, @"Source/Developer/AssetTools/Private"), + "AbilityFramework", + "AbilityFramework/Abilities", + "AbilityFramework/Attributes", + "AbilityFramework/Effects", + "AbilityFramework/Public" // ... add other private include paths required here ... } ); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp index fb4592b..77cc91b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp @@ -13,28 +13,47 @@ #include "AFAbilityActionSpecDetails.h" #include "AFAbilityPeriodSpecDetails.h" #include "AFAbilityCooldownSpecDetails.h" +#include "AFAbilityInfiniteDurationSpecDetails.h" +#include "AFAbilityInfinitePeriodSpecDetails.h" #include "EffectEditor/AssetTypeActions_GAEffectBlueprint.h" #include "AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h" #include "EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h" +#include "EffectCueEditor/AFEffectCueDetails.h" -#include "BlueprintEditorModule.h" -#include "BlueprintEditorTabs.h" -#include "LayoutExtender.h" -#include "LevelEditor.h" -#include "MovieSceneToolsProjectSettings.h" -#include "PropertyEditorModule.h" -#include "Styling/SlateStyle.h" -#include "WorkflowTabManager.h" -#include "Modules/ModuleManager.h" -#include "Widgets/Docking/SDockTab.h" - -#include "ISettingsModule.h" #include "AFCueManager.h" TSet FAbilityFrameworkEditor::EffectClasses = TSet(); +/** Shared class type that ensures safe binding to RegisterBlueprintEditorTab through an SP binding without interfering with module ownership semantics */ +FEffectCueequenceEditorTabBinding::FEffectCueequenceEditorTabBinding() +{ + FBlueprintEditorModule& BlueprintEditorModule = FModuleManager::LoadModuleChecked("Kismet"); + BlueprintEditorTabSpawnerHandle = BlueprintEditorModule.OnRegisterTabsForEditor().AddRaw(this, &FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorTab); + BlueprintEditorLayoutExtensionHandle = BlueprintEditorModule.OnRegisterLayoutExtensions().AddRaw(this, &FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorLayout); +} + +void FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) +{ + Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); +} + +void FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) +{ + TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); +} + +FEffectCueequenceEditorTabBinding::~FEffectCueequenceEditorTabBinding() +{ + FBlueprintEditorModule* BlueprintEditorModule = FModuleManager::GetModulePtr("Kismet"); + if (BlueprintEditorModule) + { + BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); + BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); + } +} + void FAbilityFrameworkEditor::RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action) { @@ -57,6 +76,8 @@ void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequenc /** IModuleInterface implementation */ void FAbilityFrameworkEditor::StartupModule() { + BlueprintEditorTabBinding = MakeShared(); + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); PropertyModule.RegisterCustomPropertyTypeLayout("GAAttribute", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAAttributeDetailCustomization::MakeInstance)); PropertyModule.RegisterCustomPropertyTypeLayout("GAEffectProperty", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); @@ -68,7 +89,10 @@ void FAbilityFrameworkEditor::StartupModule() PropertyModule.RegisterCustomClassLayout("AFAbilityActivationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); PropertyModule.RegisterCustomClassLayout("AFAbilityCooldownSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); - + PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodicInfiniteSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityInfinitePeriodSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityInfiniteDurationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityInfiniteDurationSpecDetails::MakeInstance)); + + PropertyModule.RegisterCustomClassLayout("GAEffectCue", FOnGetDetailCustomizationInstance::CreateStatic(&FAFEffectCueDetails::MakeInstance)); IAssetTools& AssetTools = FModuleManager::LoadModuleChecked("AssetTools").Get(); TSharedRef GABAction = MakeShareable(new FAssetTypeActions_GAEffectBlueprint()); @@ -92,11 +116,14 @@ void FAbilityFrameworkEditor::StartupModule() } void FAbilityFrameworkEditor::ShutdownModule() { + BlueprintEditorTabBinding = nullptr; FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); - //PropertyModule.UnregisterCustomClassLayout("GAGameEffectSpec"); + PropertyModule.UnregisterCustomClassLayout("AFEffectSpec"); PropertyModule.UnregisterCustomClassLayout("AFAbilityActivationSpec"); - //PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodSpec"); - //PropertyModule.UnregisterCustomClassLayout("AFAbilityCooldownSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityCooldownSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodicInfiniteSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityInfiniteDurationSpec"); PropertyModule.UnregisterCustomPropertyTypeLayout("GAAttribute"); PropertyModule.UnregisterCustomPropertyTypeLayout("GAEffectProperty"); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h index db82698..5a235e7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h @@ -10,34 +10,37 @@ #include "UnrealEd.h" #include "AssetToolsModule.h" #include "IAssetTypeActions.h" + +#include "BlueprintEditorModule.h" +#include "BlueprintEditorTabs.h" +#include "LayoutExtender.h" +#include "LevelEditor.h" +#include "MovieSceneToolsProjectSettings.h" +#include "PropertyEditorModule.h" +#include "Styling/SlateStyle.h" +#include "WorkflowTabManager.h" +#include "Modules/ModuleManager.h" +#include "Widgets/Docking/SDockTab.h" + +#include "ISettingsModule.h" + #include "IAbilityFrameworkEditor.h" -class FEffectCueSequenceEditorTabBinding - : public TSharedFromThis +class FEffectCueequenceEditorTabBinding + : public TSharedFromThis { public: - FEffectCueSequenceEditorTabBinding() - { + FEffectCueequenceEditorTabBinding(); - } + void RegisterBlueprintEditorLayout(FLayoutExtender& Extender); - - ~FEffectCueSequenceEditorTabBinding() - { - /*FBlueprintEditorModule* BlueprintEditorModule = FModuleManager::GetModulePtr("Kismet"); - if (BlueprintEditorModule) - { - BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); - BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); - }*/ - } + void RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor); + ~FEffectCueequenceEditorTabBinding(); private: /** Delegate binding handle for FBlueprintEditorModule::OnRegisterTabsForEditor */ FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; - - FDelegateHandle LevelEditorTabSpawnerHandle, LevelEditorLayoutExtensionHandle; }; //add static list of registered custom derived effcts. Will be used to specify, from which classes //new effect blueprints can be created, and which classes are allowed to pick (if not specified @@ -45,9 +48,8 @@ class FEffectCueSequenceEditorTabBinding class FAbilityFrameworkEditor : public IAbilityFrameworkEditor { TArray< TSharedPtr > CreatedAssetTypeActions; - TSharedPtr BlueprintEditorTabBinding; + TSharedPtr BlueprintEditorTabBinding; FDelegateHandle OnInitializeSequenceHandle; - static TSet EffectClasses; void RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp index b1c35e9..4c50866 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp @@ -26,19 +26,7 @@ #define LOCTEXT_NAMESPACE "FGAEffectCueEditor" -FEffectCueSequenceEditorSummoner::FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor) - : FWorkflowTabFactory("EmbeddedEffectCueSequenceID", BlueprintEditor) - , WeakBlueprintEditor(BlueprintEditor) -{ - bIsSingleton = true; - - TabLabel = LOCTEXT("SequencerTabName", "Cue Sequencer"); -} -TSharedRef FEffectCueSequenceEditorSummoner::CreateTabBody(const FWorkflowTabSpawnInfo& Info) const -{ - return SNew(SBox); -} //TSharedRef FEffectCueSequenceEditorSummoner::SpawnTab(const FWorkflowTabSpawnInfo& Info) const //{ // TSharedRef Tab = FWorkflowTabFactory::SpawnTab(Info); @@ -64,97 +52,19 @@ FGAEffectCueEditor::FGAEffectCueEditor() void FGAEffectCueEditor::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) { - Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); + //Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); } void FGAEffectCueEditor::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) { - TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); + //TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); } TArray FGAEffectCueEditor::GetAnimationEventContexts() const { TArray EventContexts; return EventContexts; } -void FGAEffectCueEditor::SetSequencer(UGAEffectCueSequence* NewSequence) -{ - if (UGAEffectCueSequence* OldSequence = EditedSequence.Get()) - { - if (OnSequenceChangedHandle.IsValid()) - { - OldSequence->OnSignatureChanged().Remove(OnSequenceChangedHandle); - } - } - - EditedSequence = NewSequence; - - if (NewSequence) - { - OnSequenceChangedHandle = NewSequence->OnSignatureChanged().AddSP(this, &FGAEffectCueEditor::OnSequenceChanged); - } - - // If we already have a sequencer open, just assign the sequence - if (Sequencer.IsValid() && NewSequence) - { - if (Sequencer->GetRootMovieSceneSequence() != NewSequence) - { - Sequencer->ResetToNewRootSequence(*NewSequence); - } - return; - } - - // If we're setting the sequence to none, destroy sequencer - if (!NewSequence) - { - return; - } - // We need to initialize a new sequencer instance - FSequencerInitParams SequencerInitParams; - { - TWeakObjectPtr LocalWeakSequence = NewSequence; - SequencerInitParams.RootSequence = NewSequence; - auto GetPlaybackContext = - [LocalWeakSequence]() -> UObject* - { - UGAEffectCueSequence* LocalActorSequence = LocalWeakSequence.Get(); - if (LocalActorSequence) - { - if (AGAEffectCue* Actor = LocalActorSequence->GetTypedOuter()) - { - return Actor; - } - } - return nullptr; - }; - - - SequencerInitParams.EventContexts = TAttribute>::Create(TAttribute>::FGetter::CreateLambda( - [GetPlaybackContext] { - TArray Contexts; - if (auto* Context = GetPlaybackContext()) - { - Contexts.Add(Context); - } - return Contexts; - } - )); - SequencerInitParams.PlaybackContext = TAttribute::Create(TAttribute::FGetter::CreateLambda(GetPlaybackContext)); - - SequencerInitParams.ViewParams.bReadOnly = false; // !WeakBlueprintEditor.IsValid() && !NewSequence->IsEditable(); - SequencerInitParams.bEditWithinLevelEditor = false; - SequencerInitParams.ViewParams.UniqueName = "EffectCueSequenceEditor"; - //SequencerInitParams.ViewParams.OnReceivedFocus.BindRaw(this, &SActorSequenceEditorWidgetImpl::OnSequencerReceivedFocus); - } - - Sequencer = FModuleManager::LoadModuleChecked("Sequencer").CreateSequencer(SequencerInitParams); - //FLevelEditorSequencerIntegrationOptions Options; - //Options.bRequiresLevelEvents = true; - //Options.bRequiresActorEvents = false; - //Options.bCanRecord = false; - - Sequencer->SetViewRange(TRange(0, 5)); -} void FGAEffectCueEditor::OnSequenceChanged() { UBlueprint* Blueprint = GetBlueprintObj(); @@ -180,12 +90,6 @@ FGAEffectCueEditor::~FGAEffectCueEditor() BlueprintEditorTabSpawnerHandle.Reset(); BlueprintEditorLayoutExtensionHandle.Reset(); TabManager.Pin()->UnregisterTabSpawner(FName("EmbeddedEffectCueSequenceID")); - if (Sequencer.IsValid()) - { - Sequencer->OnMovieSceneDataChanged().RemoveAll(this); - Sequencer->Close(); - Sequencer.Reset(); - } // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor } @@ -210,16 +114,7 @@ void FGAEffectCueEditor::InitEffectCueEditor(const EToolkitMode::Type Mode, cons UBlueprint* BP = InBlueprints[0]; EditedCue = BP->GeneratedClass->GetDefaultObject(); CueClass = BP->GeneratedClass; - UObjectPropertyBase* Prop = FindField(CueClass, TEXT("Sequence")); - //Cast( - UObject* Anim = Prop->GetObjectPropertyValue_InContainer(CueClass); - bool test2 = Prop->ContainsInstancedObjectProperty(); - SetSequencer(EditedCue->Sequence); - //TabManager.Pin()->InvokeTab(FName("EmbeddedEffectCueSequenceID"))->SetContent(Sequencer->GetSequencerWidget()); - - TabManager.Pin()->InvokeTab(FName("EmbeddedEffectCueSequenceID"))->SetContent(Sequencer->GetSequencerWidget()); - //TabLayout = GetDefaltEditorLayout(InBlueprintEditor); for (auto Blueprint : InBlueprints) { EnsureAbilityBlueprintIsUpToDate(Blueprint); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h index 45ad3e6..9094f6b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h @@ -16,20 +16,9 @@ class UGAEffectCueSequence; /** * Gameplay abilities asset editor (extends Blueprint editor) */ -struct FEffectCueSequenceEditorSummoner - : public FWorkflowTabFactory -{ - FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor); - virtual TSharedRef CreateTabBody(const FWorkflowTabSpawnInfo& Info) const override; - /*virtual TSharedRef SpawnTab(const FWorkflowTabSpawnInfo& Info) const override;*/ -protected: - TWeakPtr WeakBlueprintEditor; -}; class FGAEffectCueEditor : public FBlueprintEditor { - TSharedPtr Sequencer; - void SetSequencer(UGAEffectCueSequence* NewSequence); TWeakPtr TabManager; FDelegateHandle OnSequenceChangedHandle; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h deleted file mode 100644 index f4402fa..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IGameAttributesEditor.h +++ /dev/null @@ -1,39 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "Developer/AssetTools/Public/AssetToolsModule.h" -#include "IAssetTypeActions.h" -#include "ModuleManager.h" - - -/** - * The public interface to this module. In most cases, this interface is only public to sibling modules - * within this plugin. - */ -class IGameAttributesEditor : public IModuleInterface -{ - TArray< TSharedPtr > CreatedAssetTypeActions; -public: - - /** - * Singleton-like access to this module's interface. This is just for convenience! - * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. - * - * @return Returns singleton instance, loading the module on demand if needed - */ - static inline IGameAttributesEditor& Get() - { - return FModuleManager::LoadModuleChecked< IGameAttributesEditor >("GameAttributesEditor"); - } - - /** - * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. - * - * @return True if the module is loaded and ready to use - */ - static inline bool IsAvailable() - { - return FModuleManager::Get().IsModuleLoaded( "GameAttributesEditor" ); - } -}; - diff --git a/Source/ActionRPGGame/AI/ARAICharacter.cpp b/Source/ActionRPGGame/AI/ARAICharacter.cpp new file mode 100644 index 0000000..3825c9a --- /dev/null +++ b/Source/ActionRPGGame/AI/ARAICharacter.cpp @@ -0,0 +1,83 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAICharacter.h" + + +// Sets default values +AARAICharacter::AARAICharacter() +{ + // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + Abilities = CreateDefaultSubobject(TEXT("Abilities")); +} + +// Called when the game starts or when spawned +void AARAICharacter::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AARAICharacter::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + +// Called to bind functionality to input +void AARAICharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) +{ + Super::SetupPlayerInputComponent(PlayerInputComponent); + +} + +/* IAFAbilityInterface- BEGIN */ + +class UGAAttributesBase* AARAICharacter::GetAttributes() +{ + return GetAbilityComp()->DefaultAttributes; +} + +class UAFAbilityComponent* AARAICharacter::GetAbilityComp() +{ + return Abilities; +}; + +float AARAICharacter::GetAttributeValue(FGAAttribute AttributeIn) const +{ + return Abilities->GetAttributeValue(AttributeIn); +} + +void AARAICharacter::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) +{ + Abilities->ModifyAttribute(ModIn, HandleIn, InProperty); +} + +FAFAttributeBase* AARAICharacter::GetAttribute(FGAAttribute AttributeIn) +{ + return Abilities->GetAttribute(AttributeIn); +}; + +void AARAICharacter::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) +{ + Abilities->RemoveBonus(AttributeIn, HandleIn, InMod); +} + +float AARAICharacter::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return Abilities->NativeGetAttributeValue(AttributeIn); +} + +FGAEffectHandle AARAICharacter::ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) +{ + return Abilities->ApplyEffectToTarget(EffectIn, InProperty, InContext); +} + +void AARAICharacter::RemoveTagContainer(const FGameplayTagContainer& TagsIn) +{ + Abilities->RemoveTagContainer(TagsIn); +} +/* IAFAbilityInterface- END */ \ No newline at end of file diff --git a/Source/ActionRPGGame/AI/ARAICharacter.h b/Source/ActionRPGGame/AI/ARAICharacter.h new file mode 100644 index 0000000..00b0c07 --- /dev/null +++ b/Source/ActionRPGGame/AI/ARAICharacter.h @@ -0,0 +1,58 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Character.h" +#include "GameplayTags.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" + +#include "ARAICharacter.generated.h" + +UCLASS() +class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInterface +{ + GENERATED_BODY() +protected: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class UAFAbilityComponent* Abilities; +public: + // Sets default values for this character's properties + AARAICharacter(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + // Called to bind functionality to input + virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; + + + /* IAFAbilityInterface- BEGIN */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UGAAttributesBase* GetAttributes() override; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UAFAbilityComponent* GetAbilityComp() override; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; + + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) override; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; + + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; + + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; + + /* IAFAbilityInterface- END */ +}; diff --git a/Source/ActionRPGGame/AI/ARAIController.cpp b/Source/ActionRPGGame/AI/ARAIController.cpp new file mode 100644 index 0000000..62c59a4 --- /dev/null +++ b/Source/ActionRPGGame/AI/ARAIController.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAIController.h" + + + + diff --git a/Source/ActionRPGGame/AI/ARAIController.h b/Source/ActionRPGGame/AI/ARAIController.h new file mode 100644 index 0000000..44c9882 --- /dev/null +++ b/Source/ActionRPGGame/AI/ARAIController.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AIController.h" +#include "ARAIController.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARAIController : public AAIController +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/ActionRPGGameCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp similarity index 65% rename from Source/ActionRPGGame/ActionRPGGameCharacter.cpp rename to Source/ActionRPGGame/ARCharacter.cpp index d82ab6f..10664ed 100644 --- a/Source/ActionRPGGame/ActionRPGGameCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -1,7 +1,6 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "ActionRPGGameCharacter.h" -#include "HeadMountedDisplayFunctionLibrary.h" +#include "ARCharacter.h" #include "Camera/CameraComponent.h" #include "Components/CapsuleComponent.h" #include "Components/InputComponent.h" @@ -10,9 +9,9 @@ #include "GameFramework/SpringArmComponent.h" ////////////////////////////////////////////////////////////////////////// -// AActionRPGGameCharacter +// AARCharacter -AActionRPGGameCharacter::AActionRPGGameCharacter() +AARCharacter::AARCharacter() { // Set size for collision capsule GetCapsuleComponent()->InitCapsuleSize(42.f, 96.0f); @@ -43,6 +42,8 @@ AActionRPGGameCharacter::AActionRPGGameCharacter() FollowCamera->SetupAttachment(CameraBoom, USpringArmComponent::SocketName); // Attach the camera to the end of the boom and let the boom adjust to match the controller orientation FollowCamera->bUsePawnControlRotation = false; // Camera does not rotate relative to arm + Abilities = CreateDefaultSubobject(TEXT("Abilities")); + // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) } @@ -50,61 +51,40 @@ AActionRPGGameCharacter::AActionRPGGameCharacter() ////////////////////////////////////////////////////////////////////////// // Input -void AActionRPGGameCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) +void AARCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) { // Set up gameplay key bindings check(PlayerInputComponent); PlayerInputComponent->BindAction("Jump", IE_Pressed, this, &ACharacter::Jump); PlayerInputComponent->BindAction("Jump", IE_Released, this, &ACharacter::StopJumping); - PlayerInputComponent->BindAxis("MoveForward", this, &AActionRPGGameCharacter::MoveForward); - PlayerInputComponent->BindAxis("MoveRight", this, &AActionRPGGameCharacter::MoveRight); + PlayerInputComponent->BindAxis("MoveForward", this, &AARCharacter::MoveForward); + PlayerInputComponent->BindAxis("MoveRight", this, &AARCharacter::MoveRight); // We have 2 versions of the rotation bindings to handle different kinds of devices differently // "turn" handles devices that provide an absolute delta, such as a mouse. // "turnrate" is for devices that we choose to treat as a rate of change, such as an analog joystick PlayerInputComponent->BindAxis("Turn", this, &APawn::AddControllerYawInput); - PlayerInputComponent->BindAxis("TurnRate", this, &AActionRPGGameCharacter::TurnAtRate); + PlayerInputComponent->BindAxis("TurnRate", this, &AARCharacter::TurnAtRate); PlayerInputComponent->BindAxis("LookUp", this, &APawn::AddControllerPitchInput); - PlayerInputComponent->BindAxis("LookUpRate", this, &AActionRPGGameCharacter::LookUpAtRate); - - // handle touch devices - PlayerInputComponent->BindTouch(IE_Pressed, this, &AActionRPGGameCharacter::TouchStarted); - PlayerInputComponent->BindTouch(IE_Released, this, &AActionRPGGameCharacter::TouchStopped); + PlayerInputComponent->BindAxis("LookUpRate", this, &AARCharacter::LookUpAtRate); - // VR headset functionality - PlayerInputComponent->BindAction("ResetVR", IE_Pressed, this, &AActionRPGGameCharacter::OnResetVR); -} - -void AActionRPGGameCharacter::OnResetVR() -{ - UHeadMountedDisplayFunctionLibrary::ResetOrientationAndPosition(); } -void AActionRPGGameCharacter::TouchStarted(ETouchIndex::Type FingerIndex, FVector Location) -{ - Jump(); -} - -void AActionRPGGameCharacter::TouchStopped(ETouchIndex::Type FingerIndex, FVector Location) -{ - StopJumping(); -} - -void AActionRPGGameCharacter::TurnAtRate(float Rate) +void AARCharacter::TurnAtRate(float Rate) { // calculate delta for this frame from the rate information AddControllerYawInput(Rate * BaseTurnRate * GetWorld()->GetDeltaSeconds()); } -void AActionRPGGameCharacter::LookUpAtRate(float Rate) +void AARCharacter::LookUpAtRate(float Rate) { // calculate delta for this frame from the rate information AddControllerPitchInput(Rate * BaseLookUpRate * GetWorld()->GetDeltaSeconds()); } -void AActionRPGGameCharacter::MoveForward(float Value) +void AARCharacter::MoveForward(float Value) { if ((Controller != NULL) && (Value != 0.0f)) { @@ -118,7 +98,7 @@ void AActionRPGGameCharacter::MoveForward(float Value) } } -void AActionRPGGameCharacter::MoveRight(float Value) +void AARCharacter::MoveRight(float Value) { if ( (Controller != NULL) && (Value != 0.0f) ) { @@ -132,3 +112,52 @@ void AActionRPGGameCharacter::MoveRight(float Value) AddMovementInput(Direction, Value); } } +/* IAFAbilityInterface- BEGIN */ + +class UGAAttributesBase* AARCharacter::GetAttributes() +{ + return GetAbilityComp()->DefaultAttributes; +} + +class UAFAbilityComponent* AARCharacter::GetAbilityComp() +{ + return Abilities; +}; + +float AARCharacter::GetAttributeValue(FGAAttribute AttributeIn) const +{ + return Abilities->GetAttributeValue(AttributeIn); +} + +void AARCharacter::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) +{ + Abilities->ModifyAttribute(ModIn, HandleIn, InProperty); +} + +FAFAttributeBase* AARCharacter::GetAttribute(FGAAttribute AttributeIn) +{ + return Abilities->GetAttribute(AttributeIn); +}; + +void AARCharacter::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) +{ + Abilities->RemoveBonus(AttributeIn, HandleIn, InMod); +} + +float AARCharacter::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return Abilities->NativeGetAttributeValue(AttributeIn); +} + +FGAEffectHandle AARCharacter::ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) +{ + return Abilities->ApplyEffectToTarget(EffectIn, InProperty, InContext); +} + +void AARCharacter::RemoveTagContainer(const FGameplayTagContainer& TagsIn) +{ + Abilities->RemoveTagContainer(TagsIn); +} +/* IAFAbilityInterface- END */ \ No newline at end of file diff --git a/Source/ActionRPGGame/ActionRPGGameCharacter.h b/Source/ActionRPGGame/ARCharacter.h similarity index 55% rename from Source/ActionRPGGame/ActionRPGGameCharacter.h rename to Source/ActionRPGGame/ARCharacter.h index 767000c..22d99f9 100644 --- a/Source/ActionRPGGame/ActionRPGGameCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -4,10 +4,13 @@ #include "CoreMinimal.h" #include "GameFramework/Character.h" -#include "ActionRPGGameCharacter.generated.h" +#include "GameplayTags.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" +#include "ARCharacter.generated.h" UCLASS(config=Game) -class AActionRPGGameCharacter : public ACharacter +class AARCharacter : public ACharacter, public IAFAbilityInterface { GENERATED_BODY() @@ -18,8 +21,11 @@ class AActionRPGGameCharacter : public ACharacter /** Follow camera */ UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UCameraComponent* FollowCamera; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class UAFAbilityComponent* Abilities; public: - AActionRPGGameCharacter(); + AARCharacter(); /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) @@ -31,9 +37,6 @@ class AActionRPGGameCharacter : public ACharacter protected: - /** Resets HMD orientation in VR. */ - void OnResetVR(); - /** Called for forwards/backward input */ void MoveForward(float Value); @@ -52,12 +55,6 @@ class AActionRPGGameCharacter : public ACharacter */ void LookUpAtRate(float Rate); - /** Handler for when a touch input begins. */ - void TouchStarted(ETouchIndex::Type FingerIndex, FVector Location); - - /** Handler for when a touch input stops. */ - void TouchStopped(ETouchIndex::Type FingerIndex, FVector Location); - protected: // APawn interface virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; @@ -68,5 +65,28 @@ class AActionRPGGameCharacter : public ACharacter FORCEINLINE class USpringArmComponent* GetCameraBoom() const { return CameraBoom; } /** Returns FollowCamera subobject **/ FORCEINLINE class UCameraComponent* GetFollowCamera() const { return FollowCamera; } + + /* IAFAbilityInterface- BEGIN */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UGAAttributesBase* GetAttributes() override; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UAFAbilityComponent* GetAbilityComp() override; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; + + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) override; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; + + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; + + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; + + /* IAFAbilityInterface- END */ }; diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp new file mode 100644 index 0000000..848e465 --- /dev/null +++ b/Source/ActionRPGGame/ARGameMode.cpp @@ -0,0 +1,8 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "ARGameMode.h" +#include "UObject/ConstructorHelpers.h" + +AARGameMode::AARGameMode() +{ +} diff --git a/Source/ActionRPGGame/ActionRPGGameGameMode.h b/Source/ActionRPGGame/ARGameMode.h similarity index 61% rename from Source/ActionRPGGame/ActionRPGGameGameMode.h rename to Source/ActionRPGGame/ARGameMode.h index fb828e8..46e5fe9 100644 --- a/Source/ActionRPGGame/ActionRPGGameGameMode.h +++ b/Source/ActionRPGGame/ARGameMode.h @@ -4,15 +4,15 @@ #include "CoreMinimal.h" #include "GameFramework/GameModeBase.h" -#include "ActionRPGGameGameMode.generated.h" +#include "ARGameMode.generated.h" UCLASS(minimalapi) -class AActionRPGGameGameMode : public AGameModeBase +class AARGameMode : public AGameModeBase { GENERATED_BODY() public: - AActionRPGGameGameMode(); + AARGameMode(); }; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 384db7a..4eb6d60 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -7,7 +7,28 @@ public class ActionRPGGame : ModuleRules public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; + PublicIncludePaths.AddRange( + new string[] { + "AbilityFramework", + "AbilityFramework/Abilities", + "AbilityFramework/Attributes", + "AbilityFramework/Effects", + "AbilityFramework/Public" + // ... add public include paths required here ... + } + ); - PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", "HeadMountedDisplay" }); + PrivateIncludePaths.AddRange( + new string[] { + "AbilityFramework", + "AbilityFramework/Abilities", + "AbilityFramework/Attributes", + "AbilityFramework/Effects", + "AbilityFramework/Private", + // ... add other private include paths required here ... + } + ); + PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", + "GameplayTags", "AbilityFramework" }); } } diff --git a/Source/ActionRPGGame/ActionRPGGameGameMode.cpp b/Source/ActionRPGGame/ActionRPGGameGameMode.cpp deleted file mode 100644 index c5fa84c..0000000 --- a/Source/ActionRPGGame/ActionRPGGameGameMode.cpp +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "ActionRPGGameGameMode.h" -#include "ActionRPGGameCharacter.h" -#include "UObject/ConstructorHelpers.h" - -AActionRPGGameGameMode::AActionRPGGameGameMode() -{ - // set default pawn class to our Blueprinted character - static ConstructorHelpers::FClassFinder PlayerPawnBPClass(TEXT("/Game/ThirdPersonCPP/Blueprints/ThirdPersonCharacter")); - if (PlayerPawnBPClass.Class != NULL) - { - DefaultPawnClass = PlayerPawnBPClass.Class; - } -} diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp new file mode 100644 index 0000000..11a7f6b --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp @@ -0,0 +1,17 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARCharacterAttributes.h" +#include "Net/UnrealNetwork.h" + + + +void UARCharacterAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + DOREPLIFETIME(UARCharacterAttributes, Health); + DOREPLIFETIME(UARCharacterAttributes, Shield); + DOREPLIFETIME(UARCharacterAttributes, Armor); + DOREPLIFETIME(UARCharacterAttributes, Energy); + DOREPLIFETIME(UARCharacterAttributes, Stamina); + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h new file mode 100644 index 0000000..7465bae --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Attributes/GAAttributesBase.h" +#include "ARCharacterAttributes.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase +{ + GENERATED_BODY() + +public: + UPROPERTY(EditAnywhere, Replicated, Category = "Base") + FAFAttributeBase Health; + UPROPERTY(EditAnywhere, Replicated, Category = "Base") + FAFAttributeBase Shield; + UPROPERTY(EditAnywhere, Replicated, Category = "Base") + FAFAttributeBase Armor; + UPROPERTY(EditAnywhere, Replicated, Category = "Base") + FAFAttributeBase Energy; + UPROPERTY(EditAnywhere, Replicated, Category = "Base") + FAFAttributeBase Stamina; + + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Ammo; + +}; diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp new file mode 100644 index 0000000..849ac3b --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARGunAttributes.h" + + + + diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Attributes/ARGunAttributes.h new file mode 100644 index 0000000..85d84fc --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Attributes/GAAttributesBase.h" +#include "ARGunAttributes.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Attributes/ARHealthExtension.cpp b/Source/ActionRPGGame/Attributes/ARHealthExtension.cpp new file mode 100644 index 0000000..f6284d1 --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARHealthExtension.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHealthExtension.h" + + + + diff --git a/Source/ActionRPGGame/Attributes/ARHealthExtension.h b/Source/ActionRPGGame/Attributes/ARHealthExtension.h new file mode 100644 index 0000000..ab8f2d5 --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARHealthExtension.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Attributes/GAAttributeExtension.h" +#include "ARHealthExtension.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHealthExtension : public UGAAttributeExtension +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGameServer.Target.cs b/Source/ActionRPGGameServer.Target.cs new file mode 100644 index 0000000..e951c77 --- /dev/null +++ b/Source/ActionRPGGameServer.Target.cs @@ -0,0 +1,14 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; +using System.Collections.Generic; + +[SupportedPlatforms(UnrealPlatformClass.Server)] +public class ActionRPGGameServerTarget : TargetRules +{ + public ActionRPGGameServerTarget(TargetInfo Target) : base(Target) + { + Type = TargetType.Server; + ExtraModuleNames.Add("ActionRPGGame"); + } +} From 2360762012981b15e58be3e6f006f8f46d2a9e5d Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 5 Jul 2017 00:58:52 +0200 Subject: [PATCH 006/187] fixed crash on ability activation --- Config/DefaultGameplayTags.ini | 4 ++++ Config/DefaultInput.ini | 10 +++------- .../AbilityFramework/Effects/GAGameEffect.cpp | 1 + .../Attributes/ARAbilityAttributes.cpp | 7 +++++++ .../Attributes/ARAbilityAttributes.h | 20 +++++++++++++++++++ 5 files changed, 35 insertions(+), 7 deletions(-) create mode 100644 Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp create mode 100644 Source/ActionRPGGame/Attributes/ARAbilityAttributes.h diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 5f755a8..fcfe2ea 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -5,14 +5,18 @@ WarnOnInvalidTags=True FastReplication=False NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 +-GameplayTagList=(Tag="Ability.Corruption",DevComment="") -GameplayTagList=(Tag="Ability.Rifle",DevComment="") +-GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") -GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") -GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") ++GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Rifle",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") ++GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 1a6997d..d7aad39 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -1,11 +1,5 @@ [/Script/Engine.InputSettings] --AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) --AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) --AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) --AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) --AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) --AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) -AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) @@ -61,10 +55,12 @@ bDefaultViewportMouseLock=False DefaultViewportMouseLockMode=LockOnCapture -ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="NewActionMapping_0",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="Input.Ability01.Activate",Key=None,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) -AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) -AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 20fbb24..17dde99 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -326,6 +326,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr if (InProperty.Application->ApplyEffect(InProperty.Handle, EffectIn, InProperty, this, InContext)) { + Handle = InProperty.Handle; InProperty.Application->ExecuteEffect(InProperty.Handle, InProperty, InContext, Modifier); // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); } diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp new file mode 100644 index 0000000..7feff36 --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityAttributes.h" + + + + diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h new file mode 100644 index 0000000..0abd6f3 --- /dev/null +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Attributes/GAAttributesBase.h" +#include "ARAbilityAttributes.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityAttributes : public UGAAttributesBase +{ + GENERATED_BODY() + + + + +}; From 23bbc7068842ea03ee06568d17e98993974fb702 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 6 Jul 2017 00:43:51 +0200 Subject: [PATCH 007/187] Adding ability helpers --- ActionRPGGame.uproject | 3 +- Config/DefaultGameplayTags.ini | 4 + .../Abilities/GAAbilityBase.cpp | 137 ++++++++++++------ .../Abilities/GAAbilityBase.h | 68 +++++---- .../AnimNotify/AFAnimNotifyBase.cpp | 18 --- .../AnimNotify/AFAnimNotifyBase.h | 25 ---- .../AbilityFramework/Effects/GAGameEffect.cpp | 36 +++-- .../AbilityFramework/Effects/GAGameEffect.h | 70 ++++++++- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 7 + Source/ActionRPGGame/UI/ARAbilityWidget.h | 20 +++ Source/ActionRPGGame/UI/ARUIComponent.cpp | 34 +++++ Source/ActionRPGGame/UI/ARUIComponent.h | 29 ++++ 12 files changed, 323 insertions(+), 128 deletions(-) delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h create mode 100644 Source/ActionRPGGame/UI/ARAbilityWidget.cpp create mode 100644 Source/ActionRPGGame/UI/ARAbilityWidget.h create mode 100644 Source/ActionRPGGame/UI/ARUIComponent.cpp create mode 100644 Source/ActionRPGGame/UI/ARUIComponent.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 52edb78..fc0cc87 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -11,7 +11,8 @@ "AdditionalDependencies": [ "AbilityFramework", "Engine", - "AIModule" + "AIModule", + "UMG" ] } ], diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index fcfe2ea..60b2925 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -10,12 +10,16 @@ NetIndexFirstBitSegment=16 -GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") -GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +-GameplayTagList=(Tag="Damage",DevComment="") +-GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") -GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") ++GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.Rifle",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") ++GameplayTagList=(Tag="Damage",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index b0966dd..8887ee1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -166,7 +166,7 @@ void UGAAbilityBase::OnActivationEffectPeriod(const FGAEffectHandle& InHandle) void UGAAbilityBase::FinishAbility() { UE_LOG(AbilityFramework, Log, TEXT("FinishExecution in ability %s"), *GetName()); - OnFinished(); + OnAbilityFinished(); NativeFinishAbility(); AbilityState = EAFAbilityState::Waiting; AbilityComponent->AppliedTags.RemoveTagContainer(ActivationAddedTags); @@ -218,6 +218,9 @@ bool UGAAbilityBase::ApplyCooldownEffect() { return false; } + FAFFunctionModifier Modifier; + CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, + this, POwner, this, Modifier); return false; } @@ -288,49 +291,6 @@ bool UGAAbilityBase::CanReleaseAbility() } return bCanUse; } -float UGAAbilityBase::GetCurrentActivationTime() const -{ - if (ActivationEffect.Handle.IsValid()) - { - return ActivationEffect.Handle.GetEffectPtr()->GetCurrentActivationTime(); - } - return 0; -} -float UGAAbilityBase::BP_GetCurrentActivationTime() const -{ - return GetCurrentActivationTime(); -} -float UGAAbilityBase::GetCurrentCooldownTime() const -{ - return 0; -} - -float UGAAbilityBase::GetPeriodTime() const -{ - //if(Activation) - return 0; -} -float UGAAbilityBase::BP_GetPeriodTime() const -{ - return GetPeriodTime(); -} - -float UGAAbilityBase::GetCooldownTime() const -{ - return GetWorld()->GetTimeSeconds() - LastCooldownTime; -} -float UGAAbilityBase::BP_GetCooldownTime() const -{ - return GetCooldownTime(); -} -float UGAAbilityBase::GetActivationTime() const -{ - return GetWorld()->GetTimeSeconds() - LastActivationTime; -} -float UGAAbilityBase::BP_GetActivationTime() const -{ - return GetActivationTime(); -} void UGAAbilityBase::OnGameplayTaskInitialized(UGameplayTask& Task) { @@ -421,6 +381,10 @@ bool UGAAbilityBase::IsOnCooldown() { bool bOnCooldown = false; bOnCooldown = AbilityComponent->IsEffectActive(CooldownEffectHandle); + if (bOnCooldown) + { + OnNotifyOnCooldown.Broadcast(); + } return bOnCooldown; //temp } bool UGAAbilityBase::IsActivating() @@ -563,4 +527,87 @@ bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float R { return false; } -/* Tracing Helpers End */ \ No newline at end of file +/* Tracing Helpers End */ + +//Helpers +float UGAAbilityBase::GetActivationRemainingTime() const +{ + return AbilityComponent->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationRemainingTimeNormalized() const +{ + return AbilityComponent->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationCurrentTime() const +{ + return AbilityComponent->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationCurrentTimeNormalized() const +{ + return AbilityComponent->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationEndTime() const +{ + return AbilityComponent->GameEffectContainer.GetEndTime(ActivationEffectHandle); +} + +float UGAAbilityBase::BP_GetActivationRemainingTime() +{ + return GetActivationRemainingTime(); +} +float UGAAbilityBase::BP_GetActivationRemainingTimeNormalized() +{ + return GetActivationRemainingTimeNormalized(); +} +float UGAAbilityBase::BP_GetActivationCurrentTime() +{ + return GetActivationCurrentTime(); +} +float UGAAbilityBase::BP_GetActivationCurrentTimeNormalized() +{ + return GetActivationCurrentTimeNormalized(); +} +float UGAAbilityBase::BP_GetActivationEndTime() +{ + return GetActivationEndTime(); +} +float UGAAbilityBase::GetCooldownRemainingTime() const +{ + return AbilityComponent->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const +{ + return AbilityComponent->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownCurrentTime() const +{ + return AbilityComponent->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const +{ + return AbilityComponent->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownEndTime() const +{ + return AbilityComponent->GameEffectContainer.GetEndTime(CooldownEffectHandle); +} +float UGAAbilityBase::BP_GetCooldownRemainingTime() +{ + return GetCooldownRemainingTime(); +} +float UGAAbilityBase::BP_GetCooldownRemainingTimeNormalized() +{ + return GetCooldownRemainingTimeNormalized(); +} +float UGAAbilityBase::BP_GetCooldownCurrentTime() +{ + return GetCooldownCurrentTime(); +} +float UGAAbilityBase::BP_GetCooldownCurrentTimeNormalized() +{ + return GetCooldownCurrentTimeNormalized(); +} +float UGAAbilityBase::BP_GetCooldownEndTime() +{ + return GetCooldownEndTime(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 801cd32..206a32f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -255,6 +255,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask FGASGenericAbilityDelegate OnActivateBeginDelegate; UPROPERTY(BlueprintAssignable) FGASGenericAbilityDelegate OnActivationFinishedDelegate; + + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnNotifyOnCooldown; protected: EAFAbilityState AbilityState; @@ -290,8 +293,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void NativeOnAbilityConfirmed(); /* - Called when ability get message to activate. - For player it usually means on button press. + Called when StartActivation is triggered. */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnActivate(); @@ -303,12 +305,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnActivationFinished(); - /* - Called when ability deactivates. - For player it usually means in input release. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnDeactivate(); /* In blueprint, call this function to trigger event of the same name, after ability is ready to be executed (like after targeting is done, input is confirmed, @@ -336,7 +332,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask /* Event called when ability finishes it's execution. Called AFTER OnAbilityExecuted. */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnFinished(); + void OnAbilityFinished(); UFUNCTION() void OnCooldownEffectExpired(); @@ -363,23 +359,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask bool CanUseAbility(); bool CanReleaseAbility(); - - float GetCurrentActivationTime() const; - UFUNCTION(BlueprintPure, meta = (DisplayName = "Get Current Activation Time"), Category = "AbilityFramework|Abilities") - float BP_GetCurrentActivationTime() const; - float GetCurrentCooldownTime() const; - - float GetPeriodTime() const; - UFUNCTION(BlueprintPure, meta = (DisplayName = "Get Period Time"), Category = "AbilityFramework|Abilities") - float BP_GetPeriodTime() const; - - float GetCooldownTime() const; - UFUNCTION(BlueprintPure, meta=(DisplayName = "Get Cooldown Time"), Category = "AbilityFramework|Abilities") - float BP_GetCooldownTime() const; - - float GetActivationTime() const; - UFUNCTION(BlueprintPure, meta = (DisplayName = "Get Activation Time"), Category = "AbilityFramework|Abilities") - float BP_GetActivationTime() const; /** GameplayTaskOwnerInterface - Begin */ virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; @@ -488,4 +467,41 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask bool LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); /* Tracing Helpers End */ + + + //Helpers + float GetActivationRemainingTime() const; + float GetActivationRemainingTimeNormalized() const; + float GetActivationCurrentTime() const; + float GetActivationCurrentTimeNormalized() const; + float GetActivationEndTime() const; + + UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationRemainingTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationCurrentTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationEndTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationEndTime(); + + + float GetCooldownRemainingTime() const; + float GetCooldownRemainingTimeNormalized() const; + float GetCooldownCurrentTime() const; + float GetCooldownCurrentTimeNormalized() const; + float GetCooldownEndTime() const; + + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownRemainingTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownCurrentTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownEndTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownEndTime(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp deleted file mode 100644 index bd90bba..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.cpp +++ /dev/null @@ -1,18 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.h" -#include "AFAnimNotifyBase.h" - - - - -void UAFAnimNotifyBase::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) -{ - IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); - if (!IAbilities) - return; - - UAFAbilityComponent* Comp = IAbilities->GetAbilityComp(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h deleted file mode 100644 index e6172d5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotifyBase.h +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Animation/AnimNotifies/AnimNotify.h" -#include "GAGlobals.h" -#include "AFAnimNotifyBase.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFAnimNotifyBase : public UAnimNotify -{ - GENERATED_BODY() - - virtual void Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) override; - - UPROPERTY(EditAnywhere) - FAFAbilityNotifyData Data; - UPROPERTY(EditAnywhere) - FGameplayTag Tag; - UPROPERTY(EditAnywhere) - FName Name; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 17dde99..914d837 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -343,6 +343,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); } } + } else { @@ -351,14 +352,15 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr EffectIn, InProperty, this, InContext)) { InProperty.Application->ExecuteEffect(Handle, InProperty, InContext, Modifier); + ApplyReplicationInfo(Handle, InProperty); // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); } + } } EffectIn->OnApplied(); return Handle; - //ApplyReplicationInfo(HandleIn); //apply additonal effect applied with this effect. //for (TSubclassOf Spec : EffectIn.GameEffect->OnAppliedEffects) //{ @@ -367,18 +369,24 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr // EffectIn.Context.InstigatorComp->ApplyEffectToTarget(Handle.GetEffect(), Handle, InProperty); //} } - -void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& HandleIn) +void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) { - //TSharedPtr EffectPtr = HandleIn.GetEffectPtr(); - //UGAGameEffectSpec* EffectSpec = HandleIn.GetEffectSpec(); //if (EffectPtr.IsValid() && EffectSpec && EffectSpec->EffectCue) - //{ - // FGAEffectRepInfo RepInfo(0, EffectSpec->Period, EffectSpec->Duration, 0); - //// RepInfo.EffectCueClass = EffectSpec->EffectCue; - // MarkItemDirty(RepInfo); - //} + { + const UWorld* World = OwningComponent->GetWorld(); + FAFEffectRepInfo RepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0); + RepInfo.Handle = InHandle; + MarkItemDirty(RepInfo); + ActiveEffectInfos.Add(RepInfo); + MarkArrayDirty(); + ENetMode mode = OwningComponent->GetNetMode(); + if (mode == ENetMode::NM_Standalone) + { + EffectInfos.Add(InHandle, new FAFEffectRepInfo(RepInfo)); + } + } } + EGAEffectAggregation FGAEffectContainer::GetEffectAggregation(const FGAEffectHandle& HandleIn) const { UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); @@ -609,7 +617,9 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N UGAGameEffectSpec* Spec = HandleIn.Spec; EGAEffectAggregation Aggregation = Spec->EffectAggregation; TArray* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); + FAFEffectRepInfo* Out; + if (handles) { for (int32 idx = 0; idx < Num; idx++) @@ -619,6 +629,12 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N FGAEffectHandle OutHandle = (*handles)[0]; if (OutHandle.IsValid()) { + EffectInfos.RemoveAndCopyValue(OutHandle, Out); + if (Out) + { + ActiveEffectInfos.Remove(*Out); + delete Out; + } if (!ActiveEffectHandles.Contains(OutHandle)) { UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffectRef().ToString()); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 625b291..0b7150a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -613,7 +613,32 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); - + float GetRemainingTime(float InWorldTime) const + { + return Duration - (InWorldTime - AppliedTime); + } + float GetRemainingTimeNormalized(float InWorldTime) const + { + float Time = Duration - (InWorldTime - AppliedTime); + //1,0 ? + float Normalized = FMath::GetMappedRangeValueClamped(FVector2D(Duration, 0), FVector2D(1, 0), Time); + return Normalized; + } + /* Get Current effect ime clamped to max duration */ + float GetCurrentTime(float InWorldTime) const + { + return FMath::Clamp(InWorldTime - AppliedTime, 0, Duration); + } + float GetCurrentTimeNormalized(float InWorldTime) const + { + float Time = FMath::Clamp(InWorldTime - AppliedTime, 0, Duration); + float Normalized = FMath::GetMappedRangeValueClamped(FVector2D(0, Duration), FVector2D(0, 1), Time); + return Normalized; + } + float GetEndTime() const + { + return AppliedTime + Duration; + } FAFEffectRepInfo() {}; @@ -662,6 +687,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer //IDK might be actually easier to map Handles to active effects on clients //as Handle should be synced between client and server. //that's why handle should only be created on server (and by that, effects). + //change to SharedPtr ? mutable TMap EffectInfos; @@ -706,12 +732,12 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer FGAEffectHandle ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty , const FGAEffectContext& InContext , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + void ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ void RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); - /* Remove given number of effects of the same type */ - void ApplyReplicationInfo(const FGAEffectHandle& HandleIn); + inline int32 GetEffectsNum() const { return ActiveEffectHandles.Num(); }; EGAEffectAggregation GetEffectAggregation(const FGAEffectHandle& HandleIn) const; @@ -741,6 +767,44 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer } UWorld* GetWorld() const; + ///Helpers + float GetRemainingTime(const FGAEffectHandle& InHandle) const + { + FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); + if (!Info) + return 0; + //lets assume value is always valid... + return Info->GetRemainingTime(GetWorld()->GetTimeSeconds()); + } + float GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const + { + FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); + if (!Info) + return 0; + return Info->GetRemainingTimeNormalized(GetWorld()->GetTimeSeconds()); + } + /* Get Current effect ime clamped to max duration */ + float GetCurrentTime(const FGAEffectHandle& InHandle) const + { + FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); + if (!Info) + return 0; + return Info->GetCurrentTime(GetWorld()->GetTimeSeconds()); + } + float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const + { + FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); + if (!Info) + return 0; + return Info->GetCurrentTimeNormalized(GetWorld()->GetTimeSeconds()); + } + float GetEndTime(const FGAEffectHandle& InHandle) const + { + FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); + if (!Info) + return 0; + return Info->GetEndTime(); + } }; template<> struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp new file mode 100644 index 0000000..3990916 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityWidget.h" + + + + diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h new file mode 100644 index 0000000..2249ff8 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARAbilityWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityWidget : public UUserWidget +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp new file mode 100644 index 0000000..8c73f7a --- /dev/null +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARUIComponent.h" + + +// Sets default values for this component's properties +UARUIComponent::UARUIComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UARUIComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UARUIComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h new file mode 100644 index 0000000..dd25671 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "ARUIComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARUIComponent : public UActorComponent +{ + GENERATED_BODY() + +public: + // Sets default values for this component's properties + UARUIComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + +}; From 314258b69cfa8e7f97cf87cc55dc660e16986408 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 16 Jul 2017 03:06:08 +0200 Subject: [PATCH 008/187] Working on UI --- ActionRPGGame.uproject | 3 +- Config/DefaultGame.ini | 10 + Config/DefaultGameplayTags.ini | 6 + Config/DefaultInput.ini | 36 ++- .../Abilities/AFBlueprintFunctionLibrary.cpp | 4 +- .../Abilities/GAAbilityBase.cpp | 75 +++++- .../Abilities/GAAbilityBase.h | 24 ++ .../Attributes/GAAttributeBase.h | 4 +- .../Attributes/GAAttributesBase.cpp | 19 +- .../GAAttributesBlueprintFunctionLibrary.cpp | 17 +- .../GAAttributesBlueprintFunctionLibrary.h | 18 ++ .../Source/AbilityFramework/GAGlobalTypes.h | 39 +-- Source/ActionRPGGame/ARGlobals.cpp | 11 + Source/ActionRPGGame/ARGlobals.h | 36 +++ Source/ActionRPGGame/ARPlayerController.cpp | 23 ++ Source/ActionRPGGame/ARPlayerController.h | 28 +++ .../ActionRPGGame/Abilities/ARAbilityBase.cpp | 7 + .../ActionRPGGame/Abilities/ARAbilityBase.h | 22 ++ .../Abilities/ARAbilityUIData.cpp | 7 + .../ActionRPGGame/Abilities/ARAbilityUIData.h | 25 ++ Source/ActionRPGGame/ActionRPGGame.Build.cs | 14 +- Source/ActionRPGGame/ActionRPGGame.cpp | 14 +- Source/ActionRPGGame/ActionRPGGame.h | 4 + .../Attributes/ARAbilityAttributes.h | 8 +- .../Attributes/ARCharacterAttributes.h | 2 + .../Attributes/ARGunAttributes.h | 19 +- .../Calculations/ARAmmoReloadCalculation.cpp | 7 + .../Calculations/ARAmmoReloadCalculation.h | 20 ++ Source/ActionRPGGame/UI/ARAbilityData.cpp | 16 ++ Source/ActionRPGGame/UI/ARAbilityData.h | 34 +++ Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 160 ++++++++++++ Source/ActionRPGGame/UI/ARAbilityWidget.h | 63 ++++- Source/ActionRPGGame/UI/ARHUDWidget.cpp | 15 ++ Source/ActionRPGGame/UI/ARHUDWidget.h | 24 ++ .../ActionRPGGame/UI/ARWeaponInfoWidget.cpp | 40 +++ Source/ActionRPGGame/UI/ARWeaponInfoWidget.h | 28 +++ .../UI/Abilities/ARAbilityInfoWidget.cpp | 78 ++++++ .../UI/Abilities/ARAbilityInfoWidget.h | 44 ++++ .../Abilities/ARUIAbilityManagerComponent.cpp | 238 ++++++++++++++++++ .../Abilities/ARUIAbilityManagerComponent.h | 110 ++++++++ 40 files changed, 1268 insertions(+), 84 deletions(-) create mode 100644 Source/ActionRPGGame/ARGlobals.cpp create mode 100644 Source/ActionRPGGame/ARGlobals.h create mode 100644 Source/ActionRPGGame/ARPlayerController.cpp create mode 100644 Source/ActionRPGGame/ARPlayerController.h create mode 100644 Source/ActionRPGGame/Abilities/ARAbilityBase.cpp create mode 100644 Source/ActionRPGGame/Abilities/ARAbilityBase.h create mode 100644 Source/ActionRPGGame/Abilities/ARAbilityUIData.cpp create mode 100644 Source/ActionRPGGame/Abilities/ARAbilityUIData.h create mode 100644 Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.cpp create mode 100644 Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.h create mode 100644 Source/ActionRPGGame/UI/ARAbilityData.cpp create mode 100644 Source/ActionRPGGame/UI/ARAbilityData.h create mode 100644 Source/ActionRPGGame/UI/ARHUDWidget.cpp create mode 100644 Source/ActionRPGGame/UI/ARHUDWidget.h create mode 100644 Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp create mode 100644 Source/ActionRPGGame/UI/ARWeaponInfoWidget.h create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h create mode 100644 Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index fc0cc87..bd98141 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -12,7 +12,8 @@ "AbilityFramework", "Engine", "AIModule", - "UMG" + "UMG", + "CoreUObject" ] } ], diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index 31924c9..d9a4a78 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -5,4 +5,14 @@ ProjectName=Third Person Game Template [/Script/AbilityFramework.AFCueManager] DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet +[/Script/Engine.AssetManagerSettings] +-PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=False,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) +bOnlyCookProductionAssets=False +bShouldGuessTypeAndNameInEditor=True + diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 60b2925..5e41ffd 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -6,21 +6,27 @@ FastReplication=False NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 -GameplayTagList=(Tag="Ability.Corruption",DevComment="") +-GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") -GameplayTagList=(Tag="Ability.Rifle",DevComment="") +-GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") -GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") -GameplayTagList=(Tag="Damage",DevComment="") -GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +-GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") -GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.Rifle",DevComment="") ++GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") ++GameplayTagList=(Tag="Ability.Rifle.Reload",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +GameplayTagList=(Tag="Damage",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") ++GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index d7aad39..c197740 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -1,5 +1,17 @@ [/Script/Engine.InputSettings] +-AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) +-AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) @@ -15,12 +27,12 @@ -AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) @@ -36,12 +48,6 @@ +AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) bAltEnterTogglesFullscreen=True bF11TogglesFullscreen=True bUseMouseForTouch=False @@ -56,11 +62,15 @@ DefaultViewportMouseLockMode=LockOnCapture -ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="Input.Ability01.Activate",Key=None,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="SwitchAbilitySet",Key=Tilde,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="SwitchAbilitySet",Key=B,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) -AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) -AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp index 68e2a65..b27b8fd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp @@ -24,7 +24,7 @@ void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, return; } - Comp->NativeInputPressed(AbilityTag, ActionTag); + Comp->NativeInputPressed(ActionTag); } void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag) @@ -42,5 +42,5 @@ void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, return; } - Comp->NativeInputReleased(AbilityTag, ActionTag); + Comp->NativeInputReleased(ActionTag); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 8887ee1..55fb291 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -46,6 +46,39 @@ UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) TickFunction.SetTickFunctionEnable(true); } + +void UGAAbilityBase::PostInitProperties() +{ + UpdateAssetRegistryInfo(); + Super::PostInitProperties(); +} + +void UGAAbilityBase::Serialize(FArchive& Ar) +{ + if (Ar.IsSaving()) + { + UpdateAssetRegistryInfo(); + } + + Super::Serialize(Ar); + + if (Ar.IsLoading()) + { + UpdateAssetRegistryInfo(); + } +} + +#if WITH_EDITOR +void UGAAbilityBase::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) +{ + Super::PostEditChangeProperty(PropertyChangedEvent); +} +#endif // WITH_EDITOR + +void UGAAbilityBase::UpdateAssetRegistryInfo() +{ + AbilityTagSearch = AbilityTag.GetTagName(); +} void UGAAbilityBase::TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction) { @@ -56,6 +89,8 @@ void UGAAbilityBase::InitAbility() //still want to initialize, as Spec is used in multiple places. ActivationEffect.InitializeIfNotInitialized(); CooldownEffect.InitializeIfNotInitialized(); + AttributeCost.InitializeIfNotInitialized(); + AbilityAttributeCost.InitializeIfNotInitialized(); DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)); if (AbilityComponent) { @@ -73,6 +108,7 @@ void UGAAbilityBase::InitAbility() if (Attributes) { Attributes->InitializeAttributes(GetAbilityComp()); + Attributes->InitializeAttributesFromTable(); } if (!OwnerCamera) @@ -221,7 +257,9 @@ bool UGAAbilityBase::ApplyCooldownEffect() FAFFunctionModifier Modifier; CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, this, POwner, this, Modifier); + OnCooldownStart(); + CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); return false; } bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) @@ -274,6 +312,7 @@ bool UGAAbilityBase::CanUseAbility() // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); CanUse = !bIsOnCooldown && !bIsActivating; + return CanUse; } @@ -363,11 +402,22 @@ void UGAAbilityBase::RemoveTagContainer(const FGameplayTagContainer& TagsIn) bool UGAAbilityBase::ApplyAttributeCost() { - return false; + return true; } bool UGAAbilityBase::ApplyAbilityAttributeCost() { - return true; + //add checking if attribute goes below zero + //maybe let game specific code handle it.. + FAFFunctionModifier Modifier; + + if (CheckAbilityAttributeCost()) + { + AbilityAttributeCostHandle = UGABlueprintLibrary::ApplyGameEffectToObject(AbilityAttributeCost, + this, POwner, this, Modifier); + + return true; + } + return false; } bool UGAAbilityBase::BP_ApplyAttributeCost() { @@ -377,6 +427,20 @@ bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() { return ApplyAbilityAttributeCost(); } +bool UGAAbilityBase::BP_CheckAbilityAttributeCost() +{ + return CheckAbilityAttributeCost(); +} +bool UGAAbilityBase::CheckAbilityAttributeCost() +{ + float ModValue = AbilityAttributeCost.GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AbilityAttributeCost.GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Attributes->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + + return true; +} bool UGAAbilityBase::IsOnCooldown() { bool bOnCooldown = false; @@ -459,11 +523,11 @@ void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) { - AbilityComponent->NativeInputPressed(AbilityTag, ActionName); + AbilityComponent->NativeInputPressed(ActionName); } void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) { - AbilityComponent->NativeInputReleased(AbilityTag, ActionName); + AbilityComponent->NativeInputReleased(ActionName); } /* Tracing Helpers Start */ @@ -550,7 +614,6 @@ float UGAAbilityBase::GetActivationEndTime() const { return AbilityComponent->GameEffectContainer.GetEndTime(ActivationEffectHandle); } - float UGAAbilityBase::BP_GetActivationRemainingTime() { return GetActivationRemainingTime(); @@ -571,6 +634,8 @@ float UGAAbilityBase::BP_GetActivationEndTime() { return GetActivationEndTime(); } + + float UGAAbilityBase::GetCooldownRemainingTime() const { return AbilityComponent->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 206a32f..915002e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -202,6 +202,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") FGAEffectProperty ActivationEffect; FGAEffectHandle ActivationEffectHandle; + /* These attributes will be reduced by specified amount when ability is activated. Attribute cost from Ability Owner attributes @@ -213,6 +214,10 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask */ UPROPERTY(EditAnywhere, Category = "Config") FGAEffectProperty AbilityAttributeCost; + FGAEffectHandle AbilityAttributeCostHandle; + + UPROPERTY(AssetRegistrySearchable) + FName AbilityTagSearch; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") FGameplayTag AbilityTag; @@ -264,6 +269,16 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask public: UGAAbilityBase(const FObjectInitializer& ObjectInitializer); + virtual void PostInitProperties() override; + + virtual void Serialize(FArchive& Ar) override; + +#if WITH_EDITOR + virtual void PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) override; +#endif // WITH_EDITOR + + void UpdateAssetRegistryInfo(); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); @@ -334,6 +349,11 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnAbilityFinished(); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnCooldownStart(); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnCooldownEnd(const FGAEffectHandle& InHandle); + UFUNCTION() void OnCooldownEffectExpired(); UFUNCTION() @@ -405,6 +425,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask bool ApplyActivationEffect(bool bApplyActivationEffect); bool ApplyAttributeCost(); bool ApplyAbilityAttributeCost(); + bool CheckAbilityAttributeCost(); bool IsOnCooldown(); bool IsActivating(); @@ -417,6 +438,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") bool BP_ApplyAbilityAttributeCost(); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Ability Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_CheckAbilityAttributeCost(); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") float GetCurrentActivationTime(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h index f769cae..02f2d4e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -77,7 +77,9 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase inline void SetBaseValue(float ValueIn) { BaseValue = ValueIn; } inline void SetMinValue(float ValueIn) { MinValue = ValueIn; } inline void SetMaxValue(float ValueIn) { MaxValue = ValueIn; } - + //used internally. NEver call it directly. + inline void SetCurrentValue(float ValueIn) { CurrentValue = ValueIn; } + inline float GetFinalValue() { return FMath::Clamp(BaseValue + BonusValue, MinValue, MaxValue); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp index e7de1c9..57b024f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -65,6 +65,7 @@ void UGAAttributesBase::InitializeAttributesFromTable() attr->SetBaseValue(row->BaseValue); attr->SetMaxValue(row->MaxValue); attr->SetMinValue(row->MinValue); + attr->SetCurrentValue(row->CurrentValue); attr->InitializeAttribute(); } //TickableAttributes.Add(attr); @@ -157,21 +158,11 @@ float UGAAttributesBase::GetCurrentAttributeValue(const FGAAttribute& Name) } float UGAAttributesBase::GetFloatValue(const FGAAttribute& AttributeIn) { - if ((AttributeIn.AttributeName == LastAttributeName)) - { - if (CachedFloatPropety) - { - const void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); - return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); - } - } - //LastAttributeName = AttributeIn.AttributeName; - UNumericProperty* NumericProperty = CastChecked(FindProperty(AttributeIn)); - CachedFloatPropety = NumericProperty; - const void* ValuePtr = NumericProperty->ContainerPtrToValuePtr(this); - return NumericProperty->GetFloatingPointPropertyValue(ValuePtr); + FAFAttributeBase* Attribute = GetAttribute(AttributeIn); - return 0; + if (!Attribute) + return 0; + return Attribute->GetCurrentValue(); } float UGAAttributesBase::SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp index 88996e2..c4d6951 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp @@ -5,7 +5,7 @@ #include "../AFAbilityInterface.h" #include "GAAttributesBase.h" #include "../AFAbilityComponent.h" - +#include "GABlueprintLibrary.h" #include "GAAttributesBlueprintFunctionLibrary.h" @@ -48,4 +48,19 @@ float UGAAttributesBlueprintFunctionLibrary::GetAttributeFloat(AActor* Target, F return 0; return attributeInt->GetAttributes()->GetFloatValue(AttributeIn); +} + +void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues(APawn* Instigator, UObject* Causer, + UPARAM(ref) FGAEffectProperty& From, UObject* FromTarget, + UPARAM(ref) FGAEffectProperty& To, UObject* ToTarget) +{ + IAFAbilityInterface* FromInterface = Cast(FromTarget); + IAFAbilityInterface* ToInterface = Cast(ToTarget); + + if (!FromInterface || !ToInterface) + return; + + FAFFunctionModifier ModF; + UGABlueprintLibrary::ApplyGameEffectToObject(From, FromTarget, Instigator, Causer, ModF); + UGABlueprintLibrary::ApplyGameEffectToObject(To, ToTarget, Instigator, Causer, ModF); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h index d60bef2..c288148 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h @@ -1,5 +1,6 @@ #pragma once #include "../GAGlobalTypes.h" +#include "GAGameEffect.h" #include "GAAttributesBlueprintFunctionLibrary.generated.h" /* Some static helper functions, to interact with Attribute system. @@ -31,4 +32,21 @@ class ABILITYFRAMEWORK_API UGAAttributesBlueprintFunctionLibrary : public UBluep */ UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") static float GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn); + /** + * Subtracts value specified by From effect + * and adds it by effect specified by To. + * + * @param Instigator - Who Insigated effects. + * @param Causer - Who Caused Effects + * @param From - effect which will subtract Value + * @param FromTarget - from whose attributes value will be subtracted + * @param To - Effect specifing where attribute should be added. + * @param ToTarget - Target to which attributes will be added. + * + * @return value of attribute from actor. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + static void ExchangeAttributesValues(APawn* Instigator, UObject* Causer, + UPARAM(ref) FGAEffectProperty& From, UObject* FromTarget, + UPARAM(ref) FGAEffectProperty& To, UObject* ToTarget); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index a0474b9..ef094f1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -166,42 +166,7 @@ enum class EGAEffectAggregation : uint8 */ AggregateByTarget }; -UENUM() -enum class EGAStackingChannel : uint8 -{ - Channel001, - Channel002, - Channel003, - Channel004, - Channel005, - Channel006, - Channel007, - Channel008, - Channel009, - Channel010, - Channel011, - Channel012, - Channel013, - Channel014, - Channel015, - Channel016, - Channel017, - Channel018, - Channel019, - Channel020, - Channel021, - Channel022, - Channel023, - Channel024, - Channel025, - Channel026, - Channel027, - Channel028, - Channel029, - Channel030, - Channel031, - Channel032, -}; + USTRUCT() struct FAFEventData { @@ -219,6 +184,8 @@ struct FAFAtributeRowData : public FTableRowBase float MinValue; UPROPERTY(EditAnywhere, BlueprintReadOnly) float MaxValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float CurrentValue; UPROPERTY(EditAnywhere, BlueprintReadOnly) TSubclassOf Extension; }; diff --git a/Source/ActionRPGGame/ARGlobals.cpp b/Source/ActionRPGGame/ARGlobals.cpp new file mode 100644 index 0000000..ee0d8ed --- /dev/null +++ b/Source/ActionRPGGame/ARGlobals.cpp @@ -0,0 +1,11 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARGlobals.h" + +FARGlobals::FARGlobals() +{ +} + +FARGlobals::~FARGlobals() +{ +} diff --git a/Source/ActionRPGGame/ARGlobals.h b/Source/ActionRPGGame/ARGlobals.h new file mode 100644 index 0000000..56db515 --- /dev/null +++ b/Source/ActionRPGGame/ARGlobals.h @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" +#include "GameplayTags.h" + +/** + * + */ +class ACTIONRPGGAME_API FARGlobals +{ +public: + FARGlobals(); + ~FARGlobals(); + static FPrimaryAssetId MakeAbilityAssetId(const FAssetData& InAssetData) + { + return FPrimaryAssetId(FPrimaryAssetType("Ability"), InAssetData.AssetName); + } + static FAssetData GetAbilityAssetByTag(const FGameplayTag& InTag) + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("AbilityTagSearch", InTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + if (AssetData.Num() == 1) + return AssetData[0]; + + return FAssetData(); + } +}; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp new file mode 100644 index 0000000..b906635 --- /dev/null +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARPlayerController.h" +#include "ARUIComponent.h" +#include "ARUIAbilityManagerComponent.h" + +AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); + UIAbilityManagerComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIAbilityManagerComponent"); +} + +void AARPlayerController::SetupInputComponent() +{ + Super::SetupInputComponent(); + InputComponent->BindAction("SwitchAbilitySet", IE_Pressed, this, &AARPlayerController::InputSwitchAbilitySet); +} + +void AARPlayerController::InputSwitchAbilitySet() +{ + UIAbilityManagerComponent->SwitchSet(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h new file mode 100644 index 0000000..53efc3e --- /dev/null +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/PlayerController.h" +#include "ARPlayerController.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARPlayerController : public APlayerController +{ + GENERATED_BODY() +public: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UARUIComponent* UIComponent; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UARUIAbilityManagerComponent* UIAbilityManagerComponent; + +public: + AARPlayerController(const FObjectInitializer& ObjectInitializer); + + void SetupInputComponent(); + + void InputSwitchAbilitySet(); +}; diff --git a/Source/ActionRPGGame/Abilities/ARAbilityBase.cpp b/Source/ActionRPGGame/Abilities/ARAbilityBase.cpp new file mode 100644 index 0000000..bfa82c3 --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAbilityBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityBase.h" + + + + diff --git a/Source/ActionRPGGame/Abilities/ARAbilityBase.h b/Source/ActionRPGGame/Abilities/ARAbilityBase.h new file mode 100644 index 0000000..164ced0 --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAbilityBase.h @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Abilities/GAAbilityBase.h" +#include "ARAbilityBase.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityBase : public UGAAbilityBase +{ + GENERATED_BODY() + +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "UI Config") + class UARAbilityUIData* UIData; + + +}; diff --git a/Source/ActionRPGGame/Abilities/ARAbilityUIData.cpp b/Source/ActionRPGGame/Abilities/ARAbilityUIData.cpp new file mode 100644 index 0000000..48f46d8 --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAbilityUIData.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityUIData.h" + + + + diff --git a/Source/ActionRPGGame/Abilities/ARAbilityUIData.h b/Source/ActionRPGGame/Abilities/ARAbilityUIData.h new file mode 100644 index 0000000..98b2ecf --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAbilityUIData.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "ARAbilityUIData.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, EditInLineNew) +class ACTIONRPGGAME_API UARAbilityUIData : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly) + FText DisplayName; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + FText Description; + + UPROPERTY(EditAnywhere, BlueprintReadOnly) + UTexture2D* Icon; + +}; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 4eb6d60..096481e 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -13,7 +13,12 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AbilityFramework/Abilities", "AbilityFramework/Attributes", "AbilityFramework/Effects", - "AbilityFramework/Public" + "AbilityFramework/Public", + "ActionRPGGame/Abilities", + "ActionRPGGame/AI", + "ActionRPGGame/Attributes", + "ActionRPGGame/UI", + "ActionRPGGame/UI/Abilities" // ... add public include paths required here ... } ); @@ -25,10 +30,15 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AbilityFramework/Attributes", "AbilityFramework/Effects", "AbilityFramework/Private", + "ActionRPGGame/Abilities", + "ActionRPGGame/AI", + "ActionRPGGame/Attributes", + "ActionRPGGame/UI", + "ActionRPGGame/UI/Abilities" // ... add other private include paths required here ... } ); PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", - "GameplayTags", "AbilityFramework" }); + "GameplayTags", "AbilityFramework", "SlateCore" }); } } diff --git a/Source/ActionRPGGame/ActionRPGGame.cpp b/Source/ActionRPGGame/ActionRPGGame.cpp index 173c45d..3ca2847 100644 --- a/Source/ActionRPGGame/ActionRPGGame.cpp +++ b/Source/ActionRPGGame/ActionRPGGame.cpp @@ -2,6 +2,18 @@ #include "ActionRPGGame.h" #include "Modules/ModuleManager.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" +void FActionRPGGameModule::StartupModule() +{ + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + //AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); + TArray< FString > ContentPaths; + TArray RootPaths; + FPackageName::QueryRootContentPaths(ContentPaths); + AssetRegistry.ScanPathsSynchronous(ContentPaths); -IMPLEMENT_PRIMARY_GAME_MODULE( FDefaultGameModuleImpl, ActionRPGGame, "ActionRPGGame" ); +}; +IMPLEMENT_PRIMARY_GAME_MODULE(FActionRPGGameModule, ActionRPGGame, "ActionRPGGame" ); \ No newline at end of file diff --git a/Source/ActionRPGGame/ActionRPGGame.h b/Source/ActionRPGGame/ActionRPGGame.h index 25b0d29..a467361 100644 --- a/Source/ActionRPGGame/ActionRPGGame.h +++ b/Source/ActionRPGGame/ActionRPGGame.h @@ -3,3 +3,7 @@ #pragma once #include "CoreMinimal.h" +class FActionRPGGameModule : public FDefaultGameModuleImpl +{ + virtual void StartupModule() override; +}; \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h index 0abd6f3..e2703f7 100644 --- a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h @@ -13,7 +13,13 @@ UCLASS() class ACTIONRPGGAME_API UARAbilityAttributes : public UGAAttributesBase { GENERATED_BODY() - +public: + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase CastTime; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Cooldown; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase BaseDamage; diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h index 7465bae..5c2f174 100644 --- a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h @@ -28,5 +28,7 @@ class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase Ammo; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase MachineGunAmmo; }; diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Attributes/ARGunAttributes.h index 85d84fc..4812960 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.h @@ -13,8 +13,23 @@ UCLASS() class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase { GENERATED_BODY() - - +public: + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase BaseDamage; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase CritChance; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Magazine; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase RateOfFire; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase ReloadSpeed; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase HorizontalStability; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase VerticalStability; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Spread; }; diff --git a/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.cpp b/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.cpp new file mode 100644 index 0000000..9012ef7 --- /dev/null +++ b/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAmmoReloadCalculation.h" + + + + diff --git a/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.h b/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.h new file mode 100644 index 0000000..20c13ac --- /dev/null +++ b/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GACustomCalculation.h" +#include "ARAmmoReloadCalculation.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAmmoReloadCalculation : public UGACustomCalculation +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/UI/ARAbilityData.cpp b/Source/ActionRPGGame/UI/ARAbilityData.cpp new file mode 100644 index 0000000..d5afc87 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARAbilityData.cpp @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityData.h" + + + + +TArray UARAbilityData::GetAbilitiesTags() +{ + TArray Out; + for (auto It = Items.CreateIterator(); It; ++It) + { + Out.Add(It->Key); + } + return Out; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityData.h b/Source/ActionRPGGame/UI/ARAbilityData.h new file mode 100644 index 0000000..d63d87b --- /dev/null +++ b/Source/ActionRPGGame/UI/ARAbilityData.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Engine/DataAsset.h" +#include "GameplayTags.h" +#include "ARAbilityData.generated.h" + +USTRUCT() +struct FARAbilityItem +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TSubclassOf AbilityClass; + UPROPERTY(EditAnywhere) + bool bIsAvailable; + }; + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityData : public UDataAsset +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TMap Items; + + UFUNCTION(BlueprintCallable) + TArray GetAbilitiesTags(); +}; diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index 3990916..a5284f4 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -1,7 +1,167 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARAbilityWidget.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "ARUIAbilityManagerComponent.h" +#include "Abilities/GAAbilityBase.h" +#include "ARAbilityBase.h" +#include "ARAbilityUIData.h" +#include "Input/Reply.h" +#include "Input/Events.h" +#include "Blueprint/WidgetBlueprintLibrary.h" +#include "ARGlobals.h" +float UARAbilityWidget::GetActivationRemainingTime() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetActivationRemainingTime() : 0; +} +float UARAbilityWidget::GetActivationRemainingTimeNormalized() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetActivationRemainingTimeNormalized() : 0; +} +float UARAbilityWidget::GetActivationCurrentTime() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetActivationCurrentTime() : 0; +} +float UARAbilityWidget::GetActivationCurrentTimeNormalized() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetActivationCurrentTimeNormalized() : 0; +} +float UARAbilityWidget::GetActivationEndTime() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetActivationEndTime() : 0; +} +float UARAbilityWidget::GetCooldownRemainingTime() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetCooldownRemainingTime() : 0; +} +float UARAbilityWidget::GetCooldownRemainingTimeNormalized() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetCooldownRemainingTimeNormalized() : 0; +} +float UARAbilityWidget::GetCooldownCurrentTime() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetCooldownCurrentTime() : 0; +} +float UARAbilityWidget::GetCooldownCurrentTimeNormalized() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetCooldownCurrentTimeNormalized() : 0; +} +float UARAbilityWidget::GetCooldownEndTime() +{ + if (!OwningComponent) + return 0; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->GetCooldownEndTime() : 0; +} +UTexture2D* UARAbilityWidget::GetIcon() +{ + if (Icon) + return Icon; + if (!OwningComponent) + return nullptr; + UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + return Ability ? Ability->UIData->Icon : nullptr; +} + +void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) +{ + AbilityTag = InAbility; + FAssetData AssetData = FARGlobals::GetAbilityAssetByTag(AbilityTag); + TSubclassOf cls;// = nullptr; + if (AssetData.IsValid()) + { + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + PrimaryAssetId = FARGlobals::MakeAbilityAssetId(AssetData); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info))// && !Info.bHasBlueprintClasses) + { + cls = Manager->GetPrimaryAssetObjectClass(PrimaryAssetId); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityWidget::OnFinishedLoad); + AbilityLoadedHandle = Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } + } + } +} +void UARAbilityWidget::OnFinishedLoad() +{ + UObject* loaded = AbilityLoadedHandle->GetLoadedAsset(); + TSubclassOf cls = Cast(loaded); + if (cls) + { + UARAbilityBase* CDO = cls.GetDefaultObject(); + Icon = CDO->UIData->Icon; + } + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + Manager->UnloadPrimaryAsset(PrimaryAssetId); + } +} +FReply UARAbilityWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) +{ + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + //return FReply::Unhandled(); +} + +void UARAbilityWidget::NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) +{ + UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); + if (DragDropOp) + { + APlayerController* MyPC = Cast(OwningComponent->GetOwner()); + UARAbilityWidget* DragIcon = CreateWidget(MyPC, OwningComponent->DragVisualClass); + DragIcon->AbilityIndex = AbilityIndex; + DragIcon->AbilitySetIndex = AbilitySetIndex; + DragIcon->OwningComponent = OwningComponent; + + DragDropOp->Payload = this; + DragDropOp->DefaultDragVisual = DragIcon; + + OutOperation = DragDropOp; + } +} +bool UARAbilityWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UARAbilityWidget* Payload = Cast(InOperation->Payload); + Setbility(Payload->AbilityTag); + + OwningComponent->NativeEquipAbility(AbilityTagDebug, AbilitySetIndex, AbilityIndex, InputBinding); + return false; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index 2249ff8..50dc89e 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -3,18 +3,71 @@ #pragma once #include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" +#include "ARAbilityInfoWidget.h" +#include "GameplayTags.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" #include "ARAbilityWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARAbilityWidget : public UUserWidget +class ACTIONRPGGAME_API UARAbilityWidget : public UARAbilityInfoWidget { GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Config") + int32 AbilitySetIndex; + UPROPERTY(EditAnywhere, Category = "Config") + int32 AbilityIndex; + UPROPERTY(EditAnywhere, Category = "Config") + FGameplayTag InputBinding; + + UPROPERTY(EditAnywhere, Category = "Config") + UTexture2D* Icon; + + //debug + UPROPERTY(EditAnywhere, Category = "Config") + FGameplayTag AbilityTagDebug; - - - + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationRemainingTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationCurrentTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationEndTime(); + + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownRemainingTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownCurrentTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownEndTime(); + + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + UTexture2D* GetIcon(); + + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|UI|Abilities") + void Setbility(const FGameplayTag& InAbility); + + TSharedPtr AbilityLoadedHandle; + + FPrimaryAssetId PrimaryAssetId; + UFUNCTION() + void OnFinishedLoad(); + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) override; + virtual void NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; + virtual bool NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; }; diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.cpp b/Source/ActionRPGGame/UI/ARHUDWidget.cpp new file mode 100644 index 0000000..5ea9e85 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARHUDWidget.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHUDWidget.h" + + + + +void UARHUDWidget::NativeConstruct() +{ + Super::NativeConstruct(); + UPanelWidget* RootWidget = Cast(GetRootWidget()); + MainGrid = WidgetTree->ConstructWidget(UUniformGridPanel::StaticClass(), TEXT("MainGrid")); + RootWidget->AddChild(MainGrid); + // Bind delegates here. +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.h b/Source/ActionRPGGame/UI/ARHUDWidget.h new file mode 100644 index 0000000..112e6ac --- /dev/null +++ b/Source/ActionRPGGame/UI/ARHUDWidget.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "Blueprint/WidgetTree.h" +#include "Components/UniformGridPanel.h" +#include "ARHUDWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHUDWidget : public UUserWidget +{ + GENERATED_BODY() +protected: + UUniformGridPanel* MainGrid; +public: + virtual void NativeConstruct() override; + + +}; diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp new file mode 100644 index 0000000..f38ee04 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp @@ -0,0 +1,40 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponInfoWidget.h" + + +void UARWeaponInfoWidget::InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) +{ + Super::InitializeWidget(InOwningComponent); +} + +void UARWeaponInfoWidget::NativeAddAbility(const FGameplayTag& InAbilityTag) +{ + Super::NativeAddAbility(InAbilityTag); +} +void UARWeaponInfoWidget::NativeOnAbilityReady(const FGameplayTag& InAbilityTag) +{ + Super::NativeOnAbilityReady(InAbilityTag); + + WeaponAttributes = Ability->GetAttributesTyped(); +} + +float UARWeaponInfoWidget::GetMagazineAmmo() +{ + if (!WeaponAttributes) + return 0; + + return WeaponAttributes->Magazine.GetCurrentValue(); + +} +float UARWeaponInfoWidget::GetMagazineAmmoNormalized() +{ + if (!WeaponAttributes) + return 0; + + float CurrentValue = WeaponAttributes->Magazine.GetCurrentValue(); + FVector2D Input(0, WeaponAttributes->Magazine.GetFinalValue()); + + return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h new file mode 100644 index 0000000..36bfbcb --- /dev/null +++ b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Abilities/ARAbilityInfoWidget.h" +#include "ARGunAttributes.h" +#include "ARWeaponInfoWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponInfoWidget : public UARAbilityInfoWidget +{ + GENERATED_BODY() +protected: + class UARGunAttributes* WeaponAttributes; +public: + virtual void InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) override; + virtual void NativeAddAbility(const FGameplayTag& InAbilityTag) override; + virtual void NativeOnAbilityReady(const FGameplayTag& InAbilityTag) override; + + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") + float GetMagazineAmmo(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") + float GetMagazineAmmoNormalized(); +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp new file mode 100644 index 0000000..327626a --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp @@ -0,0 +1,78 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityInfoWidget.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "ARUIAbilityManagerComponent.h" +#include "Abilities/GAAbilityBase.h" +#include "ARPlayerController.h" + +void UARAbilityInfoWidget::NativePreConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + OwningComponent = MyPC->UIAbilityManagerComponent; + } + Super::NativePreConstruct(); +} +void UARAbilityInfoWidget::NativeConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + OwningComponent = MyPC->UIAbilityManagerComponent; + } + Super::NativeConstruct(); +} + +void UARAbilityInfoWidget::InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) +{ + OwningComponent = InOwningComponent; +} +void UARAbilityInfoWidget::NativeAddAbility(const FGameplayTag& InAbilityTag) +{ + IAFAbilityInterface* ABInt = Cast(GetOwningPlayer()->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARAbilityInfoWidget::OnAbilityReady)) + { + AbilityComp->OnAbilityAdded.AddDynamic(this, &UARAbilityInfoWidget::OnAbilityReady); + } + AbilityTag = InAbilityTag; + TSubclassOf AbilityClass = OwningComponent->AbilityData->Items.FindRef(InAbilityTag).AbilityClass; + AbilityComp->NativeAddAbility(AbilityClass, nullptr, FGameplayTag(), false); +} +void UARAbilityInfoWidget::NativeOnAbilityReady(const FGameplayTag& InAbilityTag) +{ + if (AbilityTag != InAbilityTag) + { + return; + } + IAFAbilityInterface* ABInt = Cast(GetOwningPlayer()->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + BP_OnAbilityReady(InAbilityTag); + Ability = AbilityComp->BP_GetAbilityByTag(InAbilityTag); +} +void UARAbilityInfoWidget::AddAbility(const FGameplayTag& InAbilityTag) +{ + NativeAddAbility(InAbilityTag); +} +void UARAbilityInfoWidget::BP_InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) +{ + InitializeWidget(InOwningComponent); +} +void UARAbilityInfoWidget::OnAbilityReady(const FGameplayTag& InAbilityTag) +{ + NativeOnAbilityReady(InAbilityTag); +} + diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h new file mode 100644 index 0000000..cc3a80f --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h @@ -0,0 +1,44 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "GameplayTags.h" +#include "Abilities/GAAbilityBase.h" +#include "ARAbilityInfoWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityInfoWidget : public UUserWidget +{ + GENERATED_BODY() +protected: + UPROPERTY() + FGameplayTag AbilityTag; + UPROPERTY() + class UGAAbilityBase* Ability; + UPROPERTY(BlueprintReadOnly) + class UARUIAbilityManagerComponent* OwningComponent; + +public: + virtual void NativePreConstruct() override; + virtual void NativeConstruct() override; + + virtual void InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent); + virtual void NativeAddAbility(const FGameplayTag& InAbilityTag); + virtual void NativeOnAbilityReady(const FGameplayTag& InAbilityTag); + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|UI|Abilities") + void AddAbility(const FGameplayTag& InAbilityTag); + UFUNCTION(BlueprintCallable, DisplayName = "Initialize Ability Widget", Category = "ActionRPGGame|UI|Abilities") + void BP_InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent); + UFUNCTION() + void OnAbilityReady(const FGameplayTag& InAbilityTag); + UFUNCTION(BlueprintImplementableEvent, DisplayName = "On Ability Ready", Category = "ActionRPGGame|UI|Abilities") + void BP_OnAbilityReady(const FGameplayTag& OutAbilityTag); + + + +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp new file mode 100644 index 0000000..d266fe6 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -0,0 +1,238 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARUIAbilityManagerComponent.h" +#include "ARAbilityInfoWidget.h" +#include "ARWeaponInfoWidget.h" +#include "ARPlayerController.h" +#include "AFAbilityComponent.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" +#include "ARAbilityBase.h" +#include "ARAbilityUIData.h" +// Sets default values for this component's properties +UARUIAbilityManagerComponent::UARUIAbilityManagerComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UARUIAbilityManagerComponent::BeginPlay() +{ + //initiazile Model (hhueheu). + AbilitySet.SetNum(2); + AbilitySet[0].SetNum(6); + AbilitySet[1].SetNum(6); + + AbilityTagsSet.SetNum(2); + AbilityTagsSet[0].SetNum(6); + AbilityTagsSet[1].SetNum(6); + + InputBindingsSet.SetNum(2); + InputBindingsSet[0].SetNum(6); + InputBindingsSet[1].SetNum(6); + + ActiveSet = 0; + + + if (AbilitySetConfigClass) + { + AbilitySetConfigWidget = CreateWidget(Cast(GetOwner()), AbilitySetConfigClass); + //AbilitySetConfigWidget->InitializeWidget(this); + AbilitySetConfigWidget->AddToViewport(); + } + if (AbilityWidgetClass) + { + AbilityWidget = CreateWidget(Cast(GetOwner()), AbilityWidgetClass); + AbilityWidget->InitializeWidget(this); + } + if (WeaponWidgetClass) + { + WeaponWidget = CreateWidget(Cast(GetOwner()), WeaponWidgetClass); + WeaponWidget->InitializeWidget(this); + } + + if (WeaponCrosshairWidgetClass) + { + WeaponCrosshairWidget = CreateWidget(Cast(GetOwner()), WeaponCrosshairWidgetClass); + WeaponCrosshairWidget->AddToViewport(); + } + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + for (const FGameplayTag& Tag : AbilityInputs) + { + AbilityComp->BP_BindAbilityToAction(Tag); + } + Super::BeginPlay(); +} + + +// Called every frame +void UARUIAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +UARAbilityBase* UARUIAbilityManagerComponent::GetAbility(int32 SetIndex, int32 AbilityIndex) +{ + if(AbilitySet[SetIndex][AbilityIndex].IsValid()) + return AbilitySet[SetIndex][AbilityIndex].Get(); + return nullptr; +} +void UARUIAbilityManagerComponent::SetAbility(int32 SetIndex, int32 AbilityIndex, UARAbilityBase* InAbility) +{ + AbilitySet[SetIndex][AbilityIndex] = InAbility; +} +FGameplayTag UARUIAbilityManagerComponent::GetAbilityTag(int32 SetIndex, int32 AbilityIndex) +{ + return AbilityTagsSet[SetIndex][AbilityIndex]; +} +void UARUIAbilityManagerComponent::SetAbilityTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag) +{ + AbilityTagsSet[SetIndex][AbilityIndex] = InAbilityTag; +} + +FGameplayTag UARUIAbilityManagerComponent::GetInputTag(int32 SetIndex, int32 AbilityIndex) +{ + return InputBindingsSet[SetIndex][AbilityIndex]; +} +void UARUIAbilityManagerComponent::SetInputTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag) +{ + InputBindingsSet[SetIndex][AbilityIndex] = InAbilityTag; +} + +void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 AbilitySet + , int32 AbilityIndex, const FGameplayTag& InputBinding) +{ + //fake implementation untill I add AssetManager support. + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARUIAbilityManagerComponent::OnAbilityReady)) + { + AbilityComp->OnAbilityAdded.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); + } + TSubclassOf AbilityClass = AbilityData->Items.FindRef(InAbilityTag).AbilityClass; + FARAbilityEquipInfo ABInfo(AbilitySet, AbilityIndex, InputBinding); + AwatingAbilityConfimation.Add(InAbilityTag, ABInfo); + AbilityComp->NativeAddAbility(AbilityClass, nullptr, InputBinding, false); + +} +void UARUIAbilityManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag) +{ + NativeOnAbilityReady(InAbilityTag); +} +void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAbilityTag) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + if (AwatingAbilityConfimation.Contains(InAbilityTag)) + { + FARAbilityEquipInfo Value; + AwatingAbilityConfimation.RemoveAndCopyValue(InAbilityTag, Value); + UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + + SetAbility(Value.AbilitySetIndex, Value.AbilityIndex, Ability); + SetAbilityTag(Value.AbilitySetIndex, Value.AbilityIndex, InAbilityTag); + SetInputTag(Value.AbilitySetIndex, Value.AbilityIndex, Value.InputBinding); + + + AbilityComp->SetAbilityToAction(InAbilityTag, Value.InputBinding); + } + +} + +void UARUIAbilityManagerComponent::SwitchSet() +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + + if (ActiveSet == 0) + { + const TArray& AbilityTags = AbilityTagsSet[0]; + const TArray& InputTags = InputBindingsSet[0]; + const TArray& InputTags2 = InputBindingsSet[1]; + for (int32 Idx = 0; Idx < 6; Idx++) + { + AbilityComp->SetBlockedInput(InputTags[Idx], true); + AbilityComp->SetBlockedInput(InputTags2[Idx], false); + //AbilityComp->BP_BindAbilityToAction(InputBinding, AbilityTag); + } + ActiveSet = 1; + OnAbilitySetChanged.Broadcast(1); + } + else if (ActiveSet == 1) + { + const TArray& AbilityTags = AbilityTagsSet[1]; + const TArray& InputTags = InputBindingsSet[1]; + const TArray& InputTags2 = InputBindingsSet[0]; + for (int32 Idx = 0; Idx < 6; Idx++) + { + AbilityComp->SetBlockedInput(InputTags[Idx], true); + AbilityComp->SetBlockedInput(InputTags2[Idx], false); + //AbilityComp->BP_BindAbilityToAction(InputBinding, AbilityTag); + } + ActiveSet = 0; + OnAbilitySetChanged.Broadcast(0); + } +} + +void UARUIAbilityManagerComponent::FinishedLoadinFiles() +{ + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + TArray AssetData; + FARFilter Filter; + Filter.ClassNames.Add(TEXT("UGAAbilityBase"));// .Classes.Add(UStaticMesh::StaticClass()); + Filter.TagsAndValues.Add("Ability.Corruption"); + Filter.bRecursiveClasses = true; + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + + FARFilter Filter2; + Filter2.bRecursiveClasses = true; + Filter2.ClassNames.Add(TEXT("UGAAbilityBase"));// .Classes.Add(UStaticMesh::StaticClass()); + + TArray AssetData2; + AssetRegistryModule.Get().GetAssets(Filter2, AssetData2); + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h new file mode 100644 index 0000000..f84d815 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -0,0 +1,110 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "ARAbilityData.h" +#include "GameplayTags.h" +#include "ARAbilityBase.h" +#include "ARUIAbilityManagerComponent.generated.h" + +USTRUCT() +struct FARAbilityEquipInfo +{ + GENERATED_BODY() +public: + int32 AbilitySetIndex; + int32 AbilityIndex; + FGameplayTag InputBinding; + + FARAbilityEquipInfo() + {}; + FARAbilityEquipInfo(int32 InAbilitySetIndex + , int32 InAbilityIndex + , FGameplayTag InInputBinding + ) + : AbilitySetIndex(InAbilitySetIndex), + AbilityIndex(InAbilityIndex), + InputBinding(InInputBinding) + {}; +}; +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAROnAbilitySetChanged, int32, AbilitySet); +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf AbilitySetConfigClass; + UPROPERTY(BlueprintReadOnly) + UUserWidget* AbilitySetConfigWidget; + + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf AbilityWidgetClass; + UPROPERTY(BlueprintReadOnly) + UARAbilityInfoWidget* AbilityWidget; + + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf WeaponWidgetClass; + UPROPERTY(BlueprintReadOnly) + UARWeaponInfoWidget* WeaponWidget; + + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf WeaponCrosshairWidgetClass; + UPROPERTY(BlueprintReadOnly) + UUserWidget* WeaponCrosshairWidget; + + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray AbilityInputs; + + TWeakObjectPtr ActiveWeapon; + TWeakObjectPtr WeaponTwo; + TWeakObjectPtr WeaponThree; + TWeakObjectPtr WeaponFour; + + int32 ActiveSet; + TArray> InputBindingsSet; + TArray> AbilityTagsSet; + TArray>> AbilitySet; + TMap AwatingAbilityConfimation; +public: + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf DragVisualClass; + + UPROPERTY(EditAnywhere, BlueprintReadOnly) + UARAbilityData* AbilityData; + UPROPERTY(BlueprintAssignable) + FAROnAbilitySetChanged OnAbilitySetChanged; +public: + // Sets default values for this component's properties + UARUIAbilityManagerComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + UARAbilityBase* GetAbility(int32 SetIndex, int32 AbilityIndex); + void SetAbility(int32 SetIndex, int32 AbilityIndex, UARAbilityBase* InAbility); + + FGameplayTag GetAbilityTag(int32 SetIndex, int32 AbilityIndex); + void SetAbilityTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag); + + FGameplayTag GetInputTag(int32 SetIndex, int32 AbilityIndex); + void SetInputTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag); + + void NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 AbilitySet + , int32 AbilityIndex, const FGameplayTag& InputBinding); + UFUNCTION() + void OnAbilityReady(const FGameplayTag& InAbilityTag); + + void NativeOnAbilityReady(const FGameplayTag& InAbilityTag); + + void SwitchSet(); + UFUNCTION() + void FinishedLoadinFiles(); +}; From a194087e371622be1a6590926a10b21976ac1e1c Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 16 Jul 2017 14:13:12 +0200 Subject: [PATCH 009/187] Added async loading of ability assets Ability assets are loadyed async, instanced and then unloaded. --- Config/DefaultEngine.ini | 2 ++ Config/DefaultGame.ini | 6 +++++- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 6 +++--- Source/ActionRPGGame/UI/ARAbilityWidget.h | 3 +-- Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp | 7 +++++++ Source/ActionRPGGame/UI/ARUMGWidgetBase.h | 20 ++++++++++++++++++++ 6 files changed, 38 insertions(+), 6 deletions(-) create mode 100644 Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp create mode 100644 Source/ActionRPGGame/UI/ARUMGWidgetBase.h diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 1350a0c..e5cb666 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -124,4 +124,6 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 +[/Script/Engine.Engine] +AssetManagerClassName=/Script/AbilityFramework.AFAssetManager diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index d9a4a78..f5b0269 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -8,7 +8,11 @@ DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet [/Script/Engine.AssetManagerSettings] -PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=False,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index a5284f4..94aa464 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -104,12 +104,12 @@ void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) { if (UAssetManager* Manager = UAssetManager::GetIfValid()) { - PrimaryAssetId = FARGlobals::MakeAbilityAssetId(AssetData); + FPrimaryAssetId PrimaryAssetId = FARGlobals::MakeAbilityAssetId(AssetData); FPrimaryAssetTypeInfo Info; if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info))// && !Info.bHasBlueprintClasses) { cls = Manager->GetPrimaryAssetObjectClass(PrimaryAssetId); - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityWidget::OnFinishedLoad); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityWidget::OnFinishedLoad, PrimaryAssetId); AbilityLoadedHandle = Manager->LoadPrimaryAsset(PrimaryAssetId, TArray(), del); @@ -117,7 +117,7 @@ void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) } } } -void UARAbilityWidget::OnFinishedLoad() +void UARAbilityWidget::OnFinishedLoad(FPrimaryAssetId PrimaryAssetId) { UObject* loaded = AbilityLoadedHandle->GetLoadedAsset(); TSubclassOf cls = Cast(loaded); diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index 50dc89e..396b488 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -61,9 +61,8 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARAbilityInfoWidget TSharedPtr AbilityLoadedHandle; - FPrimaryAssetId PrimaryAssetId; UFUNCTION() - void OnFinishedLoad(); + void OnFinishedLoad(FPrimaryAssetId PrimaryAssetId); virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) override; virtual void NativeOnDragDetected(const FGeometry& InGeometry diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp b/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp new file mode 100644 index 0000000..2bdebe0 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARUMGWidgetBase.h" + + + + diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.h b/Source/ActionRPGGame/UI/ARUMGWidgetBase.h new file mode 100644 index 0000000..9f1fe0d --- /dev/null +++ b/Source/ActionRPGGame/UI/ARUMGWidgetBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARUMGWidgetBase.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARUMGWidgetBase : public UUserWidget +{ + GENERATED_BODY() + + + + +}; From 9cf8aac653c7a3dacf5d14be06960d8758fd1aab Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 27 Jul 2017 23:45:46 +0200 Subject: [PATCH 010/187] Async ability loading fixes --- ActionRPGGame.uproject | 19 ++++++++++++++- Config/DefaultEngine.ini | 5 ++-- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 23 ++++++++++-------- Source/ActionRPGGame/UI/ARAbilityWidget.h | 2 -- .../Abilities/ARUIAbilityManagerComponent.cpp | 24 +++++++++++-------- .../Abilities/ARUIAbilityManagerComponent.h | 24 +++++++++++++++++-- 6 files changed, 70 insertions(+), 27 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index bd98141..1fd8496 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -13,7 +13,8 @@ "Engine", "AIModule", "UMG", - "CoreUObject" + "CoreUObject", + "WorldArchitectEditor" ] } ], @@ -25,6 +26,22 @@ { "Name": "ActorSequenceEditor", "Enabled": true + }, + { + "Name": "OculusVR", + "Enabled": false + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true } ] } \ No newline at end of file diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index e5cb666..40dc7f4 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -83,6 +83,9 @@ s.AsyncLoadingThreadEnabled=True +CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") +[/Script/Engine.Engine] +AssetManagerClassName=/Script/AbilityFramework.AFAssetManager + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -124,6 +127,4 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 -[/Script/Engine.Engine] -AssetManagerClassName=/Script/AbilityFramework.AFAssetManager diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index 94aa464..d3d7a07 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -110,7 +110,7 @@ void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) { cls = Manager->GetPrimaryAssetObjectClass(PrimaryAssetId); FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityWidget::OnFinishedLoad, PrimaryAssetId); - AbilityLoadedHandle = Manager->LoadPrimaryAsset(PrimaryAssetId, + Manager->LoadPrimaryAsset(PrimaryAssetId, TArray(), del); } @@ -119,16 +119,19 @@ void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) } void UARAbilityWidget::OnFinishedLoad(FPrimaryAssetId PrimaryAssetId) { - UObject* loaded = AbilityLoadedHandle->GetLoadedAsset(); - TSubclassOf cls = Cast(loaded); - if (cls) - { - UARAbilityBase* CDO = cls.GetDefaultObject(); - Icon = CDO->UIData->Icon; - } if (UAssetManager* Manager = UAssetManager::GetIfValid()) { - Manager->UnloadPrimaryAsset(PrimaryAssetId); + UObject* loaded = Manager->GetPrimaryAssetObject(PrimaryAssetId); + TSubclassOf cls = Cast(loaded); + if (cls) + { + UARAbilityBase* CDO = cls.GetDefaultObject(); + Icon = CDO->UIData->Icon; + } + + { + Manager->UnloadPrimaryAsset(PrimaryAssetId); + } } } FReply UARAbilityWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry @@ -162,6 +165,6 @@ bool UARAbilityWidget::NativeOnDrop(const FGeometry& InGeometry UARAbilityWidget* Payload = Cast(InOperation->Payload); Setbility(Payload->AbilityTag); - OwningComponent->NativeEquipAbility(AbilityTagDebug, AbilitySetIndex, AbilityIndex, InputBinding); + OwningComponent->NativeEquipAbility(Payload->AbilityTag, AbilitySetIndex, AbilityIndex); return false; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index 396b488..687709e 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -59,8 +59,6 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARAbilityInfoWidget UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|UI|Abilities") void Setbility(const FGameplayTag& InAbility); - TSharedPtr AbilityLoadedHandle; - UFUNCTION() void OnFinishedLoad(FPrimaryAssetId PrimaryAssetId); virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index d266fe6..8c7c9de 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -32,9 +32,9 @@ void UARUIAbilityManagerComponent::BeginPlay() AbilityTagsSet[0].SetNum(6); AbilityTagsSet[1].SetNum(6); - InputBindingsSet.SetNum(2); - InputBindingsSet[0].SetNum(6); - InputBindingsSet[1].SetNum(6); + //InputBindingsSet.SetNum(2); + //InputBindingsSet[0].SetNum(6); + //InputBindingsSet[1].SetNum(6); ActiveSet = 0; @@ -117,7 +117,7 @@ void UARUIAbilityManagerComponent::SetInputTag(int32 SetIndex, int32 AbilityInde } void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 AbilitySet - , int32 AbilityIndex, const FGameplayTag& InputBinding) + , int32 AbilityIndex) { //fake implementation untill I add AssetManager support. APlayerController* MyPC = Cast(GetOwner()); @@ -131,14 +131,16 @@ void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbil UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); if (!AbilityComp) return; + if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARUIAbilityManagerComponent::OnAbilityReady)) { + FGameplayTag d = GetInputTag(AbilitySet, AbilityIndex); AbilityComp->OnAbilityAdded.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); } TSubclassOf AbilityClass = AbilityData->Items.FindRef(InAbilityTag).AbilityClass; - FARAbilityEquipInfo ABInfo(AbilitySet, AbilityIndex, InputBinding); + FARAbilityEquipInfo ABInfo(AbilitySet, AbilityIndex, GetInputTag(AbilitySet, AbilityIndex)); AwatingAbilityConfimation.Add(InAbilityTag, ABInfo); - AbilityComp->NativeAddAbility(AbilityClass, nullptr, InputBinding, false); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, GetInputTag(AbilitySet, AbilityIndex)); } void UARUIAbilityManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag) @@ -176,6 +178,8 @@ void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAb void UARUIAbilityManagerComponent::SwitchSet() { + //in reality it should be vlidated on server as well + //although this system is independent from ability component. APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) return; @@ -191,8 +195,8 @@ void UARUIAbilityManagerComponent::SwitchSet() if (ActiveSet == 0) { const TArray& AbilityTags = AbilityTagsSet[0]; - const TArray& InputTags = InputBindingsSet[0]; - const TArray& InputTags2 = InputBindingsSet[1]; + const FARAbilityInputBinding& InputTags = InputBindingsSet[0]; + const FARAbilityInputBinding InputTags2 = InputBindingsSet[1]; for (int32 Idx = 0; Idx < 6; Idx++) { AbilityComp->SetBlockedInput(InputTags[Idx], true); @@ -205,8 +209,8 @@ void UARUIAbilityManagerComponent::SwitchSet() else if (ActiveSet == 1) { const TArray& AbilityTags = AbilityTagsSet[1]; - const TArray& InputTags = InputBindingsSet[1]; - const TArray& InputTags2 = InputBindingsSet[0]; + const FARAbilityInputBinding& InputTags = InputBindingsSet[1]; + const FARAbilityInputBinding& InputTags2 = InputBindingsSet[0]; for (int32 Idx = 0; Idx < 6; Idx++) { AbilityComp->SetBlockedInput(InputTags[Idx], true); diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h index f84d815..de6ce94 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -29,6 +29,24 @@ struct FARAbilityEquipInfo InputBinding(InInputBinding) {}; }; +USTRUCT(BlueprintType) +struct FARAbilityInputBinding +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray InputBinding; + + inline FGameplayTag& operator[](int32 InIndex) + { + return InputBinding[InIndex]; + } + + inline const FGameplayTag& operator[](int32 InIndex) const + { + return InputBinding[InIndex]; + } +}; DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAROnAbilitySetChanged, int32, AbilitySet); UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent @@ -64,7 +82,9 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent TWeakObjectPtr WeaponFour; int32 ActiveSet; - TArray> InputBindingsSet; + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray InputBindingsSet; + TArray> AbilityTagsSet; TArray>> AbilitySet; TMap AwatingAbilityConfimation; @@ -98,7 +118,7 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent void SetInputTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag); void NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 AbilitySet - , int32 AbilityIndex, const FGameplayTag& InputBinding); + , int32 AbilityIndex); UFUNCTION() void OnAbilityReady(const FGameplayTag& InAbilityTag); From fb8b9b9bcf9575b68b1fa2cd8646cdb4e70efd7d Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 8 Aug 2017 23:52:57 +0200 Subject: [PATCH 011/187] New event handling system Some UI work, better async loading, fundamentals of new event system for effects which decouples events from effects, making it possible to replicate only minimal info effect back to clients. --- ActionRPGGame.uproject | 8 + .../DefaultEditorPerProjectUserSettings.ini | 2 + Config/DefaultEngine.ini | 8 +- Config/DefaultGameplayTags.ini | 10 + Config/DefaultInput.ini | 32 +-- .../Abilities/GAAbilityBase.cpp | 37 +++- .../Abilities/GAAbilityBase.h | 7 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 101 ++++++++-- .../AbilityFramework/Effects/GAGameEffect.h | 31 ++- Source/ActionRPGGame/ARPlayerController.cpp | 60 ++++++ Source/ActionRPGGame/ARPlayerController.h | 20 +- .../Abilities/ARAvailableAbilities.cpp | 7 + .../Abilities/ARAvailableAbilities.h | 22 +++ .../Attributes/ARCharacterAttributes.h | 5 +- Source/ActionRPGGame/UI/ARAbilityData.cpp | 16 -- Source/ActionRPGGame/UI/ARAbilityData.h | 34 ---- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 36 +--- Source/ActionRPGGame/UI/ARAbilityWidget.h | 18 +- .../ActionRPGGame/UI/ARUIWeaponEquipment.cpp | 184 ++++++++++++++++++ Source/ActionRPGGame/UI/ARUIWeaponEquipment.h | 65 +++++++ Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp | 21 +- Source/ActionRPGGame/UI/ARUMGWidgetBase.h | 10 +- .../UI/ARWeaponActriveInfoWidget.cpp | 52 +++++ .../UI/ARWeaponActriveInfoWidget.h | 26 +++ .../ActionRPGGame/UI/ARWeaponInfoWidget.cpp | 54 ++--- Source/ActionRPGGame/UI/ARWeaponInfoWidget.h | 16 +- .../UI/Abilities/ARAbilityInfoWidget.cpp | 70 ------- .../UI/Abilities/ARAbilityInfoWidget.h | 31 +-- .../Abilities/ARAbilitySlotConfigWidget.cpp | 46 +++++ .../UI/Abilities/ARAbilitySlotConfigWidget.h | 28 +++ .../Abilities/ARUIAbilityManagerComponent.cpp | 45 +++-- .../Abilities/ARUIAbilityManagerComponent.h | 11 +- 32 files changed, 810 insertions(+), 303 deletions(-) create mode 100644 Source/ActionRPGGame/Abilities/ARAvailableAbilities.cpp create mode 100644 Source/ActionRPGGame/Abilities/ARAvailableAbilities.h delete mode 100644 Source/ActionRPGGame/UI/ARAbilityData.cpp delete mode 100644 Source/ActionRPGGame/UI/ARAbilityData.h create mode 100644 Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp create mode 100644 Source/ActionRPGGame/UI/ARUIWeaponEquipment.h create mode 100644 Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp create mode 100644 Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 1fd8496..8c2397c 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -42,6 +42,14 @@ { "Name": "PerformanceMonitor", "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true } ] } \ No newline at end of file diff --git a/Config/DefaultEditorPerProjectUserSettings.ini b/Config/DefaultEditorPerProjectUserSettings.ini index 5e1c2fc..ac90d36 100644 --- a/Config/DefaultEditorPerProjectUserSettings.ini +++ b/Config/DefaultEditorPerProjectUserSettings.ini @@ -31,4 +31,6 @@ bEnableLiveRecompilationOfAnimationBlueprints=True bMobilePIEPreviewDeviceLaunch=False bAssetMaterialBaking=False +[/Script/SourceCodeAccess.SourceCodeAccessSettings] +PreferredAccessor=VisualStudio2017 diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 40dc7f4..e1d955a 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -21,6 +21,7 @@ r.DistanceFieldBuild.EightBit=True r.SupportStationarySkylight=False r.SupportLowQualityLightmaps=False r.ClearCoatNormal=True +r.DefaultFeature.LensFlare=True [/Script/Engine.StreamingSettings] s.AsyncLoadingThreadEnabled=True @@ -86,6 +87,9 @@ s.AsyncLoadingThreadEnabled=True [/Script/Engine.Engine] AssetManagerClassName=/Script/AbilityFramework.AFAssetManager +[/Script/Engine.UserInterfaceSettings] +bLoadWidgetsOnDedicatedServer=False + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -93,8 +97,8 @@ DefaultFluidFriction=0.300000 SimulateScratchMemorySize=262144 RagdollAggregateThreshold=4 TriangleMeshTriangleMinAreaThreshold=5.000000 -bEnableAsyncScene=False -bEnableShapeSharing=False +bEnableAsyncScene=True +bEnableShapeSharing=True bEnablePCM=True bEnableStabilization=False bWarnMissingLocks=True diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 5e41ffd..83e8791 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -10,23 +10,33 @@ NetIndexFirstBitSegment=16 -GameplayTagList=(Tag="Ability.Rifle",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") +-GameplayTagList=(Tag="Ability.Rifle.Reload",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +-GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") +-GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") -GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") -GameplayTagList=(Tag="Damage",DevComment="") -GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") -GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") -GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") +-GameplayTagList=(Tag="Input.UI.WeaponNext",DevComment="") +-GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.Rifle",DevComment="") ++GameplayTagList=(Tag="Ability.Rifle.Activate",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Reload",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") ++GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") ++GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +GameplayTagList=(Tag="Damage",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") ++GameplayTagList=(Tag="Input.UI.WeaponNext",DevComment="") ++GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index c197740..b574e20 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -6,6 +6,12 @@ -AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) -AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) -AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) +-AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +-AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) @@ -21,12 +27,12 @@ -AxisConfig=(AxisKeyName="MouseWheelAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_LeftTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -AxisConfig=(AxisKeyName="Gamepad_RightTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) ++AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) @@ -42,12 +48,6 @@ +AxisConfig=(AxisKeyName="MouseWheelAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="Gamepad_LeftTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="Gamepad_RightTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) -+AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) bAltEnterTogglesFullscreen=True bF11TogglesFullscreen=True bUseMouseForTouch=False @@ -64,13 +64,19 @@ DefaultViewportMouseLockMode=LockOnCapture -ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="SwitchAbilitySet",Key=Tilde,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="SwitchAbilitySet",Key=B,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="ShowHideAbilities",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +-ActionMappings=(ActionName="PreviousWeapon",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="SwitchAbilitySet",Key=B,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="ShowHideAbilities",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Input.UI.WeaponPrevious",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) -AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) -AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 55fb291..e96547a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -175,7 +175,7 @@ void UGAAbilityBase::OnCooldownEffectExpired() } } /* Functions for activation effect delegates */ -void UGAAbilityBase::NativeOnAbilityActivationFinish(const FGAEffectHandle& InHandle) +void UGAAbilityBase::NativeOnAbilityActivationFinish(FGAEffectHandle InHandle) { UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); OnActivationFinished(); @@ -193,7 +193,7 @@ void UGAAbilityBase::NativeOnAbilityActivationCancel() OnActivationCancel(); //AbilityActivatedCounter++; } -void UGAAbilityBase::OnActivationEffectPeriod(const FGAEffectHandle& InHandle) +void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) { UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); @@ -255,11 +255,15 @@ bool UGAAbilityBase::ApplyCooldownEffect() return false; } FAFFunctionModifier Modifier; + + //FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnCooldownEnd, CooldownEffectHandle); + //AbilityComponent->AddEffectEvent(CooldownEffect.GetSpec()->OnPeriodEvent, PeriodDel); + CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, this, POwner, this, Modifier); OnCooldownStart(); - CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); + //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); return false; } bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) @@ -282,18 +286,23 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) if (ActivationEffectHandle.IsValid()) ActivationEffectHandle.Reset(); + FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); + AbilityComponent->AddEffectEvent(ActivationEffect.GetSpec()->OnAppliedEvent, AppliedDel); + FAFFunctionModifier Modifier; ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(ActivationEffect, this, POwner, this, Modifier); //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) - ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); + // ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); if (PeriodCheck > 0) { + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); + AbilityComponent->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) - ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); + // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); } } else @@ -313,6 +322,20 @@ bool UGAAbilityBase::CanUseAbility() CanUse = !bIsOnCooldown && !bIsActivating; + //now Lets check tags + if (CanUse) + { + if (AbilityComponent->HasAll(ActivationRequiredTags)) + { + CanUse = true; + } + //blocking takes precedence. + if (AbilityComponent->HasAny(ActivationBlockedTags)) + { + CanUse = false; + } + } + return CanUse; } @@ -457,6 +480,10 @@ bool UGAAbilityBase::IsActivating() bAbilityActivating = AbilityComponent->IsEffectActive(ActivationEffect.Handle) || AbilityState == EAFAbilityState::Activating; return bAbilityActivating; //temp } +bool UGAAbilityBase::BP_IsOnCooldown() +{ + return IsOnCooldown(); +} void UGAAbilityBase::BP_ApplyCooldown() { ApplyCooldownEffect(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 915002e..23a5e5c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -247,7 +247,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask float LastCooldownTime; virtual void TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction); UFUNCTION() - void OnActivationEffectPeriod(const FGAEffectHandle& InHandle); + void OnActivationEffectPeriod(FGAEffectHandle InHandle); /* Replication counters for above events. */ @@ -357,7 +357,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION() void OnCooldownEffectExpired(); UFUNCTION() - void NativeOnAbilityActivationFinish(const FGAEffectHandle& InHandle); + void NativeOnAbilityActivationFinish(FGAEffectHandle InHandle); UFUNCTION() void NativeOnAbilityActivationCancel(); @@ -429,6 +429,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask bool IsOnCooldown(); bool IsActivating(); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Is On Cooldown"), Category = "AbilityFramework|Abilities") + bool BP_IsOnCooldown(); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Cooldown"), Category = "AbilityFramework|Abilities") void BP_ApplyCooldown(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 914d837..b6b8953 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -33,29 +33,73 @@ void FGAEffectProperty::InitializeIfNotInitialized() Initialize(); } } +FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, + class UAFAbilityComponent* InComponent) + : AppliedTime(AppliedTimeIn), + PeriodTime(PeriodTimeIn), + Duration(DurationIn), + ReplicationTime(ReplicationTimeIn), + OwningComoponent(InComponent) +{ -void FAFEffectRepInfo::OnApplied() +}; +void FAFEffectRepInfo::Init() { + FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnExpired); + Timer.SetTimer(ExpiredHandle, delDuration, + Duration, false); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnPeriod); + Timer.SetTimer(PeriodHandle, PeriodDuration, + PeriodTime, true); +} +void FAFEffectRepInfo::OnExpired() +{ + OwningComoponent->ExecuteEffectEvent(OnAppliedEvent); } void FAFEffectRepInfo::OnPeriod() { - + OwningComoponent->ExecuteEffectEvent(OnPeriodEvent); } void FAFEffectRepInfo::OnRemoved() { - + FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); + Timer.ClearTimer(ExpiredHandle); + Timer.ClearTimer(PeriodHandle); + OwningComoponent->RemoveEffectEvent(OnAppliedEvent); + OwningComoponent->RemoveEffectEvent(OnPeriodEvent); + OwningComoponent->RemoveEffectEvent(OnRemovedEvent); } void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) { InArraySerializer.EffectInfos.Remove(Handle); - InArraySerializer.OwningComponent->OnEffectRepInfoRemoved.Broadcast(this); + //InArraySerializer.OwningComponent->OnEffectRepInfoRemoved.Broadcast(this); + + OwningComoponent->RemoveEffectEvent(OnAppliedEvent); + OwningComoponent->RemoveEffectEvent(OnPeriodEvent); + OwningComoponent->RemoveEffectEvent(OnRemovedEvent); } void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) { + OwningComoponent = InArraySerializer.OwningComponent; InArraySerializer.EffectInfos.Add(Handle, this); InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); + + //OwningComoponent->ExecuteEffectEvent(OnAppliedEvent); + + FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnExpired); + Timer.SetTimer(ExpiredHandle, delDuration, + Duration, false); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnPeriod); + Timer.SetTimer(PeriodHandle, PeriodDuration, + PeriodTime, true); + } void FAFEffectRepInfo::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) { @@ -313,6 +357,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr bool bHasDuration = InProperty.Duration > 0; bool bHasPeriod = InProperty.Period > 0; + //we should not generate handle on clients. if (bHasDuration || bHasPeriod) { Handle = FGAEffectHandle::GenerateHandle(EffectIn); @@ -371,18 +416,45 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr } void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) { - //if (EffectPtr.IsValid() && EffectSpec && EffectSpec->EffectCue) + ENetMode mode = OwningComponent->GetNetMode(); + ENetRole role = OwningComponent->GetOwnerRole(); + if (mode == ENetMode::NM_DedicatedServer) { const UWorld* World = OwningComponent->GetWorld(); - FAFEffectRepInfo RepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0); - RepInfo.Handle = InHandle; - MarkItemDirty(RepInfo); - ActiveEffectInfos.Add(RepInfo); + FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); + RepInfo->OnAppliedEvent = InProperty.GetSpec()->OnAppliedEvent; + RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; + RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; + RepInfo->Handle = InHandle; + RepInfo->Init(); + MarkItemDirty(*RepInfo); + ActiveEffectInfos.Add(*RepInfo); MarkArrayDirty(); - ENetMode mode = OwningComponent->GetNetMode(); - if (mode == ENetMode::NM_Standalone) + + //predictevily add effect info ? + //if (mode == ENetMode::NM_Standalone + // || role == ENetRole::ROLE_Authority) + { + EffectInfos.Add(InHandle, RepInfo); + } + } + else if(mode == ENetMode::NM_Standalone) + { + + const UWorld* World = OwningComponent->GetWorld(); + FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); + RepInfo->OnAppliedEvent = InProperty.GetSpec()->OnAppliedEvent; + RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; + RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; + RepInfo->Handle = InHandle; + RepInfo->Init(); + //MarkItemDirty(RepInfo); + ActiveEffectInfos.Add(*RepInfo); + //MarkArrayDirty(); + + //predictevily add effect info ? { - EffectInfos.Add(InHandle, new FAFEffectRepInfo(RepInfo)); + EffectInfos.Add(InHandle, RepInfo); } } } @@ -617,7 +689,7 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N UGAGameEffectSpec* Spec = HandleIn.Spec; EGAEffectAggregation Aggregation = Spec->EffectAggregation; TArray* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); - FAFEffectRepInfo* Out; + FAFEffectRepInfo* Out = nullptr; if (handles) @@ -632,7 +704,10 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N EffectInfos.RemoveAndCopyValue(OutHandle, Out); if (Out) { + MarkItemDirty(*Out); + Out->OnRemoved(); ActiveEffectInfos.Remove(*Out); + MarkArrayDirty(); delete Out; } if (!ActiveEffectHandles.Contains(OutHandle)) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 0b7150a..8e62007 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -199,6 +199,12 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject UPROPERTY(EditAnywhere, Category = "Linked Effects") TArray> OnRemovedEffects; + UPROPERTY(EditAnywhere, Category = "Event Tags") + FGameplayTag OnAppliedEvent; + UPROPERTY(EditAnywhere, Category = "Event Tags") + FGameplayTag OnPeriodEvent; + UPROPERTY(EditAnywhere, Category = "Event Tags") + FGameplayTag OnRemovedEvent; /* Effects applied only when certain criteria are met. Just dumbed here it needs it's own structure that will actually alow to setup those conditions. @@ -588,6 +594,9 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem GENERATED_USTRUCT_BODY() public: + //tags are generally unique per effect type. + UPROPERTY() + FGameplayTag EffectTag; //Handle to effect, which is using this info. UPROPERTY() FGAEffectHandle Handle; @@ -600,12 +609,22 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem UPROPERTY() float ReplicationTime; - FSimpleDelegate OnAppliedDelegate; + UPROPERTY() + FGameplayTag OnAppliedEvent; + UPROPERTY() + FGameplayTag OnPeriodEvent; + UPROPERTY() + FGameplayTag OnRemovedEvent; + + FTimerHandle ExpiredHandle; + FTimerHandle PeriodHandle; + class UAFAbilityComponent* OwningComoponent; //UPROPERTY() // FGAEffectContext Context; - void OnApplied(); + void Init(); + void OnExpired(); void OnPeriod(); void OnRemoved(); @@ -647,12 +666,8 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem return Handle == Other.Handle; } - FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn) - : AppliedTime(AppliedTimeIn), - PeriodTime(PeriodTimeIn), - Duration(DurationIn), - ReplicationTime(ReplicationTimeIn) - {}; + FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, + class UAFAbilityComponent* InComponent); }; USTRUCT() diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index b906635..0f7e369 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -3,21 +3,81 @@ #include "ARPlayerController.h" #include "ARUIComponent.h" #include "ARUIAbilityManagerComponent.h" +#include "ARUIWeaponEquipment.h" +#include "AFAbilityComponent.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" +#include "ARAbilityBase.h" AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); UIAbilityManagerComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIAbilityManagerComponent"); + UIWeaponEquipment = ObjectInitializer.CreateDefaultSubobject(this, "UIWeaponEquipment"); +} + +void AARPlayerController::SetPawn(APawn* InPawn) +{ + Super::SetPawn(InPawn); + ENetMode NetMode = GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + IAFAbilityInterface* ABInt = Cast(GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); + AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); + + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); + AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); + AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr, /*Input*/ InputNextWeapon); + + FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); + AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); + AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, /*Input*/ InputPreviousWeapon); + } } void AARPlayerController::SetupInputComponent() { Super::SetupInputComponent(); InputComponent->BindAction("SwitchAbilitySet", IE_Pressed, this, &AARPlayerController::InputSwitchAbilitySet); + //InputComponent->BindAction("NextWeapon", IE_Pressed, this, &AARPlayerController::InputNextWeapon); + //InputComponent->BindAction("PreviousWeapon", IE_Pressed, this, &AARPlayerController::InputPreviousWeapon); + } void AARPlayerController::InputSwitchAbilitySet() { UIAbilityManagerComponent->SwitchSet(); +} + +//void AARPlayerController::InputNextWeapon() +//{ +// UIWeaponEquipment->NextWeapon(); +//} +//void AARPlayerController::InputPreviousWeapon() +//{ +// UIWeaponEquipment->PreviousWeapon(); +//} +void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) +{ + IAFAbilityInterface* ABInt = Cast(GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + + AbilityComp->SetAbilityToAction(InAbilityTag, InInputTag); } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 53efc3e..9008955 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "GameFramework/PlayerController.h" +#include "GameplayTags.h" #include "ARPlayerController.generated.h" /** @@ -18,11 +19,28 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController class UARUIComponent* UIComponent; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIAbilityManagerComponent* UIAbilityManagerComponent; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UARUIWeaponEquipment* UIWeaponEquipment; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag InputNextWeapon; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag AbilitytNextWeapon; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag InputPreviousWeapon; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag AbilitytPreviousWeapon; public: AARPlayerController(const FObjectInitializer& ObjectInitializer); - + virtual void SetPawn(APawn* InPawn) override; void SetupInputComponent(); void InputSwitchAbilitySet(); + +// void InputNextWeapon(); + //void InputPreviousWeapon(); + + void OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag); }; diff --git a/Source/ActionRPGGame/Abilities/ARAvailableAbilities.cpp b/Source/ActionRPGGame/Abilities/ARAvailableAbilities.cpp new file mode 100644 index 0000000..2b9557c --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAvailableAbilities.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAvailableAbilities.h" + + + + diff --git a/Source/ActionRPGGame/Abilities/ARAvailableAbilities.h b/Source/ActionRPGGame/Abilities/ARAvailableAbilities.h new file mode 100644 index 0000000..59e9d13 --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAvailableAbilities.h @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "ARAvailableAbilities.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType) +class ACTIONRPGGAME_API UARAvailableAbilities : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly) + TArray Abilities; + + +}; diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h index 5c2f174..690d68e 100644 --- a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h @@ -30,5 +30,8 @@ class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase FAFAttributeBase Ammo; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase MachineGunAmmo; - + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase ShotgunAmmo; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase ArrowAmmo; }; diff --git a/Source/ActionRPGGame/UI/ARAbilityData.cpp b/Source/ActionRPGGame/UI/ARAbilityData.cpp deleted file mode 100644 index d5afc87..0000000 --- a/Source/ActionRPGGame/UI/ARAbilityData.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityData.h" - - - - -TArray UARAbilityData::GetAbilitiesTags() -{ - TArray Out; - for (auto It = Items.CreateIterator(); It; ++It) - { - Out.Add(It->Key); - } - return Out; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityData.h b/Source/ActionRPGGame/UI/ARAbilityData.h deleted file mode 100644 index d63d87b..0000000 --- a/Source/ActionRPGGame/UI/ARAbilityData.h +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Engine/DataAsset.h" -#include "GameplayTags.h" -#include "ARAbilityData.generated.h" - -USTRUCT() -struct FARAbilityItem -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TSubclassOf AbilityClass; - UPROPERTY(EditAnywhere) - bool bIsAvailable; - }; - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityData : public UDataAsset -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TMap Items; - - UFUNCTION(BlueprintCallable) - TArray GetAbilitiesTags(); -}; diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index d3d7a07..5d527c5 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -98,7 +98,7 @@ UTexture2D* UARAbilityWidget::GetIcon() void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) { AbilityTag = InAbility; - FAssetData AssetData = FARGlobals::GetAbilityAssetByTag(AbilityTag); + FAssetData AssetData = FARGlobals::GetAbilityAssetByTag(InAbility); TSubclassOf cls;// = nullptr; if (AssetData.IsValid()) { @@ -134,37 +134,3 @@ void UARAbilityWidget::OnFinishedLoad(FPrimaryAssetId PrimaryAssetId) } } } -FReply UARAbilityWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) -{ - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; - //return FReply::Unhandled(); -} - -void UARAbilityWidget::NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) -{ - UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); - if (DragDropOp) - { - APlayerController* MyPC = Cast(OwningComponent->GetOwner()); - UARAbilityWidget* DragIcon = CreateWidget(MyPC, OwningComponent->DragVisualClass); - DragIcon->AbilityIndex = AbilityIndex; - DragIcon->AbilitySetIndex = AbilitySetIndex; - DragIcon->OwningComponent = OwningComponent; - - DragDropOp->Payload = this; - DragDropOp->DefaultDragVisual = DragIcon; - - OutOperation = DragDropOp; - } -} -bool UARAbilityWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - UARAbilityWidget* Payload = Cast(InOperation->Payload); - Setbility(Payload->AbilityTag); - - OwningComponent->NativeEquipAbility(Payload->AbilityTag, AbilitySetIndex, AbilityIndex); - return false; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index 687709e..aeaaa0a 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -3,7 +3,7 @@ #pragma once #include "CoreMinimal.h" -#include "ARAbilityInfoWidget.h" +#include "ARUMGWidgetBase.h" #include "GameplayTags.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" @@ -13,23 +13,19 @@ * */ UCLASS() -class ACTIONRPGGAME_API UARAbilityWidget : public UARAbilityInfoWidget +class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase { GENERATED_BODY() public: + UPROPERTY(EditAnywhere, Category = "Config") int32 AbilitySetIndex; UPROPERTY(EditAnywhere, Category = "Config") int32 AbilityIndex; - UPROPERTY(EditAnywhere, Category = "Config") - FGameplayTag InputBinding; - UPROPERTY(EditAnywhere, Category = "Config") UTexture2D* Icon; - - //debug UPROPERTY(EditAnywhere, Category = "Config") - FGameplayTag AbilityTagDebug; + FGameplayTag AbilityTag; UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") float GetActivationRemainingTime(); @@ -61,10 +57,4 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARAbilityInfoWidget UFUNCTION() void OnFinishedLoad(FPrimaryAssetId PrimaryAssetId); - virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) override; - virtual void NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; - virtual bool NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; }; diff --git a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp new file mode 100644 index 0000000..04a3435 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp @@ -0,0 +1,184 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARUIWeaponEquipment.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +// Sets default values for this component's properties +UARUIWeaponEquipment::UARUIWeaponEquipment() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + Weapons.SetNum(4); + // ... +} + + +// Called when the game starts +void UARUIWeaponEquipment::BeginPlay() +{ + Super::BeginPlay(); + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + AbilityComp->BindAbilityToAction(InputComponent, ShootInput); + AbilityComp->BindAbilityToAction(InputComponent, ReloadInput); + // ... + +} + + +// Called every frame +void UARUIWeaponEquipment::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + // ... +} + +void UARUIWeaponEquipment::NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UARUIWeaponEquipment::OnWeaponReady, InAbilityTag, SlotIndex); + AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, /*Input*/ ShootInput); +} + +void UARUIWeaponEquipment::OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + if (SlotIndex == 0) + { + Weapons[SlotIndex] = Ability; + ActiveWeapon = Ability; + ActiveWeaponIndex = SlotIndex; + AbilityComp->SetAbilityToAction(InAbilityTag, ShootInput); + AbilityComp->SetAbilityToAction(InAbilityTag, ReloadInput); + } + else + { + Weapons[SlotIndex] = Ability; + } +} +void UARUIWeaponEquipment::BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) +{ + NativeEquipWeapon(InAbilityTag, SlotIndex); +} + +void UARUIWeaponEquipment::NextWeapon() +{ + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + ActiveWeaponIndex++; + if (ActiveWeaponIndex < 4) + { + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + ServerNextWeapon(ActiveWeaponIndex); + } + +} +void UARUIWeaponEquipment::PreviousWeapon() +{ + ActiveWeaponIndex--; + if (ActiveWeaponIndex >= 0) + { + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + ServerPreviousWeapon(ActiveWeaponIndex); +} + +void UARUIWeaponEquipment::ServerNextWeapon_Implementation(int32 WeaponIndex) +{ + ActiveWeaponIndex++; + if (ActiveWeaponIndex < 4) + { + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + //so Server index is different. Client might tried to cheat + //or sometrhing. We will override it. + //situation where client can chage multiple weapons within second + //should not have place, as there is animation and/or internal cooldown on weapon change. + //since it will be done trough ability. + if (ActiveWeaponIndex != WeaponIndex) + { + ClientNextWeapon(ActiveWeaponIndex); + } +} +bool UARUIWeaponEquipment::ServerNextWeapon_Validate(int32 WeaponIndex) +{ + return true; +} +void UARUIWeaponEquipment::ClientNextWeapon_Implementation(int32 WeaponIndex) +{ + ActiveWeaponIndex = WeaponIndex; + ActiveWeapon = Weapons[ActiveWeaponIndex]; +} +void UARUIWeaponEquipment::ServerPreviousWeapon_Implementation(int32 WeaponIndex) +{ + ActiveWeaponIndex--; + if (ActiveWeaponIndex >= 0) + { + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + ActiveWeapon = Weapons[ActiveWeaponIndex]; + } + if (ActiveWeaponIndex != WeaponIndex) + { + + } +} +bool UARUIWeaponEquipment::ServerPreviousWeapon_Validate(int32 WeaponIndex) +{ + return true; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.h b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.h new file mode 100644 index 0000000..51e1b5d --- /dev/null +++ b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.h @@ -0,0 +1,65 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "ARAbilityBase.h" +#include "ARUIWeaponEquipment.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARUIWeaponEquipment : public UActorComponent +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Input") + FGameplayTag ShootInput; + UPROPERTY(EditAnywhere, Category = "Input") + FGameplayTag ReloadInput; + /* + Weapons which are currently equiped. + */ + TArray> Weapons; + + /* + Weapon which is currently active. (equiped). + */ + TWeakObjectPtr ActiveWeapon; + int32 ActiveWeaponIndex; +public: + // Sets default values for this component's properties + UARUIWeaponEquipment(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + void NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); + UFUNCTION() + void OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex); + UFUNCTION(BlueprintCallable, meta=(DisplayName = "Equip Weapon"), Category = "ActionRPGGame|UI|Weapon") + void BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); + UFUNCTION(BlueprintCallable) + void NextWeapon(); + UFUNCTION(BlueprintCallable) + void PreviousWeapon(); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNextWeapon(int32 WeaponIndex); + void ServerNextWeapon_Implementation(int32 WeaponIndex); + bool ServerNextWeapon_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientNextWeapon(int32 WeaponIndex); + void ClientNextWeapon_Implementation(int32 WeaponIndex); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerPreviousWeapon(int32 WeaponIndex); + void ServerPreviousWeapon_Implementation(int32 WeaponIndex); + bool ServerPreviousWeapon_Validate(int32 WeaponIndex); +}; diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp b/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp index 2bdebe0..a67fcaa 100644 --- a/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp +++ b/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp @@ -1,7 +1,26 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARUMGWidgetBase.h" +#include "ARUIAbilityManagerComponent.h" +#include "ARPlayerController.h" - +void UARUMGWidgetBase::NativePreConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + OwningComponent = MyPC->UIAbilityManagerComponent; + UIComponent = MyPC->UIComponent; + } + Super::NativePreConstruct(); +} +void UARUMGWidgetBase::NativeConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + OwningComponent = MyPC->UIAbilityManagerComponent; + UIComponent = MyPC->UIComponent; + } + Super::NativeConstruct(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.h b/Source/ActionRPGGame/UI/ARUMGWidgetBase.h index 9f1fe0d..0ed49ef 100644 --- a/Source/ActionRPGGame/UI/ARUMGWidgetBase.h +++ b/Source/ActionRPGGame/UI/ARUMGWidgetBase.h @@ -13,8 +13,14 @@ UCLASS() class ACTIONRPGGAME_API UARUMGWidgetBase : public UUserWidget { GENERATED_BODY() - - +public: + UPROPERTY(BlueprintReadOnly) + class UARUIAbilityManagerComponent* OwningComponent; + UPROPERTY(BlueprintReadOnly) + class UARUIComponent* UIComponent; +public: + virtual void NativePreConstruct() override; + virtual void NativeConstruct() override; }; diff --git a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp new file mode 100644 index 0000000..821b814 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp @@ -0,0 +1,52 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponActriveInfoWidget.h" +#include "ARPlayerController.h" +#include "ARUIWeaponEquipment.h" +#include "ARAbilityBase.h" +#include "ARGunAttributes.h" + + + +float UARWeaponActriveInfoWidget::GetActiveMagazineAmmo() +{ + if (!WeaponEquipement.IsValid()) + return 0; + UARAbilityBase* Ability = WeaponEquipement->ActiveWeapon.Get(); + if (!Ability) + return 0; + + if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) + { + return Attributes->Magazine.GetCurrentValue(); + } + return 0; +} + +float UARWeaponActriveInfoWidget::GetActiveMagazineAmmoNormalized() +{ + if (!WeaponEquipement.IsValid()) + return 0; + UARAbilityBase* Ability = WeaponEquipement->ActiveWeapon.Get(); + if (!Ability) + return 0; + + if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) + { + float CurrentValue = Attributes->Magazine.GetCurrentValue(); + FVector2D Input(0, Attributes->Magazine.GetFinalValue()); + return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); + } + return 0; +} + +float UARWeaponActriveInfoWidget::GetReloadTimeNormalized() +{ + if (!WeaponEquipement.IsValid()) + return 0; + UARAbilityBase* Ability = WeaponEquipement->ActiveWeapon.Get(); + if (!Ability) + return 0; + + return Ability->GetCooldownRemainingTimeNormalized(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h new file mode 100644 index 0000000..c324325 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARWeaponInfoWidget.h" +#include "ARWeaponActriveInfoWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponActriveInfoWidget : public UARWeaponInfoWidget +{ + GENERATED_BODY() + +public: + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") + float GetActiveMagazineAmmo(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") + float GetActiveMagazineAmmoNormalized(); + + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") + float GetReloadTimeNormalized(); + +}; diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp index f38ee04..a4354c7 100644 --- a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp +++ b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp @@ -1,40 +1,50 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARWeaponInfoWidget.h" - - -void UARWeaponInfoWidget::InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) +#include "ARPlayerController.h" +#include "ARUIWeaponEquipment.h" +#include "ARAbilityBase.h" +#include "ARGunAttributes.h" +void UARWeaponInfoWidget::NativePreConstruct() { - Super::InitializeWidget(InOwningComponent); + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + WeaponEquipement = MyPC->UIWeaponEquipment; + } + Super::NativePreConstruct(); } - -void UARWeaponInfoWidget::NativeAddAbility(const FGameplayTag& InAbilityTag) +void UARWeaponInfoWidget::NativeConstruct() { - Super::NativeAddAbility(InAbilityTag); -} -void UARWeaponInfoWidget::NativeOnAbilityReady(const FGameplayTag& InAbilityTag) -{ - Super::NativeOnAbilityReady(InAbilityTag); - - WeaponAttributes = Ability->GetAttributesTyped(); + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + WeaponEquipement = MyPC->UIWeaponEquipment; + } + Super::NativeConstruct(); } float UARWeaponInfoWidget::GetMagazineAmmo() { - if (!WeaponAttributes) + UARAbilityBase* Ability = WeaponEquipement->Weapons[SlotIndex].Get(); + if (!Ability) return 0; - return WeaponAttributes->Magazine.GetCurrentValue(); - + if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) + { + return Attributes->Magazine.GetCurrentValue(); + } + return 0; } float UARWeaponInfoWidget::GetMagazineAmmoNormalized() { - if (!WeaponAttributes) + UARAbilityBase* Ability = WeaponEquipement->Weapons[SlotIndex].Get(); + if (!Ability) return 0; - float CurrentValue = WeaponAttributes->Magazine.GetCurrentValue(); - FVector2D Input(0, WeaponAttributes->Magazine.GetFinalValue()); - - return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); - + if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) + { + float CurrentValue = Attributes->Magazine.GetCurrentValue(); + FVector2D Input(0, Attributes->Magazine.GetFinalValue()); + return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); + } + return 0; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h index 36bfbcb..1086537 100644 --- a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h +++ b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h @@ -3,7 +3,7 @@ #pragma once #include "CoreMinimal.h" -#include "UI/Abilities/ARAbilityInfoWidget.h" +#include "ARUMGWidgetBase.h" #include "ARGunAttributes.h" #include "ARWeaponInfoWidget.generated.h" @@ -11,16 +11,18 @@ * */ UCLASS() -class ACTIONRPGGAME_API UARWeaponInfoWidget : public UARAbilityInfoWidget +class ACTIONRPGGAME_API UARWeaponInfoWidget : public UARUMGWidgetBase { GENERATED_BODY() protected: - class UARGunAttributes* WeaponAttributes; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + int32 SlotIndex; + TWeakObjectPtr WeaponEquipement; public: - virtual void InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) override; - virtual void NativeAddAbility(const FGameplayTag& InAbilityTag) override; - virtual void NativeOnAbilityReady(const FGameplayTag& InAbilityTag) override; - + + virtual void NativePreConstruct() override; + virtual void NativeConstruct() override; + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") float GetMagazineAmmo(); UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp index 327626a..112a552 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp @@ -6,73 +6,3 @@ #include "ARUIAbilityManagerComponent.h" #include "Abilities/GAAbilityBase.h" #include "ARPlayerController.h" - -void UARAbilityInfoWidget::NativePreConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - OwningComponent = MyPC->UIAbilityManagerComponent; - } - Super::NativePreConstruct(); -} -void UARAbilityInfoWidget::NativeConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - OwningComponent = MyPC->UIAbilityManagerComponent; - } - Super::NativeConstruct(); -} - -void UARAbilityInfoWidget::InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) -{ - OwningComponent = InOwningComponent; -} -void UARAbilityInfoWidget::NativeAddAbility(const FGameplayTag& InAbilityTag) -{ - IAFAbilityInterface* ABInt = Cast(GetOwningPlayer()->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARAbilityInfoWidget::OnAbilityReady)) - { - AbilityComp->OnAbilityAdded.AddDynamic(this, &UARAbilityInfoWidget::OnAbilityReady); - } - AbilityTag = InAbilityTag; - TSubclassOf AbilityClass = OwningComponent->AbilityData->Items.FindRef(InAbilityTag).AbilityClass; - AbilityComp->NativeAddAbility(AbilityClass, nullptr, FGameplayTag(), false); -} -void UARAbilityInfoWidget::NativeOnAbilityReady(const FGameplayTag& InAbilityTag) -{ - if (AbilityTag != InAbilityTag) - { - return; - } - IAFAbilityInterface* ABInt = Cast(GetOwningPlayer()->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - BP_OnAbilityReady(InAbilityTag); - Ability = AbilityComp->BP_GetAbilityByTag(InAbilityTag); -} -void UARAbilityInfoWidget::AddAbility(const FGameplayTag& InAbilityTag) -{ - NativeAddAbility(InAbilityTag); -} -void UARAbilityInfoWidget::BP_InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent) -{ - InitializeWidget(InOwningComponent); -} -void UARAbilityInfoWidget::OnAbilityReady(const FGameplayTag& InAbilityTag) -{ - NativeOnAbilityReady(InAbilityTag); -} - diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h index cc3a80f..0e652c2 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h @@ -4,41 +4,16 @@ #include "CoreMinimal.h" #include "Blueprint/UserWidget.h" +#include "ARUMGWidgetBase.h" #include "GameplayTags.h" #include "Abilities/GAAbilityBase.h" +#include "ARAbilityWidget.h" #include "ARAbilityInfoWidget.generated.h" - /** * */ UCLASS() -class ACTIONRPGGAME_API UARAbilityInfoWidget : public UUserWidget +class ACTIONRPGGAME_API UARAbilityInfoWidget : public UARAbilityWidget { GENERATED_BODY() -protected: - UPROPERTY() - FGameplayTag AbilityTag; - UPROPERTY() - class UGAAbilityBase* Ability; - UPROPERTY(BlueprintReadOnly) - class UARUIAbilityManagerComponent* OwningComponent; - -public: - virtual void NativePreConstruct() override; - virtual void NativeConstruct() override; - - virtual void InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent); - virtual void NativeAddAbility(const FGameplayTag& InAbilityTag); - virtual void NativeOnAbilityReady(const FGameplayTag& InAbilityTag); - UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|UI|Abilities") - void AddAbility(const FGameplayTag& InAbilityTag); - UFUNCTION(BlueprintCallable, DisplayName = "Initialize Ability Widget", Category = "ActionRPGGame|UI|Abilities") - void BP_InitializeWidget(UARUIAbilityManagerComponent* InOwningComponent); - UFUNCTION() - void OnAbilityReady(const FGameplayTag& InAbilityTag); - UFUNCTION(BlueprintImplementableEvent, DisplayName = "On Ability Ready", Category = "ActionRPGGame|UI|Abilities") - void BP_OnAbilityReady(const FGameplayTag& OutAbilityTag); - - - }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp new file mode 100644 index 0000000..680da53 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp @@ -0,0 +1,46 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilitySlotConfigWidget.h" +#include "Input/Reply.h" +#include "Input/Events.h" +#include "Blueprint/WidgetBlueprintLibrary.h" +#include "ARGlobals.h" +#include "AFAbilityComponent.h" +#include "ARUIAbilityManagerComponent.h" +#include "Abilities/GAAbilityBase.h" + + +FReply UARAbilitySlotConfigWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) +{ + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + //return FReply::Unhandled(); +} + +void UARAbilitySlotConfigWidget::NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) +{ + UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); + if (DragDropOp) + { + APlayerController* MyPC = Cast(OwningComponent->GetOwner()); + UARAbilityWidget* DragIcon = CreateWidget(MyPC, OwningComponent->DragVisualClass); + DragIcon->AbilityIndex = AbilityIndex; + DragIcon->AbilitySetIndex = AbilitySetIndex; + DragIcon->OwningComponent = OwningComponent; + + DragDropOp->Payload = this; + DragDropOp->DefaultDragVisual = DragIcon; + + OutOperation = DragDropOp; + } +} +bool UARAbilitySlotConfigWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UARAbilityWidget* Payload = Cast(InOperation->Payload); + Setbility(Payload->AbilityTag); + + OwningComponent->NativeEquipAbility(Payload->AbilityTag, AbilitySetIndex, AbilityIndex); + return false; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h new file mode 100644 index 0000000..9f91bee --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARAbilityWidget.h" +#include "ARAbilitySlotConfigWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilitySlotConfigWidget : public UARAbilityWidget +{ + GENERATED_BODY() +public: + + UPROPERTY(EditAnywhere, Category = "Config") + FGameplayTag InputBinding; +public: + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) override; + virtual void NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; + virtual bool NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; + +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index 8c7c9de..e8fd90c 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -38,28 +38,32 @@ void UARUIAbilityManagerComponent::BeginPlay() ActiveSet = 0; - - if (AbilitySetConfigClass) - { - AbilitySetConfigWidget = CreateWidget(Cast(GetOwner()), AbilitySetConfigClass); - //AbilitySetConfigWidget->InitializeWidget(this); - AbilitySetConfigWidget->AddToViewport(); - } - if (AbilityWidgetClass) - { - AbilityWidget = CreateWidget(Cast(GetOwner()), AbilityWidgetClass); - AbilityWidget->InitializeWidget(this); - } - if (WeaponWidgetClass) + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) { - WeaponWidget = CreateWidget(Cast(GetOwner()), WeaponWidgetClass); - WeaponWidget->InitializeWidget(this); - } + if (AbilitySetConfigClass) + { + AbilitySetConfigWidget = CreateWidget(Cast(GetOwner()), AbilitySetConfigClass); + //AbilitySetConfigWidget->InitializeWidget(this); + AbilitySetConfigWidget->AddToViewport(); + } + if (AbilityWidgetClass) + { + AbilityWidget = CreateWidget(Cast(GetOwner()), AbilityWidgetClass); + //AbilityWidget->InitializeWidget(this); + } + if (WeaponWidgetClass) + { + WeaponWidget = CreateWidget(Cast(GetOwner()), WeaponWidgetClass); + //WeaponWidget->InitializeWidget(this); + } - if (WeaponCrosshairWidgetClass) - { - WeaponCrosshairWidget = CreateWidget(Cast(GetOwner()), WeaponCrosshairWidgetClass); - WeaponCrosshairWidget->AddToViewport(); + if (WeaponCrosshairWidgetClass) + { + WeaponCrosshairWidget = CreateWidget(Cast(GetOwner()), WeaponCrosshairWidgetClass); + WeaponCrosshairWidget->AddToViewport(); + } } APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -137,7 +141,6 @@ void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbil FGameplayTag d = GetInputTag(AbilitySet, AbilityIndex); AbilityComp->OnAbilityAdded.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); } - TSubclassOf AbilityClass = AbilityData->Items.FindRef(InAbilityTag).AbilityClass; FARAbilityEquipInfo ABInfo(AbilitySet, AbilityIndex, GetInputTag(AbilitySet, AbilityIndex)); AwatingAbilityConfimation.Add(InAbilityTag, ABInfo); AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, GetInputTag(AbilitySet, AbilityIndex)); diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h index de6ce94..4f8037a 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -4,9 +4,9 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" -#include "ARAbilityData.h" #include "GameplayTags.h" #include "ARAbilityBase.h" +#include "ARAvailableAbilities.h" #include "ARUIAbilityManagerComponent.generated.h" USTRUCT() @@ -53,6 +53,8 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent { GENERATED_BODY() protected: + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Config") + TSubclassOf Abilities; UPROPERTY(EditAnywhere, Category = "Widget Config") TSubclassOf AbilitySetConfigClass; UPROPERTY(BlueprintReadOnly) @@ -76,11 +78,6 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Input Config") TArray AbilityInputs; - TWeakObjectPtr ActiveWeapon; - TWeakObjectPtr WeaponTwo; - TWeakObjectPtr WeaponThree; - TWeakObjectPtr WeaponFour; - int32 ActiveSet; UPROPERTY(EditAnywhere, Category = "Input Config") TArray InputBindingsSet; @@ -92,8 +89,6 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Widget Config") TSubclassOf DragVisualClass; - UPROPERTY(EditAnywhere, BlueprintReadOnly) - UARAbilityData* AbilityData; UPROPERTY(BlueprintAssignable) FAROnAbilitySetChanged OnAbilitySetChanged; public: From e5723680925e877632b6a22b5d6558aa16a997fc Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 11 Aug 2017 18:11:03 +0200 Subject: [PATCH 012/187] missing files --- ActionRPGGame.uproject | 11 +- .../AbilityFramework/AFAbilityComponent.cpp | 972 ++++++++++++++++++ .../AbilityFramework/AFAbilityComponent.h | 689 +++++++++++++ .../AbilityFramework/AFAbilityInterface.cpp | 10 + .../AbilityFramework/AFAbilityInterface.h | 62 ++ .../AbilityFramework/AFAssetManager.cpp | 8 + .../Source/AbilityFramework/AFAssetManager.h | 20 + .../AbilityFramework/AFAttributeComponent.cpp | 35 + .../AbilityFramework/AFAttributeComponent.h | 29 + .../AFAbilityPeriodicInfiniteSpec.cpp | 14 + .../Abilities/AFAbilityPeriodicInfiniteSpec.h | 18 + .../Abilities/GAAbilityBase.cpp | 6 +- .../Abilities/GAAbilityBase.h | 2 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 10 +- .../AbilityFramework/Effects/GAGameEffect.h | 4 +- .../AFAbilityInfiniteDurationSpecDetails.cpp | 83 ++ .../AFAbilityInfiniteDurationSpecDetails.h | 31 + .../AFAbilityInfinitePeriodSpecDetails.cpp | 83 ++ .../AFAbilityInfinitePeriodSpecDetails.h | 31 + .../EffectCueEditor/AFEffectCueDetails.cpp | 353 +++++++ .../EffectCueEditor/AFEffectCueDetails.h | 36 + Source/ActionRPGGame/ARGameMode.cpp | 16 +- Source/ActionRPGGame/ARGameMode.h | 3 +- .../Attributes/ARAbilityAttributes.cpp | 2 - .../Attributes/ARCharacterAttributes.cpp | 5 +- .../Attributes/ARCharacterAttributes.h | 4 +- 26 files changed, 2507 insertions(+), 30 deletions(-) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 8c2397c..e3b9b8b 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -13,8 +13,7 @@ "Engine", "AIModule", "UMG", - "CoreUObject", - "WorldArchitectEditor" + "CoreUObject" ] } ], @@ -27,14 +26,6 @@ "Name": "ActorSequenceEditor", "Enabled": true }, - { - "Name": "OculusVR", - "Enabled": false - }, - { - "Name": "SteamVR", - "Enabled": false - }, { "Name": "ImagePlate", "Enabled": true diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp new file mode 100644 index 0000000..e7f283a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -0,0 +1,972 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" + +#include "Abilities/GAAbilityBase.h" +#include "IAbilityFramework.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" +#include "Animation/AnimInstance.h" +#include "Animation/AnimMontage.h" +#include "GAGlobals.h" +#include "Abilities/GAAbilitySet.h" +#include "Attributes/GAAttributesBase.h" +#include "AFAbilityInterface.h" +#include "Effects/GAEffectExecution.h" +#include "Effects/GAGameEffect.h" +#include "MessageEndpoint.h" +#include "MessageEndpointBuilder.h" +#include "Effects/GAEffectExtension.h" +#include "Effects/GAEffectCue.h" +#include "AFCueSet.h" +#include "AFCueManager.h" + +#include "AFAbilityComponent.h" + + + +DEFINE_STAT(STAT_ApplyEffect); +DEFINE_STAT(STAT_ModifyAttribute); + +UAFAbilityComponent::UAFAbilityComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bWantsInitializeComponent = true; + bIsAnyAbilityActive = false; + bAutoActivate = true; + bAutoRegister = true; + PrimaryComponentTick.bCanEverTick = true; + PrimaryComponentTick.bStartWithTickEnabled = true; + PrimaryComponentTick.bRunOnAnyThread = false; + PrimaryComponentTick.bAllowTickOnDedicatedServer = true; + PrimaryComponentTick.TickGroup = ETickingGroup::TG_DuringPhysics; + +} + +void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData) +{ + FAFAttributeChangedDelegate* Delegate = AttributeChanged.Find(InAttribute); + if (Delegate) + { + Delegate->Broadcast(InData); + } +} + +bool UAFAbilityComponent::GetShouldTick() const +{ + return true; +} + +void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn + ,FGAEffectProperty& InProperty) +{ + //OnAttributePreModifed.Broadcast(ModIn, 0); + //Add log. + float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); + FAFAttributeChangedData Data; + FGAEffectContext& Context = HandleIn.GetContextRef(); + Data.Mod = ModIn; + Data.Target = Context.Target; + Data.Location = Context.HitResult.Location; + OnAttributeModifed.Broadcast(Data); + NotifyInstigatorTargetAttributeChanged(Data, Context); +}; +void UAFAbilityComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext) +{ + InContext.InstigatorComp->OnTargetAttributeModifed.Broadcast(InData); +} +void UAFAbilityComponent::GetAttributeStructTest(FGAAttribute Name) +{ + DefaultAttributes->GetAttribute(Name); +} + +void UAFAbilityComponent::OnRep_GameEffectContainer() +{ + float test = 0; +} +void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + UActorComponent::TickComponent(DeltaTime, TickType, ThisTickFunction); + if (DefaultAttributes) + { + DefaultAttributes->Tick(DeltaTime); + } +} +void UAFAbilityComponent::Update() +{ + +} +void UAFAbilityComponent::BeginPlay() +{ + Super::BeginPlay(); +} +void UAFAbilityComponent::DestroyComponent(bool bPromoteChildren) +{ + Super::DestroyComponent(bPromoteChildren); +} + +FGAEffectHandle UAFAbilityComponent::ApplyEffectToSelf(FGAEffect* EffectIn + ,FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; + FAFEventData Data; + for (const FGameplayTag& Tag : AppliedEventTags) + { + if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + { + Event->Broadcast(Data); + } + } + + //OnEffectApplyToSelf.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); + GameEffectContainer.MarkArrayDirty(); + return Handle; + //FGAEffectCueParams CueParams; + //CueParams.HitResult = EffectIn.Context.HitResult; + //OnEffectApplied.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); +} +FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + //broadcast cues first ? + //Probabaly because effect might not always apply. Or relegate cue + //application to object which was hit ? + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams; + CueParams.Instigator = InContext.Instigator; + CueParams.Causer = InContext.Causer; + CueParams.HitResult = InContext.HitResult; + CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; + CueParams.Period = InProperty.Period; + CueParams.Duration = InProperty.Duration; + //if (mode == ENetMode::NM_Standalone + // || role >= ENetRole::ROLE_Authority) + { + MulticastApplyEffectCue(CueParams); + } + } + + FString prefix = ""; + if (mode == ENetMode::NM_Standalone + || role == ENetRole::ROLE_Authority) + { + if (mode == ENetMode::NM_Client) + { + prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + } + else if (mode == ENetMode::NM_DedicatedServer) + { + prefix = FString::Printf(TEXT("DedicatedServer: ")); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), + *prefix, + *GetOwner()->GetName(), + *InContext.Instigator->GetName() + ); + //execute cue from effect regardless if we have target object or not. + if (InContext.TargetComp.IsValid()) + return InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + } + + + return FGAEffectHandle(); + +// if (EffectIn.IsValid() && EffectIn.Context.TargetComp.IsValid()) +// { + //OnEffectApplyToTarget.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); + // return EffectIn.Context.TargetComp->ApplyEffectToSelf(EffectIn, HandleIn); +// } +} + +void UAFAbilityComponent::OnAttributeModified(const FGAEffectMod& InMod, + const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) +{ + +} +void UAFAbilityComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty + ,FAFFunctionModifier Modifier, FGAEffectContext InContex) +{ + /* + this patth will give effects chance to do any replicated events, like applying cues. + WE do not make any replication at the ApplyEffect because some effect might want to apply cues + on periods on expiration etc, and all those will go trouch ExecuteEffect path. + */ + const FGameplayTagContainer& RequiredTags = InProperty.GetSpec()->RequiredTags; + if (RequiredTags.Num() > 0) + { + if (!HasAll(RequiredTags)) + { + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *HandleIn.GetEffectSpec()->GetName(), *RequiredTags.ToString()); + return; + } + } + + //apply execution events: + const FGameplayTagContainer& ExecuteEventTags = InProperty.GetSpec()->ExecuteEventTags; + FAFEventData Data; + for (const FGameplayTag& Tag : ExecuteEventTags) + { + if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + { + Event->Broadcast(Data); + } + } + + OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); + FGAEffect& Effect = HandleIn.GetEffectRef(); + FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() + , InProperty.GetSpec() + , InContex + , HandleIn); + + //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? + + Effect.OnExecuted(); + MulticastExecuteEffectCue(HandleIn); + InProperty.Execution->ExecuteEffect(HandleIn, Mod, HandleIn.GetContextRef(), InProperty, Modifier); + PostExecuteEffect(); +} +void UAFAbilityComponent::PostExecuteEffect() +{ + +} +void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty, + FGAEffectContext InContext) +{ + //call effect internal delegate: + HandleIn.GetEffectPtr()->OnExpired(); + //InternalRemoveEffect(HandleIn); + //OnEffectExpired.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams; + CueParams.Instigator = InContext.Instigator; + CueParams.Causer = InContext.Causer; + CueParams.HitResult = InContext.HitResult; + CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; + CueParams.Period = InProperty.Period; + CueParams.Duration = InProperty.Duration; + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role >= ENetRole::ROLE_Authority) + { + MulticastRemoveEffectCue(CueParams); + } + } + GameEffectContainer.RemoveEffectByHandle(HandleIn, InProperty); +} +void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, + const FGAEffectContext& InContext) +{ + //if (GetOwnerRole() == ENetRole::ROLE_Authority + // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + { + InternalRemoveEffect(InProperty, InContext); + } + //OnEffectRemoved.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); +} +void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, + const FGAEffectContext& InContext) +{ + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); + + //MulticastRemoveEffectCue(HandleIn); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams; + CueParams.Instigator = InContext.Instigator; + CueParams.Causer = InContext.Causer; + CueParams.HitResult = InContext.HitResult; + CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; + CueParams.Period = InProperty.Period; + CueParams.Duration = InProperty.Duration; + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + //if (mode == ENetMode::NM_Standalone + // || role >= ENetRole::ROLE_Authority) + { + MulticastRemoveEffectCue(CueParams); + } + } + GameEffectContainer.RemoveEffect(InProperty); +} + + +void UAFAbilityComponent::MulticastApplyEffectCue_Implementation( FGAEffectCueParams CueParams) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if(mode == ENetMode::NM_Standalone + || mode != ENetMode::NM_DedicatedServer) + { + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + int32 client = GPlayInEditorID - 1; + if (client == 2) + { + float dupa = 0; + } + prefix = FString::Printf(TEXT("Client %d: "), client); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : MulticastApplyEffectCue Owner: %s, Instigator: %s" ), + *prefix, + *GetOwner()->GetName(), + *CueParams.Instigator->GetName() + ); + + //for (const FGameplayTag& Tag : CueParams.CueTags) + //{ + // TSubclassOf CueClass = TestCueSet->Cues.FindRef(Tag); + // if (!CueClass) + // continue; + + // FActorSpawnParameters SpawnParams; + // FVector Location = CueParams.HitResult.Location; + // FRotator Rotation = FRotator::ZeroRotator; + // AGAEffectCue* actor = nullptr; + // + // actor = GetWorld()->SpawnActor(CueClass, Location, Rotation, SpawnParams); + // actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), + // CueParams.Causer.Get(), CueParams.HitResult); + + //} + + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams); + } +} + +void UAFAbilityComponent::MulticastExecuteEffectCue_Implementation(FGAEffectHandle EffectHandle) +{ + // ActiveCues.ExecuteCue(EffectHandle); +} + +void UAFAbilityComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + //if (mode == ENetMode::NM_Standalone + // || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams); + } +} + +void UAFAbilityComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} +void UAFAbilityComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) +{ + +} +void UAFAbilityComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) +{ + +} +void UAFAbilityComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} + +void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly replicate it to everyone + //to allow prediction for UI. + DOREPLIFETIME(UAFAbilityComponent, DefaultAttributes); + DOREPLIFETIME(UAFAbilityComponent, ModifiedAttribute); + DOREPLIFETIME(UAFAbilityComponent, GameEffectContainer); + + DOREPLIFETIME(UAFAbilityComponent, ActiveCues); + + DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); + DOREPLIFETIME_CONDITION(UAFAbilityComponent, RepMontage, COND_SkipOwner); + //DOREPLIFETIME(UAFAbilityComponent, RepMontage); +} +void UAFAbilityComponent::OnRep_ActiveEffects() +{ + +} +void UAFAbilityComponent::OnRep_ActiveCues() +{ + +} + +void UAFAbilityComponent::OnRep_AttributeChanged() +{ + //for (FGAModifiedAttribute& attr : ModifiedAttribute.Mods) + //{ + // attr.Causer->OnAttributeModifed.Broadcast(attr); + //} +} +bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) +{ + bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); + + if (DefaultAttributes) + { + WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); + } + for (const FGASAbilityItem& Ability : AbilityContainer.AbilitiesItems) + { + //if (Set.InputOverride) + // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); + + if (Ability.Ability) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); + } + return WroteSomething; +} +void UAFAbilityComponent::GetSubobjectsWithStableNamesForNetworking(TArray& Objs) +{ + if (DefaultAttributes && DefaultAttributes->IsNameStableForNetworking()) + { + Objs.Add(const_cast(DefaultAttributes)); + } +} + + +FAFEventDelegate& UAFAbilityComponent::GetTagEvent(FGameplayTag TagIn) +{ + FAFEventDelegate& Delegate = EffectEvents.FindChecked(TagIn); + return Delegate; +} +void UAFAbilityComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + FAFEventDelegate* Delegate = EffectEvents.Find(TagIn); + if (Delegate) + { + if (Delegate->IsBound()) + { + Delegate->Broadcast(InEventData); + } + } +} +void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const +{ + TagContainer = AppliedTags.AllTags; +} +bool UAFAbilityComponent::HasMatchingGameplayTag(FGameplayTag TagToCheck) const +{ + return AppliedTags.HasTag(TagToCheck); +} + +bool UAFAbilityComponent::HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const +{ + return AppliedTags.HasAll(TagContainer); +} + +bool UAFAbilityComponent::HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const +{ + return AppliedTags.HasAny(TagContainer); +} + +bool UAFAbilityComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) +{ + bool bDenyApplication = false; + if (InTags.Num() > 0) + { + bDenyApplication = HasAll(InTags); + } + return bDenyApplication; +} + +bool UAFAbilityComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) +{ + bool bAllowApplication = true; + if (InTags.Num() > 0) + { + bAllowApplication = HasAll(InTags); + } + return bAllowApplication; +} +void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer) +{ + +} +void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) +{ + if (InArraySerializer.AbilitiesComp.IsValid()) + { + //should be safe, since we only modify the non replicated part of struct. + FGASAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); + if (InArraySerializer.AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(InArraySerializer.AbilitiesComp->GetOwner()); + Ability->POwner = POwner; + Ability->PCOwner = Cast(POwner->Controller); + Ability->OwnerCamera = nullptr; + } + Ability->InitAbility(); + + InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); + InArraySerializerC.AbilitiesComp->NotifyOnAbilityAdded(Ability->AbilityTag); + InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(Ability->AbilityTag); + } +} +void FGASAbilityItem::PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer) +{ + +} +void FGASAbilityContainer::SetBlockedInput(const FGameplayTag& InInput, bool bBlock) +{ + if (BlockedInput.Contains(InInput)) + { + BlockedInput[InInput] = bBlock; + } + else + { + BlockedInput.Add(InInput, bBlock); + } +} +UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn, + AActor* InAvatar, + FGameplayTag ActionName) +{ + if (AbilityIn && AbilitiesComp.IsValid()) + { + UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); + ability->AbilityComponent = AbilitiesComp.Get(); + if (AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(AbilitiesComp->GetOwner()); + ability->POwner = POwner; + ability->PCOwner = Cast(POwner->Controller); + ability->OwnerCamera = nullptr; + ability->AvatarActor = InAvatar; + + //ability->AIOwner = PawnInterface->GetGameController(); + } + ability->InitAbility(); + FGameplayTag Tag = ability->AbilityTag; + + AbilitiesInputs.Add(Tag, ability); + FGASAbilityItem AbilityItem; + AbilityItem.Ability = ability; + AbilitiesItems.Add(AbilityItem); + //FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(ActionName); + //AbilityTag = Tag; + if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone + || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) + { + AbilitiesComp->NotifyOnAbilityAdded(ability->AbilityTag); + AbilitiesComp->NotifyOnAbilityReady(ability->AbilityTag); + } + /* if (ActionName.IsValid()) + { + UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); + AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); + }*/ + return ability; + } + return nullptr; +} +void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +{ + FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InInputTag); + AbilityTag = InAbilityTag; +} +UGAAbilityBase* FGASAbilityContainer::GetAbility(FGameplayTag TagIn) +{ + return AbilitiesInputs.FindRef(TagIn); +} +void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName) +{ + if (BlockedInput.FindRef(ActionName)) + { + return; + } + FGameplayTag abilityTag = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + ability->OnNativeInputPressed(ActionName); + } +} +void FGASAbilityContainer::HandleInputReleased(FGameplayTag ActionName) +{ + if (BlockedInput.FindRef(ActionName)) + { + return; + } + FGameplayTag abilityTag = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); + if (ability) + { + ability->OnNativeInputReleased(ActionName); + } +} + +void FGASAbilityContainer::TriggerAbylityByTag(FGameplayTag InTag) +{ + UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + ability->OnNativeInputPressed(FGameplayTag()); + } +} + +void UAFAbilityComponent::InitializeComponent() +{ + Super::InitializeComponent(); + //PawnInterface = Cast(GetOwner()); + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + AbilityContainer.AbilitiesComp = this; + + if (DefaultAttributes) + { + DefaultAttributes->InitializeAttributes(this); + DefaultAttributes->InitializeAttributesFromTable(); + } + GameEffectContainer.OwningComponent = this; + ActiveCues.OwningComp = this; + //ActiveCues.OwningComponent = this; + AppliedTags.AddTagContainer(DefaultTags); + //TestRunnable = new FAsyncUObjectRunnable(this); + //TEstAsyncUObject = NewObject(this, UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); + //TEstAsyncUObject->AddToRoot(); + //RouterThread = FRunnableThread::Create(TEstAsyncUObject, TEXT("AsyncUObject.Test"), 128 * 1024, TPri_Normal, FPlatformAffinity::GetPoolThreadMask()); + InitializeInstancedAbilities(); +} +void UAFAbilityComponent::UninitializeComponent() +{ + Super::UninitializeComponent(); + //GameEffectContainer +} +void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InInput, bool bBlock) +{ + AbilityContainer.SetBlockedInput(InInput, bBlock); +} +void UAFAbilityComponent::BP_BindAbilityToAction(FGameplayTag ActionName) +{ + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + BindAbilityToAction(InputComponent, ActionName); +} +void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName) +{ + if (!InputComponent) + return; + + { + FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputPressed, ActionName); + &InputComponent->AddActionBinding(AB); + } + + // Released event + { + FInputActionBinding AB(ActionName.GetTagName(), IE_Released); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputReleased, ActionName); + &InputComponent->AddActionBinding(AB); + } + SetBlockedInput(ActionName, false); +} +void UAFAbilityComponent::BP_SetAbilityToAction(FGameplayTag InAbilityTag, FGameplayTag InInputTag) +{ + SetAbilityToAction(InAbilityTag, InInputTag); +} +void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +{ + AbilityContainer.SetAbilityToAction(InAbilityTag, InInputTag); + ENetRole role = GetOwnerRole(); + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + && role == ENetRole::ROLE_AutonomousProxy) + { + ServerSetAbilityToAction(InAbilityTag, InInputTag); + } +} +void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + SetAbilityToAction(InAbilityTag, InInputTag); + } +} +bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +{ + return true; +} +void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) +{ + NativeInputPressed(ActionName); +} +void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeInputPressed(ActionName); + //UE_LOG(AbilityFramework, Log, TEXT("Client UAFAbilityComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); + //naive needs better qynchornization to what going on where. + //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + { + //if (Ability->AbilityComponent == this) + { + AbilityContainer.HandleInputPressed(ActionName); + } + } + } + else + { + //UE_LOG(AbilityFramework, Log, TEXT("Server UAFAbilityComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); + //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + { + //if (Ability->AbilityComponent == this) + { + AbilityContainer.HandleInputPressed(ActionName); + } + } + } +} + +void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName) +{ + NativeInputPressed(ActionName); +} +bool UAFAbilityComponent::ServerNativeInputPressed_Validate(FGameplayTag ActionName) +{ + return true; +} + +void UAFAbilityComponent::BP_InputReleased(FGameplayTag ActionName) +{ + NativeInputReleased(ActionName); +} + +void UAFAbilityComponent::NativeInputReleased(FGameplayTag ActionName) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + { + //if (Ability->AbilityComponent == this) + { + AbilityContainer.HandleInputReleased(ActionName); + } + } + ServerNativeInputReleased(ActionName); + } + else + { + //UE_LOG(AbilityFramework, Log, TEXT("UAFAbilityComponent::NativeInputReleased: %s"), *AbilityTag.GetTagName().ToString()); + + AbilityContainer.HandleInputReleased(ActionName); + } +} + +void UAFAbilityComponent::ServerNativeInputReleased_Implementation(FGameplayTag ActionName) +{ + NativeInputReleased(ActionName); +} +bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag ActionName) +{ + return true; +} +void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName) +{ + NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputName); +} +void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputName); + } + else + { + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("AbilityTagSearch", InAbilityTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbilityTag, InInputName, PrimaryAssetId); + + Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } + } + } + +} + +void UAFAbilityComponent::ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName) +{ + NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputName); +} + +bool UAFAbilityComponent::ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName) +{ + return true; +} +void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, + FGameplayTag InInputName, FPrimaryAssetId InPrimaryAssetId) +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); + TSubclassOf cls = Cast(loaded); + if (cls) + { + NativeAddAbility(cls, nullptr, InInputName); + } + + { + Manager->UnloadPrimaryAsset(InPrimaryAssetId); + } + } +} +void UAFAbilityComponent::BP_AddAbility(TSubclassOf AbilityClass, + AActor* InAvatar, + FGameplayTag ActionName, bool bAutoBind) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + return; + } + else + { + NativeAddAbility(AbilityClass, InAvatar, ActionName, bAutoBind); + } +} +void UAFAbilityComponent::NativeAddAbility(TSubclassOf AbilityClass, + AActor* InAvatar, + FGameplayTag ActionName, bool bAutoBind) +{ + InstanceAbility(AbilityClass, InAvatar, ActionName); +} + +void UAFAbilityComponent::BP_RemoveAbility(FGameplayTag TagIn) +{ + +} +UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(FGameplayTag TagIn) +{ + return AbilityContainer.GetAbility(TagIn); +} +UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass, + AActor* InAvatar, + FGameplayTag ActionName) +{ + if (AbilityClass) + { + UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InAvatar, ActionName); + AbilityContainer.MarkArrayDirty(); + return ability; + } + return nullptr; +} + +void UAFAbilityComponent::NativeAddAbilitiesFromSet(TSubclassOf AbilitySet) +{ + //do not let add abilities on non authority. + if (GetOwnerRole() < ENetRole::ROLE_Authority) + return; + + UGAAbilitySet* Set = AbilitySet.GetDefaultObject(); + int32 Index = 0; + for (const FGASAbilitySetItem& Item : Set->AbilitySet.Abilities) + { + InstanceAbility(Item.AbilityClass, nullptr, Item.Binding); + Index++; + } +} + +void UAFAbilityComponent::BP_AddAbilitiesFromSet(TSubclassOf AbilitySet) +{ + NativeAddAbilitiesFromSet(AbilitySet); +} + +void UAFAbilityComponent::OnRep_InstancedAbilities() +{ +} +void UAFAbilityComponent::NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag) +{ + OnAbilityAdded.Broadcast(InAbilityTag); + +} +void UAFAbilityComponent::InitializeInstancedAbilities() +{ +} + +void UAFAbilityComponent::OnRep_PlayMontage() +{ + ACharacter* MyChar = Cast(GetOwner()); + if (MyChar) + { + UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); + AnimInst->Montage_Play(RepMontage.CurrentMontage); + if (RepMontage.SectionName != NAME_None) + { + AnimInst->Montage_JumpToSection(RepMontage.SectionName, RepMontage.CurrentMontage); + } + UE_LOG(AbilityFramework, Log, TEXT("OnRep_PlayMontage MontageName: %s SectionNAme: %s ForceRep: %s"), *RepMontage.CurrentMontage->GetName(), *RepMontage.SectionName.ToString(), *FString::FormatAsNumber(RepMontage.ForceRep)); + } +} + +void UAFAbilityComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) +{ + //if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + //Probabaly want to do something different here for client non authority montage plays. + //return; + } + ACharacter* MyChar = Cast(GetOwner()); + if (MyChar) + { + UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); + AnimInst->Montage_Play(MontageIn, Speed); + if (SectionName != NAME_None) + { + AnimInst->Montage_JumpToSection(SectionName, MontageIn); + } + + UE_LOG(AbilityFramework, Log, TEXT("PlayMontage MontageName: %s SectionNAme: %s Where: %s"), *MontageIn->GetName(), *SectionName.ToString(), (GetOwnerRole() < ENetRole::ROLE_Authority ? TEXT("Client") : TEXT("Server"))); + RepMontage.SectionName = SectionName; + RepMontage.CurrentMontage = MontageIn; + RepMontage.ForceRep++; + } +} +void UAFAbilityComponent::MulticastPlayMontage_Implementation(UAnimMontage* MontageIn, FName SectionName, float Speed = 1) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h new file mode 100644 index 0000000..94cf1ac --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -0,0 +1,689 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "GameplayTaskOwnerInterface.h" +#include "GameplayTaskTypes.h" +#include "GameplayTask.h" +#include "GameplayTasksComponent.h" +#include "GameplayTags.h" +#include "GAGlobals.h" +#include "Attributes/GAAttributeBase.h" +#include "Attributes/GAAttributesBase.h" +#include "Effects/GAEffectCueGlobals.h" + +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Messaging.h" +#include "GameplayTagAssetInterface.h" +#include "AFAbilityInterface.h" + +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" +#include "AFAssetManager.h" + +#include "AFAbilityComponent.generated.h" + +DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGAGenericEffectDelegate, const FGAEffectHandle&, Handle, const FGameplayTagContainer&, Tags); + +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate , FAFEventData); +DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); + +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectRepInfoDelegate, FAFEffectRepInfo*); + +DECLARE_DELEGATE(FAFOnAbilityReady); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); + +//UAFAssetManager* GetAssetManager() +//{ +// return Cast(UAssetManager::GetIfValid()); +//}; + +USTRUCT() +struct FGAModifiedAttributeData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + TArray Mods; + UPROPERTY() + int32 ForceUpdate; + + FGAModifiedAttributeData() + : ForceUpdate(0) + {} +}; + +USTRUCT(BlueprintType) +struct FGAEffectUIData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "UI") + float RemainingTime; + + FGAEffectUIData() + : RemainingTime(0) + {}; +}; +struct FGAContextSetup +{ +public: + UGAAttributesBase* IntigatorAttributes; + UGAAttributesBase* TargetAttributes; + UAFAbilityComponent* InstigatorComp; + UAFAbilityComponent* TargetComp; + + FGAContextSetup() + {}; + FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, + UAFAbilityComponent* InstigatorCompIn, UAFAbilityComponent* TargetCompIn) + : IntigatorAttributes(IntigatorAttributesIn), + TargetAttributes(TargetAttributesIn), + InstigatorComp(InstigatorCompIn), + TargetComp(TargetCompIn) + {}; +}; +DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); +DECLARE_DELEGATE_ThreeParams(FAFMontageGenericDelegate, const FAFAbilityNotifyData&, const FGameplayTag&, const FName&); +/* TODO:: Implement fast serialization for structs. */ +/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ +/**/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASMontageRepData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + UAnimMontage* CurrentMontage; + + UPROPERTY() + FName SectionName; + + UPROPERTY() + uint8 ForceRep; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem +{ + GENERATED_BODY() + +public: + UPROPERTY() + UGAAbilityBase* Ability; + + void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); + void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); + void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); +}; +USTRUCT() +struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + + UPROPERTY() + TArray AbilitiesItems; + + TWeakObjectPtr AbilitiesComp; + TMap BlockedInput; + + + //Custom binding, for server side validation. + //ActionName, AbilityTag + TMap ActionToAbility; + TMap AbilitiesInputs; + + void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, + AActor* InAvatar, + FGameplayTag ActionName); + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + UGAAbilityBase* GetAbility(FGameplayTag TagIn); + + void HandleInputPressed(FGameplayTag ActionName); + void HandleInputReleased(FGameplayTag ActionName); + + void TriggerAbylityByTag(FGameplayTag InTag); + + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + +UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) +class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface +{ + GENERATED_BODY() + /* Attributes handling */ +public: + friend struct FAFMessageTick; + //Only for base testing and prototyping cue application. + //will be removed when Cue Manager will be more functional. + UPROPERTY(EditAnywhere) + class UAFCueSet* TestCueSet; + UPROPERTY(EditAnywhere, Category = "Test") + FGameplayTag TagTest; + /* + Set attribute which will be considered for indicating whether or not actor is dead. + */ + UPROPERTY(EditAnywhere, Category = "Config") + FGAAttribute DeathAttribute; + + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DefaultTags; + + UPROPERTY() + FGACountedTagContainer AppliedTags; + + UPROPERTY() + FGACountedTagContainer ImmunityTags; + + UFUNCTION() + void OnRep_ActiveEffects(); + + UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) + FGameCueContainer ActiveCues; + UFUNCTION() + void OnRep_ActiveCues(); + /* + Could make it array. But realistically. How many times do you really need more, than one + attribute set for actor ? + + Of course array of attributes would allow to compose attributes from small discreete + attribute sets. On the other hand similiar funcionality can be achieved by using + inheritance. + + And I think that using inheritance in this case will be easier. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) + class UGAAttributesBase* DefaultAttributes; + + //probabaly replace FGameplayTag with FObjectKey + TMap AdditionalAttributes; + + UPROPERTY(ReplicatedUsing = OnRep_AttributeChanged) + FGAModifiedAttributeData ModifiedAttribute; + UFUNCTION() + void OnRep_AttributeChanged(); + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnAttributeModifed; + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnTargetAttributeModifed; + /* Effect/Attribute System Delegates */ + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectApplied; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectApplyToTarget; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectApplyToSelf; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectExecuted; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectExpired; + + UPROPERTY(BlueprintAssignable, Category = "Effect") + FGAGenericEffectDelegate OnEffectRemoved; + + /* NEW EFFECT SYSTEM */ + UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) + FGAEffectContainer GameEffectContainer; + + FAFEffectRepInfoDelegate OnEffectRepInfoApplied; + FAFEffectRepInfoDelegate OnEffectRepInfoRemoved; + /* + Default effects applied when character spawns. + Can contain things like attribute regen, racial bonuses + racial debuffs etc. + */ + UPROPERTY(EditAnywhere, Category = "Effects") + TArray> DefaultEffects; + + TMap EffectEvents; + TMap AttributeChanged; + + void BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData); + + virtual bool GetShouldTick() const override; + + UFUNCTION() + void OnRep_GameEffectContainer(); + + template + T* GetAttributes() + { + return CastChecked(DefaultAttributes); + } + + template + T* GetAttributeSet(FGameplayTag InOwner) + { + UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); + return Cast(AttributeSet); + } + void AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) + { + bool bExists = AdditionalAttributes.Contains(InOwner); + if (bExists) + { + return; + } + AdditionalAttributes.Add(InOwner, InAttributes); + } + UFUNCTION(BlueprintCallable, Category = "Test") + void GetAttributeStructTest(FGAAttribute Name); + + virtual void BeginPlay() override; + virtual void DestroyComponent(bool bPromoteChildren = false) override; + + virtual void InitializeComponent() override; + + virtual void UninitializeComponent() override; + + +public: + ///////////////////////////////////////////////// + //////////// EFFECTS HANDLING + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + void Update(); + FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + void ApplyEffectToTarget(TSubclassOf InSpecClass, + const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); + + + /* Have to to copy handle around, because timer delegates do not support references. */ + void ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty + ,FAFFunctionModifier Modifier, FGAEffectContext InContext); + virtual void PostExecuteEffect(); + /* ExpireEffect is used to remove existing effect naturally when their time expires. */ + void ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty, + FGAEffectContext InContext); + /* RemoveEffect is used to remove effect by force. */ + void RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); + void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); + + /* + Need prediction for spawning effects on client, + and then on updateing them predicitvely on all other clients. + */ + /* + + */ + UFUNCTION(NetMulticast, Unreliable) + void MulticastApplyEffectCue(FGAEffectCueParams CueParams); + virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExecuteEffectCue(FGAEffectHandle EffectHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastRemoveEffectCue(FGAEffectCueParams CueParams); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + + //////////// EFFECTS HANDLING + ///////////////////////////////////////////////// + +public: + ///////////////////////////////////////////////// + //////////// ATTRIBUTES HANDLING + + /* + Two functions, They will allow to apply any static numerical mods from player who + initiated attribute change, and from player who will be affected by change. + + Mods will be appiled by small objects, and changed against tags. + For example there might be physical armor mod, which will apply changes only + to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. + */ + + inline float GetFinalAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetFinalAttributeValue(Name); + } + inline float GetCurrentAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetCurrentAttributeValue(Name); + } + //////////// ATTRIBUTES HANDLING + ///////////////////////////////////////////////// + /* + Attribute replication. + */ + void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); + + FAFEventDelegate& GetTagEvent(FGameplayTag TagIn); + void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + //Helper functions: +public: + /* + IGameplayTagAssetInterface Start + */ + /** + * Get any owned gameplay tags on the asset + * + * @param OutTags [OUT] Set of tags on the asset + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; + + /** + * Check if the asset has a gameplay tag that matches against the specified tag (expands to include parents of asset tags) + * + * @param TagToCheck Tag to check for a match + * + * @return True if the asset has a gameplay tag that matches, false if not + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual bool HasMatchingGameplayTag(FGameplayTag TagToCheck) const override; + + /** + * Check if the asset has gameplay tags that matches against all of the specified tags (expands to include parents of asset tags) + * + * @param TagContainer Tag container to check for a match + * + * @return True if the asset has matches all of the gameplay tags, will be true if container is empty + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual bool HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; + + /** + * Check if the asset has gameplay tags that matches against any of the specified tags (expands to include parents of asset tags) + * + * @param TagContainer Tag container to check for a match + * + * @return True if the asset has matches any of the gameplay tags, will be false if container is empty + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual bool HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; + /* + IGameplayTagAssetInterface End + */ + + bool DenyEffectApplication(const FGameplayTagContainer& InTags); + bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); + /* + Effect Container Wrapp Start + */ + /* + */ + inline bool IsEffectActive(const FGAEffectHandle& HandleIn) { return GameEffectContainer.IsEffectActive(HandleIn); }; + /* + Effect Container Wrapp End + */ + + /* Counted Tag Container Wrapper Start */ + inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; + inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; + inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; + inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; + inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } + inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; + inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; + inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; + inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; + inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; + inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } + /* Counted Tag Container Wrapper Start */ + + /* Active Effects Wrapper Start */ + inline int32 GetEffectsNum() const { return GameEffectContainer.GetEffectsNum(); }; + /* Active Effects Wrapper End */ + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; + + void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext); + FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; + float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + +private: + class IAFAbilityInterface* AttributeInterface; + +public: + UAFAbilityComponent(const FObjectInitializer& ObjectInitializer); + + UFUNCTION() + void OnRep_InstancedAbilities(); + UPROPERTY(Replicated) + FGASAbilityContainer AbilityContainer; + UPROPERTY() + TArray AbilitiesRefs; + + UPROPERTY() + APlayerController* PCOwner; + + /* Ability which is currently being executed. */ + UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") + class UGAAbilityBase* ExecutingAbility; + + TMap OnEffectEvent; + + void AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) + { + if (!InEventTag.IsValid()) + return; + if (!OnEffectEvent.Contains(InEventTag)) + { + OnEffectEvent.Add(InEventTag, InEvent); + } + } + void ExecuteEffectEvent(const FGameplayTag& InEventTag) + { + if (!InEventTag.IsValid()) + return; + FSimpleDelegate* Delegate = OnEffectEvent.Find(InEventTag); + if (Delegate) + { + Delegate->ExecuteIfBound(); + } + } + void RemoveEffectEvent(const FGameplayTag& InEventTag) + { + if (!InEventTag.IsValid()) + return; + OnEffectEvent.Remove(InEventTag); + } + /* + True if player is currently casting/channeling/activating(?) + any ability. + */ + bool bIsAnyAbilityActive; + + //AbilityTag, Delegate + TMap OnAbilityReadyMap; + + void AddOnAbilityReadyDelegate(const FGameplayTag& InAbilityTag, FAFOnAbilityReady& InDelegate) + { + OnAbilityReadyMap.Add(InAbilityTag, InDelegate); + } + + void NotifyOnAbilityReady(const FGameplayTag& InAbilityTag) + { + if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityTag)) + { + Ready->ExecuteIfBound(); + OnAbilityReadyMap.Remove(InAbilityTag); + } + } + FAFOnAbilityReady OnAbilityReady; + UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") + FAFOnAbilityAdded OnAbilityAdded; + + FAFMontageGenericDelegate OnAbilityNotifyBegin; + FAFMontageGenericDelegate OnAbilityNotifyTick; + FAFMontageGenericDelegate OnAbilityNotifyEnd; + + //class IIGIPawn* PawnInterface; +private: + + + UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) + FGASMontageRepData RepMontage; + UFUNCTION() + void OnRep_PlayMontage(); + +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + UFUNCTION(NetMulticast, Unreliable) + void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); +public: + inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) + { + return nullptr; + } + + TMap BlockedInput; + //TSharedPtr AbilityLoadedHandle; + void OnFinishedLoad(FGameplayTag InAbilityTag, + FGameplayTag InInputName, FPrimaryAssetId InPrimaryAssetId); + void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") + void BP_BindAbilityToAction(FGameplayTag ActionName); + void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); + + //need to be called on both client and server. + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + UFUNCTION(Server, Reliable, WithValidation) + void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Set Ability To Action"), Category = "AbilityFramework|Abilities") + void BP_SetAbilityToAction(FGameplayTag InAbilityTag, FGameplayTag InInputTag); + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") + void BP_InputPressed(FGameplayTag ActionName); + + void NativeInputPressed(FGameplayTag ActionName); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputPressed(FGameplayTag ActionName); + virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName); + virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName); + + + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") + void BP_InputReleased(FGameplayTag ActionName); + + void NativeInputReleased(FGameplayTag ActionName); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputReleased(FGameplayTag ActionName); + virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); + virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); + + /* + Finds ability using asset registry and then gives it to component. + Only valid on server. + Does not check if component can or can't have given ability. + So it must be checked before this function is called. + */ + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability From Tag"), Category = "AbilityFramework|Abilities") + void BP_AddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName); + + void NativeAddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeAddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName); + + void ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName); + + bool ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, + AActor* InAvatar, + FGameplayTag InInputName); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability"), Category = "AbilityFramework|Abilities") + void BP_AddAbility(TSubclassOf AbilityClass, + AActor* InAvatar, + FGameplayTag ActionName, bool bAutoBind = true); + + //TODO: Make it procted + void NativeAddAbility(TSubclassOf AbilityClass, AActor* InAvatar, + FGameplayTag ActionName, bool bAutoBind = true); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") + void BP_RemoveAbility(FGameplayTag TagIn); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") + UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); + /* + Should be called on server. + Adds new ability to ActiveAbilities; + */ + void NativeAddAbilitiesFromSet(TSubclassOf AbilitySet); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Abilities From Set"), Category = "AbilityFramework|Abilities") + void BP_AddAbilitiesFromSet(TSubclassOf AbilitySet); + + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; + void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; + + void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); +protected: + void InitializeInstancedAbilities(); + UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, + AActor* InAvatar, + FGameplayTag ActionName = FGameplayTag()); + /* + Messagin implementation for applying effects from multiple threads (in case + at some beatyfull day UObject will be able to exist on any thread), and from single thread. + + Implementation is based on FMessageEndpoint. + */ + +}; + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp new file mode 100644 index 0000000..677c6d4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp @@ -0,0 +1,10 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" + +UAFAbilityInterface::UAFAbilityInterface(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h new file mode 100644 index 0000000..27b55ba --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h @@ -0,0 +1,62 @@ +#pragma once +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypes.h" +#include "Messaging.h" +#include "AFAbilityInterface.generated.h" + + +struct FAFAttributeBase; +struct FGAEffectHandle; +UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) +class ABILITYFRAMEWORK_API UAFAbilityInterface : public UInterface +{ + GENERATED_UINTERFACE_BODY() +}; + +class IAFAbilityInterface +{ + GENERATED_IINTERFACE_BODY() +public: + virtual FVector GetSocketLocation(FName SocketNameIn){ return FVector::ZeroVector; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UGAAttributesBase* GetAttributes() = 0; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UAFAbilityComponent* GetAbilityComp() { return nullptr; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; + + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) {}; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; + + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, + FGAEffectProperty& InProperty, FGAEffectContext& InContext) { return FGAEffectHandle(); }; + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) {}; + //override to allow gathering tags from causer + //those tags will be merged into effect owned tags. + virtual FGameplayTagContainer GetCauserTags() { return FGameplayTagContainer(); } + + template + T* GetAttributesTyped() + { + return Cast(GetAttributes()); + } + template + T* GetComponentTyped() + { + return Cast(GetAbilityComp()); + } + template + T* GetAttributeTyped(FGAAttribute InAttribute) + { + return static_cast(GetAttribute(InAttribute)); + } +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp new file mode 100644 index 0000000..24126a3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAssetManager.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h new file mode 100644 index 0000000..0019a7c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Engine/AssetManager.h" +#include "AFAssetManager.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFAssetManager : public UAssetManager +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp new file mode 100644 index 0000000..3362503 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp @@ -0,0 +1,35 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAttributeComponent.h" + + +// Sets default values for this component's properties +UAFAttributeComponent::UAFAttributeComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UAFAttributeComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UAFAttributeComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h new file mode 100644 index 0000000..1140809 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "AFAttributeComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ABILITYFRAMEWORK_API UAFAttributeComponent : public UActorComponent +{ + GENERATED_BODY() + +public: + // Sets default values for this component's properties + UAFAttributeComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp new file mode 100644 index 0000000..a77c62a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h" +#include "AFAbilityPeriodicInfiniteSpec.h" + + + + +UAFAbilityPeriodicInfiniteSpec::UAFAbilityPeriodicInfiniteSpec() + :Super() +{ + Application = UAFPeriodApplicationInfiniteAdd::StaticClass(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h new file mode 100644 index 0000000..57158e4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h @@ -0,0 +1,18 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityPeriodicInfiniteSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityPeriodicInfiniteSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityPeriodicInfiniteSpec(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index e96547a..05fd566 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -256,8 +256,8 @@ bool UGAAbilityBase::ApplyCooldownEffect() } FAFFunctionModifier Modifier; - //FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnCooldownEnd, CooldownEffectHandle); - //AbilityComponent->AddEffectEvent(CooldownEffect.GetSpec()->OnPeriodEvent, PeriodDel); + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnCooldownEnd, CooldownEffectHandle); + AbilityComponent->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, this, POwner, this, Modifier); @@ -287,7 +287,7 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) ActivationEffectHandle.Reset(); FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); - AbilityComponent->AddEffectEvent(ActivationEffect.GetSpec()->OnAppliedEvent, AppliedDel); + AbilityComponent->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); FAFFunctionModifier Modifier; ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(ActivationEffect, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 23a5e5c..d5355df 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -352,7 +352,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnCooldownStart(); UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnCooldownEnd(const FGAEffectHandle& InHandle); + void OnCooldownEnd(FGAEffectHandle InHandle); UFUNCTION() void OnCooldownEffectExpired(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index b6b8953..567582e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -57,7 +57,7 @@ void FAFEffectRepInfo::Init() } void FAFEffectRepInfo::OnExpired() { - OwningComoponent->ExecuteEffectEvent(OnAppliedEvent); + OwningComoponent->ExecuteEffectEvent(OnExpiredEvent); } void FAFEffectRepInfo::OnPeriod() { @@ -68,7 +68,7 @@ void FAFEffectRepInfo::OnRemoved() FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); - OwningComoponent->RemoveEffectEvent(OnAppliedEvent); + OwningComoponent->RemoveEffectEvent(OnExpiredEvent); OwningComoponent->RemoveEffectEvent(OnPeriodEvent); OwningComoponent->RemoveEffectEvent(OnRemovedEvent); } @@ -78,7 +78,7 @@ void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InAr InArraySerializer.EffectInfos.Remove(Handle); //InArraySerializer.OwningComponent->OnEffectRepInfoRemoved.Broadcast(this); - OwningComoponent->RemoveEffectEvent(OnAppliedEvent); + OwningComoponent->RemoveEffectEvent(OnExpiredEvent); OwningComoponent->RemoveEffectEvent(OnPeriodEvent); OwningComoponent->RemoveEffectEvent(OnRemovedEvent); } @@ -422,7 +422,7 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c { const UWorld* World = OwningComponent->GetWorld(); FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); - RepInfo->OnAppliedEvent = InProperty.GetSpec()->OnAppliedEvent; + RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; RepInfo->Handle = InHandle; @@ -443,7 +443,7 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c const UWorld* World = OwningComponent->GetWorld(); FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); - RepInfo->OnAppliedEvent = InProperty.GetSpec()->OnAppliedEvent; + RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; RepInfo->Handle = InHandle; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 8e62007..f045a56 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -200,7 +200,7 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject TArray> OnRemovedEffects; UPROPERTY(EditAnywhere, Category = "Event Tags") - FGameplayTag OnAppliedEvent; + FGameplayTag OnExpiredEvent; UPROPERTY(EditAnywhere, Category = "Event Tags") FGameplayTag OnPeriodEvent; UPROPERTY(EditAnywhere, Category = "Event Tags") @@ -610,7 +610,7 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem float ReplicationTime; UPROPERTY() - FGameplayTag OnAppliedEvent; + FGameplayTag OnExpiredEvent; UPROPERTY() FGameplayTag OnPeriodEvent; UPROPERTY() diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp new file mode 100644 index 0000000..d99ea2b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp @@ -0,0 +1,83 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityInfiniteDurationSpec.h" +#include "AFAbilityInfiniteDurationSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityInfiniteDurationSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityInfiniteDurationSpecDetails); +} + +void FAFAbilityInfiniteDurationSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityInfiniteDurationSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityInfiniteDurationSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + DetailLayout.HideCategory("Duration"); + DetailLayout.HideCategory("Period"); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); + + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityInfiniteDurationSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h new file mode 100644 index 0000000..c1b4218 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityInfiniteDurationSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + TSharedPtr PeriodCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp new file mode 100644 index 0000000..de096d4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp @@ -0,0 +1,83 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityPeriodicInfiniteSpec.h" +#include "AFAbilityInfinitePeriodSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityInfinitePeriodSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityInfinitePeriodSpecDetails); +} + +void FAFAbilityInfinitePeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityInfinitePeriodSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityPeriodicInfiniteSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DetailLayout.HideCategory("Duration"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); + + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityInfinitePeriodSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h new file mode 100644 index 0000000..bdffbdd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityInfinitePeriodSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + TSharedPtr PeriodCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp new file mode 100644 index 0000000..f301611 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp @@ -0,0 +1,353 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Effects/GAEffectCue.h" +#include "Effects/GAEffectCueSequence.h" +#include "EditorReimportHandler.h" +#include "MovieScene.h" +#include "Tracks/MovieScenePropertyTrack.h" +#if WITH_EDITOR +#include "Editor.h" +#endif +#include "ISequencerModule.h" +#include "LevelEditorSequencerIntegration.h" +#include "SSCSEditor.h" +#include "SlateIconFinder.h" +#include "BlueprintEditorUtils.h" +#include "Framework/MultiBox/MultiBoxBuilder.h" +#include "Framework/Application/SlateApplication.h" + +#include "AFEffectCueDetails.h" + +class SEffectCueSequenceEditorWidget + : public SCompoundWidget +{ +private: + TWeakObjectPtr WeakSequence; + AGAEffectCue* EffectCue; + TWeakPtr WeakBlueprintEditor; + + TSharedPtr Content; + TSharedPtr Sequencer; + FDelegateHandle OnBlueprintPreCompileHandle; + FDelegateHandle OnObjectSavedHandle; + FDelegateHandle OnSequenceChangedHandle; + FDelegateHandle OnBlueprintCompileHandle; + FDelegateHandle OnBlueprintReinstancedHandle; +public: + + SLATE_BEGIN_ARGS(SEffectCueSequenceEditorWidget) {} + SLATE_END_ARGS(); + + void Construct(const FArguments&, TWeakPtr InBlueprintEditor) + { + OnBlueprintPreCompileHandle = GEditor->OnBlueprintPreCompile().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintPreCompile); + OnObjectSavedHandle = FCoreUObjectDelegates::OnObjectSaved.AddSP(this, &SEffectCueSequenceEditorWidget::OnObjectPreSave); + OnBlueprintCompileHandle = GEditor->OnBlueprintCompiled().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintCompiled); + OnBlueprintReinstancedHandle = GEditor->OnBlueprintReinstanced().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintReinstanced); + + WeakBlueprintEditor = InBlueprintEditor; + + ChildSlot + [ + SAssignNew(Content, SBox) + .MinDesiredHeight(200) + ]; + } + void OnBlueprintCompiled() + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + UBlueprint* bp = BlueprintEditor->GetBlueprintObj(); + float dupa = 0; + } + void OnBlueprintReinstanced() + { + float dupa = 0; + } + ~SEffectCueSequenceEditorWidget() + { + if (Sequencer.IsValid()) + { + Sequencer->Close(); + Sequencer = nullptr; + } + + GEditor->OnBlueprintPreCompile().Remove(OnBlueprintPreCompileHandle); + GEditor->OnBlueprintCompiled().Remove(OnBlueprintCompileHandle); + GEditor->OnBlueprintReinstanced().Remove(OnBlueprintReinstancedHandle); + FCoreUObjectDelegates::OnObjectSaved.Remove(OnObjectSavedHandle); + } + void OnObjectPreSave(UObject* InObject) + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (Sequencer.IsValid() && BlueprintEditor.IsValid() && InObject && InObject == BlueprintEditor->GetBlueprintObj()) + { + Sequencer->RestorePreAnimatedState(); + } + } + + void OnBlueprintPreCompile(UBlueprint* InBlueprint) + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (Sequencer.IsValid() && BlueprintEditor.IsValid() && InBlueprint && InBlueprint == BlueprintEditor->GetBlueprintObj()) + { + Sequencer->RestorePreAnimatedState(); + } + } + void OnSequenceChanged() + { + UGAEffectCueSequence* ActorSequence = WeakSequence.Get(); + /*UBlueprint* Blueprint = ActorSequence ? ActorSequence->GetParentBlueprint() : nullptr; + + if (Blueprint) + { + FBlueprintEditorUtils::MarkBlueprintAsModified(Blueprint); + }*/ + } + void OnSequencerReceivedFocus() + { + if (Sequencer.IsValid()) + { + FLevelEditorSequencerIntegration::Get().OnSequencerReceivedFocus(Sequencer.ToSharedRef()); + } + } + UObject* GetPlaybackContext() const + { + UGAEffectCueSequence* LocalActorSequence = WeakSequence.Get(); + if (LocalActorSequence) + { + if (AActor* Actor = LocalActorSequence->GetTypedOuter()) + { + return Actor; + } + else if (UBlueprintGeneratedClass* GeneratedClass = LocalActorSequence->GetTypedOuter()) + { + return GeneratedClass->SimpleConstructionScript->GetComponentEditorActorInstance(); + } + } + + return nullptr; + } + + TArray GetEventContexts() const + { + TArray Contexts; + if (auto* Context = GetPlaybackContext()) + { + Contexts.Add(Context); + } + return Contexts; + } + AActor* GetPreviewActor() const + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (BlueprintEditor.IsValid()) + { + return BlueprintEditor->GetPreviewActor(); + } + if (UGAEffectCueSequence* Sequence = WeakSequence.Get()) + { + return Sequence->GetTypedOuter(); + } + return nullptr; + } + void OnSelectionUpdated(TSharedPtr SelectedNode) + { + if (SelectedNode->GetNodeType() != FSCSEditorTreeNode::ComponentNode) + { + return; + } + + UActorComponent* EditingComponent = nullptr; + + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (BlueprintEditor.IsValid()) + { + UBlueprint* Blueprint = BlueprintEditor->GetBlueprintObj(); + if (Blueprint) + { + EditingComponent = SelectedNode->GetEditableComponentTemplate(Blueprint); + } + } + else if (AActor* Actor = GetPreviewActor()) + { + EditingComponent = SelectedNode->FindComponentInstanceInActor(Actor); + } + + if (EditingComponent) + { + const FScopedTransaction Transaction(FText::FromString("Add component to Sequencer")); + Sequencer->GetHandleToObject(EditingComponent, true); + } + + FSlateApplication::Get().DismissAllMenus(); + } + void AddPossessComponentMenuExtensions(FMenuBuilder& MenuBuilder) + { + AActor* Actor = GetPreviewActor(); + if (!Actor) + { + return; + } + + Sequencer->State.ClearObjectCaches(*Sequencer); + TSet AllBoundObjects; + if (UGAEffectCueSequence* Sequence = WeakSequence.Get()) + { + AllBoundObjects.Add(Sequence->GetTypedOuter()); + //return Sequence->GetTypedOuter(); + } + UMovieScene* MovieScene = Sequencer->GetFocusedMovieSceneSequence()->GetMovieScene(); + for (int32 Index = 0; Index < MovieScene->GetPossessableCount(); ++Index) + { + FMovieScenePossessable& Possessable = MovieScene->GetPossessable(Index); + for (TWeakObjectPtr<> WeakObject : Sequencer->FindBoundObjects(Possessable.GetGuid(), Sequencer->GetFocusedTemplateID())) + { + if (UObject* Object = WeakObject.Get()) + { + AllBoundObjects.Add(Object); + } + } + } + + bool bIdent = false; + /*MenuBuilder.AddWidget( + SNew(SComponentSelectionTree, Actor) + .IsInEditMode(WeakBlueprintEditor.Pin().IsValid()) + .OnComponentSelected(this, &SEffectCueSequenceEditorWidget::OnSelectionUpdated) + .IsComponentValid_Lambda( + [AllBoundObjects](UActorComponent* Component) + { + return !AllBoundObjects.Contains(Component); + } + ) + , FText(), !bIdent + );*/ + } + void SetActorSequence(UGAEffectCueSequence* NewSequence, AGAEffectCue* InEffectCue) + { + if (UGAEffectCueSequence* OldSequence = WeakSequence.Get()) + { + if (OnSequenceChangedHandle.IsValid()) + { + OldSequence->OnSignatureChanged().Remove(OnSequenceChangedHandle); + } + } + EffectCue = InEffectCue; + WeakSequence = NewSequence; + + if (NewSequence) + { + OnSequenceChangedHandle = NewSequence->OnSignatureChanged().AddSP(this, &SEffectCueSequenceEditorWidget::OnSequenceChanged); + } + + // If we already have a sequencer open, just assign the sequence + if (Sequencer.IsValid() && NewSequence) + { + if (Sequencer->GetRootMovieSceneSequence() != NewSequence) + { + Sequencer->ResetToNewRootSequence(*NewSequence); + } + return; + } + + // If we're setting the sequence to none, destroy sequencer + if (!NewSequence) + { + //Content->SetContent(SNew(STextBlock).Text(LOCTEXT("NothingSelected", "Select a sequence"))); + return; + } + + // We need to initialize a new sequencer instance + FSequencerInitParams SequencerInitParams; + { + TWeakObjectPtr LocalWeakSequence = NewSequence; + + SequencerInitParams.RootSequence = NewSequence; + SequencerInitParams.EventContexts = TAttribute>(this, &SEffectCueSequenceEditorWidget::GetEventContexts); + SequencerInitParams.PlaybackContext = TAttribute(this, &SEffectCueSequenceEditorWidget::GetPlaybackContext); + + TSharedRef AddMenuExtender = MakeShareable(new FExtender); + + AddMenuExtender->AddMenuExtension("AddTracks", EExtensionHook::Before, nullptr, + FMenuExtensionDelegate::CreateLambda([=](FMenuBuilder& MenuBuilder) { + + MenuBuilder.AddSubMenu( + FText::FromString("Component"), + FText::FromString("Add a binding to one of this actor's components and allow it to be animated by Sequencer"), + FNewMenuDelegate::CreateRaw(this, &SEffectCueSequenceEditorWidget::AddPossessComponentMenuExtensions), + false /*bInOpenSubMenuOnClick*/, + FSlateIcon()//"LevelSequenceEditorStyle", "LevelSequenceEditor.PossessNewActor") + ); + + }) + ); + + SequencerInitParams.ViewParams.bReadOnly = false;// !WeakBlueprintEditor.IsValid() && !NewSequence->IsEditable(); + SequencerInitParams.bEditWithinLevelEditor = false; + SequencerInitParams.ViewParams.AddMenuExtender = AddMenuExtender; + SequencerInitParams.ViewParams.UniqueName = "EffectCueActorSequenceEditor"; + SequencerInitParams.ViewParams.OnReceivedFocus.BindRaw(this, &SEffectCueSequenceEditorWidget::OnSequencerReceivedFocus); + } + + Sequencer = FModuleManager::LoadModuleChecked("Sequencer").CreateSequencer(SequencerInitParams); + Content->SetContent(Sequencer->GetSequencerWidget()); + } +}; + + + +FEffectCueSequenceEditorSummoner::FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor) + : FWorkflowTabFactory("EmbeddedEffectCueSequenceID", BlueprintEditor) + , WeakBlueprintEditor(BlueprintEditor) +{ + bIsSingleton = true; + + TabLabel = FText::FromString("Cue Sequencer"); +} + +TSharedRef FEffectCueSequenceEditorSummoner::CreateTabBody(const FWorkflowTabSpawnInfo& Info) const +{ + return SNew(SEffectCueSequenceEditorWidget, WeakBlueprintEditor); +} + +TSharedRef FAFEffectCueDetails::MakeInstance() +{ + return MakeShareable(new FAFEffectCueDetails); +} + +void FAFEffectCueDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + const IDetailsView* DetailsView = DetailLayout.GetDetailsView(); + if (DetailsView) + { + TSharedPtr HostTabManager = DetailsView->GetHostTabManager(); + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + AGAEffectCue* EffectCue = Cast(Objects[0].Get()); + + if (HostTabManager.IsValid() && HostTabManager->CanSpawnTab("EmbeddedEffectCueSequenceID")) + { + TSharedPtr ExistingTab = HostTabManager->FindExistingLiveTab(FName("EmbeddedEffectCueSequenceID")); + if (ExistingTab.IsValid()) + { + //EffectCue->StaticClass()->GetDefaultObject()->Sequence + + //auto SequencerWidget = StaticCastSharedRef(ExistingTab->GetContent()); + StaticCastSharedRef(ExistingTab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); + //bIsExternalTabAlreadyOpened = ThisSequence && SequencerWidget->GetSequence() == ThisSequence; + return; + } + //EffectCue->Sequence + if (!Tab.IsValid()) + Tab = HostTabManager->InvokeTab(FName("EmbeddedEffectCueSequenceID")); + //Tab->SetContent(Sequencer->GetSequencerWidget()); + StaticCastSharedRef(Tab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); + } + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h new file mode 100644 index 0000000..611e2aa --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h @@ -0,0 +1,36 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +#include "GraphEditor.h" +#include "ISequencer.h" +#include "Effects/GAEffectCueSequence.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" +#include "WorkflowTabFactory.h" + +struct FEffectCueSequenceEditorSummoner + : public FWorkflowTabFactory +{ + FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor); + + virtual TSharedRef CreateTabBody(const FWorkflowTabSpawnInfo& Info) const override; + /*virtual TSharedRef SpawnTab(const FWorkflowTabSpawnInfo& Info) const override;*/ +protected: + TWeakPtr WeakBlueprintEditor; +}; +class FAFEffectCueDetails : public IDetailCustomization +{ +protected: + TSharedPtr Sequencer; + FDelegateHandle OnBlueprintPreCompileHandle; + TSharedPtr Tab; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; +}; \ No newline at end of file diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp index 848e465..fec5719 100644 --- a/Source/ActionRPGGame/ARGameMode.cpp +++ b/Source/ActionRPGGame/ARGameMode.cpp @@ -2,7 +2,21 @@ #include "ARGameMode.h" #include "UObject/ConstructorHelpers.h" - +#include "Modules/ModuleManager.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" AARGameMode::AARGameMode() { } +void AARGameMode::BeginPlay() +{ + Super::BeginPlay(); + + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + //AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); + TArray< FString > ContentPaths; + TArray RootPaths; + FPackageName::QueryRootContentPaths(ContentPaths); + AssetRegistry.ScanPathsSynchronous(ContentPaths); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARGameMode.h b/Source/ActionRPGGame/ARGameMode.h index 46e5fe9..0965d82 100644 --- a/Source/ActionRPGGame/ARGameMode.h +++ b/Source/ActionRPGGame/ARGameMode.h @@ -1,7 +1,6 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. #pragma once - #include "CoreMinimal.h" #include "GameFramework/GameModeBase.h" #include "ARGameMode.generated.h" @@ -13,6 +12,8 @@ class AARGameMode : public AGameModeBase public: AARGameMode(); + + virtual void BeginPlay() override; }; diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp index 7feff36..54eb80a 100644 --- a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp @@ -1,5 +1,3 @@ -// Fill out your copyright notice in the Description page of Project Settings. - #include "ARAbilityAttributes.h" diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp index 11a7f6b..7a48ba8 100644 --- a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp @@ -1,5 +1,3 @@ -// Fill out your copyright notice in the Description page of Project Settings. - #include "ARCharacterAttributes.h" #include "Net/UnrealNetwork.h" @@ -13,5 +11,6 @@ void UARCharacterAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeP DOREPLIFETIME(UARCharacterAttributes, Armor); DOREPLIFETIME(UARCharacterAttributes, Energy); DOREPLIFETIME(UARCharacterAttributes, Stamina); - + DOREPLIFETIME(UARCharacterAttributes, Ammo); + DOREPLIFETIME(UARCharacterAttributes, MachineGunAmmo); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h index 690d68e..a79dd2a 100644 --- a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h @@ -26,9 +26,9 @@ class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase Stamina; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase Ammo; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase MachineGunAmmo; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase ShotgunAmmo; From b92dd1af1e9d88000c156864bb147b3b27f8148a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 13 Aug 2017 00:11:59 +0200 Subject: [PATCH 013/187] Fixed asyc loading in cooked build --- Config/DefaultGame.ini | 13 +++- .../Source/AbilityFramework/AFCueManager.cpp | 8 ++- .../Abilities/GAAbilityBase.cpp | 72 +++++++++++++++++++ .../Abilities/GAAbilityBase.h | 18 +++++ .../AbilityFramework.Build.cs | 2 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 4 +- Source/ActionRPGGame/ARGameMode.cpp | 23 +++--- Source/ActionRPGGame/ActionRPGGame.Build.cs | 2 +- Source/ActionRPGGame/ActionRPGGame.cpp | 7 +- .../Attributes/ARAbilityAttributes.cpp | 2 - .../Attributes/ARGunAttributes.cpp | 7 +- .../Attributes/ARGunAttributes.h | 2 +- 12 files changed, 138 insertions(+), 22 deletions(-) diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index f5b0269..2e03415 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -6,17 +6,24 @@ ProjectName=Third Person Game Template DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet [/Script/Engine.AssetManagerSettings] +-PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps"))) +-PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game"))) -PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) +-PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) bOnlyCookProductionAssets=False bShouldGuessTypeAndNameInEditor=True +bShouldAcquireMissingChunksOnLoad=False diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index b45079e..ab01ed8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -164,9 +164,11 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, } //actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); - actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - CueParams.Causer.Get(), CueParams.HitResult, CueParams); - + if (actor) + { + actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), + CueParams.Causer.Get(), CueParams.HitResult, CueParams); + } /*UseCues->Dequeue(actor); Cues->Enqueue(actor);*/ } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 05fd566..b32b9dd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -67,7 +67,79 @@ void UGAAbilityBase::Serialize(FArchive& Ar) UpdateAssetRegistryInfo(); } } +#if WITH_EDITORONLY_DATA +void UGAAbilityBase::UpdateAssetBundleData() +{ + AssetBundleData.Reset(); + + // By default parse the metadata + if (UAssetManager::IsValid()) + { + UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); + } +} + +void UGAAbilityBase::PreSave(const class ITargetPlatform* TargetPlatform) +{ + Super::PreSave(TargetPlatform); + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid()) + { + // Bundles may have changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +} +#endif + +FPrimaryAssetId UGAAbilityBase::GetPrimaryAssetId() const +{ + //FName Name = GetFName(); + //FName clsNam = GetClass()->GetFName(); + FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); + //FName dupa2 = FPackageName::GetShortFName(GetFName()); + const UGAAbilityBase* A = this; + return FPrimaryAssetId(FPrimaryAssetType("Ability"), dupa1); + //if (HasAnyFlags(RF_ClassDefaultObject)) + { + UClass* SearchNativeClass = GetClass(); + + while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) + { + SearchNativeClass = SearchNativeClass->GetSuperClass(); + } + + if (SearchNativeClass && SearchNativeClass != GetClass()) + { + // If blueprint, return native class and asset name + + } + + // Native CDO, return nothing + return FPrimaryAssetId(); + } + + // Data assets use Class and ShortName by default, there's no inheritance so class works fine + //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); +} +void UGAAbilityBase::PostLoad() +{ + Super::PostLoad(); + +#if WITH_EDITORONLY_DATA + FAssetBundleData OldData = AssetBundleData; + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid() && OldData != AssetBundleData) + { + // Bundles changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +#endif +} #if WITH_EDITOR void UGAAbilityBase::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index d5355df..0ed066f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -7,6 +7,8 @@ #include "../Attributes/GAAttributesBase.h" #include "AFAbilityInterface.h" #include "AFAbilityActivationSpec.h" +#include "AssetBundleData.h" +#include "SubclassOf.h" #include "GAAbilityBase.generated.h" /* @@ -272,7 +274,23 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask virtual void PostInitProperties() override; virtual void Serialize(FArchive& Ar) override; + // UObject interface + virtual FPrimaryAssetId GetPrimaryAssetId() const override; + virtual void PostLoad() override; +#if WITH_EDITORONLY_DATA + /** This scans the class for AssetBundles metadata on asset properties and initializes the AssetBundleData with InitializeAssetBundlesFromMetadata */ + virtual void UpdateAssetBundleData(); + + /** Updates AssetBundleData */ + virtual void PreSave(const class ITargetPlatform* TargetPlatform) override; + +protected: + /** Asset Bundle data computed at save time. In cooked builds this is accessible from AssetRegistry */ + UPROPERTY() + FAssetBundleData AssetBundleData; +#endif +public: #if WITH_EDITOR virtual void PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) override; #endif // WITH_EDITOR diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index 22267e6..47e74e2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -45,7 +45,7 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) "AIModule", "MovieScene", "MovieSceneTracks", - + "AssetRegistry" // ... add other public dependencies that you statically link with here ... } ); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 567582e..349a191 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -77,7 +77,9 @@ void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InAr { InArraySerializer.EffectInfos.Remove(Handle); //InArraySerializer.OwningComponent->OnEffectRepInfoRemoved.Broadcast(this); - + FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); + Timer.ClearTimer(ExpiredHandle); + Timer.ClearTimer(PeriodHandle); OwningComoponent->RemoveEffectEvent(OnExpiredEvent); OwningComoponent->RemoveEffectEvent(OnPeriodEvent); OwningComoponent->RemoveEffectEvent(OnRemovedEvent); diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp index fec5719..8bcab34 100644 --- a/Source/ActionRPGGame/ARGameMode.cpp +++ b/Source/ActionRPGGame/ARGameMode.cpp @@ -5,18 +5,25 @@ #include "Modules/ModuleManager.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" +#include "Abilities/ARAbilityBase.h" AARGameMode::AARGameMode() { } void AARGameMode::BeginPlay() { Super::BeginPlay(); - - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - //AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); - TArray< FString > ContentPaths; - TArray RootPaths; - FPackageName::QueryRootContentPaths(ContentPaths); - AssetRegistry.ScanPathsSynchronous(ContentPaths); + //FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + //IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + ////AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); + //TArray< FString > ContentPaths; + //TArray RootPaths; + //FPackageName::QueryRootContentPaths(ContentPaths); + //AssetRegistry.ScanPathsSynchronous(ContentPaths); + //if (UAssetManager* Manager = UAssetManager::GetIfValid()) + //{ + // Manager->StartBulkScanning(); + // Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); + // Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UARAbilityBase::StaticClass(), true); + // //Manager->ScanPrimaryAssetTypesFromConfig(); + //} } \ No newline at end of file diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 096481e..30690a8 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -39,6 +39,6 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) } ); PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", - "GameplayTags", "AbilityFramework", "SlateCore" }); + "GameplayTags", "AbilityFramework", "SlateCore", "AssetRegistry" }); } } diff --git a/Source/ActionRPGGame/ActionRPGGame.cpp b/Source/ActionRPGGame/ActionRPGGame.cpp index 3ca2847..de18043 100644 --- a/Source/ActionRPGGame/ActionRPGGame.cpp +++ b/Source/ActionRPGGame/ActionRPGGame.cpp @@ -4,6 +4,7 @@ #include "Modules/ModuleManager.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" +#include "Abilities/GAAbilityBase.h" void FActionRPGGameModule::StartupModule() { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); @@ -14,6 +15,10 @@ void FActionRPGGameModule::StartupModule() FPackageName::QueryRootContentPaths(ContentPaths); AssetRegistry.ScanPathsSynchronous(ContentPaths); + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); + } }; -IMPLEMENT_PRIMARY_GAME_MODULE(FActionRPGGameModule, ActionRPGGame, "ActionRPGGame" ); +IMPLEMENT_PRIMARY_GAME_MODULE(FActionRPGGameModule, ActionRPGGame, "ActionRPGGame"); \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp index 54eb80a..18272af 100644 --- a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp @@ -1,5 +1,3 @@ #include "ARAbilityAttributes.h" - - diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp index 849ac3b..01dfb7d 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp @@ -1,7 +1,12 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARGunAttributes.h" +#include "Net/UnrealNetwork.h" - +void UARGunAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + DOREPLIFETIME(UARGunAttributes, Magazine); +} diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Attributes/ARGunAttributes.h index 4812960..dafd585 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.h @@ -18,7 +18,7 @@ class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase FAFAttributeBase BaseDamage; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase CritChance; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase Magazine; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase RateOfFire; From 20ceeebfa0c08f91a7f540414dc5aae456e2dadc Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 17 Aug 2017 21:08:11 +0200 Subject: [PATCH 014/187] Fixing linux build --- ActionRPGGame.uproject | 4 ++++ Config/DefaultGame.ini | 3 +++ .../Source/AbilityFramework/AFAbilityComponent.cpp | 4 ++-- .../Source/AbilityFramework/AFCueManager.cpp | 8 ++++---- .../AbilityFramework/Attributes/GAAttributeBase.cpp | 4 ++-- .../AbilityFramework/Effects/GABlueprintLibrary.cpp | 2 +- .../Source/AbilityFramework/GAGlobalTypes.cpp | 8 ++++---- .../UI/Abilities/ARUIAbilityManagerComponent.cpp | 8 ++++---- .../UI/Abilities/ARUIAbilityManagerComponent.h | 2 +- 9 files changed, 25 insertions(+), 18 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index e3b9b8b..1cee936 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -42,5 +42,9 @@ "Name": "OnlineFramework", "Enabled": true } + ], + "TargetPlatforms": [ + "LinuxNoEditor", + "WindowsNoEditor" ] } \ No newline at end of file diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index 2e03415..43abb89 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -26,4 +26,7 @@ bOnlyCookProductionAssets=False bShouldGuessTypeAndNameInEditor=True bShouldAcquireMissingChunksOnLoad=False +[/Script/UnrealEd.ProjectPackagingSettings] +IncludeAppLocalPrerequisites=True +ApplocalPrerequisitesDirectory=(Path="$(EngineDir)/Binaries/ThirdParty/AppLocalDependencies") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index e7f283a..cea001d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -673,14 +673,14 @@ void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, F { FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputPressed, ActionName); - &InputComponent->AddActionBinding(AB); + InputComponent->AddActionBinding(AB); } // Released event { FInputActionBinding AB(ActionName.GetTagName(), IE_Released); AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputReleased, ActionName); - &InputComponent->AddActionBinding(AB); + InputComponent->AddActionBinding(AB); } SetBlockedInput(ActionName, false); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index ab01ed8..584815a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -118,10 +118,10 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, } FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - } + //if (mode == ENetMode::NM_Client) + //{ + // prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + //} UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), *prefix, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp index e271f71..d44e579 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -147,7 +147,7 @@ bool FAFAttributeBase::CheckIfModsMatch(const FGAEffectHandle& InHandle, const F { TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; auto It = mods.CreateConstIterator(); - for (It; It; ++It) + for (; It; ++It) { if (It->Key.HasAllAttributeTags(InHandle)) //or maybe the other way around ? { @@ -162,7 +162,7 @@ bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) { TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; auto It = mods.CreateConstIterator(); - for (It; It; ++It) + for (; It; ++It) { if (InMod > It->Value) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 2bb3311..a8c5df0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -175,7 +175,7 @@ FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class A instiComp = instiAttr->GetAbilityComp(); } - FVector location = targetComp ? targetComp->GetOwner()->GetActorLocation() : HitIn.ImpactPoint; + FVector location = targetComp ? targetComp->GetOwner()->GetActorLocation() : FVector(HitIn.ImpactPoint.X, HitIn.ImpactPoint.Y, HitIn.ImpactPoint.Z); FGAEffectContext Context( targetAttr ? targetAttr->GetAttributes() : nullptr, instiAttr ? instiAttr->GetAttributes() : nullptr, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index 8888e3e..0291d69 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -14,15 +14,15 @@ FGAEffectContext::FGAEffectContext(TWeakObjectPtr Targe TWeakObjectPtr TargetCompIn, TWeakObjectPtr InstigatorCompIn, TWeakObjectPtr InAvatar) - : TargetAttributes(TargetAttributesIn), + : TargetHitLocation(TargetHitLocationIn), + TargetAttributes(TargetAttributesIn), InstigatorAttributes(InstigatorAttributesIn), - TargetHitLocation(TargetHitLocationIn), Target(TargetIn), Causer(CauserIn), Instigator(InstigatorIn), + Avatar(InAvatar), TargetComp(TargetCompIn), - InstigatorComp(InstigatorCompIn), - Avatar(InAvatar) + InstigatorComp(InstigatorCompIn) { TargetInterface = Cast(TargetIn.Get()); InstigatorInterface = Cast(Instigator.Get()); diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index e8fd90c..ab6712c 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -120,7 +120,7 @@ void UARUIAbilityManagerComponent::SetInputTag(int32 SetIndex, int32 AbilityInde InputBindingsSet[SetIndex][AbilityIndex] = InAbilityTag; } -void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 AbilitySet +void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 InAbilitySet , int32 AbilityIndex) { //fake implementation untill I add AssetManager support. @@ -138,12 +138,12 @@ void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbil if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARUIAbilityManagerComponent::OnAbilityReady)) { - FGameplayTag d = GetInputTag(AbilitySet, AbilityIndex); + FGameplayTag d = GetInputTag(InAbilitySet, AbilityIndex); AbilityComp->OnAbilityAdded.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); } - FARAbilityEquipInfo ABInfo(AbilitySet, AbilityIndex, GetInputTag(AbilitySet, AbilityIndex)); + FARAbilityEquipInfo ABInfo(InAbilitySet, AbilityIndex, GetInputTag(InAbilitySet, AbilityIndex)); AwatingAbilityConfimation.Add(InAbilityTag, ABInfo); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, GetInputTag(AbilitySet, AbilityIndex)); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, GetInputTag(InAbilitySet, AbilityIndex)); } void UARUIAbilityManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag) diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h index 4f8037a..1811c3d 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -112,7 +112,7 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent FGameplayTag GetInputTag(int32 SetIndex, int32 AbilityIndex); void SetInputTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag); - void NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 AbilitySet + void NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 InAbilitySet , int32 AbilityIndex); UFUNCTION() void OnAbilityReady(const FGameplayTag& InAbilityTag); From c4e4d0f22a8d8c10d18dca55130f294e8d0fa319 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 20 Aug 2017 14:21:09 +0200 Subject: [PATCH 015/187] Disabled unused pluygins and fixed crashes when changing map --- ActionRPGGame.uproject | 8 +++ .../AbilityFramework/AFAbilityComponent.cpp | 18 +++++- .../AbilityFramework/AFAbilityComponent.h | 4 ++ .../Source/AbilityFramework/AFCueManager.cpp | 61 ++++++++++++++++++- .../Source/AbilityFramework/AFCueManager.h | 2 + .../Abilities/GAAbilityBase.cpp | 15 +++-- .../Abilities/GAAbilityBase.h | 2 +- .../Attributes/GAAttributesBase.cpp | 5 +- .../Attributes/GAAttributesBase.h | 9 ++- .../AbilityFrameworkEditor.Build.cs | 2 +- .../Attributes/ARGunAttributes.cpp | 11 +++- .../Attributes/ARGunAttributes.h | 5 +- 12 files changed, 129 insertions(+), 13 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 1cee936..2f8fe22 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -41,6 +41,14 @@ { "Name": "OnlineFramework", "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false } ], "TargetPlatforms": [ diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index cea001d..78de1d8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -155,6 +155,9 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn } } + //here, we should start attribute change prediction + //either change attribute or apply effect which will do so + FString prefix = ""; if (mode == ENetMode::NM_Standalone || role == ENetRole::ROLE_Authority) @@ -386,6 +389,7 @@ void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProp //possibly replicate it to everyone //to allow prediction for UI. DOREPLIFETIME(UAFAbilityComponent, DefaultAttributes); + DOREPLIFETIME(UAFAbilityComponent, RepAttributes); DOREPLIFETIME(UAFAbilityComponent, ModifiedAttribute); DOREPLIFETIME(UAFAbilityComponent, GameEffectContainer); @@ -427,6 +431,16 @@ bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, clas if (Ability.Ability) WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); } + + for (UGAAttributesBase* Attribute : RepAttributes) + { + //if (Set.InputOverride) + // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); + + if (Attribute) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Attribute), *Bunch, *RepFlags); + } + return WroteSomething; } void UAFAbilityComponent::GetSubobjectsWithStableNamesForNetworking(TArray& Objs) @@ -511,7 +525,9 @@ void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArr Ability->OwnerCamera = nullptr; } Ability->InitAbility(); - + Ability->Attributes = nullptr; + //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->AdditionalAttributes.FindRef(Ability->AbilityTag); + //Ability->Attributes = attr; InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); InArraySerializerC.AbilitiesComp->NotifyOnAbilityAdded(Ability->AbilityTag); InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(Ability->AbilityTag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 94cf1ac..b94beec 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -219,6 +219,9 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, //probabaly replace FGameplayTag with FObjectKey TMap AdditionalAttributes; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Replicated) + TArray RepAttributes; + UPROPERTY(ReplicatedUsing = OnRep_AttributeChanged) FGAModifiedAttributeData ModifiedAttribute; UFUNCTION() @@ -290,6 +293,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, { return; } + RepAttributes.Add(InAttributes); AdditionalAttributes.Add(InOwner, InAttributes); } UFUNCTION(BlueprintCallable, Category = "Test") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index 584815a..f117ce3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -30,6 +30,8 @@ void UAFCueManager::Initialize() #if WITH_EDITOR FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); #endif //WITH_EDITOR + FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); + FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); } void UAFCueManager::LoadCueSet() { @@ -79,10 +81,67 @@ void UAFCueManager::HandleOnPIEEnd(bool InVal) UsedCues.Remove(It->Key); } } - + } } #endif //WITH_EDITOR +void UAFCueManager::HandlePreLoadMap(const FString& InMapName) +{ + CurrentWorld = nullptr; + + InstancedCues.Reset(); + InstancedCues.Compact(); + UsedCues.Reset(); + UsedCues.Compact(); + //for (auto It = InstancedCues.CreateIterator(); It; ++It) + //{ + // if (It->Value.IsValid()) + // { + // while (!It->Value->IsEmpty()) + // { + // AGAEffectCue* ToDestroy = nullptr; + // It->Value->Dequeue(ToDestroy); + // if (ToDestroy) + // { + // ToDestroy->Destroy(); + // } + // } + // } + //} + //for (auto It = UsedCues.CreateIterator(); It; ++It) + //{ + // if (It->Value.Num() <= 0) + // { + // UsedCues.Remove(It->Key); + // } + // for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) + // { + // if (QIt->Value.IsValid()) + // { + // while (!QIt->Value->IsEmpty()) + // { + // AGAEffectCue* ToDestroy = nullptr; + // QIt->Value->Dequeue(ToDestroy); + // if (ToDestroy) + // { + // ToDestroy->Destroy(); + // } + // } + // } + // if (It->Value.Num() <= 0) + // { + // UsedCues.Remove(It->Key); + // } + // } + + //} +} +void UAFCueManager::HandlePostLoadMap(UWorld* InWorld) +{ + CurrentWorld = InWorld; +} + + void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h index 777afce..97efa3b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h @@ -39,6 +39,8 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject //handle clearing up cache when PIE mode is ending. void HandleOnPIEEnd(bool InVal); #endif //WITH_EDITOR + void HandlePreLoadMap(const FString& InMapName); + void HandlePostLoadMap(UWorld* InWorld); public: static UAFCueManager* Get(); void HandleCue(const FGameplayTagContainer& Tags, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index b32b9dd..67f2372 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -172,10 +172,6 @@ void UGAAbilityBase::InitAbility() if (!AbilityComponent) { AbilityComponent = GetAbilityComp(); - if (AbilityComponent) - { - AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes); - } } if (Attributes) { @@ -183,6 +179,17 @@ void UGAAbilityBase::InitAbility() Attributes->InitializeAttributesFromTable(); } + ENetRole role = AbilityComponent->GetOwnerRole(); + ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); + if (role == ENetRole::ROLE_Authority || + mode == ENetMode::NM_Standalone) + { + if (AbilityComponent && Attributes) + { + AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes); + } + } + if (!OwnerCamera) { OwnerCamera = POwner->FindComponentByClass(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 0ed066f..e9d3432 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -272,7 +272,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UGAAbilityBase(const FObjectInitializer& ObjectInitializer); virtual void PostInitProperties() override; - + virtual void Serialize(FArchive& Ar) override; // UObject interface virtual FPrimaryAssetId GetPrimaryAssetId() const override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp index 57b024f..e6daa97 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -17,7 +17,10 @@ UGAAttributesBase::~UGAAttributesBase() LastAttributeProp = nullptr; //make sure we clear this pointer. CachedFloatPropety = nullptr; } - +//void UGAAttributesBase::PostNetReceive() +//{ +// Super::PostNetReceive(); +//} void UGAAttributesBase::InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) { OwningAttributeComp = InOwningAttributeComp; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h index 2256045..b5786b6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h @@ -1,4 +1,11 @@ #pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "UObject/Object.h" +#include "UObject/Class.h" +#include "Templates/SubclassOf.h" +#include "UObject/UnrealType.h" +#include "UObject/CoreNet.h" #include "../Effects/GAGameEffect.h" #include "../GAGlobalTypes.h" #include "GAAttributeBase.h" @@ -46,7 +53,7 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject UDataTable* AttributeValues; UGAAttributesBase(const FObjectInitializer& ObjectInitializer); ~UGAAttributesBase(); - + //virtual void PostNetReceive() override; virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp); void InitializeAttributesFromTable(); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs index 03137c6..27d4dfe 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs @@ -7,7 +7,7 @@ public class AbilityFrameworkEditor : ModuleRules { public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) { - var EngineDir = Path.GetFullPath(BuildConfiguration.RelativeEnginePath); + var EngineDir = Path.GetFullPath(Target.RelativeEnginePath); PublicIncludePaths.AddRange( new string[] { "AbilityFramework", diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp index 01dfb7d..da12572 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp @@ -2,7 +2,7 @@ #include "ARGunAttributes.h" #include "Net/UnrealNetwork.h" - +#include "AFAbilityComponent.h" void UARGunAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const { @@ -10,3 +10,12 @@ void UARGunAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimePropert DOREPLIFETIME(UARGunAttributes, Magazine); } +void UARGunAttributes::OnRep_Magazine() +{ + float dua = 0; + UARGunAttributes* asd = this; + if (OwningAttributeComp->GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + Magazine = this->Magazine; + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Attributes/ARGunAttributes.h index dafd585..ae4ebfd 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.h @@ -18,7 +18,7 @@ class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase FAFAttributeBase BaseDamage; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase CritChance; - UPROPERTY(EditAnywhere, Replicated, Category = "Base") + UPROPERTY(EditAnywhere, ReplicatedUsing=OnRep_Magazine, Category = "Base") FAFAttributeBase Magazine; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase RateOfFire; @@ -31,5 +31,6 @@ class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase Spread; - + UFUNCTION() + void OnRep_Magazine(); }; From 3445d59aaaba7e1538c6662f27ae32a1416ed840 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 16 Sep 2017 00:02:29 +0200 Subject: [PATCH 016/187] Fixes --- ActionRPGGame.uproject | 72 +++++++------ Config/DefaultEngine.ini | 8 ++ .../AbilityFramework/AbilityFramework.uplugin | 58 +++++----- .../AbilityFramework/AFAbilityComponent.cpp | 102 +++++------------- .../AbilityFramework/AFAbilityComponent.h | 70 ++++++------ .../AbilityFramework/AFAbilityInterface.h | 2 +- .../Attributes/GAAttributeBase.h | 2 +- .../Effects/GAEffectCueSequence.cpp | 10 +- .../Effects/GAEffectCueSequence.h | 7 +- .../Source/AbilityFramework/GAGlobalTypes.h | 2 +- .../LatentActions/GALatentFunctionBase.h | 2 +- Source/ActionRPGGame/ARGameMode.cpp | 25 ++--- Source/ActionRPGGame/ARPlayerController.cpp | 6 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 15 ++- .../ActionRPGGame/UI/ARUIWeaponEquipment.cpp | 6 +- .../Abilities/ARUIAbilityManagerComponent.cpp | 40 +++---- .../Abilities/ARUIAbilityManagerComponent.h | 27 +---- 17 files changed, 207 insertions(+), 247 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 2f8fe22..cd474a3 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -17,40 +17,44 @@ ] } ], - "Plugins": [ - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "ActorSequenceEditor", - "Enabled": true - }, - { - "Name": "ImagePlate", - "Enabled": true - }, - { - "Name": "PerformanceMonitor", - "Enabled": true - }, - { - "Name": "OnlineSubsystemAmazon", - "Enabled": true - }, - { - "Name": "OnlineFramework", - "Enabled": true - }, - { - "Name": "SteamVR", - "Enabled": false - }, - { - "Name": "OculusVR", - "Enabled": false - } - ], + "Plugins": [ + { + "Name": "ActorSequence", + "Enabled": true + }, + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false + } + ], "TargetPlatforms": [ "LinuxNoEditor", "WindowsNoEditor" diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index e1d955a..23bc6b9 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -90,6 +90,14 @@ AssetManagerClassName=/Script/AbilityFramework.AFAssetManager [/Script/Engine.UserInterfaceSettings] bLoadWidgetsOnDedicatedServer=False +[/Script/Engine.NavigationSystem] +DataGatheringMode=Lazy + +[/Script/AIModule.AISystem] +HotSpotManagerClassName=/Script/AIModule.AIHotSpotManager +bAllowStrafing=True +bEnableBTAITasks=True + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 diff --git a/Plugins/AbilityFramework/AbilityFramework.uplugin b/Plugins/AbilityFramework/AbilityFramework.uplugin index b301dbe..cc4aedc 100644 --- a/Plugins/AbilityFramework/AbilityFramework.uplugin +++ b/Plugins/AbilityFramework/AbilityFramework.uplugin @@ -1,28 +1,34 @@ { - "FileVersion": 3, - "Version": 1, - "VersionName": "1.0", - "FriendlyName": "AbilityFramework", - "Description": "", - "Category": "Gameplay", - "CreatedBy": "", - "CreatedByURL": "", - "DocsURL": "", - "MarketplaceURL": "", - "SupportURL": "", - "CanContainContent": true, - "IsBetaVersion": true, - "Installed": false, - "Modules": [ - { - "Name": "AbilityFramework", - "Type": "Runtime", - "LoadingPhase": "Default" - }, - { - "Name": "AbilityFrameworkEditor", - "Type": "Editor", - "LoadingPhase": "PostEngineInit" - } - ] + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "AbilityFramework", + "Description": "", + "Category": "Gameplay", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": true, + "Installed": false, + "Modules": [ + { + "Name": "AbilityFramework", + "Type": "Runtime", + "LoadingPhase": "Default" + }, + { + "Name": "AbilityFrameworkEditor", + "Type": "Editor", + "LoadingPhase": "PostEngineInit" + } + ], + "Plugins": [ + { + "Name": "ActorSequence", + "Enabled": true + } + ] } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 78de1d8..c0ca615 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -529,7 +529,6 @@ void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArr //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->AdditionalAttributes.FindRef(Ability->AbilityTag); //Ability->Attributes = attr; InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); - InArraySerializerC.AbilitiesComp->NotifyOnAbilityAdded(Ability->AbilityTag); InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(Ability->AbilityTag); } } @@ -549,8 +548,7 @@ void FGASAbilityContainer::SetBlockedInput(const FGameplayTag& InInput, bool bBl } } UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn, - AActor* InAvatar, - FGameplayTag ActionName) + AActor* InAvatar) { if (AbilityIn && AbilitiesComp.IsValid()) { @@ -563,8 +561,6 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOfPCOwner = Cast(POwner->Controller); ability->OwnerCamera = nullptr; ability->AvatarActor = InAvatar; - - //ability->AIOwner = PawnInterface->GetGameController(); } ability->InitAbility(); FGameplayTag Tag = ability->AbilityTag; @@ -573,12 +569,10 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOfGetNetMode() == ENetMode::NM_Standalone || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) { - AbilitiesComp->NotifyOnAbilityAdded(ability->AbilityTag); AbilitiesComp->NotifyOnAbilityReady(ability->AbilityTag); } /* if (ActionName.IsValid()) @@ -661,10 +655,6 @@ void UAFAbilityComponent::InitializeComponent() ActiveCues.OwningComp = this; //ActiveCues.OwningComponent = this; AppliedTags.AddTagContainer(DefaultTags); - //TestRunnable = new FAsyncUObjectRunnable(this); - //TEstAsyncUObject = NewObject(this, UAsyncUObject::StaticClass(), TEXT("AwesomeObject"), RF_StrongRefOnFrame | RF_Standalone); - //TEstAsyncUObject->AddToRoot(); - //RouterThread = FRunnableThread::Create(TEstAsyncUObject, TEXT("AsyncUObject.Test"), 128 * 1024, TPri_Normal, FPlatformAffinity::GetPoolThreadMask()); InitializeInstancedAbilities(); } void UAFAbilityComponent::UninitializeComponent() @@ -700,11 +690,9 @@ void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, F } SetBlockedInput(ActionName, false); } -void UAFAbilityComponent::BP_SetAbilityToAction(FGameplayTag InAbilityTag, FGameplayTag InInputTag) -{ - SetAbilityToAction(InAbilityTag, InInputTag); -} -void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) + +void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, + const FAFOnAbilityReady& InputDelegate) { AbilityContainer.SetAbilityToAction(InAbilityTag, InInputTag); ENetRole role = GetOwnerRole(); @@ -712,6 +700,10 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c if (GetOwner()->GetNetMode() == ENetMode::NM_Client && role == ENetRole::ROLE_AutonomousProxy) { + if (InputDelegate.IsBound()) + { + AddOnAbilityInputReadyDelegate(InAbilityTag, InputDelegate); + } ServerSetAbilityToAction(InAbilityTag, InInputTag); } } @@ -719,13 +711,19 @@ void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGamepla { if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) { - SetAbilityToAction(InAbilityTag, InInputTag); + SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); } } bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { return true; } + +void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag) +{ + NotifyOnAbilityInputReady(AbilityTag); +} + void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) { NativeInputPressed(ActionName); @@ -802,18 +800,16 @@ bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag Action return true; } void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName) + AActor* InAvatar) { - NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputName); + NativeAddAbilityFromTag(InAbilityTag, InAvatar); } void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName) + AActor* InAvatar) { if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputName); + ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar); } else { @@ -830,7 +826,7 @@ void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, FPrimaryAssetTypeInfo Info; if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbilityTag, InInputName, PrimaryAssetId); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbilityTag, PrimaryAssetId); Manager->LoadPrimaryAsset(PrimaryAssetId, TArray(), @@ -842,20 +838,18 @@ void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, } void UAFAbilityComponent::ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName) + AActor* InAvatar) { - NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputName); + NativeAddAbilityFromTag(InAbilityTag, InAvatar); } bool UAFAbilityComponent::ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName) + AActor* InAvatar) { return true; } void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, - FGameplayTag InInputName, FPrimaryAssetId InPrimaryAssetId) + FPrimaryAssetId InPrimaryAssetId) { if (UAssetManager* Manager = UAssetManager::GetIfValid()) { @@ -863,7 +857,7 @@ void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, TSubclassOf cls = Cast(loaded); if (cls) { - NativeAddAbility(cls, nullptr, InInputName); + InstanceAbility(cls, nullptr); } { @@ -871,25 +865,6 @@ void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, } } } -void UAFAbilityComponent::BP_AddAbility(TSubclassOf AbilityClass, - AActor* InAvatar, - FGameplayTag ActionName, bool bAutoBind) -{ - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - return; - } - else - { - NativeAddAbility(AbilityClass, InAvatar, ActionName, bAutoBind); - } -} -void UAFAbilityComponent::NativeAddAbility(TSubclassOf AbilityClass, - AActor* InAvatar, - FGameplayTag ActionName, bool bAutoBind) -{ - InstanceAbility(AbilityClass, InAvatar, ActionName); -} void UAFAbilityComponent::BP_RemoveAbility(FGameplayTag TagIn) { @@ -900,38 +875,17 @@ UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(FGameplayTag TagIn) return AbilityContainer.GetAbility(TagIn); } UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass, - AActor* InAvatar, - FGameplayTag ActionName) + AActor* InAvatar) { if (AbilityClass) { - UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InAvatar, ActionName); + UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InAvatar); AbilityContainer.MarkArrayDirty(); return ability; } return nullptr; } -void UAFAbilityComponent::NativeAddAbilitiesFromSet(TSubclassOf AbilitySet) -{ - //do not let add abilities on non authority. - if (GetOwnerRole() < ENetRole::ROLE_Authority) - return; - - UGAAbilitySet* Set = AbilitySet.GetDefaultObject(); - int32 Index = 0; - for (const FGASAbilitySetItem& Item : Set->AbilitySet.Abilities) - { - InstanceAbility(Item.AbilityClass, nullptr, Item.Binding); - Index++; - } -} - -void UAFAbilityComponent::BP_AddAbilitiesFromSet(TSubclassOf AbilitySet) -{ - NativeAddAbilitiesFromSet(AbilitySet); -} - void UAFAbilityComponent::OnRep_InstancedAbilities() { } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index b94beec..23382da 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -12,7 +12,7 @@ #include "Effects/GAGameEffect.h" #include "GAGlobalTypes.h" -#include "Messaging.h" +//#include "Messaging.h" #include "GameplayTagAssetInterface.h" #include "AFAbilityInterface.h" @@ -143,8 +143,7 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, - AActor* InAvatar, - FGameplayTag ActionName); + AActor* InAvatar); void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); UGAAbilityBase* GetAbility(FGameplayTag TagIn); @@ -554,15 +553,32 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, OnAbilityReadyMap.Remove(InAbilityTag); } } + + TMap OnAbilityInputReadyMap; + + void AddOnAbilityInputReadyDelegate(const FGameplayTag& InAbilityTag, const FAFOnAbilityReady& InDelegate) + { + OnAbilityInputReadyMap.Add(InAbilityTag, InDelegate); + } + + void NotifyOnAbilityInputReady(const FGameplayTag& InAbilityTag) + { + if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityTag)) + { + Ready->ExecuteIfBound(); + OnAbilityInputReadyMap.Remove(InAbilityTag); + } + } + FAFOnAbilityReady OnAbilityReady; + UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") FAFOnAbilityAdded OnAbilityAdded; FAFMontageGenericDelegate OnAbilityNotifyBegin; FAFMontageGenericDelegate OnAbilityNotifyTick; FAFMontageGenericDelegate OnAbilityNotifyEnd; - - //class IIGIPawn* PawnInterface; + private: @@ -584,22 +600,25 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, TMap BlockedInput; //TSharedPtr AbilityLoadedHandle; - void OnFinishedLoad(FGameplayTag InAbilityTag, - FGameplayTag InInputName, FPrimaryAssetId InPrimaryAssetId); + void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId); void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") void BP_BindAbilityToAction(FGameplayTag ActionName); void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); //need to be called on both client and server. - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, const FAFOnAbilityReady& InputDelegate); + UFUNCTION(Server, Reliable, WithValidation) void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Set Ability To Action"), Category = "AbilityFramework|Abilities") - void BP_SetAbilityToAction(FGameplayTag InAbilityTag, FGameplayTag InInputTag); + /* Called when ability action has been binded on server. */ + UFUNCTION(Client, Reliable) + void ClientNotifyAbilityInputReady(FGameplayTag AbilityTag); + void ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag); + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") void BP_InputPressed(FGameplayTag ActionName); @@ -628,48 +647,30 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, */ UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability From Tag"), Category = "AbilityFramework|Abilities") void BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName); + AActor* InAvatar); void NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName); + AActor* InAvatar); UFUNCTION(Server, Reliable, WithValidation) void ServerNativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName); + AActor* InAvatar); void ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName); + AActor* InAvatar); bool ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar, - FGameplayTag InInputName); + AActor* InAvatar); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability"), Category = "AbilityFramework|Abilities") - void BP_AddAbility(TSubclassOf AbilityClass, - AActor* InAvatar, - FGameplayTag ActionName, bool bAutoBind = true); //TODO: Make it procted - void NativeAddAbility(TSubclassOf AbilityClass, AActor* InAvatar, - FGameplayTag ActionName, bool bAutoBind = true); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") void BP_RemoveAbility(FGameplayTag TagIn); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); - /* - Should be called on server. - Adds new ability to ActiveAbilities; - */ - void NativeAddAbilitiesFromSet(TSubclassOf AbilitySet); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Abilities From Set"), Category = "AbilityFramework|Abilities") - void BP_AddAbilitiesFromSet(TSubclassOf AbilitySet); bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; @@ -678,8 +679,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, protected: void InitializeInstancedAbilities(); UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, - AActor* InAvatar, - FGameplayTag ActionName = FGameplayTag()); + AActor* InAvatar); /* Messagin implementation for applying effects from multiple threads (in case at some beatyfull day UObject will be able to exist on any thread), and from single thread. diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h index 27b55ba..d15c9bf 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h @@ -3,7 +3,7 @@ #include "Effects/GAGameEffect.h" #include "Attributes/GAAttributeGlobals.h" #include "GAGlobalTypes.h" -#include "Messaging.h" +//#include "Messaging.h" #include "AFAbilityInterface.generated.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h index 02f2d4e..2b9559f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -4,7 +4,7 @@ #include "../Effects/GAEffectGlobalTypes.h" // Messaging -#include "Messaging.h" +//#include "Messaging.h" #include "GAAttributeBase.generated.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp index 55157b3..86ed0f2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp @@ -12,7 +12,7 @@ #include "Classes/Engine/SimpleConstructionScript.h" #include "Engine/Blueprint.h" #include "UObject/Package.h" - +#include "ActorSequenceObjectReference.h" #include "GAEffectCueSequence.h" @@ -40,7 +40,7 @@ void UGAEffectCueSequence::PostInitProperties() if (!bHasBeenInitialized && !HasAnyFlags(RF_ClassDefaultObject) && OwnerCue && !OwnerCue->HasAnyFlags(RF_ClassDefaultObject)) { FGuid BindingID = MovieScene->AddPossessable(OwnerCue ? OwnerCue->GetActorLabel() : TEXT("Owner"), OwnerCue ? OwnerCue->GetClass() : AGAEffectCue::StaticClass()); - ObjectReferences.CreateBinding(BindingID, FActorSequenceObjectReference::CreateForContextActor()); + //ObjectReferences.CreateBinding(BindingID, FActorSequenceObjectReference::CreateForContextActor()); OnInitializeSequenceEvent.Broadcast(this); bHasBeenInitialized = true; @@ -87,7 +87,7 @@ void UGAEffectCueSequence::BindPossessableObject(const FGuid& ObjectId, UObject& if (AActor* Actor = Cast(&PossessedObject)) { - ObjectReferences.CreateBinding(ObjectId, FActorSequenceObjectReference::CreateForActor(Actor, ActorContext)); + //ObjectReferences.CreateBinding(ObjectId, FActorSequenceObjectReference::CreateForActor(Actor, ActorContext)); } } @@ -107,7 +107,7 @@ void UGAEffectCueSequence::LocateBoundObjects(const FGuid& ObjectId, UObject* Co { if (Context) { - ObjectReferences.ResolveBinding(ObjectId, CastChecked(Context), OutObjects); + //ObjectReferences.ResolveBinding(ObjectId, CastChecked(Context), OutObjects); } } @@ -126,5 +126,5 @@ UObject* UGAEffectCueSequence::GetParentObject(UObject* Object) const void UGAEffectCueSequence::UnbindPossessableObjects(const FGuid& ObjectId) { - ObjectReferences.RemoveBinding(ObjectId); + //ObjectReferences.RemoveBinding(ObjectId); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h index 9d46082..3f21841 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h @@ -6,8 +6,7 @@ #include "MovieSceneSequence.h" #include "MovieScene.h" #include "LazyObjectPtr.h" -///D:\Unreal\UnrealEngine-Master\Engine\Source\Runtime\ActorSequence\Public\ActorSequenceObjectReference.h -#include "Runtime/ActorSequence/Public/ActorSequenceObjectReference.h" +#include "ActorSequence.h" #include "GAEffectCueSequence.generated.h" UCLASS(BlueprintType, DefaultToInstanced) @@ -20,8 +19,8 @@ class ABILITYFRAMEWORK_API UGAEffectCueSequence : public UMovieSceneSequence UMovieScene* MovieScene; private: /** Collection of object references. */ - UPROPERTY() - FActorSequenceObjectReferenceMap ObjectReferences; + //UPROPERTY() + // FActorSequenceObjectReferenceMap ObjectReferences; #if WITH_EDITORONLY_DATA private: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index ef094f1..63f80b8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "GameplayTagsModule.h" #include "GameplayTagContainer.h" -#include "Messaging.h" +//#include "Messaging.h" #include "GAGlobalTypes.generated.h" /* diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h index 7c5c16e..a9e3773 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h @@ -1,7 +1,7 @@ #pragma once #include "CoreMinimal.h" #include "Engine/EngineBaseTypes.h" -#include "Messaging.h" +//#include "Messaging.h" #include "GALatentFunctionBase.generated.h" struct FGALatentFunctionTick: public FTickFunction diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp index 8bcab34..7bc2c4f 100644 --- a/Source/ActionRPGGame/ARGameMode.cpp +++ b/Source/ActionRPGGame/ARGameMode.cpp @@ -6,24 +6,21 @@ #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "Abilities/ARAbilityBase.h" +//#include "IpConnec" +//#include "OnlineSubsystemUtils/IpConnection.h" +#include "IPAddress.h" + AARGameMode::AARGameMode() { } void AARGameMode::BeginPlay() { Super::BeginPlay(); - //FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - //IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - ////AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); - //TArray< FString > ContentPaths; - //TArray RootPaths; - //FPackageName::QueryRootContentPaths(ContentPaths); - //AssetRegistry.ScanPathsSynchronous(ContentPaths); - //if (UAssetManager* Manager = UAssetManager::GetIfValid()) - //{ - // Manager->StartBulkScanning(); - // Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); - // Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UARAbilityBase::StaticClass(), true); - // //Manager->ScanPrimaryAssetTypesFromConfig(); - //} + //if (GetNetMode() == ENetMode::NM_DedicatedServer) + { + if (UNetConnection* Conn = GetNetConnection()) + { + UE_LOG(LogTemp, Warning, TEXT("Your message, %s \n"), *FString::FromInt(Conn->GetAddrAsInt())); + } + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 0f7e369..3a93410 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -37,11 +37,11 @@ void AARPlayerController::SetPawn(APawn* InPawn) FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); - AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr, /*Input*/ InputNextWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr); FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); - AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, /*Input*/ InputPreviousWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr); } } @@ -79,5 +79,5 @@ void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGamepl UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - AbilityComp->SetAbilityToAction(InAbilityTag, InInputTag); + AbilityComp->SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); } \ No newline at end of file diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 30690a8..5311281 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -38,7 +38,18 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) // ... add other private include paths required here ... } ); - PublicDependencyModuleNames.AddRange(new string[] { "Core", "CoreUObject", "Engine", "InputCore", - "GameplayTags", "AbilityFramework", "SlateCore", "AssetRegistry" }); + PublicDependencyModuleNames.AddRange(new string[] { + "Core", + "CoreUObject", + "Engine", + "InputCore", + "GameplayTags", + "AbilityFramework", + "SlateCore", + "AssetRegistry", + "Sockets", + "OnlineSubsystemUtils", + "ActorSequence" + }); } } diff --git a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp index 04a3435..b63b8fd 100644 --- a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp +++ b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp @@ -60,7 +60,7 @@ void UARUIWeaponEquipment::NativeEquipWeapon(const FGameplayTag& InAbilityTag, i FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UARUIWeaponEquipment::OnWeaponReady, InAbilityTag, SlotIndex); AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, /*Input*/ ShootInput); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , /*Input*/ ShootInput); } void UARUIWeaponEquipment::OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex) @@ -82,8 +82,8 @@ void UARUIWeaponEquipment::OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIn Weapons[SlotIndex] = Ability; ActiveWeapon = Ability; ActiveWeaponIndex = SlotIndex; - AbilityComp->SetAbilityToAction(InAbilityTag, ShootInput); - AbilityComp->SetAbilityToAction(InAbilityTag, ReloadInput); + AbilityComp->SetAbilityToAction(InAbilityTag, ShootInput, FAFOnAbilityReady()); + AbilityComp->SetAbilityToAction(InAbilityTag, ReloadInput, FAFOnAbilityReady()); } else { diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index ab6712c..bddbbc6 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -136,21 +136,26 @@ void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbil if (!AbilityComp) return; - if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARUIAbilityManagerComponent::OnAbilityReady)) + /*if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARUIAbilityManagerComponent::OnAbilityReady)) { FGameplayTag d = GetInputTag(InAbilitySet, AbilityIndex); - AbilityComp->OnAbilityAdded.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); - } - FARAbilityEquipInfo ABInfo(InAbilitySet, AbilityIndex, GetInputTag(InAbilitySet, AbilityIndex)); - AwatingAbilityConfimation.Add(InAbilityTag, ABInfo); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, GetInputTag(InAbilitySet, AbilityIndex)); + AbilityComp->OnAbilityReady.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); + }*/ + FGameplayTag IAbilityInput = GetInputTag(InAbilitySet, AbilityIndex); + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARUIAbilityManagerComponent::OnAbilityReady, + InAbilityTag, IAbilityInput, InAbilitySet, AbilityIndex); + AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, ReadyDelegate); + + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , GetInputTag(InAbilitySet, AbilityIndex)); } -void UARUIAbilityManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag) +void UARUIAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, + int32 InAbilitySet, int32 InAbilityIndex) { - NativeOnAbilityReady(InAbilityTag); + NativeOnAbilityReady(InAbilityTag, InAbilityInput, InAbilitySet, InAbilityIndex); } -void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAbilityTag) +void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAbilityTag, const FGameplayTag InAbilityInput, + int32 InAbilitySet, int32 InAbilityIndex) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -163,20 +168,15 @@ void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAb if (!AbilityComp) return; - if (AwatingAbilityConfimation.Contains(InAbilityTag)) - { - FARAbilityEquipInfo Value; - AwatingAbilityConfimation.RemoveAndCopyValue(InAbilityTag, Value); - UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + + UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - SetAbility(Value.AbilitySetIndex, Value.AbilityIndex, Ability); - SetAbilityTag(Value.AbilitySetIndex, Value.AbilityIndex, InAbilityTag); - SetInputTag(Value.AbilitySetIndex, Value.AbilityIndex, Value.InputBinding); + SetAbility(InAbilitySet, InAbilityIndex, Ability); + SetAbilityTag(InAbilitySet, InAbilityIndex, InAbilityTag); + SetInputTag(InAbilitySet, InAbilityIndex, InAbilityInput); - AbilityComp->SetAbilityToAction(InAbilityTag, Value.InputBinding); - } - + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); } void UARUIAbilityManagerComponent::SwitchSet() diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h index 1811c3d..60c1698 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -9,26 +9,6 @@ #include "ARAvailableAbilities.h" #include "ARUIAbilityManagerComponent.generated.h" -USTRUCT() -struct FARAbilityEquipInfo -{ - GENERATED_BODY() -public: - int32 AbilitySetIndex; - int32 AbilityIndex; - FGameplayTag InputBinding; - - FARAbilityEquipInfo() - {}; - FARAbilityEquipInfo(int32 InAbilitySetIndex - , int32 InAbilityIndex - , FGameplayTag InInputBinding - ) - : AbilitySetIndex(InAbilitySetIndex), - AbilityIndex(InAbilityIndex), - InputBinding(InInputBinding) - {}; -}; USTRUCT(BlueprintType) struct FARAbilityInputBinding { @@ -84,7 +64,6 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent TArray> AbilityTagsSet; TArray>> AbilitySet; - TMap AwatingAbilityConfimation; public: UPROPERTY(EditAnywhere, Category = "Widget Config") TSubclassOf DragVisualClass; @@ -115,9 +94,11 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent void NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 InAbilitySet , int32 AbilityIndex); UFUNCTION() - void OnAbilityReady(const FGameplayTag& InAbilityTag); + void OnAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, + int32 InAbilitySet, int32 InAbilityIndex); - void NativeOnAbilityReady(const FGameplayTag& InAbilityTag); + void NativeOnAbilityReady(const FGameplayTag& InAbilityTag, const FGameplayTag InAbilityInput, + int32 InAbilitySet, int32 InAbilityIndex); void SwitchSet(); UFUNCTION() From 14d5c61cfdc23a66f4de5625e73f4c51c446f59c Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 15 Oct 2017 00:23:38 +0200 Subject: [PATCH 017/187] fixing multiplayer issues and working on better prediction. --- ActionRPGGame.uproject | 80 ++++---- Config/DefaultEngine.ini | 10 + Config/DefaultGame.ini | 1 + .../AbilityFramework/AFAbilityComponent.cpp | 134 ++++++++----- .../AbilityFramework/AFAbilityComponent.h | 124 ++++++++++-- .../AbilityFramework/AFAbilityInterface.h | 2 + .../Abilities/GAAbilityBase.cpp | 66 ++++++- .../Abilities/GAAbilityBase.h | 32 +++- .../Abilities/Tasks/GAAbilityTask.cpp | 25 +++ .../Abilities/Tasks/GAAbilityTask.h | 4 + .../Attributes/GAAttributeBase.cpp | 18 +- .../Attributes/GAAttributeBase.h | 15 +- .../Attributes/GAAttributeExtension.cpp | 15 ++ .../Attributes/GAAttributeExtension.h | 11 +- .../Attributes/GAAttributesBase.cpp | 5 +- .../Effects/GABlueprintLibrary.cpp | 9 + .../AbilityFramework/Effects/GAGameEffect.cpp | 53 +++++- .../AbilityFramework/Effects/GAGameEffect.h | 72 +++---- .../Source/AbilityFramework/GAGlobalTypes.cpp | 21 ++ .../Source/AbilityFramework/GAGlobalTypes.h | 57 ++++-- .../LatentActions/GALatentFunctionBase.cpp | 5 - .../LatentActions/GALatentFunctionBase.h | 1 - .../Tests/GAAttributesTests.cpp | 48 ++--- Source/ActionRPGGame/ARCharacter.h | 4 + Source/ActionRPGGame/ARPlayerController.cpp | 25 +-- Source/ActionRPGGame/ARPlayerController.h | 8 +- .../Attributes/ARGunAttributes.cpp | 6 +- .../Attributes/ARGunAttributes.h | 8 +- .../ActionRPGGame/UI/ARUIWeaponEquipment.cpp | 12 +- .../Abilities/ARUIAbilityManagerComponent.cpp | 44 +++-- .../Abilities/ARUIAbilityManagerComponent.h | 6 + .../Weapons/ARWeaponAbilityBase.cpp | 15 ++ .../Weapons/ARWeaponAbilityBase.h | 23 +++ .../ActionRPGGame/Weapons/ARWeaponAvatar.cpp | 27 +++ Source/ActionRPGGame/Weapons/ARWeaponAvatar.h | 28 +++ .../Weapons/ARWeaponManagerComponent.cpp | 179 ++++++++++++++++++ .../Weapons/ARWeaponManagerComponent.h | 66 +++++++ 37 files changed, 996 insertions(+), 263 deletions(-) create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponAvatar.h create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index cd474a3..01a8ce9 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -17,44 +17,48 @@ ] } ], - "Plugins": [ - { - "Name": "ActorSequence", - "Enabled": true - }, - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "ActorSequenceEditor", - "Enabled": true - }, - { - "Name": "ImagePlate", - "Enabled": true - }, - { - "Name": "PerformanceMonitor", - "Enabled": true - }, - { - "Name": "OnlineSubsystemAmazon", - "Enabled": true - }, - { - "Name": "OnlineFramework", - "Enabled": true - }, - { - "Name": "SteamVR", - "Enabled": false - }, - { - "Name": "OculusVR", - "Enabled": false - } - ], + "Plugins": [ + { + "Name": "ActorSequence", + "Enabled": true + }, + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false + }, + { + "Name": "Niagara", + "Enabled": true + } + ], "TargetPlatforms": [ "LinuxNoEditor", "WindowsNoEditor" diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 23bc6b9..ca25dd0 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -98,6 +98,16 @@ HotSpotManagerClassName=/Script/AIModule.AIHotSpotManager bAllowStrafing=True bEnableBTAITasks=True +[PacketSimulationSettings] +PktLag=500 +PktLagVariance=0 +PktLoss=10 +PktOrder=0 +PktDup=0 + +[/Script/UnrealEd.HierarchicalLODSettings] +bForceSettingsInAllMaps=False + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index 43abb89..94d0dab 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -29,4 +29,5 @@ bShouldAcquireMissingChunksOnLoad=False [/Script/UnrealEd.ProjectPackagingSettings] IncludeAppLocalPrerequisites=True ApplocalPrerequisitesDirectory=(Path="$(EngineDir)/Binaries/ThirdParty/AppLocalDependencies") +bGenerateChunks=True diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index c0ca615..222b25d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -29,6 +29,33 @@ DEFINE_STAT(STAT_ApplyEffect); DEFINE_STAT(STAT_ModifyAttribute); +void FAFReplicatedAttributeItem::PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer) +{ + FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); + ArraySerializer.AttributeMap.Remove(AttributeTag); +} +void FAFReplicatedAttributeItem::PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer) +{ + FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); + UGAAttributesBase*& Attribute = ArraySerializer.AttributeMap.FindOrAdd(AttributeTag); + Attribute = Attributes; +} +void FAFReplicatedAttributeItem::PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer) +{ + +} +UGAAttributesBase* FAFReplicatedAttributeContainer::Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter) +{ + UGAAttributesBase* AttributesDup = DuplicateObject(InAttributes, InOuter); + FAFReplicatedAttributeItem Item; + Item.AttributeTag = InTag; + Item.Attributes = AttributesDup; + Attributes.Add(Item); + MarkItemDirty(Item); + UGAAttributesBase*& Added = AttributeMap.FindOrAdd(InTag); + Added = AttributesDup; + return AttributesDup; +} UAFAbilityComponent::UAFAbilityComponent(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { @@ -154,46 +181,39 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn MulticastApplyEffectCue(CueParams); } } - + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + } + else if (mode == ENetMode::NM_DedicatedServer) + { + prefix = FString::Printf(TEXT("DedicatedServer: ")); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), + *prefix, + *GetOwner()->GetName(), + *InContext.Instigator->GetName() + ); //here, we should start attribute change prediction //either change attribute or apply effect which will do so - FString prefix = ""; - if (mode == ENetMode::NM_Standalone - || role == ENetRole::ROLE_Authority) + + //if (mode == ENetMode::NM_Standalone + // || role >= ENetRole::ROLE_Authority) { - if (mode == ENetMode::NM_Client) - { - prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - } - else if (mode == ENetMode::NM_DedicatedServer) - { - prefix = FString::Printf(TEXT("DedicatedServer: ")); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), - *prefix, - *GetOwner()->GetName(), - *InContext.Instigator->GetName() - ); //execute cue from effect regardless if we have target object or not. if (InContext.TargetComp.IsValid()) return InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); } - return FGAEffectHandle(); - -// if (EffectIn.IsValid() && EffectIn.Context.TargetComp.IsValid()) -// { - //OnEffectApplyToTarget.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); - // return EffectIn.Context.TargetComp->ApplyEffectToSelf(EffectIn, HandleIn); -// } } void UAFAbilityComponent::OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) { - + } void UAFAbilityComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty ,FAFFunctionModifier Modifier, FGAEffectContext InContex) @@ -432,13 +452,13 @@ bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, clas WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); } - for (UGAAttributesBase* Attribute : RepAttributes) + for (const FAFReplicatedAttributeItem& Attribute : RepAttributes.Attributes) { //if (Set.InputOverride) // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); - if (Attribute) - WroteSomething |= Channel->ReplicateSubobject(const_cast(Attribute), *Bunch, *RepFlags); + if (Attribute.Attributes) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Attribute.Attributes), *Bunch, *RepFlags); } return WroteSomething; @@ -526,8 +546,8 @@ void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArr } Ability->InitAbility(); Ability->Attributes = nullptr; - //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->AdditionalAttributes.FindRef(Ability->AbilityTag); - //Ability->Attributes = attr; + UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); + Ability->Attributes = attr; InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(Ability->AbilityTag); } @@ -588,12 +608,19 @@ void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, { FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InInputTag); AbilityTag = InAbilityTag; + + if (!AbilitiesComp.IsValid()) + return; + if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + AbilitiesComp->ClientNotifyAbilityInputReady(InAbilityTag); + } } UGAAbilityBase* FGASAbilityContainer::GetAbility(FGameplayTag TagIn) { return AbilitiesInputs.FindRef(TagIn); } -void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName) +void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) { if (BlockedInput.FindRef(ActionName)) { @@ -608,7 +635,7 @@ void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName) ability->ConfirmAbility(); return; } - ability->OnNativeInputPressed(ActionName); + ability->OnNativeInputPressed(ActionName, InPredictionHandle); } } void FGASAbilityContainer::HandleInputReleased(FGameplayTag ActionName) @@ -635,7 +662,8 @@ void FGASAbilityContainer::TriggerAbylityByTag(FGameplayTag InTag) ability->ConfirmAbility(); return; } - ability->OnNativeInputPressed(FGameplayTag()); + FAFPredictionHandle PredHandle = FAFPredictionHandle::GenerateClientHandle(AbilitiesComp.Get()); + ability->OnNativeInputPressed(FGameplayTag(), PredHandle); } } @@ -730,37 +758,43 @@ void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) } void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) { - if (GetOwnerRole() < ENetRole::ROLE_Authority) + FAFPredictionHandle PredHandle; + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { - ServerNativeInputPressed(ActionName); + PredHandle = FAFPredictionHandle::GenerateClientHandle(this); + } + //if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeInputPressed(ActionName, PredHandle); //UE_LOG(AbilityFramework, Log, TEXT("Client UAFAbilityComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); //naive needs better qynchornization to what going on where. //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) { //if (Ability->AbilityComponent == this) { - AbilityContainer.HandleInputPressed(ActionName); + AbilityContainer.HandleInputPressed(ActionName, PredHandle); } } } - else - { + //else + //{ //UE_LOG(AbilityFramework, Log, TEXT("Server UAFAbilityComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - { + //{ //if (Ability->AbilityComponent == this) - { - AbilityContainer.HandleInputPressed(ActionName); - } - } - } + //{ + // AbilityContainer.HandleInputPressed(ActionName); + //} + //} + //} } -void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName) +void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) { - NativeInputPressed(ActionName); + AbilityContainer.HandleInputPressed(ActionName, InPredictionHandle); + //NativeInputPressed(ActionName); } -bool UAFAbilityComponent::ServerNativeInputPressed_Validate(FGameplayTag ActionName) +bool UAFAbilityComponent::ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) { return true; } @@ -851,6 +885,10 @@ bool UAFAbilityComponent::ServerNativeAddAbilityFromTag_Validate(FGameplayTag In void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId) { + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + return; + } if (UAssetManager* Manager = UAssetManager::GetIfValid()) { UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); @@ -927,7 +965,7 @@ void UAFAbilityComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName AnimInst->Montage_Play(MontageIn, Speed); if (SectionName != NAME_None) { - AnimInst->Montage_JumpToSection(SectionName, MontageIn); + //AnimInst->Montage_JumpToSection(SectionName, MontageIn); } UE_LOG(AbilityFramework, Log, TEXT("PlayMontage MontageName: %s SectionNAme: %s Where: %s"), *MontageIn->GetName(), *SectionName.ToString(), (GetOwnerRole() < ENetRole::ROLE_Authority ? TEXT("Client") : TEXT("Server"))); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 23382da..a1f5ad3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -38,6 +38,7 @@ DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectRepInfoDelegate, FAFEffectRepInfo*) DECLARE_DELEGATE(FAFOnAbilityReady); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); +DECLARE_DELEGATE(FAFGenericAttributeDelegate); //UAFAssetManager* GetAssetManager() //{ @@ -147,7 +148,7 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); UGAAbilityBase* GetAbility(FGameplayTag TagIn); - void HandleInputPressed(FGameplayTag ActionName); + void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); void HandleInputReleased(FGameplayTag ActionName); void TriggerAbylityByTag(FGameplayTag InTag); @@ -167,6 +168,48 @@ struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTrait }; }; + +USTRUCT() +struct FAFReplicatedAttributeItem : public FFastArraySerializerItem +{ + GENERATED_BODY() +public: + UPROPERTY() + FGameplayTag AttributeTag; + UPROPERTY() + UGAAttributesBase* Attributes; + + void PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer); + void PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer); + void PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer); +}; + +USTRUCT() +struct FAFReplicatedAttributeContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + UPROPERTY() + TArray Attributes; + + TMap AttributeMap; + + UGAAttributesBase* Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter); + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(Attributes, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FAFReplicatedAttributeContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface { @@ -218,8 +261,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, //probabaly replace FGameplayTag with FObjectKey TMap AdditionalAttributes; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Replicated) - TArray RepAttributes; + UPROPERTY(Replicated) + FAFReplicatedAttributeContainer RepAttributes; UPROPERTY(ReplicatedUsing = OnRep_AttributeChanged) FGAModifiedAttributeData ModifiedAttribute; @@ -285,15 +328,13 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); return Cast(AttributeSet); } - void AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) + UGAAttributesBase* AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) { - bool bExists = AdditionalAttributes.Contains(InOwner); - if (bExists) - { - return; - } - RepAttributes.Add(InAttributes); - AdditionalAttributes.Add(InOwner, InAttributes); + if (!InAttributes) + return nullptr; + UGAAttributesBase* retVal = RepAttributes.Add(InOwner, InAttributes, this); + RepAttributes.MarkArrayDirty(); + return retVal; } UFUNCTION(BlueprintCallable, Category = "Test") void GetAttributeStructTest(FGAAttribute Name); @@ -320,8 +361,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void ApplyEffectToTarget(TSubclassOf InSpecClass, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); - - + /* Have to to copy handle around, because timer delegates do not support references. */ void ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty ,FAFFunctionModifier Modifier, FGAEffectContext InContext); @@ -512,6 +552,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, return; if (!OnEffectEvent.Contains(InEventTag)) { + UE_LOG(AbilityFramework, Log, TEXT("AddEffectEvent: %s"), *InEventTag.ToString()); OnEffectEvent.Add(InEventTag, InEvent); } } @@ -522,6 +563,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, FSimpleDelegate* Delegate = OnEffectEvent.Find(InEventTag); if (Delegate) { + UE_LOG(AbilityFramework, Log, TEXT("ExecuteEffectEvent: %s"), *InEventTag.ToString()); Delegate->ExecuteIfBound(); } } @@ -529,6 +571,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, { if (!InEventTag.IsValid()) return; + UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); OnEffectEvent.Remove(InEventTag); } /* @@ -570,8 +613,52 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, } } - FAFOnAbilityReady OnAbilityReady; + TMap> OnPreAttributeModifiedMap; + void AddOnPreAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) + { + TArray& delegates = OnPreAttributeModifiedMap.FindOrAdd(InAttribute); + delegates.Add(InDelegate); + } + + void NotifyOnPreAttributeModified(const FGAAttribute& InAttribute) + { + if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) + { + for(const FAFGenericAttributeDelegate& delegate : *Ready) + delegate.ExecuteIfBound(); + } + } + void RemoveOnPreAttributeModified(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& Delegate) + { + if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) + { + //Ready->RemoveSingle(Delegate); + if (Ready->Num() <= 0) + { + OnPreAttributeModifiedMap.Remove(InAttribute); + } + } + } + + TMap> OnPostAttributeModifiedMap; + void AddOnPostAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) + { + TArray& delegates = OnPostAttributeModifiedMap.FindOrAdd(InAttribute); + delegates.Add(InDelegate); + } + + void NotifyOnPostAttributeModified(const FGAAttribute& InAttribute) + { + if (TArray* Ready = OnPostAttributeModifiedMap.Find(InAttribute)) + { + for (const FAFGenericAttributeDelegate& delegate : *Ready) + delegate.ExecuteIfBound(); + } + } + + FAFOnAbilityReady OnAbilityReady; + UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") FAFOnAbilityAdded OnAbilityAdded; @@ -618,15 +705,16 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UFUNCTION(Client, Reliable) void ClientNotifyAbilityInputReady(FGameplayTag AbilityTag); void ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag); - + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") void BP_InputPressed(FGameplayTag ActionName); void NativeInputPressed(FGameplayTag ActionName); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputPressed(FGameplayTag ActionName); - virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName); - virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName); + void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h index d15c9bf..9be3384 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h @@ -44,6 +44,8 @@ class IAFAbilityInterface //those tags will be merged into effect owned tags. virtual FGameplayTagContainer GetCauserTags() { return FGameplayTagContainer(); } + virtual FAFPredictionHandle GetPredictionHandle() { return FAFPredictionHandle(); } + template T* GetAttributesTyped() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 67f2372..0778404 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -16,7 +16,7 @@ #include "Kismet/KismetSystemLibrary.h" #include "GAAbilityBase.h" - +FAFPredictionHandle UGAAbilityBase::GetPredictionHandle() { return PredictionHandle; } void FGAAbilityTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) { if (Target && !Target->IsPendingKillOrUnreachable()) @@ -186,7 +186,9 @@ void UGAAbilityBase::InitAbility() { if (AbilityComponent && Attributes) { - AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes); + UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes);; + Attributes = nullptr; + Attributes = NewAttributes; } } @@ -197,12 +199,17 @@ void UGAAbilityBase::InitAbility() TickFunction.Target = this; TickFunction.RegisterTickFunction(AbilityComponent->GetWorld()->GetCurrentLevel()); TickFunction.SetTickFunctionEnable(true); + OnAbilityInited(); } +void UGAAbilityBase::OnAbilityInited() +{ -void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName) +} +void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) { { UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); + PredictionHandle = InPredictionHandle; OnInputPressed(ActionName); OnInputPressedDelegate.Broadcast(); } @@ -221,6 +228,7 @@ void UGAAbilityBase::StartActivation(bool bApplyActivationEffect) { if (!CanUseAbility()) { + UE_LOG(AbilityFramework, Log, TEXT("Cannot use Ability: %s"), *GetName()); return; } //AbilityComponent->ExecutingAbility = this; @@ -340,11 +348,22 @@ bool UGAAbilityBase::ApplyCooldownEffect() CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, this, POwner, this, Modifier); + ENetMode nm = AbilityComponent->GetOwner()->GetNetMode(); + ENetRole role = AbilityComponent->GetOwnerRole(); + + if (role >= ENetRole::ROLE_Authority) + { + ClientSetCooldownHandle(CooldownEffectHandle); + } OnCooldownStart(); //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); return false; } +void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) +{ + //CooldownEffectHandle = InCooldownHandle; +} bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) { if (!ActivationEffect.GetSpec()) @@ -400,7 +419,7 @@ bool UGAAbilityBase::CanUseAbility() // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); CanUse = !bIsOnCooldown && !bIsActivating; - + UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility Ability, Cooldown: %s, Activating: %s \n"), bIsOnCooldown ? TEXT("true") : TEXT("false"), bIsActivating ? TEXT("true") : TEXT("false") ); //now Lets check tags if (CanUse) { @@ -417,7 +436,10 @@ bool UGAAbilityBase::CanUseAbility() return CanUse; } - +bool UGAAbilityBase::BP_CanUseAbility() +{ + return CanUseAbility(); +} bool UGAAbilityBase::CanReleaseAbility() { bool bCanUse = true; @@ -556,7 +578,11 @@ bool UGAAbilityBase::IsOnCooldown() bool UGAAbilityBase::IsActivating() { bool bAbilityActivating = false; - bAbilityActivating = AbilityComponent->IsEffectActive(ActivationEffect.Handle) || AbilityState == EAFAbilityState::Activating; + bool bHaveEffect = AbilityComponent->IsEffectActive(ActivationEffect.Handle); + bool bInActivatingState = AbilityState == EAFAbilityState::Activating; + UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); + bAbilityActivating = bHaveEffect || bInActivatingState; + return bAbilityActivating; //temp } bool UGAAbilityBase::BP_IsOnCooldown() @@ -616,7 +642,8 @@ void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, flo void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const { Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly can be infered apon replication. + //possibly can be infered upon replication. + //does other players need info about this ? DOREPLIFETIME(UGAAbilityBase, POwner); DOREPLIFETIME(UGAAbilityBase, Character); DOREPLIFETIME(UGAAbilityBase, PCOwner); @@ -624,7 +651,30 @@ void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. DOREPLIFETIME(UGAAbilityBase, AvatarActor) - //DOREPLIFETIME(UAFAbilityComponent, RepMontage); +} +int32 UGAAbilityBase::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) +{ + if (HasAnyFlags(RF_ClassDefaultObject)) + { + return FunctionCallspace::Local; + } + check(POwner != NULL); + return POwner->GetFunctionCallspace(Function, Parameters, Stack); +} +bool UGAAbilityBase::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) +{ + check(!HasAnyFlags(RF_ClassDefaultObject)); + check(POwner != NULL); + + + UNetDriver* NetDriver = POwner->GetNetDriver(); + if (NetDriver) + { + NetDriver->ProcessRemoteFunction(POwner, Function, Parameters, OutParms, Stack, this); + return true; + } + + return false; } void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index e9d3432..a10cb1d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -1,5 +1,6 @@ #pragma once #include "GAGlobals.h" +#include "../GAGlobalTypes.h" #include "../Effects/GAGameEffect.h" #include "GameplayTasksComponent.h" #include "GameplayTask.h" @@ -122,6 +123,11 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask public: FGAAbilityTick TickFunction; + /* + Since each ability is instanced per owner, and cannot be activated multiple times (ie, to run in background), + we can assume that PredictionHandle will always be unique per activation. + */ + FAFPredictionHandle PredictionHandle; /* By default all abilities are considered to be replicated. */ UPROPERTY(EditAnywhere, Category = "Replication") bool bReplicate; @@ -243,10 +249,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask FGameplayTagContainer ActivationBlockedTags; public: //because I'm to lazy to write all those friend states.. - UPROPERTY() - float LastActivationTime; - UPROPERTY() - float LastCooldownTime; virtual void TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction); UFUNCTION() void OnActivationEffectPeriod(FGAEffectHandle InHandle); @@ -265,6 +267,10 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UPROPERTY(BlueprintAssignable) FGASGenericAbilityDelegate OnNotifyOnCooldown; + + /* Stub, I think replicating montage directly from ability will be better, as abilities are replicated regardless. */ + UPROPERTY() + UAnimMontage* RepMontage; protected: EAFAbilityState AbilityState; @@ -301,12 +307,15 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); virtual void InitAbility(); + + //called on both server and client after InitAbility(); + virtual void OnAbilityInited(); /* Called when ability received input. One ability can receive multiple input calls, how those will be handled is up to ability. */ - void OnNativeInputPressed(FGameplayTag ActionName); + void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); /* Called when ability receive input press. Does not start ability execution automatically, so it is safe to make any pre execution preparations of ability here. @@ -398,6 +407,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask bool CanUseAbility(); bool CanReleaseAbility(); + UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") + bool BP_CanUseAbility(); + /** GameplayTaskOwnerInterface - Begin */ virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ @@ -433,13 +445,17 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; - + virtual FAFPredictionHandle GetPredictionHandle() override; /* IAFAbilityInterface End **/ UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") virtual float GetAttributeVal(FGAAttribute AttributeIn) const; public: //protected ? bool ApplyCooldownEffect(); + UFUNCTION(Client, Reliable) + void ClientSetCooldownHandle(FGAEffectHandle InCooldownHandle); + void ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle); + bool ApplyActivationEffect(bool bApplyActivationEffect); bool ApplyAttributeCost(); bool ApplyAbilityAttributeCost(); @@ -477,6 +493,10 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask } void SetNetAddressable(); +public: + int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; + virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") void ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp index 294b044..e6b3bb0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp @@ -34,4 +34,29 @@ void UGAAbilityTask::Initialize() void UGAAbilityTask::EndAbilityTask() { +} + +int32 UGAAbilityTask::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) +{ + if (HasAnyFlags(RF_ClassDefaultObject)) + { + return FunctionCallspace::Local; + } + check(AbilityComponent.IsValid()); + return AbilityComponent->GetFunctionCallspace(Function, Parameters, Stack); +} +bool UGAAbilityTask::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) +{ + check(!HasAnyFlags(RF_ClassDefaultObject)); + check(AbilityComponent.IsValid()); + + + UNetDriver* NetDriver = AbilityComponent->GetOwner()->GetNetDriver(); + if (NetDriver) + { + NetDriver->ProcessRemoteFunction(AbilityComponent->GetOwner(), Function, Parameters, OutParms, Stack, this); + return true; + } + + return false; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 3e81f74..37e6930 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -67,6 +67,10 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask { static_assert(DelayedFalse(), "UAbilityTask::NewTask should never be used. Use NewAbilityTask instead"); } + + //network overrides: + int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; + virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; protected: void EndAbilityTask(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp index d44e579..7142125 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -5,6 +5,7 @@ #include "../AFAbilityComponent.h" #include "GAAttributesBase.h" #include "../AFAbilityInterface.h" +#include "GAAttributeExtension.h" #include "GAAttributeBase.h" DEFINE_STAT(STAT_CalculateBonus); @@ -30,7 +31,7 @@ FAFAttributeBase::FAFAttributeBase(float BaseValueIn) }; -void FAFAttributeBase::InitializeAttribute() +void FAFAttributeBase::InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName) { CurrentValue = BaseValue; CalculateBonus(); @@ -38,7 +39,10 @@ void FAFAttributeBase::InitializeAttribute() Modifiers.Empty(); Modifiers.AddDefaulted(7);// static_cast(EGAAttributeMod::Invalid)); //Modifiers.AddDefaulted(static_cast(EGAAttributeMod::Invalid)); - + if (ExtensionClass) + { + ExtensionClass.GetDefaultObject()->Initialize(InComponent, InAttributeName); + } } void FAFAttributeBase::CalculateBonus() @@ -154,6 +158,7 @@ bool FAFAttributeBase::CheckIfModsMatch(const FGAEffectHandle& InHandle, const F return true; } } + if (mods.Num() <= 0) return true; return false; @@ -178,6 +183,11 @@ bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty) { + //FString name = GetTypeName(); + if (ExtensionClass) + { + ExtensionClass.GetDefaultObject()->OnPreAttributeModify(CurrentValue); + } float returnValue = -1; bool isPeriod = InProperty.Period > 0; bool IsDuration = InProperty.Duration > 0; @@ -231,6 +241,10 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& } } } + if (ExtensionClass) + { + ExtensionClass.GetDefaultObject()->OnPreAttributeModify(returnValue); + } return returnValue; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h index 2b9559f..249b954 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -28,6 +28,18 @@ struct QueuedAttributeMods Mod = Other.Mod; } }; + +//wrapper for multi-precision attribute. +//works like any numeric type, but depending on preprocessor flag it can int16,in32, float or double. + +typedef int16 AttributeReal; + +struct FNumericAttribute +{ + AttributeReal Value; +}; + +class UAFAbilityComponent; /* I probabaly should chaange attribute to use int's instead of floats. Stable, accurate and I can still have decimal values with them. @@ -71,7 +83,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase TArray> Modifiers; FAFAttributeBase(); FAFAttributeBase(float BaseValueIn); - void InitializeAttribute(); + void InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName); /* You should never use those tree function to set attributes. Only use them for testing/debugging and setting initial values for attributes. */ inline void SetBaseValue(float ValueIn) { BaseValue = ValueIn; } @@ -91,6 +103,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); + void SetExtensionClass(TSubclassOf InExtensionClass) { ExtensionClass = InExtensionClass; }; //EAFAttributeStacking GetStacking() const { return Stacking; } }; template<> diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp index 973393c..6066955 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp @@ -1,8 +1,23 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "../AbilityFramework.h" +#include "../AFAbilityComponent.h" #include "GAAttributeExtension.h" +void UGAAttributeExtension::Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName) +{ + AbilityComponent = InAbilityComponent; + Attribute = FGAAttribute(InAttributeName); +} + +void UGAAttributeExtension::OnPreAttributeModify(float InValue) +{ + AbilityComponent->NotifyOnPreAttributeModified(Attribute); +} +void UGAAttributeExtension::OnPostAttributeModify(float InValue) +{ + AbilityComponent->NotifyOnPostAttributeModified(Attribute); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h index 57f9a70..34b4b7c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h @@ -14,10 +14,17 @@ class ABILITYFRAMEWORK_API UGAAttributeExtension : public UObject { GENERATED_BODY() public: + UPROPERTY() + class UAFAbilityComponent* AbilityComponent; + UPROPERTY() + FGAAttribute Attribute; + void Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName); + + void OnPreAttributeModify(float InValue); + void OnPostAttributeModify(float InValue); + virtual void PreAttributeModify() {}; virtual void PostAttributeModify() {}; - virtual void OnPreAttributeModified() {}; - virtual void OnPostAttributeModified() {}; virtual float CalculateBonusValueByTags(const FGAIndividualMods& Mods) { return 0; } virtual float CalculateCurentValue() { return 0; } virtual bool CanModifyAttribute() { return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp index e6daa97..e66bd5e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -29,7 +29,7 @@ void UGAAttributesBase::InitializeAttributes(UAFAbilityComponent* InOwningAttrib FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); if (attr) { - attr->InitializeAttribute(); + attr->InitializeAttribute(InOwningAttributeComp, StrIt->GetFName()); TickableAttributes.Add(attr); } } @@ -69,7 +69,8 @@ void UGAAttributesBase::InitializeAttributesFromTable() attr->SetMaxValue(row->MaxValue); attr->SetMinValue(row->MinValue); attr->SetCurrentValue(row->CurrentValue); - attr->InitializeAttribute(); + attr->SetExtensionClass(row->Extension); + attr->InitializeAttribute(OwningAttributeComp, StrIt->GetFName()); } //TickableAttributes.Add(attr); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index a8c5df0..c7dd88b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -64,6 +64,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); InEffect.Duration = InEffect.GetSpec()->Duration.GetFloatValue(Context); InEffect.Period = InEffect.GetSpec()->Period.GetFloatValue(Context); + FGAEffect* effect = nullptr; if (InEffect.Duration <= 0 && InEffect.Period <= 0) { @@ -86,6 +87,14 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, effect->Context = Context; effect->GameEffect = InEffect.GetSpec(); } + if (IAFAbilityInterface* Ability = Cast(Causer)) + { + InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); + if (effect) + { + effect->PredictionHandle = Ability->GetPredictionHandle(); + } + } return Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 349a191..44c86a9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -33,6 +33,7 @@ void FGAEffectProperty::InitializeIfNotInitialized() Initialize(); } } + FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, class UAFAbilityComponent* InComponent) : AppliedTime(AppliedTimeIn), @@ -57,6 +58,7 @@ void FAFEffectRepInfo::Init() } void FAFEffectRepInfo::OnExpired() { + UE_LOG(AbilityFramework, Log, TEXT("Client FAFEffectRepInfo. OnExpired")); OwningComoponent->ExecuteEffectEvent(OnExpiredEvent); } void FAFEffectRepInfo::OnPeriod() @@ -65,6 +67,9 @@ void FAFEffectRepInfo::OnPeriod() } void FAFEffectRepInfo::OnRemoved() { + FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnRemoved ")); + EffectInfoLog += EffectTag.ToString(); + AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); @@ -86,6 +91,21 @@ void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InAr } void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) { + if (PredictionHandle.IsValid() && InArraySerializer.PredictedEffectInfos.Contains(PredictionHandle)) + { + FGAEffectContainer& cont = const_cast(InArraySerializer); + auto RemovePredicate = [&](const FAFEffectRepInfo& EmitterHandle) { return EmitterHandle.Handle == Handle; }; + //cont.ActiveEffectInfos.Remove(*this); + cont.ActiveEffectInfos.RemoveAll(RemovePredicate); + return; + //remove replicated rep info ? + //keep client side handle. + //possibly override client predicted repinfo with informations from server. + } + else + { + //remove predicted effect. + } OwningComoponent = InArraySerializer.OwningComponent; InArraySerializer.EffectInfos.Add(Handle, this); InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); @@ -93,7 +113,7 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra //OwningComoponent->ExecuteEffectEvent(OnAppliedEvent); FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - + AppliedTime = OwningComoponent->GetWorld()->GetTimeSeconds(); FTimerDelegate delDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnExpired); Timer.SetTimer(ExpiredHandle, delDuration, Duration, false); @@ -358,15 +378,17 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr FGAEffectHandle Handle; bool bHasDuration = InProperty.Duration > 0; bool bHasPeriod = InProperty.Period > 0; - + ENetRole role = OwningComponent->GetOwnerRole(); + ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); //we should not generate handle on clients. + //do we need valid handle for instant effects ? if (bHasDuration || bHasPeriod) { Handle = FGAEffectHandle::GenerateHandle(EffectIn); } if (InProperty.ApplicationRequirement->CanApply(EffectIn, InProperty, this, InContext, Handle)) { - if(!bHasDuration && !bHasPeriod) + if(!bHasDuration && !bHasPeriod) //instatnt effect. { if (InProperty.Handle.IsValid()) { @@ -399,10 +421,15 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr EffectIn, InProperty, this, InContext)) { InProperty.Application->ExecuteEffect(Handle, InProperty, InContext, Modifier); + //generate it only on client, and apply prediction key from client. + //if server replicates with valid key, then nothing happens. + //if not we try to rewind effect application. + //we probabaly don't need to unwind attribute changes, since next replication from + //server will overridem them anyway. ApplyReplicationInfo(Handle, InProperty); - // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); + bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()); + UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::EffectApplied %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Handle.GetEffectSpec()->GetName() ); } - } } @@ -420,6 +447,10 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c { ENetMode mode = OwningComponent->GetNetMode(); ENetRole role = OwningComponent->GetOwnerRole(); + + bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; + UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::ApplyReplicationInfo"), bIsServer ? TEXT("Server") : TEXT("Client")); + if (mode == ENetMode::NM_DedicatedServer) { const UWorld* World = OwningComponent->GetWorld(); @@ -428,6 +459,7 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; RepInfo->Handle = InHandle; + RepInfo->PredictionHandle = InProperty.PredictionHandle; RepInfo->Init(); MarkItemDirty(*RepInfo); ActiveEffectInfos.Add(*RepInfo); @@ -440,22 +472,24 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c EffectInfos.Add(InHandle, RepInfo); } } - else if(mode == ENetMode::NM_Standalone) + else if(mode == ENetMode::NM_Standalone || mode == ENetMode::NM_Client) { - + //add replication handle (and send it to server ?) const UWorld* World = OwningComponent->GetWorld(); FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; RepInfo->Handle = InHandle; + RepInfo->PredictionHandle = InProperty.PredictionHandle; RepInfo->Init(); //MarkItemDirty(RepInfo); ActiveEffectInfos.Add(*RepInfo); //MarkArrayDirty(); - + UE_LOG(AbilityFramework, Log, TEXT("Client ApplyReplicationInfo. Duration: %f"), InProperty.Duration); //predictevily add effect info ? { + PredictedEffectInfos.Add(InProperty.PredictionHandle, RepInfo); EffectInfos.Add(InHandle, RepInfo); } } @@ -706,6 +740,9 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N EffectInfos.RemoveAndCopyValue(OutHandle, Out); if (Out) { + FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); + EffectInfoLog += Out->EffectTag.ToString(); + AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); MarkItemDirty(*Out); Out->OnRemoved(); ActiveEffectInfos.Remove(*Out); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index f045a56..d8fa9b7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -8,27 +8,6 @@ DECLARE_STATS_GROUP(TEXT("GameEffect"), STATGROUP_GameEffect, STATCAT_Advanced); DECLARE_CYCLE_STAT_EXTERN(TEXT("GatherModifiers"), STAT_GatherModifiers, STATGROUP_GameEffect, ); -/* - Modifier type for simple attribute operatinos. - It's only additive or subtractive due to possible race conditions with multiplicative/divide - mods. -*/ -UENUM() -enum class EGASimpleAttributeOperation : uint8 -{ - Additive, - Subtractive, - Invalid -}; - -UENUM() -enum class EGAMakeSpecResult : uint8 -{ - NewHandle, - OldHandle, - Invalid -}; - USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAMagnitude { @@ -282,14 +261,6 @@ class ABILITYFRAMEWORK_API UAFEffectSpec : public UGAGameEffectSpec GENERATED_BODY() public: }; -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectSpec -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere, Instanced, Category = "Effect") - UGAGameEffectSpec* Spec; -}; USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectClass @@ -341,11 +312,14 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty class UGAEffectExecution* Execution; UPROPERTY() class UGAGameEffectSpec* Spec; + UPROPERTY() + FAFPredictionHandle PredictionHandle; UPROPERTY() float Duration; UPROPERTY() float Period; + /* Handle to effect created from SpecClass This handle is only created and kept for instant effects, @@ -353,8 +327,10 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty as potentially there can be quite a lot of allocations. */ FGAEffectHandle Handle; - //target of handle, handle to effect. - //only used for duration effcts, and cleared after effect is removed. + /* + Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. + + */ TMap Handles; FGAEffectProperty() : ApplicationRequirement(nullptr), @@ -375,6 +351,11 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty void Initialize(); void InitializeIfNotInitialized(); + void SetPredictionHandle(const FAFPredictionHandle& InHandle) + { + PredictionHandle = InHandle; + } + FGAAttributeModifier& GetAttributeModifier() { return Spec->AtributeModifier; @@ -463,6 +444,7 @@ struct ABILITYFRAMEWORK_API FGAEffect : public TSharedFromThis FGameplayTagContainer RequiredTags; FGAEffectHandle Handle; + FAFPredictionHandle PredictionHandle; mutable FTimerHandle PeriodTimerHandle; mutable FTimerHandle DurationTimerHandle; @@ -558,19 +540,6 @@ struct FGAEffectDuration UPROPERTY(EditAnywhere, Category = "Duration") float PeriodNum; }; -/* - Effect spec struct, which can be used to create effect specs directly inside abitrary classes ? -*/ -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectSpecDefinition -{ - GENERATED_USTRUCT_BODY() -}; - -struct FGAActiveGameEffect -{ - FGAActiveGameEffect(); -}; USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer @@ -582,10 +551,7 @@ struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer }; /* - Contains all active effects (which have duration, period or are infinite). - - The only reason this is USTRUCT() is because we need to hold hard references somewhere to instanced - effects. + Simplified and minimal version of game effect replicated back to clients. */ USTRUCT(BlueprintType) @@ -600,6 +566,10 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem //Handle to effect, which is using this info. UPROPERTY() FGAEffectHandle Handle; + + UPROPERTY() + FAFPredictionHandle PredictionHandle; + UPROPERTY() float AppliedTime; UPROPERTY() @@ -665,6 +635,10 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem { return Handle == Other.Handle; } + friend uint32 GetTypeHash(const FAFEffectRepInfo& InHandle) + { + return GetTypeHash(InHandle.Handle); + } FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, class UAFAbilityComponent* InComponent); @@ -705,7 +679,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer //change to SharedPtr ? mutable TMap EffectInfos; - + TMap PredictedEffectInfos; TMap> EffectByAttribute; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index 0291d69..9da2ce3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -8,6 +8,13 @@ #include "Effects/GAEffectExecution.h" #include "AFAbilityInterface.h" #include "Effects/GACustomCalculation.h" + +void AddLogDebugInfo(FString Text, UWorld* World) +{ + bool bIsServer = GEngine->GetNetMode(World) == ENetMode::NM_DedicatedServer; + UE_LOG(AbilityFramework, Log, TEXT("%s :: %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Text); +} + FGAEffectContext::FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, @@ -126,6 +133,20 @@ void FGAEffectHandle::Reset() Handle = 0; EffectPtr.Reset(); } + +FAFPredictionHandle FAFPredictionHandle::GenerateClientHandle(UAFAbilityComponent* InComponent) +{ + if (InComponent->GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + static uint32 Counter = 1; + Counter++; + FAFPredictionHandle Handle; + Handle.Handle = Counter; + return Handle; + } + return FAFPredictionHandle(); +} + FGAHashedGameplayTagContainer::FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn) : Tags(TagsIn) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 63f80b8..187a13b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -5,6 +5,8 @@ //#include "Messaging.h" #include "GAGlobalTypes.generated.h" +void AddLogDebugInfo(FString Text, UWorld* World); + /* Explanation of tags from Fred K, on forums: https://forums.unrealengine.com/showthread.php?57988-GameplayAbilities-questions&p=220315#post220315 @@ -82,22 +84,6 @@ enum class EGAEffectType : uint8 Infinite = 2, }; -/* How applied effects should stack on Attribute */ -UENUM() -enum class EGAAttributeStacking : uint8 -{ - Add, - Intensity, - Override, - Stronger -}; -UENUM() -enum class EAFAttributeStacking : uint8 -{ - Add, - Override, - StrongerOverride -}; /* StrongetOverride - Does not check for effect type/tags. It will just check if modified @@ -407,6 +393,45 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle // }; //}; + +USTRUCT() +struct FAFPredictionHandle +{ + GENERATED_BODY() +public: + //ID of current handle. + UPROPERTY() + uint32 Handle; + UPROPERTY() + FGAEffectHandle EffectHandle; + + uint64 Timestamp; + + static FAFPredictionHandle GenerateClientHandle(UAFAbilityComponent* InComponent); + /* + Was prediction successful ? + If true nothing happens on client (might interpolate to result from server). + If false, server will override client predicted results. + */ + UPROPERTY() + bool bPredictionValid; + + + bool IsValid() const + { + return true; + } + + const bool operator==(const FAFPredictionHandle& Other) const + { + return Handle == Other.Handle; + } + friend uint32 GetTypeHash(const FAFPredictionHandle& InHandle) + { + return InHandle.Handle; + } +}; + DECLARE_MULTICAST_DELEGATE(FGAGenericDelegate); struct ABILITYFRAMEWORK_API EnumToString diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp index 9c9ce07..097463e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp @@ -55,11 +55,6 @@ void UGALatentFunctionBase::EndTask() void UGALatentFunctionBase::BeginDestroy() { Super::BeginDestroy(); - if (Endpoint.IsValid()) - { - FMessageEndpoint::SafeRelease(Endpoint); - Endpoint.Reset(); - } } UWorld* UGALatentFunctionBase::GetWorld() const { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h index a9e3773..5e94d4d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h @@ -32,7 +32,6 @@ class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject friend struct FGALatentFunctionTick; FGALatentFunctionTick TickFunction; - TSharedPtr Endpoint; UGALatentFunctionBase(const FObjectInitializer& ObjectInitializer); virtual UWorld* GetWorld() const override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp index 50d3a1a..b4beef4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp @@ -129,13 +129,13 @@ class GameEffectsTestSuite //SourceComponent->GetAttributes()->PhysicalBonus.Stacking = EAFAttributeStacking::Add; //SourceComponent->GetAttributes()->MagicResistance.Stacking = EAFAttributeStacking::Override; - SourceComponent->GetAttributes()->Health.InitializeAttribute(); - SourceComponent->GetAttributes()->Energy.InitializeAttribute(); - SourceComponent->GetAttributes()->Stamina.InitializeAttribute(); + SourceComponent->GetAttributes()->Health.InitializeAttribute(SourceComponent, TEXT("Health")); + SourceComponent->GetAttributes()->Energy.InitializeAttribute(SourceComponent, TEXT("Energy")); + SourceComponent->GetAttributes()->Stamina.InitializeAttribute(SourceComponent, TEXT("Stamina")); - SourceComponent->GetAttributes()->MagicalBonus.InitializeAttribute(); - SourceComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(); - SourceComponent->GetAttributes()->MagicResistance.InitializeAttribute(); + SourceComponent->GetAttributes()->MagicalBonus.InitializeAttribute(SourceComponent, TEXT("MagicalBonus")); + SourceComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(SourceComponent, TEXT("PhysicalBonus")); + SourceComponent->GetAttributes()->MagicResistance.InitializeAttribute(SourceComponent, TEXT("MagicResistance")); SourceComponent->DefaultAttributes->InitializeAttributes(SourceComponent); DestActor = World->SpawnActor(); @@ -154,13 +154,13 @@ class GameEffectsTestSuite DestComponent->GetAttributes()->PhysicalBonus.SetMaxValue(500); DestComponent->GetAttributes()->MagicResistance.SetMaxValue(500); - DestComponent->GetAttributes()->Health.InitializeAttribute(); - DestComponent->GetAttributes()->Energy.InitializeAttribute(); - DestComponent->GetAttributes()->Stamina.InitializeAttribute(); + DestComponent->GetAttributes()->Health.InitializeAttribute(DestComponent, TEXT("Health")); + DestComponent->GetAttributes()->Energy.InitializeAttribute(DestComponent, TEXT("Energy")); + DestComponent->GetAttributes()->Stamina.InitializeAttribute(DestComponent, TEXT("Stamina")); - DestComponent->GetAttributes()->MagicalBonus.InitializeAttribute(); - DestComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(); - DestComponent->GetAttributes()->MagicResistance.InitializeAttribute(); + DestComponent->GetAttributes()->MagicalBonus.InitializeAttribute(DestComponent, TEXT("MagicalBonus")); + DestComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(DestComponent, TEXT("PhysicalBonus")); + DestComponent->GetAttributes()->MagicResistance.InitializeAttribute(DestComponent, TEXT("MagicResistance")); DestComponent->DefaultAttributes->InitializeAttributes(DestComponent); TargetOne = World->SpawnActor(); @@ -179,13 +179,13 @@ class GameEffectsTestSuite TargetCompOne->GetAttributes()->PhysicalBonus.SetMaxValue(500); TargetCompOne->GetAttributes()->MagicResistance.SetMaxValue(500); - TargetCompOne->GetAttributes()->Health.InitializeAttribute(); - TargetCompOne->GetAttributes()->Energy.InitializeAttribute(); - TargetCompOne->GetAttributes()->Stamina.InitializeAttribute(); + TargetCompOne->GetAttributes()->Health.InitializeAttribute(TargetCompOne, TEXT("Health")); + TargetCompOne->GetAttributes()->Energy.InitializeAttribute(TargetCompOne, TEXT("Energy")); + TargetCompOne->GetAttributes()->Stamina.InitializeAttribute(TargetCompOne, TEXT("Stamina")); - TargetCompOne->GetAttributes()->MagicalBonus.InitializeAttribute(); - TargetCompOne->GetAttributes()->PhysicalBonus.InitializeAttribute(); - TargetCompOne->GetAttributes()->MagicResistance.InitializeAttribute(); + TargetCompOne->GetAttributes()->MagicalBonus.InitializeAttribute(TargetCompOne, TEXT("MagicalBonus")); + TargetCompOne->GetAttributes()->PhysicalBonus.InitializeAttribute(TargetCompOne, TEXT("PhysicalBonus")); + TargetCompOne->GetAttributes()->MagicResistance.InitializeAttribute(TargetCompOne, TEXT("MagicResistance")); TargetCompOne->DefaultAttributes->InitializeAttributes(TargetCompOne); @@ -205,13 +205,13 @@ class GameEffectsTestSuite TargetCompTwo->GetAttributes()->PhysicalBonus.SetMaxValue(500); TargetCompTwo->GetAttributes()->MagicResistance.SetMaxValue(500); - TargetCompTwo->GetAttributes()->Health.InitializeAttribute(); - TargetCompTwo->GetAttributes()->Energy.InitializeAttribute(); - TargetCompTwo->GetAttributes()->Stamina.InitializeAttribute(); + TargetCompTwo->GetAttributes()->Health.InitializeAttribute(TargetCompTwo, TEXT("Health")); + TargetCompTwo->GetAttributes()->Energy.InitializeAttribute(TargetCompTwo, TEXT("Energy")); + TargetCompTwo->GetAttributes()->Stamina.InitializeAttribute(TargetCompTwo, TEXT("Stamina")); - TargetCompTwo->GetAttributes()->MagicalBonus.InitializeAttribute(); - TargetCompTwo->GetAttributes()->PhysicalBonus.InitializeAttribute(); - TargetCompTwo->GetAttributes()->MagicResistance.InitializeAttribute(); + TargetCompTwo->GetAttributes()->MagicalBonus.InitializeAttribute(TargetCompTwo, TEXT("MagicalBonus")); + TargetCompTwo->GetAttributes()->PhysicalBonus.InitializeAttribute(TargetCompTwo, TEXT("PhysicalBonus")); + TargetCompTwo->GetAttributes()->MagicResistance.InitializeAttribute(TargetCompTwo, TEXT("MagicResistance")); TargetCompTwo->DefaultAttributes->InitializeAttributes(TargetCompTwo); //DestActor->BeginPlay(); diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 22d99f9..2d31f86 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -24,6 +24,10 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFAbilityComponent* Abilities; + + + UPROPERTY(EditAnywhere, Category = "Default Abilities") + TArray AbilitiesToGive; public: AARCharacter(); diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 3a93410..c7c4102 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -9,12 +9,15 @@ #include "Engine/AssetManager.h" #include "ARAbilityBase.h" +#include "Weapons/ARWeaponManagerComponent.h" + AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); UIAbilityManagerComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIAbilityManagerComponent"); UIWeaponEquipment = ObjectInitializer.CreateDefaultSubobject(this, "UIWeaponEquipment"); + WeaponManager = ObjectInitializer.CreateDefaultSubobject(this, "WeaponManager"); } void AARPlayerController::SetPawn(APawn* InPawn) @@ -35,6 +38,7 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); + //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr); @@ -49,9 +53,6 @@ void AARPlayerController::SetupInputComponent() { Super::SetupInputComponent(); InputComponent->BindAction("SwitchAbilitySet", IE_Pressed, this, &AARPlayerController::InputSwitchAbilitySet); - //InputComponent->BindAction("NextWeapon", IE_Pressed, this, &AARPlayerController::InputNextWeapon); - //InputComponent->BindAction("PreviousWeapon", IE_Pressed, this, &AARPlayerController::InputPreviousWeapon); - } void AARPlayerController::InputSwitchAbilitySet() @@ -59,14 +60,6 @@ void AARPlayerController::InputSwitchAbilitySet() UIAbilityManagerComponent->SwitchSet(); } -//void AARPlayerController::InputNextWeapon() -//{ -// UIWeaponEquipment->NextWeapon(); -//} -//void AARPlayerController::InputPreviousWeapon() -//{ -// UIWeaponEquipment->PreviousWeapon(); -//} void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) { IAFAbilityInterface* ABInt = Cast(GetPawn()); @@ -80,4 +73,14 @@ void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGamepl UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); AbilityComp->SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); +} + +void AARPlayerController::NextWeapon() +{ + WeaponManager->NextWeapon(); +} + +void AARPlayerController::PreviousWeapon() +{ + WeaponManager->PreviousWeapon(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 9008955..c87ae41 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -21,6 +21,8 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController class UARUIAbilityManagerComponent* UIAbilityManagerComponent; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIWeaponEquipment* UIWeaponEquipment; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UARWeaponManagerComponent* WeaponManager; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputNextWeapon; @@ -39,8 +41,10 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController void InputSwitchAbilitySet(); -// void InputNextWeapon(); - //void InputPreviousWeapon(); + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapons") + void NextWeapon(); + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapons") + void PreviousWeapon(); void OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag); }; diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp index da12572..dacfd5f 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp @@ -10,12 +10,8 @@ void UARGunAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimePropert DOREPLIFETIME(UARGunAttributes, Magazine); } -void UARGunAttributes::OnRep_Magazine() +void UARGunAttributes::OnRep_Magazine(FAFAttributeBase OldVal) { float dua = 0; UARGunAttributes* asd = this; - if (OwningAttributeComp->GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - Magazine = this->Magazine; - } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Attributes/ARGunAttributes.h index ae4ebfd..63874c1 100644 --- a/Source/ActionRPGGame/Attributes/ARGunAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARGunAttributes.h @@ -7,7 +7,11 @@ #include "ARGunAttributes.generated.h" /** - * + * 1. Register FAFReplicationHandle with attribute change. + * 2. If handle is valid then attribute change is also valid (for attribute prediction) + * 3. If valid we don't override with server values. + * 4. Wont work on attributes which can be changed by several sources at the same time like HP. + * This will require custom treatment. */ UCLASS() class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase @@ -32,5 +36,5 @@ class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase FAFAttributeBase Spread; UFUNCTION() - void OnRep_Magazine(); + void OnRep_Magazine(FAFAttributeBase OldVal); }; diff --git a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp index b63b8fd..62ee99b 100644 --- a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp +++ b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp @@ -10,6 +10,7 @@ UARUIWeaponEquipment::UARUIWeaponEquipment() // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; Weapons.SetNum(4); + ActiveWeaponIndex = 0; // ... } @@ -32,6 +33,7 @@ void UARUIWeaponEquipment::BeginPlay() UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); AbilityComp->BindAbilityToAction(InputComponent, ShootInput); AbilityComp->BindAbilityToAction(InputComponent, ReloadInput); + //alt fire ? // ... } @@ -111,6 +113,10 @@ void UARUIWeaponEquipment::NextWeapon() ActiveWeaponIndex = 0; ActiveWeapon = Weapons[ActiveWeaponIndex]; } + } + + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { ServerNextWeapon(ActiveWeaponIndex); } @@ -127,7 +133,11 @@ void UARUIWeaponEquipment::PreviousWeapon() ActiveWeaponIndex = 0; ActiveWeapon = Weapons[ActiveWeaponIndex]; } - ServerPreviousWeapon(ActiveWeaponIndex); + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerPreviousWeapon(ActiveWeaponIndex); + } + } void UARUIWeaponEquipment::ServerNextWeapon_Implementation(int32 WeaponIndex) diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index bddbbc6..fef4e90 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -136,18 +136,12 @@ void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbil if (!AbilityComp) return; - /*if (!AbilityComp->OnAbilityAdded.IsAlreadyBound(this, &UARUIAbilityManagerComponent::OnAbilityReady)) - { - FGameplayTag d = GetInputTag(InAbilitySet, AbilityIndex); - AbilityComp->OnAbilityReady.AddDynamic(this, &UARUIAbilityManagerComponent::OnAbilityReady); - }*/ FGameplayTag IAbilityInput = GetInputTag(InAbilitySet, AbilityIndex); FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARUIAbilityManagerComponent::OnAbilityReady, InAbilityTag, IAbilityInput, InAbilitySet, AbilityIndex); AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, ReadyDelegate); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , GetInputTag(InAbilitySet, AbilityIndex)); - + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr); } void UARUIAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, int32 InAbilitySet, int32 InAbilityIndex) @@ -170,15 +164,39 @@ void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAb UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARUIAbilityManagerComponent::OnAbilityInputReady, + InAbilityTag, InAbilityInput, InAbilitySet, InAbilityIndex); + + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); + } + else + { + SetAbility(InAbilitySet, InAbilityIndex, Ability); + SetAbilityTag(InAbilitySet, InAbilityIndex, InAbilityTag); + SetInputTag(InAbilitySet, InAbilityIndex, InAbilityInput); + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + } +} +void UARUIAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, + int32 InAbilitySet, int32 InAbilityIndex) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); SetAbility(InAbilitySet, InAbilityIndex, Ability); SetAbilityTag(InAbilitySet, InAbilityIndex, InAbilityTag); SetInputTag(InAbilitySet, InAbilityIndex, InAbilityInput); - - - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); } - void UARUIAbilityManagerComponent::SwitchSet() { //in reality it should be vlidated on server as well @@ -204,7 +222,6 @@ void UARUIAbilityManagerComponent::SwitchSet() { AbilityComp->SetBlockedInput(InputTags[Idx], true); AbilityComp->SetBlockedInput(InputTags2[Idx], false); - //AbilityComp->BP_BindAbilityToAction(InputBinding, AbilityTag); } ActiveSet = 1; OnAbilitySetChanged.Broadcast(1); @@ -218,7 +235,6 @@ void UARUIAbilityManagerComponent::SwitchSet() { AbilityComp->SetBlockedInput(InputTags[Idx], true); AbilityComp->SetBlockedInput(InputTags2[Idx], false); - //AbilityComp->BP_BindAbilityToAction(InputBinding, AbilityTag); } ActiveSet = 0; OnAbilitySetChanged.Broadcast(0); diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h index 60c1698..d147944 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -100,6 +100,12 @@ class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent void NativeOnAbilityReady(const FGameplayTag& InAbilityTag, const FGameplayTag InAbilityInput, int32 InAbilitySet, int32 InAbilityIndex); + //only used in Client-Server mode. Abilities are additionaly binded on server + //so we need to wait for server response to make sure that ability is bound on server. + UFUNCTION() + void OnAbilityInputReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, + int32 InAbilitySet, int32 InAbilityIndex); + void SwitchSet(); UFUNCTION() void FinishedLoadinFiles(); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp new file mode 100644 index 0000000..fd3b7f2 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponAbilityBase.h" +#include "ARWeaponAvatar.h" + + +void UARWeaponAbilityBase::OnAbilityInited() +{ + UWorld* world = GetWorld(); + if (!world) + return; + + FActorSpawnParameters SpawnParams; + AvatarActor = world->SpawnActor(WeaponAvatar, SpawnParams); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h new file mode 100644 index 0000000..998717c --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Abilities/ARAbilityBase.h" +#include "ARWeaponAbilityBase.generated.h" + +class AARWeaponAvatar; +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase +{ + GENERATED_BODY() + +public: + UPROPERTY(EditAnywhere, Category = "Configuration") + TSubclassOf WeaponAvatar; + + virtual void OnAbilityInited() override; +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp new file mode 100644 index 0000000..2a3870c --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponAvatar.h" + + +// Sets default values +AARWeaponAvatar::AARWeaponAvatar() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AARWeaponAvatar::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AARWeaponAvatar::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAvatar.h b/Source/ActionRPGGame/Weapons/ARWeaponAvatar.h new file mode 100644 index 0000000..2d403db --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponAvatar.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "ARWeaponAvatar.generated.h" + +UCLASS() +class ACTIONRPGGAME_API AARWeaponAvatar : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + AARWeaponAvatar(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp new file mode 100644 index 0000000..1d047e3 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -0,0 +1,179 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponManagerComponent.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "ARWeaponAbilityBase.h" +// Sets default values for this component's properties +UARWeaponManagerComponent::UARWeaponManagerComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + AllWeapons.SetNum(4); + // ... +} + + +// Called when the game starts +void UARWeaponManagerComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UARWeaponManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} +void UARWeaponManagerComponent::BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) +{ + NativeEquipWeapon(InAbilityTag, SlotIndex); +} +void UARWeaponManagerComponent::NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponReady, InAbilityTag, SlotIndex); + AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , /*Input*/ ShootInput); +} +void UARWeaponManagerComponent::OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + UARWeaponAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + if (SlotIndex == 0) + { + AllWeapons[SlotIndex] = Ability; + CurrentWeapon = Ability; + ActiveWeaponIndex = SlotIndex; + AbilityComp->SetAbilityToAction(InAbilityTag, ShootInput, FAFOnAbilityReady()); + AbilityComp->SetAbilityToAction(InAbilityTag, ReloadInput, FAFOnAbilityReady()); + } + else + { + AllWeapons[SlotIndex] = Ability; + } +} + +void UARWeaponManagerComponent::NextWeapon() +{ + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + ActiveWeaponIndex++; + if (ActiveWeaponIndex < 4) + { + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + } + + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNextWeapon(ActiveWeaponIndex); + } + +} +void UARWeaponManagerComponent::PreviousWeapon() +{ + ActiveWeaponIndex--; + if (ActiveWeaponIndex >= 0) + { + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerPreviousWeapon(ActiveWeaponIndex); + } + +} + +void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponIndex) +{ + ActiveWeaponIndex++; + if (ActiveWeaponIndex < 4) + { + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + //so Server index is different. Client might tried to cheat + //or sometrhing. We will override it. + //situation where client can chage multiple weapons within second + //should not have place, as there is animation and/or internal cooldown on weapon change. + //since it will be done trough ability. + if (ActiveWeaponIndex != WeaponIndex) + { + ClientNextWeapon(ActiveWeaponIndex); + } +} +bool UARWeaponManagerComponent::ServerNextWeapon_Validate(int32 WeaponIndex) +{ + return true; +} +void UARWeaponManagerComponent::ClientNextWeapon_Implementation(int32 WeaponIndex) +{ + ActiveWeaponIndex = WeaponIndex; + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; +} +void UARWeaponManagerComponent::ServerPreviousWeapon_Implementation(int32 WeaponIndex) +{ + ActiveWeaponIndex--; + if (ActiveWeaponIndex >= 0) + { + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + else + { + ActiveWeaponIndex = 0; + CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + } + if (ActiveWeaponIndex != WeaponIndex) + { + + } +} +bool UARWeaponManagerComponent::ServerPreviousWeapon_Validate(int32 WeaponIndex) +{ + return true; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h new file mode 100644 index 0000000..13d705c --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -0,0 +1,66 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "GameplayTags.h" +#include "ARWeaponManagerComponent.generated.h" + +class UARWeaponAbilityBase; + +/* Add On Character. */ +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARWeaponManagerComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Input") + FGameplayTag ShootInput; + UPROPERTY(EditAnywhere, Category = "Input") + FGameplayTag ReloadInput; + + TArray> AllWeapons; + + TWeakObjectPtr CurrentWeapon; + + UPROPERTY() + int32 ActiveWeaponIndex; +public: + // Sets default values for this component's properties + UARWeaponManagerComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + UFUNCTION(BlueprintCallable) + void NextWeapon(); + UFUNCTION(BlueprintCallable) + void PreviousWeapon(); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNextWeapon(int32 WeaponIndex); + void ServerNextWeapon_Implementation(int32 WeaponIndex); + bool ServerNextWeapon_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientNextWeapon(int32 WeaponIndex); + void ClientNextWeapon_Implementation(int32 WeaponIndex); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerPreviousWeapon(int32 WeaponIndex); + void ServerPreviousWeapon_Implementation(int32 WeaponIndex); + bool ServerPreviousWeapon_Validate(int32 WeaponIndex); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Weapon"), Category = "ActionRPGGame|UI|Weapon") + void BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); + + void NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); + UFUNCTION() + void OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex); +}; From 2aeb2d100f0576d3a1ba22fee39c60410d30c5d8 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 16 Oct 2017 00:34:41 +0200 Subject: [PATCH 018/187] Better handling for replicated attribute sets. --- Config/DefaultGameplayTags.ini | 8 +++ .../AbilityFramework/AFAbilityComponent.cpp | 31 +++++++-- .../AbilityFramework/AFAbilityComponent.h | 33 +++++++++- .../Abilities/GAAbilityBase.cpp | 15 +++++ .../Abilities/GAAbilityBase.h | 5 +- .../Effects/GABlueprintLibrary.cpp | 12 +++- .../AbilityFramework/Effects/GAGameEffect.cpp | 64 ++++++++++--------- .../AbilityFramework/Effects/GAGameEffect.h | 3 + 8 files changed, 131 insertions(+), 40 deletions(-) diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 83e8791..36a060e 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -7,7 +7,11 @@ NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 -GameplayTagList=(Tag="Ability.Corruption",DevComment="") -GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +-GameplayTagList=(Tag="Ability.Input.NextWeapon",DevComment="") +-GameplayTagList=(Tag="Ability.Input.PreviousWeapon",DevComment="") +-GameplayTagList=(Tag="Ability.Input.SwitchAbilities",DevComment="") -GameplayTagList=(Tag="Ability.Rifle",DevComment="") +-GameplayTagList=(Tag="Ability.Rifle.Activate",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") -GameplayTagList=(Tag="Ability.Rifle.Reload",DevComment="") @@ -23,6 +27,10 @@ NetIndexFirstBitSegment=16 -GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") ++GameplayTagList=(Tag="Ability.Input.Jump",DevComment="") ++GameplayTagList=(Tag="Ability.Input.NextWeapon",DevComment="") ++GameplayTagList=(Tag="Ability.Input.PreviousWeapon",DevComment="") ++GameplayTagList=(Tag="Ability.Input.SwitchAbilities",DevComment="") +GameplayTagList=(Tag="Ability.Rifle",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Activate",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 222b25d..9782930 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -39,6 +39,7 @@ void FAFReplicatedAttributeItem::PostReplicatedAdd(const struct FAFReplicatedAtt FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); UGAAttributesBase*& Attribute = ArraySerializer.AttributeMap.FindOrAdd(AttributeTag); Attribute = Attributes; + InArraySerializer.OnAttributeReplicated(AttributeTag); } void FAFReplicatedAttributeItem::PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer) { @@ -166,6 +167,7 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn //application to object which was hit ? ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams; @@ -204,7 +206,14 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn { //execute cue from effect regardless if we have target object or not. if (InContext.TargetComp.IsValid()) - return InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + { + FGAEffectHandle Handle; + Handle = InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + if (!PropertyByHandle.Contains(Handle)) + PropertyByHandle.Add(Handle, &InProperty); + + return Handle; + } } return FGAEffectHandle(); @@ -268,8 +277,15 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper { //call effect internal delegate: HandleIn.GetEffectPtr()->OnExpired(); - //InternalRemoveEffect(HandleIn); - //OnEffectExpired.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + + if (mode == ENetMode::NM_DedicatedServer + || mode == ENetMode::NM_ListenServer) + { + ClientExpireEffect(InProperty.PredictionHandle); + } + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams; @@ -279,8 +295,7 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; CueParams.Period = InProperty.Period; CueParams.Duration = InProperty.Duration; - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone || role >= ENetRole::ROLE_Authority) { @@ -289,6 +304,12 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper } GameEffectContainer.RemoveEffectByHandle(HandleIn, InProperty); } + +void UAFAbilityComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) +{ + +} + void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index a1f5ad3..dc89ca4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -192,7 +192,28 @@ struct FAFReplicatedAttributeContainer : public FFastArraySerializer UPROPERTY() TArray Attributes; - TMap AttributeMap; + UPROPERTY() + TMap AttributeMap; + + + TMap AttributeReplicatedEvent; + + void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FSimpleDelegate& InDelegate) + { + if (!AttributeReplicatedEvent.Contains(InTag)) + return; + + AttributeReplicatedEvent.Add(InTag, InDelegate); + } + + void OnAttributeReplicated(const FGameplayTag& InTag) const + { + if (const FSimpleDelegate* Delegate = AttributeReplicatedEvent.Find(InTag)) + { + Delegate->Execute(); + //AttributeReplicatedEvent.Remove(InTag); + } + } UGAAttributesBase* Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter); bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) @@ -295,6 +316,10 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) FGAEffectContainer GameEffectContainer; + //Maps effect handles to Properties from which effect was created. + //usefull when all we have is handle or PredictionHandle. + TMap PropertyByHandle; + FAFEffectRepInfoDelegate OnEffectRepInfoApplied; FAFEffectRepInfoDelegate OnEffectRepInfoRemoved; /* @@ -334,6 +359,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, return nullptr; UGAAttributesBase* retVal = RepAttributes.Add(InOwner, InAttributes, this); RepAttributes.MarkArrayDirty(); + return retVal; } UFUNCTION(BlueprintCallable, Category = "Test") @@ -369,6 +395,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, /* ExpireEffect is used to remove existing effect naturally when their time expires. */ void ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty, FGAEffectContext InContext); + + UFUNCTION(Client, Reliable) + void ClientExpireEffect(FAFPredictionHandle PredictionHandle); + void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); + /* RemoveEffect is used to remove effect by force. */ void RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 0778404..e20e4b0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -181,6 +181,14 @@ void UGAAbilityBase::InitAbility() ENetRole role = AbilityComponent->GetOwnerRole(); ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); + + if (role < ENetRole::ROLE_Authority) + { + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); + AbilityComponent->RepAttributes.RegisterAttributeRepEvent(AbilityTag, Delegate); + } + + //AbilityComponent->RepAttributes.AttributeMap.Add(AbilityTag, Attributes); if (role == ENetRole::ROLE_Authority || mode == ENetMode::NM_Standalone) { @@ -201,6 +209,13 @@ void UGAAbilityBase::InitAbility() TickFunction.SetTickFunctionEnable(true); OnAbilityInited(); } + +void UGAAbilityBase::OnAttributeSetReplicated() +{ + UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); + Attributes = attributes; +} + void UGAAbilityBase::OnAbilityInited() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index a10cb1d..79f7324 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -306,8 +306,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); - virtual void InitAbility(); - + void InitAbility(); + UFUNCTION() + void OnAttributeSetReplicated(); //called on both server and client after InitAbility(); virtual void OnAbilityInited(); /* diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index c7dd88b..d62ac1c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -1,4 +1,4 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #include "../AbilityFramework.h" #include "../AFAbilityComponent.h" @@ -40,6 +40,14 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier ) { + + IAFAbilityInterface* Ability = Cast(Causer); + if (!Ability) + { + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); + return FGAEffectHandle(); + } + InEffect.InitializeIfNotInitialized(); if (!InEffect.IsInitialized()) @@ -87,7 +95,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, effect->Context = Context; effect->GameEffect = InEffect.GetSpec(); } - if (IAFAbilityInterface* Ability = Cast(Causer)) + if (Ability) { InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); if (effect) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 44c86a9..2a11f75 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -380,8 +380,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr bool bHasPeriod = InProperty.Period > 0; ENetRole role = OwningComponent->GetOwnerRole(); ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); - //we should not generate handle on clients. - //do we need valid handle for instant effects ? + if (bHasDuration || bHasPeriod) { Handle = FGAEffectHandle::GenerateHandle(EffectIn); @@ -433,7 +432,12 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr } } + + HandleByPrediction.Add(InProperty.PredictionHandle, Handle); + PredictionByHandle.Add(Handle, InProperty.PredictionHandle); + EffectIn->OnApplied(); + return Handle; //apply additonal effect applied with this effect. //for (TSubclassOf Spec : EffectIn.GameEffect->OnAppliedEffects) @@ -451,8 +455,26 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::ApplyReplicationInfo"), bIsServer ? TEXT("Server") : TEXT("Client")); - if (mode == ENetMode::NM_DedicatedServer) + //we need it to mark array dirt on server. Do we ? + /*if (mode == ENetMode::NM_DedicatedServer) + {*/ + //const UWorld* World = OwningComponent->GetWorld(); + //FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); + //RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; + //RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; + //RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; + //RepInfo->Handle = InHandle; + //RepInfo->PredictionHandle = InProperty.PredictionHandle; + //RepInfo->EffectTag = InProperty.GetSpec()->EffectTag; + //RepInfo->Init(); + //MarkItemDirty(*RepInfo); + //ActiveEffectInfos.Add(*RepInfo); + //MarkArrayDirty(); + //EffectInfos.Add(InHandle, RepInfo); + //} + //else if(mode == ENetMode::NM_Standalone || mode == ENetMode::NM_Client) { + //add replication handle (and send it to server ?) const UWorld* World = OwningComponent->GetWorld(); FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; @@ -460,38 +482,15 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; RepInfo->Handle = InHandle; RepInfo->PredictionHandle = InProperty.PredictionHandle; + RepInfo->EffectTag = InProperty.GetSpec()->EffectTag; RepInfo->Init(); MarkItemDirty(*RepInfo); ActiveEffectInfos.Add(*RepInfo); MarkArrayDirty(); - - //predictevily add effect info ? - //if (mode == ENetMode::NM_Standalone - // || role == ENetRole::ROLE_Authority) - { - EffectInfos.Add(InHandle, RepInfo); - } - } - else if(mode == ENetMode::NM_Standalone || mode == ENetMode::NM_Client) - { - //add replication handle (and send it to server ?) - const UWorld* World = OwningComponent->GetWorld(); - FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); - RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; - RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; - RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; - RepInfo->Handle = InHandle; - RepInfo->PredictionHandle = InProperty.PredictionHandle; - RepInfo->Init(); - //MarkItemDirty(RepInfo); - ActiveEffectInfos.Add(*RepInfo); - //MarkArrayDirty(); - UE_LOG(AbilityFramework, Log, TEXT("Client ApplyReplicationInfo. Duration: %f"), InProperty.Duration); //predictevily add effect info ? - { - PredictedEffectInfos.Add(InProperty.PredictionHandle, RepInfo); - EffectInfos.Add(InHandle, RepInfo); - } + + PredictedEffectInfos.Add(InProperty.PredictionHandle, RepInfo); + EffectInfos.Add(InHandle, RepInfo); } } @@ -737,6 +736,11 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N FGAEffectHandle OutHandle = (*handles)[0]; if (OutHandle.IsValid()) { + HandleByPrediction.Remove(HandleIn.PredictionHandle); + + if(PredictionByHandle.Contains(OutHandle)) + PredictionByHandle.Remove(OutHandle); + EffectInfos.RemoveAndCopyValue(OutHandle, Out); if (Out) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index d8fa9b7..c1f0939 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -679,6 +679,9 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer //change to SharedPtr ? mutable TMap EffectInfos; + TMap HandleByPrediction; + TMap PredictionByHandle; + TMap PredictedEffectInfos; TMap> EffectByAttribute; From 56723f789a2278aded21827757da25db3567210a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 14 Dec 2017 23:08:36 +0100 Subject: [PATCH 019/187] Started work on in game ability framework debugger. Added separate module which is sample implementation of ability managment --- ActionRPGGame.uproject | 77 ++- Config/DefaultEditor.ini | 3 + Config/DefaultEngine.ini | 2 +- .../AbilityFramework/AFAbilityComponent.cpp | 163 ++++-- .../AbilityFramework/AFAbilityComponent.h | 102 +++- .../Abilities/AFBlueprintFunctionLibrary.cpp | 46 -- .../Abilities/AFBlueprintFunctionLibrary.h | 15 - .../Abilities/GAAbilityBase.cpp | 30 ++ .../Abilities/GAAbilityBase.h | 125 +++-- .../AbilityFramework/AbilityFramework.cpp | 186 ++++++- .../AbilityFramework/AbilityFramework.h | 127 ++++- .../Attributes/GAAttributesBase.cpp | 1 + .../Effects/AFEffectApplicationRequirement.h | 1 + .../Effects/AFEffectCustomApplication.cpp | 1 + .../Effects/GABlueprintLibrary.cpp | 82 +++ .../Effects/GABlueprintLibrary.h | 5 + .../AbilityFramework/Effects/GAGameEffect.cpp | 161 +++--- .../AbilityFramework/Effects/GAGameEffect.h | 64 ++- .../AFEK2Node_AsyncEffectTaskCall.cpp | 4 +- .../GAEK2Node_LatentAbilityTaskCall.cpp | 4 +- .../GAEK2Node_LatentAction.cpp | 2 +- .../AFDAbilityGiveTrigger.cpp | 104 ++++ .../AFDAbilityGiveTrigger.h | 80 +++ .../AFDBlueprintFunctionLibrary.cpp | 11 + .../AFDBlueprintFunctionLibrary.h | 20 + .../AbilityFrameworkDebugger/AFDManager.cpp | 32 ++ .../AbilityFrameworkDebugger/AFDManager.h | 34 ++ .../AbilityFrameworkDebugger.Build.cs | 62 +++ .../AbilityFrameworkDebugger.cpp | 34 ++ .../AbilityFrameworkDebugger.h | 18 + .../SAFDAttributes.cpp | 55 ++ .../AbilityFrameworkDebugger/SAFDAttributes.h | 31 ++ .../SAFDDesktopWidget.cpp | 129 +++++ .../SAFDDesktopWidget.h | 42 ++ .../SAFDEffectInspector.cpp | 16 + .../SAFDEffectInspector.h | 20 + .../AbilityFrameworkDebugger/SAFDEffects.cpp | 20 + .../AbilityFrameworkDebugger/SAFDEffects.h | 23 + .../SAFDViewportMouseCapture.cpp | 22 + .../SAFDViewportMouseCapture.h | 24 + .../AMAbilityManagerComponent.cpp | 286 ++++++++++ .../AMAbilityManagerComponent.h | 148 ++++++ .../Source/AbilityManager/AMTypes.cpp | 3 + .../Source/AbilityManager/AMTypes.h | 95 ++++ .../AbilityManager/AbilityManager.Build.cs | 58 +++ .../Source/AbilityManager/AbilityManager.cpp | 20 + .../Source/AbilityManager/AbilityManager.h | 15 + .../DraggableWindow/DraggableWindow.Build.cs | 57 ++ .../DraggableWindow/DraggableWindow.cpp | 20 + .../Source/DraggableWindow/DraggableWindow.h | 15 + .../SDraggableWindowWidget.cpp | 493 ++++++++++++++++++ .../DraggableWindow/SDraggableWindowWidget.h | 174 +++++++ Source/ActionRPGGame/ARGameMode.cpp | 11 +- Source/ActionRPGGame/ARPlayerController.cpp | 10 +- Source/ActionRPGGame/ARPlayerController.h | 5 +- .../Abilities/ARAbilityManagerComponent.cpp | 34 ++ .../Abilities/ARAbilityManagerComponent.h | 37 ++ Source/ActionRPGGame/ActionRPGGame.Build.cs | 12 +- .../ActionRPGGame/UI/ARUIWeaponEquipment.cpp | 194 ------- Source/ActionRPGGame/UI/ARUIWeaponEquipment.h | 65 --- .../UI/ARWeaponActriveInfoWidget.cpp | 12 +- .../ActionRPGGame/UI/ARWeaponInfoWidget.cpp | 25 +- Source/ActionRPGGame/UI/ARWeaponInfoWidget.h | 16 +- .../Abilities/ARUIAbilityManagerComponent.h | 1 + .../Weapons/ARWeaponManagerComponent.cpp | 165 ++---- .../Weapons/ARWeaponManagerComponent.h | 72 +-- .../ActionRPGGame/Weapons/ARWeaponsTypes.cpp | 3 + Source/ActionRPGGame/Weapons/ARWeaponsTypes.h | 15 + 68 files changed, 3327 insertions(+), 712 deletions(-) delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMTypes.h create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h create mode 100644 Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp create mode 100644 Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h delete mode 100644 Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp delete mode 100644 Source/ActionRPGGame/UI/ARUIWeaponEquipment.h create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponsTypes.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponsTypes.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 01a8ce9..4458fe8 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -1,6 +1,6 @@ { "FileVersion": 3, - "EngineAssociation": "{C19309FF-49B1-44A8-E307-2B81122303E8}", + "EngineAssociation": "{A36EBF10-476D-8159-343E-8FA796F9AC8F}", "Category": "", "Description": "", "Modules": [ @@ -57,6 +57,81 @@ { "Name": "Niagara", "Enabled": true + }, + { + "Name": "SoundUtilities", + "Enabled": true + }, + { + "Name": "SoundVisualizations", + "Enabled": true + }, + { + "Name": "BlueprintStats", + "Enabled": true + }, + { + "Name": "LocationServicesBPLibrary", + "Enabled": false + }, + { + "Name": "WindowsDeviceProfileSelector", + "Enabled": true + }, + { + "Name": "AndroidDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "IOSDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "AndroidMedia", + "Enabled": false + }, + { + "Name": "MobileLauncherProfileWizard", + "Enabled": false + }, + { + "Name": "MobilePatchingUtils", + "Enabled": false + }, + { + "Name": "AndroidMoviePlayer", + "Enabled": false + }, + { + "Name": "AppleMoviePlayer", + "Enabled": false + }, + { + "Name": "GoogleCloudMessaging", + "Enabled": false + }, + { + "Name": "OnlineSubsystemIOS", + "Enabled": false, + "SupportedTargetPlatforms": [ + "IOS", + "TVOS" + ] + }, + { + "Name": "OnlineSubsystemGooglePlay", + "Enabled": false, + "SupportedTargetPlatforms": [ + "Android" + ] + }, + { + "Name": "ApexDestruction", + "Enabled": true + }, + { + "Name": "AndroidPermission", + "Enabled": false } ], "TargetPlatforms": [ diff --git a/Config/DefaultEditor.ini b/Config/DefaultEditor.ini index 68e034e..b229537 100644 --- a/Config/DefaultEditor.ini +++ b/Config/DefaultEditor.ini @@ -4,4 +4,7 @@ bReplaceBlueprintWithClass= true bDontLoadBlueprintOutsideEditor= true bBlueprintIsNotBlueprintType= true +[/Script/UnrealEd.EditorProjectAppearanceSettings] +bDisplayUnitsOnComponentTransforms=True + diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index ca25dd0..854e7c9 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -118,7 +118,7 @@ TriangleMeshTriangleMinAreaThreshold=5.000000 bEnableAsyncScene=True bEnableShapeSharing=True bEnablePCM=True -bEnableStabilization=False +bEnableStabilization=True bWarnMissingLocks=True bEnable2DPhysics=False LockedAxis=Invalid diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 9782930..910b151 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -21,7 +21,8 @@ #include "Effects/GAEffectCue.h" #include "AFCueSet.h" #include "AFCueManager.h" - +#include "Effects/GABlueprintLibrary.h" +#include "Async.h" #include "AFAbilityComponent.h" @@ -29,6 +30,8 @@ DEFINE_STAT(STAT_ApplyEffect); DEFINE_STAT(STAT_ModifyAttribute); + + void FAFReplicatedAttributeItem::PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer) { FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); @@ -69,7 +72,6 @@ UAFAbilityComponent::UAFAbilityComponent(const FObjectInitializer& ObjectInitial PrimaryComponentTick.bRunOnAnyThread = false; PrimaryComponentTick.bAllowTickOnDedicatedServer = true; PrimaryComponentTick.TickGroup = ETickingGroup::TG_DuringPhysics; - } void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribute, @@ -130,10 +132,17 @@ void UAFAbilityComponent::Update() void UAFAbilityComponent::BeginPlay() { Super::BeginPlay(); + FAFEffectTimerManager::Get(); +} +void UAFAbilityComponent::EndPlay(const EEndPlayReason::Type EndPlayReason) +{ + Super::EndPlay(EndPlayReason); + } void UAFAbilityComponent::DestroyComponent(bool bPromoteChildren) { Super::DestroyComponent(bPromoteChildren); + } FGAEffectHandle UAFAbilityComponent::ApplyEffectToSelf(FGAEffect* EffectIn @@ -142,6 +151,7 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToSelf(FGAEffect* EffectIn { const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; FAFEventData Data; + for (const FGameplayTag& Tag : AppliedEventTags) { if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) @@ -149,25 +159,29 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToSelf(FGAEffect* EffectIn Event->Broadcast(Data); } } - - //OnEffectApplyToSelf.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); + if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) + { + Delegate->ExecuteIfBound(); + } + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); GameEffectContainer.MarkArrayDirty(); + OnEffectAppliedToSelf.Broadcast(Handle); return Handle; - //FGAEffectCueParams CueParams; - //CueParams.HitResult = EffectIn.Context.HitResult; - //OnEffectApplied.Broadcast(HandleIn, HandleIn.GetEffectPtr()->OwnedTags); } + + FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn , FGAEffectProperty& InProperty, FGAEffectContext& InContext , const FAFFunctionModifier& Modifier) { - //broadcast cues first ? - //Probabaly because effect might not always apply. Or relegate cue - //application to object which was hit ? + if(FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) + { + Delegate->ExecuteIfBound(); + } ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); - + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams; @@ -180,7 +194,10 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn //if (mode == ENetMode::NM_Standalone // || role >= ENetRole::ROLE_Authority) { - MulticastApplyEffectCue(CueParams); + //AsyncTask(ENamedThreads::GameThread, [=]() + //{ + MulticastApplyEffectCue(CueParams); + //}); } } FString prefix = ""; @@ -211,7 +228,8 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn Handle = InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); if (!PropertyByHandle.Contains(Handle)) PropertyByHandle.Add(Handle, &InProperty); - + + OnEffectAppliedToTarget.Broadcast(Handle); return Handle; } } @@ -253,7 +271,7 @@ void UAFAbilityComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectPrope } } - OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); FGAEffect& Effect = HandleIn.GetEffectRef(); FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() @@ -431,7 +449,6 @@ void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProp //to allow prediction for UI. DOREPLIFETIME(UAFAbilityComponent, DefaultAttributes); DOREPLIFETIME(UAFAbilityComponent, RepAttributes); - DOREPLIFETIME(UAFAbilityComponent, ModifiedAttribute); DOREPLIFETIME(UAFAbilityComponent, GameEffectContainer); DOREPLIFETIME(UAFAbilityComponent, ActiveCues); @@ -449,13 +466,6 @@ void UAFAbilityComponent::OnRep_ActiveCues() } -void UAFAbilityComponent::OnRep_AttributeChanged() -{ - //for (FGAModifiedAttribute& attr : ModifiedAttribute.Mods) - //{ - // attr.Causer->OnAttributeModifed.Broadcast(attr); - //} -} bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) { bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); @@ -547,9 +557,22 @@ bool UAFAbilityComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InT } return bAllowApplication; } +const bool FGASAbilityItem::operator==(const FGameplayTag& AbilityTag) const +{ + return Ability->AbilityTag == AbilityTag; +} void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer) { - + if (InArraySerializer.AbilitiesComp.IsValid()) + { + FGASAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + //remove attributes + //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); + Ability->Attributes = nullptr; + FGameplayTag AbilityTag = Ability->AbilityTag; + InArraySerializerC.RemoveAbilityFromAction(AbilityTag, FGameplayTag()); + InArraySerializerC.AbilitiesInputs.Remove(AbilityTag); + } } void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) { @@ -625,11 +648,40 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf OutActions; + AbilityToAction.RemoveAndCopyValue(InAbilityTag, OutActions); + + for(const FGameplayTag& Action : OutActions) + { + ActionToAbility.Remove(Action); + } + + AbilitiesInputs.Remove(InAbilityTag); +} void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InInputTag); AbilityTag = InAbilityTag; + TArray& ActionTag = AbilityToAction.FindOrAdd(InAbilityTag); + ActionTag.Add(InInputTag); + if (!AbilitiesComp.IsValid()) return; if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) @@ -637,9 +689,11 @@ void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, AbilitiesComp->ClientNotifyAbilityInputReady(InAbilityTag); } } + UGAAbilityBase* FGASAbilityContainer::GetAbility(FGameplayTag TagIn) { - return AbilitiesInputs.FindRef(TagIn); + UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(TagIn); + return retAbility; } void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) { @@ -694,7 +748,9 @@ void UAFAbilityComponent::InitializeComponent() //PawnInterface = Cast(GetOwner()); UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); AbilityContainer.AbilitiesComp = this; - + //EffectTimerManager = MakeShareable(new FAFEffectTimerManager()); + + //EffectTimerManager.InitThread(); if (DefaultAttributes) { DefaultAttributes->InitializeAttributes(this); @@ -705,10 +761,18 @@ void UAFAbilityComponent::InitializeComponent() //ActiveCues.OwningComponent = this; AppliedTags.AddTagContainer(DefaultTags); InitializeInstancedAbilities(); + + AActor* MyOwner = GetOwner(); + if (!MyOwner || !MyOwner->IsTemplate()) + { + ULevel* ComponentLevel = (MyOwner ? MyOwner->GetLevel() : GetWorld()->PersistentLevel); + } } void UAFAbilityComponent::UninitializeComponent() { Super::UninitializeComponent(); + //EffectTimerManager.Deinitialize(); + //EffectTimerManager.Reset(); //GameEffectContainer } void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InInput, bool bBlock) @@ -739,10 +803,20 @@ void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, F } SetBlockedInput(ActionName, false); } - +void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag + , const FAFOnAbilityReady& InputDelegate) +{ + for (const FGameplayTag& Tag : InInputTag) + { + SetAbilityToAction(InAbilityTag, Tag, InputDelegate); + } +} void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, const FAFOnAbilityReady& InputDelegate) { + //check if there is input under tag + //clear it + //then bind. AbilityContainer.SetAbilityToAction(InAbilityTag, InInputTag); ENetRole role = GetOwnerRole(); @@ -756,6 +830,14 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c ServerSetAbilityToAction(InAbilityTag, InInputTag); } } +bool UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +{ + return AbilityContainer.IsAbilityBoundToAction(InAbilityTag, InInputTag); +} +void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +{ + AbilityContainer.RemoveAbilityFromAction(InAbilityTag, InInputTag); +} void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) @@ -784,30 +866,8 @@ void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) { PredHandle = FAFPredictionHandle::GenerateClientHandle(this); } - //if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNativeInputPressed(ActionName, PredHandle); - //UE_LOG(AbilityFramework, Log, TEXT("Client UAFAbilityComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); - //naive needs better qynchornization to what going on where. - //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - { - //if (Ability->AbilityComponent == this) - { - AbilityContainer.HandleInputPressed(ActionName, PredHandle); - } - } - } - //else - //{ - //UE_LOG(AbilityFramework, Log, TEXT("Server UAFAbilityComponent::NativeInputPressed: %s"), *AbilityTag.GetTagName().ToString()); - //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - //{ - //if (Ability->AbilityComponent == this) - //{ - // AbilityContainer.HandleInputPressed(ActionName); - //} - //} - //} + ServerNativeInputPressed(ActionName, PredHandle); + AbilityContainer.HandleInputPressed(ActionName, PredHandle); } void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) @@ -931,7 +991,8 @@ void UAFAbilityComponent::BP_RemoveAbility(FGameplayTag TagIn) } UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(FGameplayTag TagIn) { - return AbilityContainer.GetAbility(TagIn); + UGAAbilityBase* retVal = AbilityContainer.GetAbility(TagIn); + return retVal; } UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass, AActor* InAvatar) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index dc89ca4..047b7ab 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -29,7 +29,7 @@ DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_Modify DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGAGenericEffectDelegate, const FGAEffectHandle&, Handle, const FGameplayTagContainer&, Tags); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle, Handle); DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate , FAFEventData); DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); @@ -40,6 +40,7 @@ DECLARE_DELEGATE(FAFOnAbilityReady); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); DECLARE_DELEGATE(FAFGenericAttributeDelegate); +DECLARE_DELEGATE(FAFEffectEvent); //UAFAssetManager* GetAssetManager() //{ // return Cast(UAssetManager::GetIfValid()); @@ -123,6 +124,16 @@ struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); + + const bool operator==(const FGameplayTag& AbilityTag) const; + const bool operator==(UGAAbilityBase* OtherAbility) const + { + return Ability == OtherAbility; + } + const bool operator==(const FGASAbilityItem& OtherItem) const + { + return Ability == OtherItem.Ability; + } }; USTRUCT() struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer @@ -138,14 +149,22 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer //Custom binding, for server side validation. - //ActionName, AbilityTag + //ActionInput, AbilityTag TMap ActionToAbility; + //AbilityTag, ActionInput + TMap> AbilityToAction; + //abilityTag, Ability Ptr TMap AbilitiesInputs; void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, AActor* InAvatar); + void RemoveAbility(const FGameplayTag& AbilityIn); + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + bool IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + UGAAbilityBase* GetAbility(FGameplayTag TagIn); void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); @@ -237,9 +256,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, GENERATED_BODY() /* Attributes handling */ public: - friend struct FAFMessageTick; //Only for base testing and prototyping cue application. //will be removed when Cue Manager will be more functional. + + //FAFEffectTimerManager EffectTimerManager; + UPROPERTY(EditAnywhere) class UAFCueSet* TestCueSet; UPROPERTY(EditAnywhere, Category = "Test") @@ -285,23 +306,16 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UPROPERTY(Replicated) FAFReplicatedAttributeContainer RepAttributes; - UPROPERTY(ReplicatedUsing = OnRep_AttributeChanged) - FGAModifiedAttributeData ModifiedAttribute; - UFUNCTION() - void OnRep_AttributeChanged(); UPROPERTY(BlueprintAssignable, Category = "Game Attributes") FGAOnAttributeModifed OnAttributeModifed; UPROPERTY(BlueprintAssignable, Category = "Game Attributes") FGAOnAttributeModifed OnTargetAttributeModifed; /* Effect/Attribute System Delegates */ UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectApplied; - - UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectApplyToTarget; + FGAGenericEffectDelegate OnEffectAppliedToTarget; UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectApplyToSelf; + FGAGenericEffectDelegate OnEffectAppliedToSelf; UPROPERTY(BlueprintAssignable, Category = "Effect") FGAGenericEffectDelegate OnEffectExecuted; @@ -365,26 +379,58 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UFUNCTION(BlueprintCallable, Category = "Test") void GetAttributeStructTest(FGAAttribute Name); + /** UActorComponent Interface - Begin */ virtual void BeginPlay() override; + virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; virtual void DestroyComponent(bool bPromoteChildren = false) override; - virtual void InitializeComponent() override; - virtual void UninitializeComponent() override; - + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + /* UActorComponent Interface - End **/ public: ///////////////////////////////////////////////// //////////// EFFECTS HANDLING - virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + void Update(); + + /* + * @call Order: + * Previous Function: UAFAbilityComponent::ApplyEffectToTarget + * Next Function: FGAEffectContainer::ApplyEffect + * Apply target to Me. Try to apply effect to container and launch Events in: + * TMap OnEffectEvent - event is called before application; + * TMap OnEffectApplyToSelf - event is called before application; + * + * @param EffectIn* - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect; + */ FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn, FGAEffectProperty& InProperty, FGAEffectContext& InContext , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + /* + * @call Order: + * Previous Function: UGABlueprintLibrary::ApplyEffect + * Next Function: UAFAbilityComponent::ApplyEffectToSelf + * Apply effect to target provided inside Context. + * Try launch events: + * TMap OnEffectApplyToTarget - event is called before application + * + * @param EffectIn* - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect; + */ FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, FGAEffectProperty& InProperty, FGAEffectContext& InContext , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + void ApplyEffectToTarget(TSubclassOf InSpecClass, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); @@ -404,6 +450,14 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); + const TSet& GetAllEffectsHandles() const + { + return GameEffectContainer.GetAllEffectHandles(); + } + const TArray& GetAllEffectsInfo() const + { + return GameEffectContainer.GetAllEffectsInfo(); + } /* Need prediction for spawning effects on client, and then on updateing them predicitvely on all other clients. @@ -515,13 +569,13 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, bool DenyEffectApplication(const FGameplayTagContainer& InTags); bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); /* - Effect Container Wrapp Start + Effect Container Wrapp Start */ /* */ inline bool IsEffectActive(const FGAEffectHandle& HandleIn) { return GameEffectContainer.IsEffectActive(HandleIn); }; /* - Effect Container Wrapp End + Effect Container Wrapp End */ /* Counted Tag Container Wrapper Start */ @@ -605,6 +659,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); OnEffectEvent.Remove(InEventTag); } + + TMap OnEffectApplyToSelf; + + TMap OnEffectApplyToTarget; + /* True if player is currently casting/channeling/activating(?) any ability. @@ -688,6 +747,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, } } + + FAFOnAbilityReady OnAbilityReady; UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") @@ -725,8 +786,13 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); //need to be called on both client and server. + //Change InInputTag To Array, clear previous binds on the same tag. + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, const FAFOnAbilityReady& InputDelegate); + bool IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + UFUNCTION(Server, Reliable, WithValidation) void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp deleted file mode 100644 index b27b8fd..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.cpp +++ /dev/null @@ -1,46 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" - -#include "GAAbilityBase.h" -#include "../Effects/GAEffectField.h" -#include "../AFAbilityInterface.h" -#include "../AFAbilityComponent.h" -#include "AFBlueprintFunctionLibrary.h" - -void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, - const FGameplayTag& AbilityTag, FGameplayTag ActionTag) -{ - IAFAbilityInterface* Interface = Cast(Target); - if (!Interface) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Invalid Target")); - return; - } - UAFAbilityComponent* Comp = Interface->GetAbilityComp(); - if (!Comp) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Target %s InvalidComponent"), *Target->GetName()); - return; - } - - Comp->NativeInputPressed(ActionTag); -} -void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, - const FGameplayTag& AbilityTag, FGameplayTag ActionTag) -{ - IAFAbilityInterface* Interface = Cast(Target); - if (!Interface) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Invalid Target")); - return; - } - UAFAbilityComponent* Comp = Interface->GetAbilityComp(); - if (!Comp) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Target %s InvalidComponent"), *Target->GetName()); - return; - } - - Comp->NativeInputReleased(ActionTag); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h deleted file mode 100644 index 2ec187d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFBlueprintFunctionLibrary.h +++ /dev/null @@ -1,15 +0,0 @@ -#pragma once -#include "AFBlueprintFunctionLibrary.generated.h" -/* - Some static helper functions, to interact with Attribute system. -*/ -UCLASS() -class ABILITYFRAMEWORK_API UAFBlueprintFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_BODY() -public: - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - static void TriggerAbilityPressedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - static void TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index e20e4b0..5a5b5d0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -701,6 +701,36 @@ void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagI AbilityComponent->NativeInputReleased(ActionName); } +bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) +{ + bool bHaveTag = false; + if (IAFAbilityInterface* Interface = Cast(Target)) + { + if (UAFAbilityComponent* Comp = Interface->GetAbilityComp()) + { + if (Comp->HasTag(Tag)) + { + bHaveTag = true; + } + } + } + return bHaveTag; +} +bool UGAAbilityBase::HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag) +{ + bool bHaveTag = false; + if (IAFAbilityInterface* Interface = Cast(Target)) + { + if (UAFAbilityComponent* Comp = Interface->GetAbilityComp()) + { + if (Comp->HasAny(Tag)) + { + bHaveTag = true; + } + } + } + return bHaveTag; +} /* Tracing Helpers Start */ bool UGAAbilityBase::LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 79f7324..4122638 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -312,16 +312,28 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask //called on both server and client after InitAbility(); virtual void OnAbilityInited(); /* - Called when ability received input. - One ability can receive multiple input calls, how those will be handled - is up to ability. - */ + * @call Order: + * Previous Function: FGASAbilityContainer::HandleInputPressed + * Next Function: UGAAbilityBase::OnInputPressed + * + * Called on both Client and Server. + * + * @param ActionName - Name of action which tirggered this ability + * @param InPredictionHandle - Prediction Handle Generate By Client + */ void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); /* - Called when ability receive input press. Does not start ability execution automatically, so it - is safe to make any pre execution preparations of ability here. - - To start ability execution you must call ExecuteAbility. + * @call Order: + * Previous Function: UGAAbilityBase::OnNativeInputPressed + * Next Function: Multiple Choices. Next function is usually called from within Ability Blueprint + * Default Choices: + * UGAAbilityBase::StartActivation + * UGAAbilityBase::CanUseAbility + * Custom Function + * + * Called on both Client and Server. + * + * @param ActionName - Name of action which tirggered this ability */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnInputPressed(FGameplayTag ActionName); @@ -331,15 +343,11 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void OnInputReleased(FGameplayTag ActionName); - virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); + void NativeOnAbilityConfirmed(); - /* - Called when StartActivation is triggered. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivate(); + /* Called When activation effect expired. @@ -349,33 +357,57 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void OnActivationFinished(); /* - In blueprint, call this function to trigger event of the same name, - after ability is ready to be executed (like after targeting is done, input is confirmed, - or simply after receiving first input press. - - This function will trigger selected Activation State, which then will trigger Event OnAbilityExecuted. - In C++ it will trigger OnAbilityExecutedNative(). - - ActiveState will always be called first, so it is possible to bypass entire state stage if ActivationState will - go straight away for event call. - - bApplyActivationEffect - should apply activation effect ? - if Period or Activation is > 0, it will be overrided to true. + * @call Order: + * Previous Function: (Blueprint) UGAAbilityBase::OnInputPressed + * Next Function: UGAAbilityBase::NativeOnBeginAbilityActivation + * + * Called on both Client and Server. + * + * @param bApplyActivationEffect - Should apply activation effect to Owner. */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") void StartActivation(bool bApplyActivationEffect); + /* + * @call Order: + * Previous Function: UGAAbilityBase::StartActivation + * Next Function: UGAAbilityBase::ApplyActivationEffect + * Next Function: (Blueprint) UGAAbilityBase::OnActivate + * + * Called on both Client and Server. + * + * @param bApplyActivationEffect - Should apply activation effect to Owner. + */ + virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called on both Client and Server. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivate(); /* Event called when ability activation has been canceled. */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnActivationCancel(); - + /* + * @call Order: + * Previous Function: Called if Periodic effect has been applied and is active. Otherwise inactive. + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * + * Called on both Client and Server. + */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnPeriod(); - /* Event called when ability finishes it's execution. Called AFTER OnAbilityExecuted. */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnAbilityFinished(); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnCooldownStart(); @@ -390,11 +422,37 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void NativeOnAbilityActivationCancel(); /* - Finishes ability. Use it to finish ability after activation or released input. + * @call Order: + * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called to finish ability and start clean up. */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") void FinishAbility(); + /* + * @call Order: + * Previous Function: UGAAbilityBase::FinishAbility + * Next Function: (Blueprint) UGAAbilityBase::OnAbilityFinished + * + * Called to finish ability and start clean up. + */ void NativeFinishAbility(); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeFinishAbility + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called to finish ability and start clean up. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnAbilityFinished(); /* Stop effect activation and remove activation effect. */ @@ -517,6 +575,11 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask return AbilityTasks.FindRef(InName); } + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") + bool HaveGameplayTag(AActor* Target, const FGameplayTag& Tag); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") + bool HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag); + /* Tracing Helpers Start */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") bool LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp index 4f11d80..78b0df8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp @@ -1,24 +1,195 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #pragma once #include "AbilityFramework.h" -#include "IAbilityFramework.h" + DEFINE_LOG_CATEGORY(AbilityFramework); DEFINE_LOG_CATEGORY(GameAttributesGeneral); DEFINE_LOG_CATEGORY(GameAttributes); DEFINE_LOG_CATEGORY(GameAttributesEffects); -class FAbilityFramework : public IAbilityFramework +FAFEffectTimerManager* FAFEffectTimerManager::Instance = nullptr; + +DECLARE_CYCLE_STAT(TEXT("EffectTimer.Run"), STAT_EffectTimerRun, STATGROUP_EffectTimer); +FAFEffectTimer::FAFEffectTimer() +{ + +} +FAFEffectTimerWorker::FAFEffectTimerWorker() +{ + bActive = true; + Timers.Reset(); + Timers.SetNumZeroed(0); + InternalTime = FPlatformTime::ToSeconds64(FPlatformTime::Cycles64()); + for (int Idx = 0; Idx < 10000; Idx++) + { + float Duration = FMath::RandRange(15, 25); + AddTimer(Duration, 0.2); + } +} +FAFEffectTimerManager::FAFEffectTimerManager() +{ + TimerWorker = new FAFEffectTimerWorker(); + TimerThread = FRunnableThread::Create(TimerWorker, TEXT("EffectTimerThread"), 512*1024, TPri_Normal); + + check(TimerWorker != nullptr); +} +FAFEffectTimerManager::~FAFEffectTimerManager() +{ + //if (TimerThread) + //{ + // TimerThread->Kill(); + // delete TimerThread; + // TimerThread = nullptr; + //} +} +uint32 FAFEffectTimerWorker::Run() +{ + while (1) + { + SCOPE_CYCLE_COUNTER(STAT_EffectTimerRun); + InternalTime = FPlatformTime::ToSeconds64(FPlatformTime::Cycles64()); + //while (Timers.Num() > 0) + { +//#if UE_BUILD_DEVELOPTMENT || UE_BUILD_DEBUG + +//#endif // UE_BUILD_DEVELOPTMENT || UE_BUILD_DEBUG + + //for (FAFEffectTimer& Timer : Timers) + { + //auto It = Timers.CreateIterator(); + //for (; It; ++It) + //{ + + // if (It->bHavePeriod && (InternalTime > It->NextPeriodTime)) + // { + // double asdasd = It->ExpireTime - InternalTime; + // double FinalTime = InternalTime - It->StartTime; + // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Period TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + + // It->NextPeriodTime = InternalTime + It->PeriodTime; + // //It->PeriodDelegate.ExecuteIfBound(); + + // } + // if (It->bHaveDuration && (InternalTime > It->ExpireTime)) + // { + // double asdasd = It->ExpireTime - InternalTime; + // double FinalTime = InternalTime - It->StartTime; + // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + // //It->ExpireDelegate.ExecuteIfBound(); + + // //FAFEffectTimer Out; + // //Timers.Remove(*It); + // //Timers.Shrink(); + // } + //} + for (FAFEffectTimer& Timer : Timers) + { + if (!Timer.bActive) + continue; + + if (Timer.bHavePeriod && (InternalTime > Timer.NextPeriodTime)) + { + double asdasd = Timer.ExpireTime - InternalTime; + double FinalTime = InternalTime - Timer.StartTime; + //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Period TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + + Timer.NextPeriodTime = InternalTime + Timer.PeriodTime; + //Timer.PeriodDelegate.ExecuteIfBound(); + + } + if (Timer.bHaveDuration && (InternalTime > Timer.ExpireTime)) + { + double asdasd = Timer.ExpireTime - InternalTime; + double FinalTime = InternalTime - Timer.StartTime; + //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + //Timer.ExpireDelegate.ExecuteIfBound(); + //Timer.bActive = false; + //FAFEffectTimer Out; + //Timers.Remove(*It); + //Timers.Shrink(); + } + } + //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer TimeRemaining: %f"), asdasd); + //FAFEffectTimer& Top = Timers.HeapTop(); + + //if (Timer.bActive) + //{ + // if (Top.bHaveDuration && (InternalTime > Top.ExpireTime)) + // { + // double asdasd = Top.ExpireTime - InternalTime; + // double FinalTime = InternalTime - Top.StartTime; + // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + // Top.ExpireDelegate.ExecuteIfBound(); + + // FAFEffectTimer Out; + // Timers.HeapPop(Out); + // Timers.Shrink(); + // } + //} + } + } + FPlatformProcess::Sleep(0.01); + } + return 0; +} +bool FAFEffectTimerWorker::Init() { - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; + return true; +} +void FAFEffectTimerWorker::Stop() +{ + bActive = false; +} -IMPLEMENT_MODULE( FAbilityFramework, AbilityFramework) +/** +* Exits the runnable object. +* +* Called in the context of the aggregating thread to perform any cleanup. +* @see Init, Run, Stop +*/ +void FAFEffectTimerWorker::Exit() +{ + //Timers.Empty(); + //bActive = false; +} + +FAFEffectTimeHandle FAFEffectTimerWorker::AddTimer(double InDuration, double InPeriod) +{ + FScopeLock lock(&CS); + //bActive = false; + FAFEffectTimer Timer; + Timer.Duration = InDuration; + Timer.PeriodTime = InPeriod; + Timer.bHaveDuration = InDuration <= 0 ? false : true; + Timer.bHavePeriod = InPeriod <= 0 ? false : true; + Timer.StartTime = InternalTime; // FPlatformTime::ToSeconds64(FPlatformTime::Cycles64());// InternalTime; + + Timer.ExpireTime = InternalTime + Timer.Duration; + Timer.NextPeriodTime = InternalTime + Timer.PeriodTime; + Timer.bActive = true; + Timers.Add(Timer); + int32 idx = Timers.Num() - 1; + //Timers.Push(Timer); + //Timers.Heapify(); + FAFEffectTimeHandle Handle; + Handle.Index = idx; + Timers[idx].Handle = Handle; + UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Start TimeDifference: %f"), (Timer.ExpireTime - InternalTime)); + //since there is at least one timer, set timer manager to be active. + + bActive = true; + return Handle; +} + +FAFEffectTimeHandle FAFEffectTimerManager::AddTimer(double InDuration, double InPeriod) +{ + return TimerWorker->AddTimer(InDuration, InPeriod); +} void FAbilityFramework::StartupModule() { + //FAFEffectTimerManager::Get(); // This code will execute after your module is loaded into memory (but after global variables are initialized, of course.) } @@ -31,3 +202,4 @@ void FAbilityFramework::ShutdownModule() +IMPLEMENT_MODULE(FAbilityFramework, AbilityFramework) \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h index 59764c8..4ae9424 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h @@ -2,7 +2,7 @@ #pragma once #include "Engine.h" - +#include "IAbilityFramework.h" #include "InputCoreTypes.h" #include "Runtime/UMG/Public/UMG.h" @@ -12,6 +12,131 @@ #include "Runtime/UMG/Public/Blueprint/UserWidget.h" //#include "GameTrace.h" +enum class EAFEffectTimerStatus : uint8 +{ + Pending, + Active, + Executing, + Paused +}; + +struct FAFEffectTimeHandle +{ + int32 Index; + bool operator==(const FAFEffectTimeHandle& Other) const + { + return Index == Other.Index; + } +}; + +struct FAFEffectTimer +{ + double StartTime; //when started + double ExpireTime; + double NextPeriodTime; + double PeriodTime; + double Duration; //how often timer is executed + + bool bHaveDuration; //does it loop + bool bHavePeriod; + bool bActive; + + EAFEffectTimerStatus Status; + + FSimpleDelegate ExpireDelegate; + FSimpleDelegate PeriodDelegate; + + FAFEffectTimeHandle Handle; + + FAFEffectTimer(); + + bool operator<(const FAFEffectTimer& Other) const + { + return ExpireTime < Other.ExpireTime; + } + bool operator==(const FAFEffectTimer& Other) const + { + return Handle == Other.Handle; + } +}; + +DECLARE_STATS_GROUP(TEXT("EffectTimer"), STATGROUP_EffectTimer, STATCAT_Advanced); +class FAFEffectTimerWorker : public FRunnable +{ + FCriticalSection CS; + TArray Timers; + TArray ActiveTimers; + UWorld* World; + double InternalTime; + bool bActive; +public: + FAFEffectTimerWorker(); + virtual bool Init() override; + + /** + * Runs the runnable object. + * + * This is where all per object thread work is done. This is only called if the initialization was successful. + * + * @return The exit code of the runnable object + * @see Init, Stop, Exit + */ + virtual uint32 Run() override; + + /** + * Stops the runnable object. + * + * This is called if a thread is requested to terminate early. + * @see Init, Run, Exit + */ + virtual void Stop() override; + + /** + * Exits the runnable object. + * + * Called in the context of the aggregating thread to perform any cleanup. + * @see Init, Run, Stop + */ + virtual void Exit() override; + + FAFEffectTimeHandle AddTimer(double InDuration, double InPeriod); +}; + +class FAFEffectTimerManager +{ + FRunnableThread* TimerThread; + FAFEffectTimerWorker* TimerWorker; + + +public: + static FAFEffectTimerManager* Instance; + static FAFEffectTimerManager* Get() + { + //static FAFEffectTimerManager Obj;// = nullptr; + //return Obj; + if (!Instance) + Instance = new FAFEffectTimerManager(); + + return Instance; + + } + + FAFEffectTimerManager(); + + ~FAFEffectTimerManager(); + + void TickTimer(float InDeltaTime); + FAFEffectTimeHandle AddTimer(double InDuration, double InPeriod); +}; + +class FAbilityFramework : public IAbilityFramework +{ + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; + + DECLARE_LOG_CATEGORY_EXTERN(AbilityFramework, Log, All); DECLARE_LOG_CATEGORY_EXTERN(GameAttributesGeneral, Log, All); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp index e66bd5e..6c7d0a9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -3,6 +3,7 @@ #include "../AbilityFramework.h" #include "../GAGlobalTypes.h" #include "../AFAbilityComponent.h" +#include "Net/UnrealNetwork.h" #include "GAAttributesBase.h" UGAAttributesBase::UGAAttributesBase(const FObjectInitializer& ObjectInitializer) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h index 0701ab1..76ae53d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h @@ -5,6 +5,7 @@ #include "CoreMinimal.h" #include "UObject/NoExportTypes.h" #include "../GAGlobalTypes.h" +#include "GAGameEffect.h" #include "AFEffectApplicationRequirement.generated.h" /** diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp index 05bb6d0..c6d124e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp @@ -1,6 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" +#include "../AFAbilityComponent.h" #include "AFEffectCustomApplication.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index d62ac1c..e8cc419 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -55,7 +55,19 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); return FGAEffectHandle(); } + FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + + //FAFQueueApplyEffect QueuedEffect; + //QueuedEffect.Effect = &InEffect; + //QueuedEffect.Target = Target; + //QueuedEffect.Causer = Causer; + //QueuedEffect.Instigator = Instigator; + //QueuedEffect.HitIn = HitIn; + //QueuedEffect.Modifier = Modifier; + // + //Context.InstigatorComp->QueuedEffects.Enqueue(QueuedEffect); + //return FGAEffectHandle(); /*if (!Context.IsValid()) { return FGAEffectHandle(); @@ -106,7 +118,77 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, return Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); } +FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier) +{ + IAFAbilityInterface* Ability = Cast(Causer); + if (!Ability) + { + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); + return FGAEffectHandle(); + } + + InEffect->InitializeIfNotInitialized(); + + if (!InEffect->IsInitialized()) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + return FGAEffectHandle(); + } + + FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + + /*if (!Context.IsValid()) + { + return FGAEffectHandle(); + }*/ + UAFAbilityComponent* Target2 = Context.TargetComp.Get(); + if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) + { + return FGAEffectHandle(); + } + if (Target2->DenyEffectApplication(InEffect->GetSpec()->DenyTags)) + { + return FGAEffectHandle(); + } + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); + InEffect->Duration = InEffect->GetSpec()->Duration.GetFloatValue(Context); + InEffect->Period = InEffect->GetSpec()->Period.GetFloatValue(Context); + FGAEffect* effect = nullptr; + if (InEffect->Duration <= 0 && InEffect->Period <= 0) + { + if (!InEffect->Handle.IsValid()) + { + effect = new FGAEffect(InEffect->GetSpec(), Context); + AddTagsToEffect(effect); + effect->Context = Context; + effect->GameEffect = InEffect->GetSpec(); + } + else + { + effect = InEffect->Handle.GetEffectPtr().Get(); + } + } + else + { + effect = new FGAEffect(InEffect->GetSpec(), Context); + AddTagsToEffect(effect); + effect->Context = Context; + effect->GameEffect = InEffect->GetSpec(); + } + if (Ability) + { + InEffect->SetPredictionHandle(Ability->GetPredictionHandle()); + if (effect) + { + effect->PredictionHandle = Ability->GetPredictionHandle(); + } + } + + return Context.InstigatorComp->ApplyEffectToTarget(effect, *InEffect, Context, Modifier); +} FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit(FGAEffectProperty& InEffect, const FHitResult& Target, class APawn* Instigator, UObject* Causer, const FAFFunctionModifier& Modifier) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h index 3655783..95752cb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h @@ -24,6 +24,7 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar static FGAEffectHandle ApplyGameEffectToActor(UPARAM(ref) FGAEffectProperty& InEffect, class AActor* Target, class APawn* Instigator, UObject* Causer, const FAFFunctionModifier& Modifier); + /* Makes outgoing effect spec and assign handle to it. If valid handle is provided it will instead reuse existing effect spec from handle, @@ -39,6 +40,10 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + static FGAEffectHandle ApplyEffect(FGAEffectProperty* InEffect, + class UObject* Target, class APawn* Instigator, + UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + static FGAEffectHandle ApplyEffectFromHit(FGAEffectProperty& InEffect, const FHitResult& Target, class APawn* Instigator, UObject* Causer, const FAFFunctionModifier& Modifier); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 2a11f75..fe428fb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -6,13 +6,13 @@ #include "../Attributes/GAAttributesBase.h" #include "../AFAbilityInterface.h" -#include "../AFAbilityComponent.h" #include "GAEffectExecution.h" #include "GAEffectExtension.h" #include "../GAGlobalTypes.h" #include "AFEffectApplicationRequirement.h" #include "AFEffectCustomApplication.h" #include "GAGameEffect.h" +#include "GABlueprintLibrary.h" DEFINE_STAT(STAT_GatherModifiers); @@ -380,7 +380,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr bool bHasPeriod = InProperty.Period > 0; ENetRole role = OwningComponent->GetOwnerRole(); ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); - + if (bHasDuration || bHasPeriod) { Handle = FGAEffectHandle::GenerateHandle(EffectIn); @@ -425,8 +425,9 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr //if not we try to rewind effect application. //we probabaly don't need to unwind attribute changes, since next replication from //server will overridem them anyway. + ApplyReplicationInfo(Handle, InProperty); - bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()); + bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::EffectApplied %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Handle.GetEffectSpec()->GetName() ); } } @@ -438,14 +439,18 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr EffectIn->OnApplied(); - return Handle; - //apply additonal effect applied with this effect. - //for (TSubclassOf Spec : EffectIn.GameEffect->OnAppliedEffects) - //{ - // FGAEffectHandle Handle = EffectIn.Context.TargetComp->MakeGameEffect(Spec, EffectIn.Context); + if (InProperty.Spec->IfHaveTagEffect.RequiredTag.IsValid() + && InContext.TargetComp->HasTag(InProperty.Spec->IfHaveTagEffect.RequiredTag)) + { + for (TSubclassOf& Effect : InProperty.Spec->IfHaveTagEffect.Effects) + { + FGAEffectProperty prop(Effect); + UGABlueprintLibrary::ApplyEffect(prop, InContext.Target.Get(), InContext.Instigator.Get(), InContext.Causer.Get(), InContext.HitResult); + } + } - // EffectIn.Context.InstigatorComp->ApplyEffectToTarget(Handle.GetEffect(), Handle, InProperty); - //} + return Handle; + } void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) { @@ -455,43 +460,23 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::ApplyReplicationInfo"), bIsServer ? TEXT("Server") : TEXT("Client")); - //we need it to mark array dirt on server. Do we ? - /*if (mode == ENetMode::NM_DedicatedServer) - {*/ - //const UWorld* World = OwningComponent->GetWorld(); - //FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); - //RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; - //RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; - //RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; - //RepInfo->Handle = InHandle; - //RepInfo->PredictionHandle = InProperty.PredictionHandle; - //RepInfo->EffectTag = InProperty.GetSpec()->EffectTag; - //RepInfo->Init(); - //MarkItemDirty(*RepInfo); - //ActiveEffectInfos.Add(*RepInfo); - //MarkArrayDirty(); - //EffectInfos.Add(InHandle, RepInfo); - //} - //else if(mode == ENetMode::NM_Standalone || mode == ENetMode::NM_Client) - { - //add replication handle (and send it to server ?) - const UWorld* World = OwningComponent->GetWorld(); - FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); - RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; - RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; - RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; - RepInfo->Handle = InHandle; - RepInfo->PredictionHandle = InProperty.PredictionHandle; - RepInfo->EffectTag = InProperty.GetSpec()->EffectTag; - RepInfo->Init(); - MarkItemDirty(*RepInfo); - ActiveEffectInfos.Add(*RepInfo); - MarkArrayDirty(); - //predictevily add effect info ? + //add replication handle (and send it to server ?) + const UWorld* World = OwningComponent->GetWorld(); + FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); + RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; + RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; + RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; + RepInfo->Handle = InHandle; + RepInfo->PredictionHandle = InProperty.PredictionHandle; + RepInfo->EffectTag = InProperty.GetSpec()->EffectTag; + RepInfo->Init(); + MarkItemDirty(*RepInfo); + ActiveEffectInfos.Add(*RepInfo); + MarkArrayDirty(); + //predictevily add effect info ? - PredictedEffectInfos.Add(InProperty.PredictionHandle, RepInfo); - EffectInfos.Add(InHandle, RepInfo); - } + PredictedEffectInfos.Add(InProperty.PredictionHandle, RepInfo); + EffectInfos.Add(InHandle, RepInfo); } EGAEffectAggregation FGAEffectContainer::GetEffectAggregation(const FGAEffectHandle& HandleIn) const @@ -726,53 +711,53 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N TArray* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); FAFEffectRepInfo* Out = nullptr; + + if (!handles) + return; - if (handles) + for (int32 idx = 0; idx < Num; idx++) { - for (int32 idx = 0; idx < Num; idx++) + if (handles->IsValidIndex(0)) { - if (handles->IsValidIndex(0)) + FGAEffectHandle OutHandle = (*handles)[0]; + if (OutHandle.IsValid()) { - FGAEffectHandle OutHandle = (*handles)[0]; - if (OutHandle.IsValid()) + HandleByPrediction.Remove(HandleIn.PredictionHandle); + + if (PredictionByHandle.Contains(OutHandle)) + PredictionByHandle.Remove(OutHandle); + + EffectInfos.RemoveAndCopyValue(OutHandle, Out); + if (Out) { - HandleByPrediction.Remove(HandleIn.PredictionHandle); - - if(PredictionByHandle.Contains(OutHandle)) - PredictionByHandle.Remove(OutHandle); - - EffectInfos.RemoveAndCopyValue(OutHandle, Out); - if (Out) - { - FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); - EffectInfoLog += Out->EffectTag.ToString(); - AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); - MarkItemDirty(*Out); - Out->OnRemoved(); - ActiveEffectInfos.Remove(*Out); - MarkArrayDirty(); - delete Out; - } - if (!ActiveEffectHandles.Contains(OutHandle)) - { - UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffectRef().ToString()); - continue; - } - switch (Aggregation) - { - case EGAEffectAggregation::AggregateByInstigator: - { - RemoveInstigatorEffect(OutHandle, HandleIn); - break; - } - case EGAEffectAggregation::AggregateByTarget: - { - RemoveTargetEffect(OutHandle, HandleIn); - break; - } - default: - break; - } + FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); + EffectInfoLog += Out->EffectTag.ToString(); + AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); + MarkItemDirty(*Out); + Out->OnRemoved(); + ActiveEffectInfos.Remove(*Out); + MarkArrayDirty(); + delete Out; + } + if (!ActiveEffectHandles.Contains(OutHandle)) + { + UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffectRef().ToString()); + continue; + } + switch (Aggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + RemoveInstigatorEffect(OutHandle, HandleIn); + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + RemoveTargetEffect(OutHandle, HandleIn); + break; + } + default: + break; } } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index c1f0939..bed8175 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -93,6 +93,20 @@ struct ABILITYFRAMEWORK_API FAFCueContainer FGameplayTagContainer CueTags; }; +USTRUCT(BlueprintType) +struct FAFConditionalEffectContainer +{ + GENERATED_BODY() +public: + /* If target have this tag apply specified effects */ + UPROPERTY(EditAnywhere) + FGameplayTag RequiredTag; + + UPROPERTY(EditAnywhere) + TArray> Effects; +}; + + /* Base effect class. You can derive your own specialized classes from it with preset customizations and values. You should never directly inherit blueprints from it. @@ -184,12 +198,19 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject FGameplayTag OnPeriodEvent; UPROPERTY(EditAnywhere, Category = "Event Tags") FGameplayTag OnRemovedEvent; + + + UPROPERTY(EditAnywhere, Category = "Event Application Tags") + FGameplayTag OnEffectApplyToTargetEvent; + UPROPERTY(EditAnywhere, Category = "Event Application Tags") + FGameplayTag OnEffectApplyToSelfEvent; + /* Effects applied only when certain criteria are met. Just dumbed here it needs it's own structure that will actually alow to setup those conditions. */ UPROPERTY(EditAnywhere, Category = "Linked Effects") - TArray> ConditonalEffects; + FAFConditionalEffectContainer IfHaveTagEffect; /* Remove effects with these tags. */ @@ -270,6 +291,11 @@ struct ABILITYFRAMEWORK_API FGAEffectClass UPROPERTY(EditAnywhere, Category = "Effect") TSubclassOf SpecClass; + FGAEffectClass() + {} + FGAEffectClass(TSubclassOf InClass) + : SpecClass(InClass) + {} const bool operator==(const FGAEffectClass& Other) const { return SpecClass == Other.SpecClass; @@ -339,6 +365,14 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty Spec(nullptr) {}; + FGAEffectProperty(TSubclassOf InClass) + : SpecClass(InClass), + ApplicationRequirement(nullptr), + Application(nullptr), + Execution(nullptr), + Spec(nullptr) + {}; + TSubclassOf GetClass() const { return SpecClass.SpecClass; } const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } UGAGameEffectSpec* GetSpec() const { return Spec; } @@ -721,9 +755,26 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer class UAFAbilityComponent* OwningComponent; public: //FGAEffectContainer(); + /* + * @call Order: + * Previous Function: UAFAbilityComponent::ApplyEffectToSelf + * Next Function: InProperty.Application->ApplyEffect(); + * FGAEffectContainer::ApplyReplicationInfo() + * + * Apply target to Me. Try to apply effect to container and launch Events in: + * TMap OnEffectEvent - event is called before application; + * TMap OnEffectApplyToSelf - event is called before application; + * + * @param EffectIn* - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect @ UAFAbilityComponent::ApplyEffectToSelf + */ FGAEffectHandle ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty , const FGAEffectContext& InContext , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + void ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ void RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); @@ -757,6 +808,17 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer //return FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); } + + const TSet& GetAllEffectHandles() const + { + return ActiveEffectHandles; + } + + const TArray& GetAllEffectsInfo() const + { + return ActiveEffectInfos; + } + UWorld* GetWorld() const; ///Helpers diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp index b8105cb..de15873 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp @@ -4,7 +4,7 @@ #include "Kismet/KismetArrayLibrary.h" #include "GameplayTask.h" #include "Effects/EffectTasks/AFEffectTask.h" -#include "Abilities/AFBlueprintFunctionLibrary.h" +#include "AFBlueprintFunctionLibrary.h" #include "Effects/GAEffectExtension.h" #include "KismetCompiler.h" #include "BlueprintEditorUtils.h" @@ -80,7 +80,7 @@ void UAFEK2Node_AsyncEffectTaskCall::GetMenuActions(FBlueprintActionDatabaseRegi check(NodeSpawner != nullptr); NodeSpawner->NodeClass = NodeClass; - TWeakObjectPtr FunctionPtr = FactoryFunc; + TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); return NodeSpawner; })); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp index 1f7dde8..b039916 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -4,7 +4,7 @@ #include "Kismet/KismetArrayLibrary.h" #include "GameplayTask.h" #include "Abilities/Tasks/GAAbilityTask.h" -#include "Abilities/AFBlueprintFunctionLibrary.h" +#include "AFBlueprintFunctionLibrary.h" #include "Abilities/GAAbilityBase.h" #include "KismetCompiler.h" #include "BlueprintEditorUtils.h" @@ -80,7 +80,7 @@ void UGAEK2Node_LatentAbilityTaskCall::GetMenuActions(FBlueprintActionDatabaseRe check(NodeSpawner != nullptr); NodeSpawner->NodeClass = NodeClass; - TWeakObjectPtr FunctionPtr = FactoryFunc; + TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); return NodeSpawner; })); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp index 0519e76..0a4dd85 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp @@ -67,7 +67,7 @@ void UGAEK2Node_LatentAction::GetMenuActions(FBlueprintActionDatabaseRegistrar& check(NodeSpawner != nullptr); NodeSpawner->NodeClass = NodeClass; - TWeakObjectPtr FunctionPtr = FactoryFunc; + TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); return NodeSpawner; })); diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp new file mode 100644 index 0000000..a76a2ab --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp @@ -0,0 +1,104 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDAbilityGiveTrigger.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "Abilities/GAAbilityBase.h" + +// Sets default values +AAFDAbilityGiveTrigger::AAFDAbilityGiveTrigger() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + RootComp = CreateDefaultSubobject(RootCompName); + RootComponent = RootComp; + + Icon = CreateDefaultSubobject(IconName); + Trigger = CreateDefaultSubobject(TriggerName); + Trigger->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); + +} + +// Called when the game starts or when spawned +void AAFDAbilityGiveTrigger::BeginPlay() +{ + Super::BeginPlay(); + Trigger->OnComponentBeginOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::BeginOverlap); + Trigger->OnComponentEndOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::EndOverlap); +} + +// Called every frame +void AAFDAbilityGiveTrigger::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + +void AAFDAbilityGiveTrigger::BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, + int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) +{ + if (!AbilityConfig.AbilityTag.IsValid()) + return; + + IAFAbilityInterface* AbilityInterface = Cast(OtherActor); + if (!AbilityInterface) + return; + + if(!CurrentComponent) + CurrentComponent = AbilityInterface->GetAbilityComp(); + + //FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityReady, AbilityConfig.AbilityTag, + // AbilityConfig.InputTag); + + APawn* pawn = Cast(OtherActor); + if(pawn) + { + AController* AC = pawn->GetController(); + if(AC) + { + TArray Comps = AC->GetComponentsByTag(UAMAbilityManagerComponent::StaticClass(), TEXT("AbilityManager")); + if(Comps.Num() == 1 && !AbilityManager) + { + AbilityManager = Cast(Comps[0]); + } + + if(AbilityManager) + AbilityManager->BP_EquipAbility(AbilityConfig.AbilityTag, AbilityConfig.Group, AbilityConfig.Slot); + } + } + + //if(AbilityManager) + //{ + // + //} + //CurrentComponent->AddOnAbilityReadyDelegate(AbilityConfig.AbilityTag, del); + //CurrentComponent->NativeAddAbilityFromTag(AbilityConfig.AbilityTag, nullptr);// , /*Input*/ ShootInput); +} + +void AAFDAbilityGiveTrigger::EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex) +{ + if (!AbilityConfig.AbilityTag.IsValid()) + return; +} + +void AAFDAbilityGiveTrigger::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput) +{ + UGAAbilityBase* Ability = Cast(CurrentComponent->BP_GetAbilityByTag(InAbilityTag)); + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityInputReady, + InAbilityTag, InAbilityInput); + + CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); + } + else + { + CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + } +} + + +void AAFDAbilityGiveTrigger::OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h new file mode 100644 index 0000000..f010fce --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h @@ -0,0 +1,80 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "Components/BoxComponent.h" +#include "GameplayTags.h" +#include "AMTypes.h" +#include "AMAbilityManagerComponent.h" +#include "AFDAbilityGiveTrigger.generated.h" + +USTRUCT() +struct FAFDAbilityConfig +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Config") + EAMGroup Group; + UPROPERTY(EditAnywhere, Category = "Config") + EAMSlot Slot; + UPROPERTY(EditAnywhere, Category = "Config") + FGameplayTag AbilityTag; + UPROPERTY(EditAnywhere, Category = "Config") + TArray InputTag; +}; + +static const FName RootCompName = TEXT("RootComp"); +static const FName TriggerName = TEXT("Trigger"); +static const FName IconName = TEXT("Icon"); +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor +{ + GENERATED_BODY() +protected: + UPROPERTY(BlueprintReadOnly) + USceneComponent* RootComp; + + UPROPERTY(BlueprintReadOnly) + UBillboardComponent* Icon; + + UPROPERTY(EditAnywhere, BlueprintReadOnly) + UBoxComponent* Trigger; + + + UPROPERTY(EditAnywhere, Category = "Config") + FAFDAbilityConfig AbilityConfig; + + UPROPERTY() + class UAFAbilityComponent* CurrentComponent; + UPROPERTY() + class UAMAbilityManagerComponent* AbilityManager; + +public: + // Sets default values for this actor's properties + AAFDAbilityGiveTrigger(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; +protected: + UFUNCTION() + void BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, + int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult); + /** Delegate for notification of end of overlap with a specific component */ + UFUNCTION() + void EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex); + + UFUNCTION() + void OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput); + + UFUNCTION() + void OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput); + + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..d33bda5 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp @@ -0,0 +1,11 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDBlueprintFunctionLibrary.h" +#include "AFDManager.h" + + + +//void UAFDBlueprintFunctionLibrary::OpenAbilityDebugger() +//{ +// FAFDManager::Get(); +//} diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h new file mode 100644 index 0000000..49d85b9 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Kismet/BlueprintFunctionLibrary.h" +#include "AFDBlueprintFunctionLibrary.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API UAFDBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() +public: + //UFUNCTION(Exec) + // static void OpenAbilityDebugger(); + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp new file mode 100644 index 0000000..2ba3971 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDManager.h" +#include "EngineGlobals.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" +#include "Slate.h" +#include "SlateCore.h" + +FAFDManager* FAFDManager::Instance = nullptr; + +FAFDManager::FAFDManager() +{ +} + +FAFDManager::~FAFDManager() +{ +} + +void FAFDManager::Init() +{ + Dekstop = SNew(SAFDDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); + GEngine->GameViewport->AddViewportWidgetContent(Dekstop.ToSharedRef()); + + WindowDesktop = SNew(SDraggableDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); + GEngine->GameViewport->AddViewportWidgetContent(WindowDesktop.ToSharedRef()); +} + +FDWWWindowHandle FAFDManager::AddNewWindow(TSharedPtr InWindow) +{ + return WindowDesktop->AddWindow(InWindow); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h new file mode 100644 index 0000000..90a0d43 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SAFDDesktopWidget.h" +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API FAFDManager +{ +private: + static FAFDManager* Instance; + TSharedPtr Dekstop; + TSharedPtr WindowDesktop; +protected: + void Init(); +public: + + static FAFDManager& Get() + { + if(!Instance) + { + Instance = new FAFDManager(); + Instance->Init(); + } + return*Instance; + } + + FDWWWindowHandle AddNewWindow(TSharedPtr InWindow); + + FAFDManager(); + ~FAFDManager(); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs new file mode 100644 index 0000000..14db1b5 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs @@ -0,0 +1,62 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class AbilityFrameworkDebugger : ModuleRules +{ + public AbilityFrameworkDebugger(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "AbilityFrameworkDebugger/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "AbilityFrameworkDebugger/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "InputCore", + "UMG", + "Slate", + "SlateCore", + "GameplayTags", + "GameplayTasks", + "AbilityFramework", + "AbilityManager", + "DraggableWindow" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp new file mode 100644 index 0000000..6a252ba --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp @@ -0,0 +1,34 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkDebugger.h" +#include "HAL/IConsoleManager.h" +#include "AFDManager.h" + +#define LOCTEXT_NAMESPACE "FAbilityFrameworkDebuggerModule" + +void FAbilityFrameworkDebuggerModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module + CommandOpenAbilityDebugger = IConsoleManager::Get().RegisterConsoleCommand( + TEXT("OpenAbilityDebugger"), + TEXT("Opens ability debugger"), + FConsoleCommandDelegate::CreateStatic(OpenAbilityDebugger), + ECVF_Default + ); +} + +void FAbilityFrameworkDebuggerModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. + IConsoleManager::Get().UnregisterConsoleObject(CommandOpenAbilityDebugger); +} + +void FAbilityFrameworkDebuggerModule::OpenAbilityDebugger() +{ + FAFDManager::Get(); +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FAbilityFrameworkDebuggerModule, AbilityFrameworkDebugger) \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h new file mode 100644 index 0000000..34de4ca --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h @@ -0,0 +1,18 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FAbilityFrameworkDebuggerModule : public IModuleInterface +{ +private: + IConsoleObject* CommandOpenAbilityDebugger; + static void OpenAbilityDebugger(); +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp new file mode 100644 index 0000000..9b470d1 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp @@ -0,0 +1,55 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDAttributes.h" +#include "SlateOptMacros.h" +#include "SListView.h" +#include "Attributes/GAAttributesBase.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDAttributes::Construct(const FArguments& InArgs) +{ + AFInterface = InArgs._AbilityInterface; + ChildSlot + [ + SNew(SOverlay) + +SOverlay::Slot() + [ + SNew(SListView>) + .ListItemsSource(&Attributes) + .OnGenerateRow(this, &SAFDAttributes::GenerateListRow) + ] + ]; + GatherAttributes(); +} +void SAFDAttributes::GatherAttributes() +{ + if (!AFInterface) + return; + + UGAAttributesBase* AttributesObject = AFInterface->GetAttributes(); + if (!AttributesObject) + return; + + Attributes.Empty(); + for(TFieldIterator It(AttributesObject->GetClass(), EFieldIteratorFlags::IncludeSuper); It; ++It) + { + TSharedPtr AttributeRow = MakeShareable(new FAttributeRow); + AttributeRow->Name = It->GetName(); + Attributes.Add(AttributeRow); + } + +} +TSharedRef SAFDAttributes::GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable) +{ + return + SNew(STableRow< TSharedRef >, OwnerTable) + [ + SNew(SBox) + .HAlign(HAlign_Left) + [ + SNew(STextBlock) + .Text(FText::FromString(NotifyName->Name)) + ] + ]; +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h new file mode 100644 index 0000000..cdc81ba --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" +#include "AFAbilityInterface.h" + +struct FAttributeRow +{ + FString Name; +}; + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDAttributes : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDAttributes) + {} + SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) + SLATE_END_ARGS() + + IAFAbilityInterface* AFInterface; + TArray> Attributes; + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + void GatherAttributes(); + TSharedRef GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp new file mode 100644 index 0000000..1fc3eba --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp @@ -0,0 +1,129 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDDesktopWidget.h" +#include "SlateCore.h" +#include "Slate.h" +#include "SlateOptMacros.h" +#include "SBoxPanel.h" +#include "SButton.h" +#include "STextBlock.h" +#include "AFDManager.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" +#include "GameFramework/PlayerController.h" +#include "SAFDViewportMouseCapture.h" +#include "SAFDEffects.h" +#include "SAFDAttributes.h" + +void SAFDMainWidget::Construct(const FArguments& InArgs) +{ + FWorldContext* WorldContext = GEngine->GetWorldContextFromGameViewport(GEngine->GameViewport); + UWorld* world = WorldContext->World(); + World = world; + FOnClicked OnPickActorClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnPickActorClicked); + + ChildSlot + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + [ + SAssignNew(Content, SOverlay) + ] + +SVerticalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnPickActorClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("Pick Actor")) + ] + ] + ]; + + Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Left) + .VAlign(EVerticalAlignment::VAlign_Top) + [ + SNew(STextBlock) + .Text(this, &SAFDMainWidget::GetActorName) + ]; +} + +FText SAFDMainWidget::GetActorName() const +{ + if(SelectedActor.IsValid()) + { + return FText::FromString(SelectedActor->GetName()); + } + return FText::FromString("Select Actor from viewport."); +} +FReply SAFDMainWidget::OnPickActorClicked() +{ + CaptureWidget = SNew(SAFDViewportMouseCapture); + FSimpleDelegate del = FSimpleDelegate::CreateSP(this, &SAFDMainWidget::OnActorPicked); + CaptureWidget->OnMouseButtonDownDelegate = del; + GEngine->GameViewport->AddViewportWidgetContent(CaptureWidget.ToSharedRef(), 1001); + + return FReply::Handled(); +} +void SAFDMainWidget::OnActorPicked() +{ + APlayerController* PC = World->GetFirstPlayerController(); + FHitResult OutHit; + PC->GetHitResultUnderCursor(ECollisionChannel::ECC_Visibility, false, OutHit); + + if(OutHit.bBlockingHit) + { + AActor* actor = OutHit.GetActor(); + SelectedActor = OutHit.Actor; + if(IAFAbilityInterface* Interface = Cast(OutHit.GetActor())) + { + Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Left) + .VAlign(EVerticalAlignment::VAlign_Top) + [ + SNew(SAFDAttributes) + .AbilityInterface(Interface) + ]; + } + } + + GEngine->GameViewport->RemoveViewportWidgetContent(CaptureWidget.ToSharedRef()); +} +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDDesktopWidget::Construct(const FArguments& InArgs) +{ + FOnClicked OnNewDebugWindowClickedDel = FOnClicked::CreateSP(this, &SAFDDesktopWidget::OnNewDebugWindowClicked); + ChildSlot + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Right) + .VAlign(EVerticalAlignment::VAlign_Top) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnNewDebugWindowClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("New Debug Window")) + ] + ] + ] + // Populate the widget + ]; + +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +FReply SAFDDesktopWidget::OnNewDebugWindowClicked() +{ + TSharedPtr window = SNew(SDraggableWindowWidget); + FDWWWindowHandle Handle = FAFDManager::Get().AddNewWindow(window); + TSharedPtr wid = SNew(SAFDMainWidget); + window->AddContent(wid); + wid->WindowHandle = Handle; + return FReply::Handled(); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h new file mode 100644 index 0000000..c637f63 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h @@ -0,0 +1,42 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" +#include "SDraggableWindowWidget.h" + +class ABILITYFRAMEWORKDEBUGGER_API SAFDMainWidget : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDMainWidget) + {} + SLATE_END_ARGS() + TWeakObjectPtr World; + TWeakObjectPtr SelectedActor; + TSharedPtr Content; + FDWWWindowHandle WindowHandle; + TSharedPtr CaptureWidget; + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + FReply OnPickActorClicked(); + void OnActorPicked(); + + FText GetActorName() const; +}; + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDDesktopWidget : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDDesktopWidget) + {} + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + + FReply OnNewDebugWindowClicked(); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp new file mode 100644 index 0000000..babb94a --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDEffectInspector.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDEffectInspector::Construct(const FArguments& InArgs) +{ + /* + ChildSlot + [ + // Populate the widget + ]; + */ +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h new file mode 100644 index 0000000..e9de984 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDEffectInspector : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDEffectInspector) + {} + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp new file mode 100644 index 0000000..617cc2a --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDEffects.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDEffects::Construct(const FArguments& InArgs) +{ + + ChildSlot + [ + SNew(SOverlay) + +SOverlay::Slot() + [ + SNew(SButton) + ] + ]; + +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h new file mode 100644 index 0000000..79baffa --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +#include "AFAbilityInterface.h" +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDEffects : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDEffects) + {} + SLATE_END_ARGS() + + IAFAbilityInterface* AFInterface; + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp new file mode 100644 index 0000000..5560253 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDViewportMouseCapture.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDViewportMouseCapture::Construct(const FArguments& InArgs) +{ + /* + ChildSlot + [ + // Populate the widget + ]; + */ +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +FReply SAFDViewportMouseCapture::OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) +{ + OnMouseButtonDownDelegate.ExecuteIfBound(); + return FReply::Handled(); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h new file mode 100644 index 0000000..30e79b2 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDViewportMouseCapture : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDViewportMouseCapture) + {} + SLATE_END_ARGS() + + FSimpleDelegate OnMouseButtonDownDelegate; + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + + virtual FReply OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) override; +}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp new file mode 100644 index 0000000..003e5dc --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -0,0 +1,286 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AMAbilityManagerComponent.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" + +// Sets default values for this component's properties +UAMAbilityManagerComponent::UAMAbilityManagerComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + bWantsInitializeComponent = true; + // ... +} + + +// Called when the game starts +void UAMAbilityManagerComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} +void UAMAbilityManagerComponent::InitializeComponent() +{ + AbilitySet.SetNum(MaxGroups); + AbilityTagsSet.SetNum(MaxGroups); + for(int32 Idx = 0; Idx < MaxGroups; Idx++) + { + AbilitySet[Idx].SetNum(1); + AbilityTagsSet[Idx].SetNum(1); + } +} + +// Called every frame +void UAMAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +void UAMAbilityManagerComponent::BindInputs() +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + for (const FGameplayTag& Tag : InputsToBind) + { + AbilityComp->BP_BindAbilityToAction(Tag); + } +} + +UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) +{ + return AbilitySet.Num() >= MaxGroups ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; +} +void UAMAbilityManagerComponent::SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility) +{ + if (AbilitySet.Num() < MaxGroups) + return; + + AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbility; +} + +TArray UAMAbilityManagerComponent::GetInputTag(EAMGroup InGroup, EAMSlot InSlot) +{ + return InputSetup.GetInputs(InGroup, InSlot); +} +void UAMAbilityManagerComponent::SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag) +{ + +} +void UAMAbilityManagerComponent::BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) +{ + NativeEquipAbility(InAbilityTag, InGroup, InSlot); +} +FGameplayTag UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) +{ + return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; +} +void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, FGameplayTag InAbilityTag) +{ + AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; +} +void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + TArray IAbilityInput = GetInputTag(InGroup, InSlot); + FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReady, InAbilityTag, + IAbilityInput, InGroup, InSlot); + + AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , /*Input*/ ShootInput); +} +void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityInputReady, + InAbilityTag, InAbilityInput, InGroup, InSlot); + + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); + } + else + { + SetAbility(InGroup, InSlot, Ability); + SetAbilityTag(InGroup, InSlot, InAbilityTag); + SetInputTag(InGroup, InSlot, InAbilityInput); + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + } +} + +void UAMAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + SetAbility(InGroup, InSlot, Ability); + SetAbilityTag(InGroup, InSlot, InAbilityTag); + SetInputTag(InGroup, InSlot, InAbilityInput); +} + +void UAMAbilityManagerComponent::NextGroup() +{ + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex++; + if(CurrentIndex > MaxGroups) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } + + if (ActiveGroup < AMIntToEnum(MaxGroups)) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + } + + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNextGroup(AMEnumToInt(ActiveGroup)); + } +} + +void UAMAbilityManagerComponent::PreviousGroup() +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex--; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (ActiveGroup >= EAMGroup::Group001) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerPreviousGroup(static_cast(ActiveGroup)); + } +} + +void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponIndex) +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex++; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (CurrentIndex > MaxGroups) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } + if (ActiveGroup < AMIntToEnum(MaxGroups)) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + //so Server index is different. Client might tried to cheat + //or sometrhing. We will override it. + //situation where client can chage multiple weapons within second + //should not have place, as there is animation and/or internal cooldown on weapon change. + //since it will be done trough ability. + if (ActiveGroup != AMIntToEnum(WeaponIndex)) + { + ClientNextGroup(AMEnumToInt(ActiveGroup)); + } +} +bool UAMAbilityManagerComponent::ServerNextGroup_Validate(int32 WeaponIndex) +{ + return true; +} +void UAMAbilityManagerComponent::ClientNextGroup_Implementation(int32 WeaponIndex) +{ + ActiveGroup = AMIntToEnum(WeaponIndex); +} + +void UAMAbilityManagerComponent::ServerPreviousGroup_Implementation(int32 WeaponIndex) +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex--; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (ActiveGroup >= EAMGroup::Group001) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + if (ActiveGroup != AMIntToEnum(WeaponIndex)) + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup)); + } +} +bool UAMAbilityManagerComponent::ServerPreviousGroup_Validate(int32 WeaponIndex) +{ + return true; +} +void UAMAbilityManagerComponent::ClientPreviousGroup_Implementation(int32 WeaponIndex) +{ + ActiveGroup = AMIntToEnum(WeaponIndex); +} + +void UAMAbilityManagerComponent::SelectGroup(EAMGroup InGroup) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h new file mode 100644 index 0000000..899d85d --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -0,0 +1,148 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "AMTypes.h" +#include "GameplayTags.h" +#include "Abilities/GAAbilityBase.h" +#include "AMAbilityManagerComponent.generated.h" + +/* +- Group +- Set +- Ability +-Inputs (multiple); + +*/ + +//all the inputs assigned to SINGLE ability; +USTRUCT() +struct FAMAbilityInputs +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Inputs; +}; + +USTRUCT() +struct FAMAbilityInputSlot +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FAMAbilityInputs Inputs; + + TArray operator()() + { + return Inputs.Inputs; + } +}; + + +USTRUCT() +struct FAMAbilityInputGroup +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Slots; +}; + + +USTRUCT() +struct FAMAbilityInputContainer +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Groups; + + + TArray GetInputs(EAMGroup InGroup, EAMSlot InSlot) + { + return Groups[AMEnumToInt(InGroup)].Slots[AMEnumToInt(InSlot)](); + } +}; + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere) + uint8 MaxGroups; + + UPROPERTY(EditAnywhere) + FAMAbilityInputContainer InputSetup; + + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray InputsToBind; + + EAMGroup ActiveGroup; + //UPROPERTY(EditAnywhere, Category = "Input Config") + // TArray InputBindingsSet; + + TArray> AbilityTagsSet; + TArray>> AbilitySet; +public: + // Sets default values for this component's properties + UAMAbilityManagerComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + virtual void InitializeComponent() override; +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + void BindInputs(); + UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); + void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); + + FGameplayTag GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); + void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, FGameplayTag InAbilityTag); + + TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); + void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Ability"), Category = "Ability Manager") + void BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); + + void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); + UFUNCTION() + void OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot); + + UFUNCTION() + void OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot); + + UFUNCTION(BlueprintCallable) + void NextGroup(); + UFUNCTION(BlueprintCallable) + void PreviousGroup(); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNextGroup(int32 WeaponIndex); + void ServerNextGroup_Implementation(int32 WeaponIndex); + bool ServerNextGroup_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientNextGroup(int32 WeaponIndex); + void ClientNextGroup_Implementation(int32 WeaponIndex); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerPreviousGroup(int32 WeaponIndex); + void ServerPreviousGroup_Implementation(int32 WeaponIndex); + bool ServerPreviousGroup_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientPreviousGroup(int32 WeaponIndex); + void ClientPreviousGroup_Implementation(int32 WeaponIndex); + + + UFUNCTION(BlueprintCallable) + void SelectGroup(EAMGroup InGroup); +}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp new file mode 100644 index 0000000..d34aeaf --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp @@ -0,0 +1,3 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AMTypes.h" \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMTypes.h b/Plugins/AbilityManager/Source/AbilityManager/AMTypes.h new file mode 100644 index 0000000..90b017d --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AMTypes.h @@ -0,0 +1,95 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AMTypes.generated.h" + +UENUM(BlueprintType) +enum class EAMSlot : uint8 +{ + Slot001 = 0, + Slot002 = 1, + Slot003 = 2, + Slot004 = 3, + Slot005 = 4, + Slot006 = 5, + Slot007 = 6, + Slot008 = 7, + Slot009 = 8, + Slot010 = 9, + Slot011 = 10, + Slot012 = 11, + Slot013 = 12, + Slot014 = 13, + Slot015 = 14, + Slot016 = 15, + Slot017 = 16, + Slot018 = 17, + Slot019 = 18, + Slot020 = 19, + Slot021 = 20, + Slot022 = 21, + Slot023 = 22, + Slot024 = 23, + Slot025 = 24, + Slot026 = 25, + Slot027 = 26, + Slot028 = 27, + Slot029 = 28, + Slot030 = 29, + Slot031 = 30, + Slot032 = 31, + MAX +}; + +UENUM(BlueprintType) +enum class EAMGroup : uint8 +{ + Group001 = 0, + Group002 = 1, + Group003 = 2, + Group004 = 3, + Group005 = 4, + Group006 = 5, + Group007 = 6, + Group008 = 7, + Group009 = 8, + Group010 = 9, + Group011 = 10, + Group012 = 11, + Group013 = 12, + Group014 = 13, + Group015 = 14, + Group016 = 15, + Group017 = 16, + Group018 = 17, + Group019 = 18, + Group020 = 19, + Group021 = 20, + Group022 = 21, + Group023 = 22, + Group024 = 23, + Group025 = 24, + Group026 = 25, + Group027 = 26, + Group028 = 27, + Group029 = 28, + Group030 = 29, + Group031 = 30, + Group032 = 31, + + MAX +}; + +template +int32 AMEnumToInt(T InVal) +{ + return static_cast(InVal); +} + +template +T AMIntToEnum(int32 InVal) +{ + return static_cast(InVal); +} \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs new file mode 100644 index 0000000..b57046b --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs @@ -0,0 +1,58 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class AbilityManager : ModuleRules +{ + public AbilityManager(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "AbilityManager/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "AbilityManager/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "GameplayTags", + "GameplayTasks", + "AbilityFramework" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp new file mode 100644 index 0000000..3f142ff --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityManager.h" + +#define LOCTEXT_NAMESPACE "FAbilityManagerModule" + +void FAbilityManagerModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FAbilityManagerModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FAbilityManagerModule, AbilityManager) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h new file mode 100644 index 0000000..677d67e --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FAbilityManagerModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs new file mode 100644 index 0000000..773b006 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs @@ -0,0 +1,57 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class DraggableWindow : ModuleRules +{ + public DraggableWindow(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "DraggableWindow/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "DraggableWindow/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "InputCore", + "Slate", + "SlateCore", + "UMG" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp new file mode 100644 index 0000000..c3765cb --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "DraggableWindow.h" + +#define LOCTEXT_NAMESPACE "FDraggableWindowModule" + +void FDraggableWindowModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FDraggableWindowModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FDraggableWindowModule, DraggableWindow) \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h new file mode 100644 index 0000000..072d102 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FDraggableWindowModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp new file mode 100644 index 0000000..4c670d2 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -0,0 +1,493 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SDraggableWindowWidget.h" +#include "SlateOptMacros.h" + +#include "Slate.h" +#include "SlateCore.h" +#include "SBorder.h" +#include "Widgets/Layout/SGridPanel.h" + +FDWWWindowHandle FDWWWindowHandle::Make(TSharedPtr InWindow) +{ + static uint32 NewHandle = 0; + NewHandle++; + FDWWWindowHandle Handle(NewHandle); + Handle.Window = InWindow; + return NewHandle; +} + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SDraggableDesktopWidget::Construct(const FArguments& InArgs) +{ + Container = SNew(SOverlay).Visibility(EVisibility::SelfHitTestInvisible); + ChildSlot + [ + Container.ToSharedRef() + ]; +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +FDWWWindowHandle SDraggableDesktopWidget::AddWindow(TSharedPtr InWindow) +{ + if (!Container.IsValid()) + return FDWWWindowHandle(); + + Container->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Left) + .VAlign(EVerticalAlignment::VAlign_Top) + [ + InWindow.ToSharedRef() + ]; + + FDWWWindowHandle Handle = FDWWWindowHandle::Make(InWindow); + return Handle; +} +void SWindowBox::Construct(const FArguments& InArgs) +{ + WidthOverride = InArgs._WidthOverride.Get(); + HeightOverride = InArgs._HeightOverride.Get(); + + ChildSlot + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + InArgs._Content.Widget + ]; +} +void SWindowBox::SetWidthOverride(float InWidthOverride) +{ + if (WidthOverride != InWidthOverride) + { + WidthOverride = InWidthOverride; + + Invalidate(EInvalidateWidget::Layout); + } +} + +void SWindowBox::SetHeightOverride(float InHeightOverride) +{ + if (HeightOverride != InHeightOverride) + { + HeightOverride = InHeightOverride; + + Invalidate(EInvalidateWidget::Layout); + } +} +void SWindowBox::OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedChildren& ArrangedChildren) const +{ + const EVisibility& MyCurrentVisibility = this->GetVisibility(); + if (ArrangedChildren.Accepts(MyCurrentVisibility)) + { + //const FOptionalSize CurrentMaxAspectRatio = MaxAspectRatio.Get(); + const FMargin SlotPadding(ChildSlot.SlotPadding.Get()); + bool bAlignChildren = true; + + AlignmentArrangeResult XAlignmentResult(0, 0); + AlignmentArrangeResult YAlignmentResult(0, 0); + + if (bAlignChildren) + { + XAlignmentResult = AlignChild(AllottedGeometry.GetLocalSize().X, ChildSlot, SlotPadding); + YAlignmentResult = AlignChild(AllottedGeometry.GetLocalSize().Y, ChildSlot, SlotPadding); + } + + const float AlignedSizeX = XAlignmentResult.Size; + const float AlignedSizeY = YAlignmentResult.Size; + + ArrangedChildren.AddWidget( + AllottedGeometry.MakeChild( + ChildSlot.GetWidget(), + FVector2D(XAlignmentResult.Offset, YAlignmentResult.Offset), + FVector2D(AlignedSizeX, AlignedSizeY) + //FVector2D(WidthOverride.Get().Get(), HeightOverride.Get().Get()) + ) + ); + } +} +FChildren* SWindowBox::GetChildren() +{ + return &ChildSlot; +} +FVector2D SWindowBox::ComputeDesiredSize(float) const +{ + EVisibility ChildVisibility = ChildSlot.GetWidget()->GetVisibility(); + + if (ChildVisibility != EVisibility::Collapsed) + { + // If the user specified a fixed width or height, those values override the Box's content. + + const float CurrentWidthOverride = WidthOverride; + const float CurrentHeightOverride = HeightOverride; + + + return FVector2D(CurrentWidthOverride, CurrentHeightOverride); + } + + return FVector2D::ZeroVector; +} +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SDraggableWindowWidget::Construct(const FArguments& InArgs) +{ + CurrentSize = FVector2D(1, 1); + ResizingState = EDDWState::NoResize; + + FSimpleDelegate OnPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnPressed); + FSimpleDelegate OnReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnReleased); + TAttribute posAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetPosition)); + TAttribute sizeAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetSize)); + + + TAttribute widthAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetWidth)); + TAttribute heightAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetHeight)); + + FSimpleDelegate OnHorizontalPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizePressed); + FSimpleDelegate OnHorizontalReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeReleased); + FSimpleDelegate OnHorizontalLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeLeftPressed); + FSimpleDelegate OnHorizontalLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeLeftReleased); + + FSimpleDelegate OnVerticalTopPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalTopResizePressed); + FSimpleDelegate OnVerticalTopReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalTopResizeReleased); + FSimpleDelegate OnVerticalBottomPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalBottomResizePressed); + FSimpleDelegate OnVerticalBottomReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalBottomResizeReleased); + + FSimpleDelegate OnBottomRightPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomRightResizePressed); + FSimpleDelegate OnBottomRightReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomRightResizeReleased); + + FSimpleDelegate OnBottomLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizePressed); + FSimpleDelegate OnBottomLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizeReleased); + + CurrentHeight = 200; + CurrentWidth = 200; + + bDragging = false; + + ChildSlot + [ + SNew(SCanvas) + + SCanvas::Slot() + .HAlign(EHorizontalAlignment::HAlign_Left) + .VAlign(EVerticalAlignment::VAlign_Top) + .Position(posAttr) + //.Size(sizeAttr) + [ + SNew(SGridPanel) + + +SGridPanel::Slot(0, 0) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + ] + ] + + SGridPanel::Slot(1 ,0) + [ + SNew(SBox) + .HeightOverride(3) + [ + SNew(SButton) + .OnPressed(OnVerticalTopPressedDel) + .OnReleased(OnVerticalTopReleasedDel) + ] + ] + + SGridPanel::Slot(2, 0) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + ] + ] + + SGridPanel::Slot(0, 1) + [ + SNew(SBox) + .WidthOverride(3) + [ + SNew(SButton) + .OnPressed(OnHorizontalLeftPressedDel) + .OnReleased(OnHorizontalLeftReleasedDel) + ] + ] + + SGridPanel::Slot(1, 1) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SAssignNew(WindowBox, SWindowBox) + /*.HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill)*/ + //.HeightOverride(heightAttr) + //.WidthOverride(widthAttr) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + //.FillHeight(0.2f) + .MaxHeight(32) + .MaxHeight(32) + [ + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnPressed(OnPressedDel) + .OnReleased(OnReleasedDel) + ] + + ] + + SVerticalBox::Slot() + .FillHeight(1.0f) + [ + SAssignNew(Content, SOverlay) + ] + ] + + ] + + SGridPanel::Slot(2, 1) + [ + SNew(SBox) + .WidthOverride(3) + [ + SNew(SButton) + .OnPressed(OnHorizontalPressedDel) + .OnReleased(OnHorizontalReleasedDel) + ] + ] + + SGridPanel::Slot(0, 2) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + .OnPressed(OnBottomLeftPressedDel) + .OnReleased(OnBottomLeftReleasedDel) + ] + ] + + SGridPanel::Slot(1, 2) + [ + SNew(SBox) + .HeightOverride(3) + [ + SNew(SButton) + .OnPressed(OnVerticalBottomPressedDel) + .OnReleased(OnVerticalBottomReleasedDel) + ] + ] + + SGridPanel::Slot(2, 2) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + .OnPressed(OnBottomRightPressedDel) + .OnReleased(OnBottomRightReleasedDel) + ] + ] + ] + // Populate the widget + ]; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + /*Content->AddSlot() + [ + SNew(SButton) + [ + SNew(STextBlock) + .Text(this, &SDraggableWindowWidget::GetCurrentX) + ] + ];*/ + +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION +FVector2D SDraggableWindowWidget::ComputeDesiredSize(float) const +{ + return SCompoundWidget::ComputeDesiredSize(1); + //return FVector2D(CurrentWidth, CurrentHeight); +} +void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) +{ + SCompoundWidget::Tick(AllottedGeometry, InCurrentTime, InDeltaTime); + + FVector2D LastPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); + FVector2D CurrentPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); + float dist = FVector2D::Distance(CurrentPosition, LastPosition);// *InDeltaTime; + + if (bDragging) + { + FVector2D locaPos = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); + CurrentCursorPosition = locaPos; + } + if(ResizingState == EDDWState::HorizontalRight) + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if(dist != 0) + { + CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); + } + CurrentX = CurrentXX; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetWidthOverride(CurrentWidth); + } + else if (ResizingState == EDDWState::HorizontalLeft) + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; + } + //float CurrentXX = LastPosition.X - CurrentPosition.X; + CurrentCursorPosition.X -= CurrentXX; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetWidthOverride(CurrentWidth); + } + else if(ResizingState == EDDWState::VerticalTop) + { + + } + else if (ResizingState == EDDWState::VerticalBottom) + { + float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + //CurrentX = CurrentY; + CurrentHeight = CurrentHeight + CurrentY; + WindowBox->SetHeightOverride(CurrentHeight); + } + else if(ResizingState == EDDWState::DiagonalBottomRight) + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); + CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + CurrentX = CurrentXX; + CurrentWidth = CurrentWidth + CurrentXX; + CurrentHeight = CurrentHeight + CurrentY; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + } + else if(ResizingState == EDDWState::DiagonalBottomLeft) + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; + CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + CurrentX = CurrentXX; + CurrentCursorPosition.X -= CurrentXX; + CurrentWidth = CurrentWidth + CurrentXX; + CurrentHeight = CurrentHeight + CurrentY; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + } + +} +void SDraggableWindowWidget::AddContent(TSharedPtr InWidget) +{ + Content->AddSlot() + [ + InWidget.ToSharedRef() + ]; +} +void SDraggableWindowWidget::OnPressed() +{ + bDragging = true; + //CurrentCursorPosition = FSlateApplication::Get().GetCursorPos(); +} +void SDraggableWindowWidget::OnReleased() +{ + bDragging = false; +} + +void SDraggableWindowWidget::OnHorizontalResizePressed() +{ + ResizingState = EDDWState::HorizontalRight; +} +void SDraggableWindowWidget::OnHorizontalResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} +void SDraggableWindowWidget::OnHorizontalResizeLeftPressed() +{ + ResizingState = EDDWState::HorizontalLeft; +} +void SDraggableWindowWidget::OnHorizontalResizeLeftReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnVerticalTopResizePressed() +{ + ResizingState = EDDWState::VerticalTop; +} +void SDraggableWindowWidget::OnVerticalTopResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} +void SDraggableWindowWidget::OnVerticalBottomResizePressed() +{ + ResizingState = EDDWState::VerticalBottom; +} +void SDraggableWindowWidget::OnVerticalBottomResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnDirectionalResizePressed() +{ +} + +void SDraggableWindowWidget::OnDirectionalResizeReleased() +{ +} + +void SDraggableWindowWidget::OnBottomRightResizePressed() +{ + ResizingState = EDDWState::DiagonalBottomRight; +} +void SDraggableWindowWidget::OnBottomRightResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnBottomLeftResizePressed() +{ + ResizingState = EDDWState::DiagonalBottomLeft; +} +void SDraggableWindowWidget::OnBottomLeftResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +FVector2D SDraggableWindowWidget::GetPosition() const +{ + return CurrentCursorPosition; +} +FVector2D SDraggableWindowWidget::GetSize() const +{ + return CurrentSize; +} +FOptionalSize SDraggableWindowWidget::GetHeight() const +{ + return CurrentHeight; +} +FOptionalSize SDraggableWindowWidget::GetWidth() const +{ + return CurrentWidth; +} +FText SDraggableWindowWidget::GetCurrentX() const +{ + FString ret = FString("Right") + FString::FormatAsNumber(CurrentSize.X) + FString("\n") + + FString("CurrentWidth ") + FString::FormatAsNumber(CurrentWidth) + FString("\n") + + FString("CurrentX ") + FString::FormatAsNumber(CurrentX) + FString("\n"); + return FText::FromString(ret); +} diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h new file mode 100644 index 0000000..e00b084 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h @@ -0,0 +1,174 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Input/Events.h" +#include "Widgets/SCompoundWidget.h" +#include "SOverlay.h" +#include "SGridPanel.h" +#include "SBox.h" +#include "SConstraintCanvas.h" +struct FDWWWindowHandle +{ + TWeakPtr Window; +protected: + uint32 Handle; +public: + FDWWWindowHandle() + {}; + FDWWWindowHandle(uint32 InHandle) + : Handle(InHandle) + { + + } + static FDWWWindowHandle Make(TSharedPtr InWindow); +}; +enum class EDDWState : uint8 +{ + Dragging = 0, + HorizontalRight = 1, + HorizontalLeft = 2, + VerticalTop = 3, + VerticalBottom = 4, + DiagonalBottomRight = 5, + DiagonalBottomLeft = 6, + DiagonalTopRight = 7, + DiagonalTopLeft = 8, + + NoResize +}; +class DRAGGABLEWINDOW_API SDraggableDesktopWidget : public SCompoundWidget +{ + SLATE_BEGIN_ARGS(SDraggableDesktopWidget) {} + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + + TArray> Windows; + TSharedPtr Container; + FDWWWindowHandle AddWindow(TSharedPtr InWindow); +}; + +class SWindowBox : public SPanel +{ +public: + class FBoxSlot : public TSupportsOneChildMixin, public TSupportsContentAlignmentMixin, public TSupportsContentPaddingMixin + { + public: + FBoxSlot() + : TSupportsOneChildMixin() + , TSupportsContentAlignmentMixin(HAlign_Fill, VAlign_Fill) + { + } + }; + SLATE_BEGIN_ARGS(SWindowBox) + : _Content() + , _WidthOverride() + , _HeightOverride() + { + _Visibility = EVisibility::SelfHitTestInvisible; + } + SLATE_DEFAULT_SLOT(FArguments, Content) + /** When specified, ignore the content's desired size and report the WidthOverride as the Box's desired width. */ + SLATE_ATTRIBUTE(float, WidthOverride) + + /** When specified, ignore the content's desired size and report the HeightOverride as the Box's desired height. */ + SLATE_ATTRIBUTE(float, HeightOverride) + SLATE_END_ARGS() +private: + /** When specified, ignore the content's desired size and report the.WidthOverride as the Box's desired width. */ + float WidthOverride; + + /** When specified, ignore the content's desired size and report the.HeightOverride as the Box's desired height. */ + float HeightOverride; +protected: + + FBoxSlot ChildSlot; +public: + void Construct(const FArguments& InArgs); + /** See WidthOverride attribute */ + void SetWidthOverride(float InWidthOverride); + + /** See HeightOverride attribute */ + void SetHeightOverride(float InHeightOverride); +protected: + /** + * Panels arrange their children in a space described by the AllottedGeometry parameter. The results of the arrangement + * should be returned by appending a FArrangedWidget pair for every child widget. See StackPanel for an example + * + * @param AllottedGeometry The geometry allotted for this widget by its parent. + * @param ArrangedChildren The array to which to add the WidgetGeometries that represent the arranged children. + */ + virtual void OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedChildren& ArrangedChildren) const override; + // Begin SWidget overrides. + virtual FVector2D ComputeDesiredSize(float) const override; + + /** + * All widgets must provide a way to access their children in a layout-agnostic way. + * Panels store their children in Slots, which creates a dilemma. Most panels + * can store their children in a TPanelChildren, where the Slot class + * provides layout information about the child it stores. In that case + * GetChildren should simply return the TPanelChildren. See StackPanel for an example. + */ + virtual FChildren* GetChildren() override; +}; + +/** + * Check IF cursor is moving during resizing. + */ +class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SDraggableWindowWidget){} + SLATE_END_ARGS() +protected: + EDDWState ResizingState; + bool bDragging; + + FVector2D CurrentSize; + FVector2D CurrentCursorPosition; + + TSharedPtr Content; + TSharedPtr WindowBox; + float CurrentHeight; + float CurrentWidth; + float CurrentX; +public: + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + virtual FVector2D ComputeDesiredSize(float) const override; + virtual void Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) override; + + void AddContent(TSharedPtr InWidget); +protected: + void OnPressed(); + void OnReleased(); + + void OnHorizontalResizePressed(); + void OnHorizontalResizeReleased(); + void OnHorizontalResizeLeftPressed(); + void OnHorizontalResizeLeftReleased(); + + void OnVerticalTopResizePressed(); + void OnVerticalTopResizeReleased(); + void OnVerticalBottomResizePressed(); + void OnVerticalBottomResizeReleased(); + + void OnDirectionalResizePressed(); + void OnDirectionalResizeReleased(); + + void OnBottomRightResizePressed(); + void OnBottomRightResizeReleased(); + + void OnBottomLeftResizePressed(); + void OnBottomLeftResizeReleased(); + + FVector2D GetPosition() const; + FVector2D GetSize() const; + + FOptionalSize GetHeight() const; + FOptionalSize GetWidth() const; + FText GetCurrentX() const; +}; diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp index 7bc2c4f..8b19f70 100644 --- a/Source/ActionRPGGame/ARGameMode.cpp +++ b/Source/ActionRPGGame/ARGameMode.cpp @@ -9,7 +9,7 @@ //#include "IpConnec" //#include "OnlineSubsystemUtils/IpConnection.h" #include "IPAddress.h" - +#include "SDraggableWindowWidget.h" AARGameMode::AARGameMode() { } @@ -23,4 +23,13 @@ void AARGameMode::BeginPlay() UE_LOG(LogTemp, Warning, TEXT("Your message, %s \n"), *FString::FromInt(Conn->GetAddrAsInt())); } } + TSharedPtr desktop = SNew(SDraggableDesktopWidget); + GEngine->GameViewport->AddViewportWidgetContent(desktop.ToSharedRef()); + + //TSharedPtr window = SNew(SDraggableWindowWidget); + //GEngine->GameViewport->AddViewportWidgetContent(window.ToSharedRef()); + //desktop->AddWindow(window); + //TSharedPtr window1 = SNew(SDraggableWindowWidget); + //GEngine->GameViewport->AddViewportWidgetContent(window1.ToSharedRef()); + //desktop->AddWindow(window1); } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index c7c4102..d1434fd 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -3,21 +3,25 @@ #include "ARPlayerController.h" #include "ARUIComponent.h" #include "ARUIAbilityManagerComponent.h" -#include "ARUIWeaponEquipment.h" #include "AFAbilityComponent.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "ARAbilityBase.h" #include "Weapons/ARWeaponManagerComponent.h" +#include "Abilities/ARAbilityManagerComponent.h" + + AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); UIAbilityManagerComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIAbilityManagerComponent"); - UIWeaponEquipment = ObjectInitializer.CreateDefaultSubobject(this, "UIWeaponEquipment"); WeaponManager = ObjectInitializer.CreateDefaultSubobject(this, "WeaponManager"); + AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); + + AbilityManager->ComponentTags.Add(TEXT("AbilityManager")); } void AARPlayerController::SetPawn(APawn* InPawn) @@ -37,7 +41,7 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); - + WeaponManager->BindInputs(); //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index c87ae41..57de46f 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -19,11 +19,12 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController class UARUIComponent* UIComponent; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIAbilityManagerComponent* UIAbilityManagerComponent; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") - class UARUIWeaponEquipment* UIWeaponEquipment; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARWeaponManagerComponent* WeaponManager; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UARAbilityManagerComponent* AbilityManager; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputNextWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp new file mode 100644 index 0000000..1632f8d --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityManagerComponent.h" + + +// Sets default values for this component's properties +UARAbilityManagerComponent::UARAbilityManagerComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UARAbilityManagerComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UARAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h new file mode 100644 index 0000000..3dd6b4d --- /dev/null +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -0,0 +1,37 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" + +#include "Components/ActorComponent.h" +#include "GameplayTags.h" +#include "Abilities/GAAbilityBase.h" +#include "AMAbilityManagerComponent.h" +#include "ARAbilityManagerComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerComponent +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf DragVisualClass; + + +public: + // Sets default values for this component's properties + UARAbilityManagerComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + +}; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 5311281..6c4d72f 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -43,13 +43,17 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "CoreUObject", "Engine", "InputCore", + "Slate", + "SlateCore", + "UMG", "GameplayTags", "AbilityFramework", - "SlateCore", "AssetRegistry", - "Sockets", - "OnlineSubsystemUtils", - "ActorSequence" + //"Sockets", + //"OnlineSubsystemUtils", + "ActorSequence", + "AbilityManager", + "DraggableWindow" }); } } diff --git a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp deleted file mode 100644 index 62ee99b..0000000 --- a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.cpp +++ /dev/null @@ -1,194 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARUIWeaponEquipment.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -// Sets default values for this component's properties -UARUIWeaponEquipment::UARUIWeaponEquipment() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - Weapons.SetNum(4); - ActiveWeaponIndex = 0; - // ... -} - - -// Called when the game starts -void UARUIWeaponEquipment::BeginPlay() -{ - Super::BeginPlay(); - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - AbilityComp->BindAbilityToAction(InputComponent, ShootInput); - AbilityComp->BindAbilityToAction(InputComponent, ReloadInput); - //alt fire ? - // ... - -} - - -// Called every frame -void UARUIWeaponEquipment::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - // ... -} - -void UARUIWeaponEquipment::NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UARUIWeaponEquipment::OnWeaponReady, InAbilityTag, SlotIndex); - AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , /*Input*/ ShootInput); -} - -void UARUIWeaponEquipment::OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - if (SlotIndex == 0) - { - Weapons[SlotIndex] = Ability; - ActiveWeapon = Ability; - ActiveWeaponIndex = SlotIndex; - AbilityComp->SetAbilityToAction(InAbilityTag, ShootInput, FAFOnAbilityReady()); - AbilityComp->SetAbilityToAction(InAbilityTag, ReloadInput, FAFOnAbilityReady()); - } - else - { - Weapons[SlotIndex] = Ability; - } -} -void UARUIWeaponEquipment::BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) -{ - NativeEquipWeapon(InAbilityTag, SlotIndex); -} - -void UARUIWeaponEquipment::NextWeapon() -{ - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - ActiveWeaponIndex++; - if (ActiveWeaponIndex < 4) - { - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - } - - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNextWeapon(ActiveWeaponIndex); - } - -} -void UARUIWeaponEquipment::PreviousWeapon() -{ - ActiveWeaponIndex--; - if (ActiveWeaponIndex >= 0) - { - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerPreviousWeapon(ActiveWeaponIndex); - } - -} - -void UARUIWeaponEquipment::ServerNextWeapon_Implementation(int32 WeaponIndex) -{ - ActiveWeaponIndex++; - if (ActiveWeaponIndex < 4) - { - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - //so Server index is different. Client might tried to cheat - //or sometrhing. We will override it. - //situation where client can chage multiple weapons within second - //should not have place, as there is animation and/or internal cooldown on weapon change. - //since it will be done trough ability. - if (ActiveWeaponIndex != WeaponIndex) - { - ClientNextWeapon(ActiveWeaponIndex); - } -} -bool UARUIWeaponEquipment::ServerNextWeapon_Validate(int32 WeaponIndex) -{ - return true; -} -void UARUIWeaponEquipment::ClientNextWeapon_Implementation(int32 WeaponIndex) -{ - ActiveWeaponIndex = WeaponIndex; - ActiveWeapon = Weapons[ActiveWeaponIndex]; -} -void UARUIWeaponEquipment::ServerPreviousWeapon_Implementation(int32 WeaponIndex) -{ - ActiveWeaponIndex--; - if (ActiveWeaponIndex >= 0) - { - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - ActiveWeapon = Weapons[ActiveWeaponIndex]; - } - if (ActiveWeaponIndex != WeaponIndex) - { - - } -} -bool UARUIWeaponEquipment::ServerPreviousWeapon_Validate(int32 WeaponIndex) -{ - return true; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.h b/Source/ActionRPGGame/UI/ARUIWeaponEquipment.h deleted file mode 100644 index 51e1b5d..0000000 --- a/Source/ActionRPGGame/UI/ARUIWeaponEquipment.h +++ /dev/null @@ -1,65 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "ARAbilityBase.h" -#include "ARUIWeaponEquipment.generated.h" - - -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARUIWeaponEquipment : public UActorComponent -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Input") - FGameplayTag ShootInput; - UPROPERTY(EditAnywhere, Category = "Input") - FGameplayTag ReloadInput; - /* - Weapons which are currently equiped. - */ - TArray> Weapons; - - /* - Weapon which is currently active. (equiped). - */ - TWeakObjectPtr ActiveWeapon; - int32 ActiveWeaponIndex; -public: - // Sets default values for this component's properties - UARUIWeaponEquipment(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - - void NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); - UFUNCTION() - void OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex); - UFUNCTION(BlueprintCallable, meta=(DisplayName = "Equip Weapon"), Category = "ActionRPGGame|UI|Weapon") - void BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); - UFUNCTION(BlueprintCallable) - void NextWeapon(); - UFUNCTION(BlueprintCallable) - void PreviousWeapon(); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerNextWeapon(int32 WeaponIndex); - void ServerNextWeapon_Implementation(int32 WeaponIndex); - bool ServerNextWeapon_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientNextWeapon(int32 WeaponIndex); - void ClientNextWeapon_Implementation(int32 WeaponIndex); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerPreviousWeapon(int32 WeaponIndex); - void ServerPreviousWeapon_Implementation(int32 WeaponIndex); - bool ServerPreviousWeapon_Validate(int32 WeaponIndex); -}; diff --git a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp index 821b814..7770b2f 100644 --- a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp +++ b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp @@ -2,17 +2,17 @@ #include "ARWeaponActriveInfoWidget.h" #include "ARPlayerController.h" -#include "ARUIWeaponEquipment.h" + #include "ARAbilityBase.h" #include "ARGunAttributes.h" - - +#include "../Weapons/ARWeaponManagerComponent.h" +#include "../Weapons/ARWeaponAbilityBase.h" float UARWeaponActriveInfoWidget::GetActiveMagazineAmmo() { if (!WeaponEquipement.IsValid()) return 0; - UARAbilityBase* Ability = WeaponEquipement->ActiveWeapon.Get(); + UGAAbilityBase* Ability = WeaponEquipement->GetCurrentWeapon(); if (!Ability) return 0; @@ -27,7 +27,7 @@ float UARWeaponActriveInfoWidget::GetActiveMagazineAmmoNormalized() { if (!WeaponEquipement.IsValid()) return 0; - UARAbilityBase* Ability = WeaponEquipement->ActiveWeapon.Get(); + UGAAbilityBase* Ability = WeaponEquipement->GetCurrentWeapon(); if (!Ability) return 0; @@ -44,7 +44,7 @@ float UARWeaponActriveInfoWidget::GetReloadTimeNormalized() { if (!WeaponEquipement.IsValid()) return 0; - UARAbilityBase* Ability = WeaponEquipement->ActiveWeapon.Get(); + UGAAbilityBase* Ability = WeaponEquipement->GetCurrentWeapon(); if (!Ability) return 0; diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp index a4354c7..1c19fc8 100644 --- a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp +++ b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp @@ -2,29 +2,37 @@ #include "ARWeaponInfoWidget.h" #include "ARPlayerController.h" -#include "ARUIWeaponEquipment.h" #include "ARAbilityBase.h" #include "ARGunAttributes.h" +#include "../Weapons/ARWeaponAbilityBase.h" +#include "../Weapons/ARWeaponManagerComponent.h" void UARWeaponInfoWidget::NativePreConstruct() { if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) { - WeaponEquipement = MyPC->UIWeaponEquipment; + WeaponEquipement = MyPC->WeaponManager; } - Super::NativePreConstruct(); +Super::NativePreConstruct(); } void UARWeaponInfoWidget::NativeConstruct() { + UARWeaponManagerComponent* WMC = nullptr; if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) { - WeaponEquipement = MyPC->UIWeaponEquipment; + WeaponEquipement = MyPC->WeaponManager; + WMC = MyPC->WeaponManager; + } + if (WeaponSlotTag.IsValid()) + { + // FAROnWeaponReady Delegate = FAROnWeaponReady::CreateUObject(this, &UARWeaponInfoWidget::OnWeaponChanged); + // WMC->AddOnWeaponChangedEvent(WeaponSlotTag, Delegate); } Super::NativeConstruct(); } float UARWeaponInfoWidget::GetMagazineAmmo() { - UARAbilityBase* Ability = WeaponEquipement->Weapons[SlotIndex].Get(); + UGAAbilityBase* Ability = WeaponEquipement->GetAbility(SlotIndex, EAMSlot::Slot001); if (!Ability) return 0; @@ -36,7 +44,7 @@ float UARWeaponInfoWidget::GetMagazineAmmo() } float UARWeaponInfoWidget::GetMagazineAmmoNormalized() { - UARAbilityBase* Ability = WeaponEquipement->Weapons[SlotIndex].Get(); + UGAAbilityBase* Ability = WeaponEquipement->GetAbility(SlotIndex, EAMSlot::Slot001); if (!Ability) return 0; @@ -47,4 +55,9 @@ float UARWeaponInfoWidget::GetMagazineAmmoNormalized() return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); } return 0; +} + +void UARWeaponInfoWidget::OnWeaponChanged(class UARWeaponAbilityBase* InAbility) +{ + } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h index 1086537..d3eab88 100644 --- a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h +++ b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h @@ -5,6 +5,9 @@ #include "CoreMinimal.h" #include "ARUMGWidgetBase.h" #include "ARGunAttributes.h" +#include "GameplayTags.h" +#include "../Weapons/ARWeaponsTypes.h" +#include "AMTypes.h" #include "ARWeaponInfoWidget.generated.h" /** @@ -16,8 +19,14 @@ class ACTIONRPGGAME_API UARWeaponInfoWidget : public UARUMGWidgetBase GENERATED_BODY() protected: UPROPERTY(EditAnywhere, BlueprintReadOnly) - int32 SlotIndex; - TWeakObjectPtr WeaponEquipement; + EAMGroup SlotIndex; + + UPROPERTY(EditAnywhere, BlueprintReadOnly) + FGameplayTag WeaponSlotTag; + + TWeakObjectPtr Weapon; + + TWeakObjectPtr WeaponEquipement; public: virtual void NativePreConstruct() override; @@ -27,4 +36,7 @@ class ACTIONRPGGAME_API UARWeaponInfoWidget : public UARUMGWidgetBase float GetMagazineAmmo(); UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") float GetMagazineAmmoNormalized(); + + UFUNCTION() + void OnWeaponChanged(class UARWeaponAbilityBase* InAbility); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h index d147944..96fe27c 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h @@ -9,6 +9,7 @@ #include "ARAvailableAbilities.h" #include "ARUIAbilityManagerComponent.generated.h" + USTRUCT(BlueprintType) struct FARAbilityInputBinding { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 1d047e3..1572d21 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -4,13 +4,29 @@ #include "AFAbilityInterface.h" #include "AFAbilityComponent.h" #include "ARWeaponAbilityBase.h" +#include "../Weapons/ARWeaponManagerComponent.h" // Sets default values for this component's properties UARWeaponManagerComponent::UARWeaponManagerComponent() { // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; - AllWeapons.SetNum(4); + AbilitySet.SetNum(MaxGroups); + if (MaxGroups > 0) + { + AbilitySet[0].SetNum(1); + AbilitySet[1].SetNum(1); + AbilitySet[2].SetNum(1); + AbilitySet[3].SetNum(1); + } + AbilityTagsSet.SetNum(MaxGroups); + if (MaxGroups > 0) + { + AbilityTagsSet[0].SetNum(1); + AbilityTagsSet[1].SetNum(1); + AbilityTagsSet[2].SetNum(1); + AbilityTagsSet[3].SetNum(1); + } // ... } @@ -20,24 +36,6 @@ void UARWeaponManagerComponent::BeginPlay() { Super::BeginPlay(); - // ... - -} - - -// Called every frame -void UARWeaponManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} -void UARWeaponManagerComponent::BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) -{ - NativeEquipWeapon(InAbilityTag, SlotIndex); -} -void UARWeaponManagerComponent::NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex) -{ APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) return; @@ -50,130 +48,33 @@ void UARWeaponManagerComponent::NativeEquipWeapon(const FGameplayTag& InAbilityT if (!AbilityComp) return; - FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponReady, InAbilityTag, SlotIndex); - AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , /*Input*/ ShootInput); -} -void UARWeaponManagerComponent::OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - UARWeaponAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - if (SlotIndex == 0) - { - AllWeapons[SlotIndex] = Ability; - CurrentWeapon = Ability; - ActiveWeaponIndex = SlotIndex; - AbilityComp->SetAbilityToAction(InAbilityTag, ShootInput, FAFOnAbilityReady()); - AbilityComp->SetAbilityToAction(InAbilityTag, ReloadInput, FAFOnAbilityReady()); - } - else + //for (const FGameplayTag& Tag : AbilityInputs) { - AllWeapons[SlotIndex] = Ability; + AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[0]); + AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[1]); } + // ... + } -void UARWeaponManagerComponent::NextWeapon() -{ - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - ActiveWeaponIndex++; - if (ActiveWeaponIndex < 4) - { - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - } - - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNextWeapon(ActiveWeaponIndex); - } -} -void UARWeaponManagerComponent::PreviousWeapon() +// Called every frame +void UARWeaponManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) { - ActiveWeaponIndex--; - if (ActiveWeaponIndex >= 0) - { - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerPreviousWeapon(ActiveWeaponIndex); - } - -} + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); -void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponIndex) -{ - ActiveWeaponIndex++; - if (ActiveWeaponIndex < 4) - { - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - //so Server index is different. Client might tried to cheat - //or sometrhing. We will override it. - //situation where client can chage multiple weapons within second - //should not have place, as there is animation and/or internal cooldown on weapon change. - //since it will be done trough ability. - if (ActiveWeaponIndex != WeaponIndex) - { - ClientNextWeapon(ActiveWeaponIndex); - } -} -bool UARWeaponManagerComponent::ServerNextWeapon_Validate(int32 WeaponIndex) -{ - return true; + // ... } -void UARWeaponManagerComponent::ClientNextWeapon_Implementation(int32 WeaponIndex) +UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() { - ActiveWeaponIndex = WeaponIndex; - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; + return GetAbility(ActiveGroup, EAMSlot::Slot001); } -void UARWeaponManagerComponent::ServerPreviousWeapon_Implementation(int32 WeaponIndex) -{ - ActiveWeaponIndex--; - if (ActiveWeaponIndex >= 0) - { - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - else - { - ActiveWeaponIndex = 0; - CurrentWeapon = AllWeapons[ActiveWeaponIndex]; - } - if (ActiveWeaponIndex != WeaponIndex) - { - } +void UARWeaponManagerComponent::NextWeapon() +{ + NextGroup(); } -bool UARWeaponManagerComponent::ServerPreviousWeapon_Validate(int32 WeaponIndex) +void UARWeaponManagerComponent::PreviousWeapon() { - return true; + PreviousGroup(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 13d705c..767db89 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -5,27 +5,33 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" #include "GameplayTags.h" +#include "ARWeaponsTypes.h" +#include "AMAbilityManagerComponent.h" #include "ARWeaponManagerComponent.generated.h" -class UARWeaponAbilityBase; +DECLARE_DELEGATE_OneParam(FAROnWeaponReady, class UARWeaponAbilityBase*); + /* Add On Character. */ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARWeaponManagerComponent : public UActorComponent +class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComponent { GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Input") - FGameplayTag ShootInput; - UPROPERTY(EditAnywhere, Category = "Input") - FGameplayTag ReloadInput; - - TArray> AllWeapons; - - TWeakObjectPtr CurrentWeapon; - - UPROPERTY() - int32 ActiveWeaponIndex; +//public: +// UPROPERTY(EditAnywhere, Category = "Input") +// FGameplayTag ShootInput; +// UPROPERTY(EditAnywhere, Category = "Input") +// FGameplayTag ReloadInput; +// +// TArray> AllWeapons; +// +// TMap> AllWeapons2; +// //Maps weapon slot to delegate to broadcast that weapon changed in given slot. +// TMap OnWeaponChanged; +// TWeakObjectPtr CurrentWeapon; +// +// UPROPERTY() +// EARWeaponSlot ActiveWeaponIndex; public: // Sets default values for this component's properties UARWeaponManagerComponent(); @@ -38,29 +44,31 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UActorComponent public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + UGAAbilityBase* GetCurrentWeapon(); + //void AddOnWeaponChangedEvent(const FGameplayTag& InTag, FAROnWeaponReady& InDelegate); + //void SendOnWeaponChangedEvent(const FGameplayTag& InTag, UARWeaponAbilityBase* InAbility); UFUNCTION(BlueprintCallable) void NextWeapon(); UFUNCTION(BlueprintCallable) void PreviousWeapon(); - UFUNCTION(Server, Reliable, WithValidation) - void ServerNextWeapon(int32 WeaponIndex); - void ServerNextWeapon_Implementation(int32 WeaponIndex); - bool ServerNextWeapon_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientNextWeapon(int32 WeaponIndex); - void ClientNextWeapon_Implementation(int32 WeaponIndex); + //UFUNCTION(Server, Reliable, WithValidation) + // void ServerNextWeapon(int32 WeaponIndex); + //void ServerNextWeapon_Implementation(int32 WeaponIndex); + //bool ServerNextWeapon_Validate(int32 WeaponIndex); + //UFUNCTION(Client, Reliable) + // void ClientNextWeapon(int32 WeaponIndex); + //void ClientNextWeapon_Implementation(int32 WeaponIndex); - UFUNCTION(Server, Reliable, WithValidation) - void ServerPreviousWeapon(int32 WeaponIndex); - void ServerPreviousWeapon_Implementation(int32 WeaponIndex); - bool ServerPreviousWeapon_Validate(int32 WeaponIndex); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Weapon"), Category = "ActionRPGGame|UI|Weapon") - void BP_EquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); + //UFUNCTION(Server, Reliable, WithValidation) + // void ServerPreviousWeapon(int32 WeaponIndex); + //void ServerPreviousWeapon_Implementation(int32 WeaponIndex); + //bool ServerPreviousWeapon_Validate(int32 WeaponIndex); + // + //UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Weapon"), Category = "ActionRPGGame|UI|Weapon") + // void BP_EquipWeapon(const FGameplayTag& InAbilityTag, EARWeaponSlot SlotIndex); - void NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); - UFUNCTION() - void OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex); + //void NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); + //UFUNCTION() + // void OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex); }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponsTypes.cpp b/Source/ActionRPGGame/Weapons/ARWeaponsTypes.cpp new file mode 100644 index 0000000..dcd3165 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponsTypes.cpp @@ -0,0 +1,3 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponsTypes.h" diff --git a/Source/ActionRPGGame/Weapons/ARWeaponsTypes.h b/Source/ActionRPGGame/Weapons/ARWeaponsTypes.h new file mode 100644 index 0000000..ca151b1 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponsTypes.h @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "ARWeaponsTypes.generated.h" + +UENUM(BlueprintType) +enum class EARWeaponSlot : uint8 +{ + Slot1 = 0, + Slot2 = 1, + Slot3 = 2, + Slot4 = 3, + + MAX +}; From a645a210275f71c6ba51f17a1e545427d94137fe Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 17 Dec 2017 15:47:10 +0100 Subject: [PATCH 020/187] Speculative fix for condition race When effects are removed/expired. Add Removed event for instant effects (for them OnApplied and OnRemoved are called one after another). --- .../AbilityFramework/AFAbilityComponent.cpp | 18 +++- .../AbilityFramework/AFAbilityComponent.h | 24 +++-- .../Abilities/GAAbilityBase.cpp | 7 +- .../Abilities/GAAbilityBase.h | 2 + .../AFAtributeDurationAdd.cpp | 2 +- .../AFAttributeDurationInfinite.cpp | 2 +- .../AFAttributeDurationOverride.cpp | 2 +- .../AFPeriodApplicationAdd.cpp | 2 +- .../AFPeriodApplicationExtend.cpp | 2 +- .../AFPeriodApplicationInfiniteAdd.cpp | 2 +- .../AFPeriodApplicationOverride.cpp | 2 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 57 +++++----- .../AbilityFramework/Effects/GAGameEffect.h | 24 ++++- .../SAFDAttributes.cpp | 29 ++++- .../AbilityFrameworkDebugger/SAFDAttributes.h | 10 +- .../SAFDDesktopWidget.cpp | 100 +++++++++++++++--- .../SAFDDesktopWidget.h | 14 ++- .../AbilityFrameworkDebugger/SAFDEffects.cpp | 91 +++++++++++++++- .../AbilityFrameworkDebugger/SAFDEffects.h | 44 +++++++- .../SDraggableWindowWidget.cpp | 16 ++- 20 files changed, 376 insertions(+), 74 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 910b151..65fe389 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -230,6 +230,11 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn PropertyByHandle.Add(Handle, &InProperty); OnEffectAppliedToTarget.Broadcast(Handle); + if(InProperty.Duration == 0 + && InProperty.Period == 0) + { + OnEffectRemoved.Broadcast(Handle); + } return Handle; } } @@ -320,7 +325,11 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper MulticastRemoveEffectCue(CueParams); } } - GameEffectContainer.RemoveEffectByHandle(HandleIn, InProperty); + TArray handles = GameEffectContainer.RemoveEffect(InProperty); + for (const FGAEffectHandle& Handle : handles) + { + OnEffectExpired.Broadcast(Handle); + } } void UAFAbilityComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) @@ -336,7 +345,6 @@ void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, { InternalRemoveEffect(InProperty, InContext); } - //OnEffectRemoved.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); } void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) @@ -361,7 +369,11 @@ void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProper MulticastRemoveEffectCue(CueParams); } } - GameEffectContainer.RemoveEffect(InProperty); + TArray handles = GameEffectContainer.RemoveEffect(InProperty); + for(const FGAEffectHandle& Handle : handles) + { + OnEffectRemoved.Broadcast(Handle); + } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 047b7ab..bca3f82 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -29,7 +29,7 @@ DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_Modify DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle, Handle); +DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate , FAFEventData); DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); @@ -311,19 +311,19 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UPROPERTY(BlueprintAssignable, Category = "Game Attributes") FGAOnAttributeModifed OnTargetAttributeModifed; /* Effect/Attribute System Delegates */ - UPROPERTY(BlueprintAssignable, Category = "Effect") + //UPROPERTY(BlueprintAssignable, Category = "Effect") FGAGenericEffectDelegate OnEffectAppliedToTarget; - UPROPERTY(BlueprintAssignable, Category = "Effect") + //UPROPERTY(BlueprintAssignable, Category = "Effect") FGAGenericEffectDelegate OnEffectAppliedToSelf; - UPROPERTY(BlueprintAssignable, Category = "Effect") + //UPROPERTY(BlueprintAssignable, Category = "Effect") FGAGenericEffectDelegate OnEffectExecuted; - UPROPERTY(BlueprintAssignable, Category = "Effect") + //UPROPERTY(BlueprintAssignable, Category = "Effect") FGAGenericEffectDelegate OnEffectExpired; - UPROPERTY(BlueprintAssignable, Category = "Effect") + //UPROPERTY(BlueprintAssignable, Category = "Effect") FGAGenericEffectDelegate OnEffectRemoved; /* NEW EFFECT SYSTEM */ @@ -347,6 +347,18 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, TMap EffectEvents; TMap AttributeChanged; + + const FGAGenericEffectDelegate& GetOnEffectApppliedToTarget() const + { + return OnEffectAppliedToTarget; + } + const FGAGenericEffectDelegate& GetOnEffectRemoved() const + { + return OnEffectRemoved; + } + + void RegisterToEffectEvents(void* Object, TFunction InFunction); + void BroadcastAttributeChange(const FGAAttribute& InAttribute, const FAFAttributeChangedData& InData); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 5a5b5d0..e575c37 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -358,7 +358,7 @@ bool UGAAbilityBase::ApplyCooldownEffect() } FAFFunctionModifier Modifier; - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnCooldownEnd, CooldownEffectHandle); + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); AbilityComponent->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, @@ -375,6 +375,11 @@ bool UGAAbilityBase::ApplyCooldownEffect() //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); return false; } +void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) +{ + AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); + OnCooldownEnd(InHandle); +} void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) { //CooldownEffectHandle = InCooldownHandle; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 4122638..6ab63e9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -414,6 +414,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnCooldownEnd(FGAEffectHandle InHandle); + void NativeOnCooldownEnd(FGAEffectHandle InHandle); + UFUNCTION() void OnCooldownEffectExpired(); UFUNCTION() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp index cafb889..2743ce4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -19,7 +19,7 @@ bool UAFAtributeDurationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); - InContainer->AddEffect(InHandle); + InContainer->AddEffect(InProperty, InHandle); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp index 3cb3784..63fe53f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp @@ -11,7 +11,7 @@ bool UAFAttributeDurationInfinite::ApplyEffect(const FGAEffectHandle& InHandle, const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier) { - InContainer->AddEffect(InHandle, true); + InContainer->AddEffect(InProperty, InHandle, true); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp index 8e51b5b..1da6d76 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -34,7 +34,7 @@ bool UAFAttributeDurationOverride::ApplyEffect(const FGAEffectHandle& InHandle, DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.Duration, false); - InContainer->AddEffect(InHandle); + InContainer->AddEffect(InProperty, InHandle); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp index 0edde1c..a820ad7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -23,7 +23,7 @@ bool UAFPeriodApplicationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struc PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); - InContainer->AddEffect(InHandle); + InContainer->AddEffect(InProperty, InHandle); //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index 1d574ee..034d4c6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -40,7 +40,7 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); - InContainer->AddEffect(InHandle); + InContainer->AddEffect(InProperty, InHandle); } return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp index 3e973b0..567f2cd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -16,7 +16,7 @@ bool UAFPeriodApplicationInfiniteAdd::ApplyEffect(const FGAEffectHandle& InHandl FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); - InContainer->AddEffect(InHandle, true); + InContainer->AddEffect(InProperty, InHandle, true); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp index 2193360..5afd83d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -32,7 +32,7 @@ bool UAFPeriodApplicationOverride::ApplyEffect(const FGAEffectHandle& InHandle, PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.Period, true); - InContainer->AddEffect(InHandle); + InContainer->AddEffect(InProperty, InHandle); //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index fe428fb..cb650e3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -533,16 +533,20 @@ TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectPrope return Handles; } -void FGAEffectContainer::AddEffect(const FGAEffectHandle& HandleIn, bool bInfinite) +void FGAEffectContainer::AddEffect(FGAEffectProperty& InProperty, const FGAEffectHandle& HandleIn, bool bInfinite) { TSet& AttributeEffect = EffectByAttribute.FindOrAdd(HandleIn.GetAttribute()); AttributeEffect.Add(HandleIn); ActiveEffectHandles.Add(HandleIn); AddEffectByClass(HandleIn); UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); - FObjectKey key(HandleIn.GetEffectSpec()->GetClass()); + FObjectKey key(InProperty.GetClass()); TArray& handles = EffectByClass.FindOrAdd(key); handles.Add(HandleIn); + if(EffectByClass.Num() == 0) + { + int asasd = 0; + } if (bInfinite) { InfiniteEffects.Add(HandleIn); @@ -617,6 +621,26 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn EffectByClass.Remove(FObjectKey(InProperty.GetClass())); } } + FAFEffectRepInfo* Out = nullptr; + EffectInfos.RemoveAndCopyValue(HandleIn, Out); + if (Out) + { + FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); + EffectInfoLog += Out->EffectTag.ToString(); + AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); + MarkItemDirty(*Out); + Out->OnRemoved(); + ActiveEffectInfos.Remove(*Out); + MarkArrayDirty(); + delete Out; + } + FAFPredictionHandle* PredHandle = PredictionByHandle.Find(HandleIn); + if(PredHandle) + { + PredictedEffectInfos.Remove(*PredHandle); + HandleByPrediction.Remove(*PredHandle); + PredictionByHandle.Remove(HandleIn); + } } void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn , const FGAEffectProperty& InProperty) @@ -704,41 +728,25 @@ void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn } } -void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num) +TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num) { UGAGameEffectSpec* Spec = HandleIn.Spec; EGAEffectAggregation Aggregation = Spec->EffectAggregation; - TArray* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); + FObjectKey key(HandleIn.GetClass()); + TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); FAFEffectRepInfo* Out = nullptr; - if (!handles) - return; + return TArray(); + TArray copy = *handles; for (int32 idx = 0; idx < Num; idx++) { if (handles->IsValidIndex(0)) { - FGAEffectHandle OutHandle = (*handles)[0]; + FGAEffectHandle OutHandle = (*handles)[idx]; if (OutHandle.IsValid()) { - HandleByPrediction.Remove(HandleIn.PredictionHandle); - - if (PredictionByHandle.Contains(OutHandle)) - PredictionByHandle.Remove(OutHandle); - - EffectInfos.RemoveAndCopyValue(OutHandle, Out); - if (Out) - { - FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); - EffectInfoLog += Out->EffectTag.ToString(); - AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); - MarkItemDirty(*Out); - Out->OnRemoved(); - ActiveEffectInfos.Remove(*Out); - MarkArrayDirty(); - delete Out; - } if (!ActiveEffectHandles.Contains(OutHandle)) { UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffectRef().ToString()); @@ -762,6 +770,7 @@ void FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 N } } } + return copy; } //FGAEffectContainer::FGAEffectContainer() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index bed8175..66d4688 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -362,7 +362,9 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty : ApplicationRequirement(nullptr), Application(nullptr), Execution(nullptr), - Spec(nullptr) + Spec(nullptr), + Duration(0), + Period(0) {}; FGAEffectProperty(TSubclassOf InClass) @@ -370,7 +372,9 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty ApplicationRequirement(nullptr), Application(nullptr), Execution(nullptr), - Spec(nullptr) + Spec(nullptr), + Duration(0), + Period(0) {}; TSubclassOf GetClass() const { return SpecClass.SpecClass; } @@ -712,24 +716,32 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer //that's why handle should only be created on server (and by that, effects). //change to SharedPtr ? mutable TMap EffectInfos; - + + UPROPERTY() TMap HandleByPrediction; + + UPROPERTY() TMap PredictionByHandle; + TMap PredictedEffectInfos; + TMap> EffectByAttribute; + TMap> EffectByClass; //TQueue dupa; /* All effects. */ + UPROPERTY() TSet ActiveEffectHandles; /* Contains effects with infinite duration. Infinite effects are considred to be special case, where they can only be self spplied and must be manually removed. */ + UPROPERTY() TSet InfiniteEffects; //not really sure if we really need set.\ @@ -739,12 +751,14 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer FName = Effect class name FGAEffectHandle = handle to effect of class. */ + TMap>> InstigatorEffectByClass; /* FName = Effect class name FGAEffectHandle = handle to effect of class. */ + TMap> TargetEffectByClass; /* Keeps effects instanced per target actor. */ @@ -777,7 +791,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer void ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - void RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); + TArray RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); @@ -790,7 +804,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TSet GetHandlesByClass(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); - void AddEffect(const FGAEffectHandle& HandleIn, bool bInfinite = false); + void AddEffect(FGAEffectProperty& InProperty, const FGAEffectHandle& HandleIn, bool bInfinite = false); void AddEffectByClass(const FGAEffectHandle& HandleIn); void RemoveFromAttribute(const FGAEffectHandle& HandleIn); diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp index 9b470d1..48c1171 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp @@ -3,16 +3,20 @@ #include "SAFDAttributes.h" #include "SlateOptMacros.h" #include "SListView.h" -#include "Attributes/GAAttributesBase.h" +#include "SGridPanel.h" BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION void SAFDAttributes::Construct(const FArguments& InArgs) { AFInterface = InArgs._AbilityInterface; ChildSlot + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ SNew(SOverlay) +SOverlay::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ SNew(SListView>) .ListItemsSource(&Attributes) @@ -31,10 +35,17 @@ void SAFDAttributes::GatherAttributes() return; Attributes.Empty(); - for(TFieldIterator It(AttributesObject->GetClass(), EFieldIteratorFlags::IncludeSuper); It; ++It) + for(TFieldIterator It(AttributesObject->GetClass(), EFieldIteratorFlags::IncludeSuper); It; ++It) { TSharedPtr AttributeRow = MakeShareable(new FAttributeRow); - AttributeRow->Name = It->GetName(); + UStructProperty* Prop = *It; + FAFAttributeBase* Attr = Prop->ContainerPtrToValuePtr(AttributesObject); + if (Attr) + { + AttributeRow->Attribute = Attr; + AttributeRow->Name = It->GetName(); + AttributeRow->Value = TAttribute::Create(TAttribute::FGetter::CreateSP(AttributeRow.Get(), &FAttributeRow::GetValue)); + } Attributes.Add(AttributeRow); } @@ -44,12 +55,20 @@ TSharedRef SAFDAttributes::GenerateListRow(TSharedPtr return SNew(STableRow< TSharedRef >, OwnerTable) [ - SNew(SBox) - .HAlign(HAlign_Left) + SNew(SGridPanel) + .FillColumn(0, 1) + +SGridPanel::Slot(0,0) + .HAlign(EHorizontalAlignment::HAlign_Fill) [ SNew(STextBlock) .Text(FText::FromString(NotifyName->Name)) ] + + SGridPanel::Slot(1, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(NotifyName->Value) + ] ]; } END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h index cdc81ba..57f937b 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h @@ -5,10 +5,18 @@ #include "CoreMinimal.h" #include "Widgets/SCompoundWidget.h" #include "AFAbilityInterface.h" +#include "Attributes/GAAttributesBase.h" -struct FAttributeRow +struct FAttributeRow : public TSharedFromThis { FString Name; + FAFAttributeBase* Attribute; + TAttribute Value; + + FText GetValue() const + { + return FText::AsNumber(Attribute->GetCurrentValue()); + } }; /** diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp index 1fc3eba..8b02163 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp @@ -22,14 +22,79 @@ void SAFDMainWidget::Construct(const FArguments& InArgs) World = world; FOnClicked OnPickActorClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnPickActorClicked); + FOnClicked OnAttributesClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnAttributesClicked); + FOnClicked OnEffectsClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnEffectsClicked); + ChildSlot + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ SNew(SVerticalBox) +SVerticalBox::Slot() + .FillHeight(1.0f) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ - SAssignNew(Content, SOverlay) + SNew(SOverlay) + +SOverlay::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Top) + .AutoHeight() + [ + SNew(STextBlock) + .Text(this, &SAFDMainWidget::GetActorName) + ] + + SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Top) + .MaxHeight(24) + .AutoHeight() + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnAttributesClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("Attributes")) + ] + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnEffectsClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("Effects")) + ] + ] + ] + + SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + .FillWidth(1.0f) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SAssignNew(Content, SWidgetSwitcher) + ] + ] + ] ] +SVerticalBox::Slot() + .MaxHeight(32.0f) + .AutoHeight() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Bottom) [ SNew(SButton) .OnClicked(OnPickActorClickedDel) @@ -39,14 +104,6 @@ void SAFDMainWidget::Construct(const FArguments& InArgs) ] ] ]; - - Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Left) - .VAlign(EVerticalAlignment::VAlign_Top) - [ - SNew(STextBlock) - .Text(this, &SAFDMainWidget::GetActorName) - ]; } FText SAFDMainWidget::GetActorName() const @@ -66,6 +123,18 @@ FReply SAFDMainWidget::OnPickActorClicked() return FReply::Handled(); } + +FReply SAFDMainWidget::OnAttributesClicked() +{ + Content->SetActiveWidgetIndex(0); + return FReply::Handled(); +} +FReply SAFDMainWidget::OnEffectsClicked() +{ + Content->SetActiveWidgetIndex(1); + return FReply::Handled(); +} + void SAFDMainWidget::OnActorPicked() { APlayerController* PC = World->GetFirstPlayerController(); @@ -79,12 +148,19 @@ void SAFDMainWidget::OnActorPicked() if(IAFAbilityInterface* Interface = Cast(OutHit.GetActor())) { Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Left) - .VAlign(EVerticalAlignment::VAlign_Top) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ SNew(SAFDAttributes) .AbilityInterface(Interface) ]; + Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SAFDEffects) + .AbilityInterface(Interface) + ]; } } @@ -124,6 +200,6 @@ FReply SAFDDesktopWidget::OnNewDebugWindowClicked() FDWWWindowHandle Handle = FAFDManager::Get().AddNewWindow(window); TSharedPtr wid = SNew(SAFDMainWidget); window->AddContent(wid); - wid->WindowHandle = Handle; + wid->SetWindowHandle(Handle); return FReply::Handled(); } \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h index c637f63..73f612c 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h @@ -5,6 +5,7 @@ #include "CoreMinimal.h" #include "Widgets/SCompoundWidget.h" #include "SDraggableWindowWidget.h" +#include "SWidgetSwitcher.h" class ABILITYFRAMEWORKDEBUGGER_API SAFDMainWidget : public SCompoundWidget { @@ -12,17 +13,28 @@ class ABILITYFRAMEWORKDEBUGGER_API SAFDMainWidget : public SCompoundWidget SLATE_BEGIN_ARGS(SAFDMainWidget) {} SLATE_END_ARGS() +protected: TWeakObjectPtr World; TWeakObjectPtr SelectedActor; - TSharedPtr Content; + TSharedPtr Content; FDWWWindowHandle WindowHandle; TSharedPtr CaptureWidget; /** Constructs this widget with InArgs */ +public: void Construct(const FArguments& InArgs); +protected: FReply OnPickActorClicked(); + FReply OnAttributesClicked(); + FReply OnEffectsClicked(); + void OnActorPicked(); FText GetActorName() const; +public: + void SetWindowHandle(const FDWWWindowHandle& InHandle) + { + WindowHandle = InHandle; + } }; /** diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp index 617cc2a..7d07745 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp @@ -6,15 +6,100 @@ BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION void SAFDEffects::Construct(const FArguments& InArgs) { - + AFInterface = InArgs._AbilityInterface; + AbilityComponent = AFInterface->GetAbilityComp(); + + OnEffectAppliedHandle = AbilityComponent->OnEffectAppliedToTarget.AddSP(this, &SAFDEffects::OnEffectApplied); + OnEffectRemovedHandle = AbilityComponent->OnEffectRemoved.AddSP(this, &SAFDEffects::OnEffectRemoved); + OnEffectExpiredHandle = AbilityComponent->OnEffectExpired.AddSP(this, &SAFDEffects::OnEffectRemoved); + + InitializeEffects(); ChildSlot [ SNew(SOverlay) - +SOverlay::Slot() + + SOverlay::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ - SNew(SButton) + SAssignNew(ListView, SListView>) + .ListItemsSource(&Effects) + .OnGenerateRow(this, &SAFDEffects::GenerateListRow) ] ]; } END_SLATE_FUNCTION_BUILD_OPTIMIZATION +SAFDEffects::~SAFDEffects() +{ + AbilityComponent->OnEffectAppliedToTarget.Remove(OnEffectAppliedHandle); + AbilityComponent->OnEffectRemoved.Remove(OnEffectRemovedHandle); + AbilityComponent->OnEffectExpired.Remove(OnEffectExpiredHandle); +} + +void SAFDEffects::InitializeEffects() +{ + if (!AbilityComponent.IsValid()) + return; + + for(const FAFEffectRepInfo& RepInfo : AbilityComponent->GetAllEffectsInfo()) + { + TSharedPtr Row = MakeShareable(new FAFDEffectRow); + Row->Handle = RepInfo.Handle; + Row->EffectClassName = RepInfo.Handle.GetEffectSpec()->GetName(); + Effects.Add(Row); + } + //ListView->RebuildList(); +} + + +TSharedRef SAFDEffects::GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable) +{ + return + SNew(STableRow< TSharedRef >, OwnerTable) + [ + SNew(SGridPanel) + .FillColumn(0, 1) + + SGridPanel::Slot(0, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(FText::FromString(EffectRow->EffectClassName)) + ] + ]; +} + +void SAFDEffects::OnEffectApplied(FGAEffectHandle InHandle) +{ + TSharedPtr Row = MakeShareable(new FAFDEffectRow); + Row->Handle = InHandle; + Row->EffectClassName = InHandle.GetEffectSpec()->GetName(); + UE_LOG(LogTemp, Warning, TEXT("SAFDEffects::OnEffectAppliede")); + Effects.Add(Row); + ListView->RebuildList(); +} +void SAFDEffects::OnEffectRemoved(FGAEffectHandle InHandle) +{ + class Predicate + { + FGAEffectHandle HandleC; + public: + Predicate(const FGAEffectHandle& InH) + :HandleC(InH) + {} + bool operator()(const FAFDEffectRow& Other) const + { + return HandleC == Other.Handle; + } + bool operator()(TSharedPtr Other) const + { + return HandleC == Other->Handle; + } + }; + int32 Idx = Effects.IndexOfByPredicate(Predicate(InHandle)); //Effects.IndexOfByKey(InHandle); + if(Idx > -1) + { + Effects.RemoveAt(Idx); + } + + ListView->RebuildList(); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h index 79baffa..7843397 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h @@ -6,6 +6,33 @@ #include "Widgets/SCompoundWidget.h" #include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" + +struct FAFDEffectRow +{ + FString EffectClassName; + FGAEffectHandle Handle; + + const bool operator==(const FAFDEffectRow& Other) const + { + return Handle == Other.Handle; + } + + const bool operator==(const FGAEffectHandle& InHandle) const + { + return Handle == InHandle; + } + const bool operator==(FGAEffectHandle InHandle) const + { + return Handle == InHandle; + } + const bool operator==(TSharedPtr InHandle) const + { + return Handle == InHandle->Handle; + } +}; + + /** * */ @@ -14,10 +41,25 @@ class ABILITYFRAMEWORKDEBUGGER_API SAFDEffects : public SCompoundWidget public: SLATE_BEGIN_ARGS(SAFDEffects) {} + SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) SLATE_END_ARGS() - +protected: IAFAbilityInterface* AFInterface; + TWeakObjectPtr AbilityComponent; + TSharedPtr>> ListView; + FDelegateHandle OnEffectAppliedHandle; + FDelegateHandle OnEffectRemovedHandle; + FDelegateHandle OnEffectExpiredHandle; + TArray> Effects; + +public: /** Constructs this widget with InArgs */ void Construct(const FArguments& InArgs); + ~SAFDEffects(); +protected: + TSharedRef GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable); + void InitializeEffects(); + void OnEffectApplied(FGAEffectHandle InHandle); + void OnEffectRemoved(FGAEffectHandle InHandle); }; diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index 4c670d2..3560b8a 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -216,15 +216,12 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .VAlign(EVerticalAlignment::VAlign_Fill) [ SAssignNew(WindowBox, SWindowBox) - /*.HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill)*/ //.HeightOverride(heightAttr) //.WidthOverride(widthAttr) [ SNew(SVerticalBox) + SVerticalBox::Slot() - //.FillHeight(0.2f) - .MaxHeight(32) + .AutoHeight() .MaxHeight(32) [ SNew(SHorizontalBox) @@ -237,9 +234,16 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) ] + SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) .FillHeight(1.0f) [ - SAssignNew(Content, SOverlay) + SNew(SBox) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SAssignNew(Content, SOverlay) + ] ] ] @@ -394,6 +398,8 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl void SDraggableWindowWidget::AddContent(TSharedPtr InWidget) { Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) [ InWidget.ToSharedRef() ]; From f454fd8a79786e36789b9f733ad3ac470678cce6 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 22 Dec 2017 01:42:57 +0100 Subject: [PATCH 021/187] added very ugly hack to make Standalone Game from editor work, aded missing files --- ActionRPGGame.uproject | 295 ++++++++++-------- Config/DefaultEngine.ini | 6 +- .../AbilityFramework/AbilityFramework.uplugin | 2 +- .../AbilityFramework/AFAbilityComponent.cpp | 21 +- .../AbilityFramework/AFAbilityComponent.h | 2 +- .../Source/AbilityFramework/AFCueManager.cpp | 12 +- .../Abilities/GAAbilityBase.cpp | 8 +- .../AbilityFramework.Build.cs | 8 +- .../AbilityFramework/AbilityFramework.cpp | 3 + .../Effects/GABlueprintLibrary.cpp | 9 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 45 ++- .../AbilityFramework/Effects/GAGameEffect.h | 77 ++++- .../Tests/GAAttributesTests.cpp | 2 +- .../GAAbilityBlueprintFactory.cpp | 8 +- .../AbilityFrameworkEditor.cpp | 5 +- .../AbilityFrameworkDebugger.uplugin | 37 +++ .../AbilityFrameworkDebugger/SAFDEffects.cpp | 23 ++ .../AbilityFrameworkDebugger/SAFDEffects.h | 20 +- Plugins/AbilityManager/AbilityManager.uplugin | 29 ++ .../DraggableWindow/DraggableWindow.uplugin | 23 ++ Source/ActionRPGGame/ARGameMode.cpp | 8 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 7 +- Source/ActionRPGGame/ActionRPGGame.cpp | 7 + .../Abilities/ARUIAbilityManagerComponent.cpp | 5 +- Source/ActionRPGGameEditor.Target.cs | 3 +- .../ActionRPGGameEditor.Build.cs | 37 +++ .../ActionRPGGameEditor.cpp | 14 + .../ActionRPGGameEditor/ActionRPGGameEditor.h | 9 + 28 files changed, 539 insertions(+), 186 deletions(-) create mode 100644 Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin create mode 100644 Plugins/AbilityManager/AbilityManager.uplugin create mode 100644 Plugins/DraggableWindow/DraggableWindow.uplugin create mode 100644 Source/ActionRPGGameEditor/ActionRPGGameEditor.Build.cs create mode 100644 Source/ActionRPGGameEditor/ActionRPGGameEditor.cpp create mode 100644 Source/ActionRPGGameEditor/ActionRPGGameEditor.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 4458fe8..afefb76 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -3,139 +3,164 @@ "EngineAssociation": "{A36EBF10-476D-8159-343E-8FA796F9AC8F}", "Category": "", "Description": "", - "Modules": [ - { - "Name": "ActionRPGGame", - "Type": "Runtime", - "LoadingPhase": "Default", - "AdditionalDependencies": [ - "AbilityFramework", - "Engine", - "AIModule", - "UMG", - "CoreUObject" - ] - } - ], - "Plugins": [ - { - "Name": "ActorSequence", - "Enabled": true - }, - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "ActorSequenceEditor", - "Enabled": true - }, - { - "Name": "ImagePlate", - "Enabled": true - }, - { - "Name": "PerformanceMonitor", - "Enabled": true - }, - { - "Name": "OnlineSubsystemAmazon", - "Enabled": true - }, - { - "Name": "OnlineFramework", - "Enabled": true - }, - { - "Name": "SteamVR", - "Enabled": false - }, - { - "Name": "OculusVR", - "Enabled": false - }, - { - "Name": "Niagara", - "Enabled": true - }, - { - "Name": "SoundUtilities", - "Enabled": true - }, - { - "Name": "SoundVisualizations", - "Enabled": true - }, - { - "Name": "BlueprintStats", - "Enabled": true - }, - { - "Name": "LocationServicesBPLibrary", - "Enabled": false - }, - { - "Name": "WindowsDeviceProfileSelector", - "Enabled": true - }, - { - "Name": "AndroidDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "IOSDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "AndroidMedia", - "Enabled": false - }, - { - "Name": "MobileLauncherProfileWizard", - "Enabled": false - }, - { - "Name": "MobilePatchingUtils", - "Enabled": false - }, - { - "Name": "AndroidMoviePlayer", - "Enabled": false - }, - { - "Name": "AppleMoviePlayer", - "Enabled": false - }, - { - "Name": "GoogleCloudMessaging", - "Enabled": false - }, - { - "Name": "OnlineSubsystemIOS", - "Enabled": false, - "SupportedTargetPlatforms": [ - "IOS", - "TVOS" - ] - }, - { - "Name": "OnlineSubsystemGooglePlay", - "Enabled": false, - "SupportedTargetPlatforms": [ - "Android" - ] - }, - { - "Name": "ApexDestruction", - "Enabled": true - }, - { - "Name": "AndroidPermission", - "Enabled": false - } - ], - "TargetPlatforms": [ - "LinuxNoEditor", - "WindowsNoEditor" - ] + "Modules": [ + { + "Name": "ActionRPGGame", + "Type": "Runtime", + "LoadingPhase": "Default", + "AdditionalDependencies": [ + "AbilityFramework", + "AbilityFrameworkDebugger", + "AbilityManager", + "Engine", + "AIModule", + "UMG", + "CoreUObject" + ] + }, + { + "Name": "ActionRPGGameEditor", + "Type": "Editor", + "LoadingPhase": "Default", + "AdditionalDependencies": [ + "AbilityFramework", + "AbilityFrameworkEditor", + "AbilityFrameworkDebugger", + "AbilityManager", + "Engine", + "AIModule", + "UMG", + "CoreUObject" + ] + } + ], + "Plugins" : [ + { + "Name": "ActorSequence", + "Enabled": true + }, + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "AbilityFrameworkDebugger", + "Enabled": true + }, + { + "Name": "AbilityManager", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false + }, + { + "Name": "Niagara", + "Enabled": true + }, + { + "Name": "SoundUtilities", + "Enabled": true + }, + { + "Name": "SoundVisualizations", + "Enabled": true + }, + { + "Name": "BlueprintStats", + "Enabled": true + }, + { + "Name": "LocationServicesBPLibrary", + "Enabled": false + }, + { + "Name": "WindowsDeviceProfileSelector", + "Enabled": true + }, + { + "Name": "AndroidDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "IOSDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "AndroidMedia", + "Enabled": false + }, + { + "Name": "MobileLauncherProfileWizard", + "Enabled": false + }, + { + "Name": "MobilePatchingUtils", + "Enabled": false + }, + { + "Name": "AndroidMoviePlayer", + "Enabled": false + }, + { + "Name": "AppleMoviePlayer", + "Enabled": false + }, + { + "Name": "GoogleCloudMessaging", + "Enabled": false + }, + { + "Name": "OnlineSubsystemIOS", + "Enabled": false, + "SupportedTargetPlatforms": [ + "IOS", + "TVOS" + ] + }, + { + "Name": "OnlineSubsystemGooglePlay", + "Enabled": false, + "SupportedTargetPlatforms": [ + "Android" + ] + }, + { + "Name": "ApexDestruction", + "Enabled": true + }, + { + "Name": "AndroidPermission", + "Enabled": false + } + ], + "TargetPlatforms": [ + "LinuxNoEditor", + "WindowsNoEditor" + ] } \ No newline at end of file diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 854e7c9..d3b9082 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -99,10 +99,10 @@ bAllowStrafing=True bEnableBTAITasks=True [PacketSimulationSettings] -PktLag=500 -PktLagVariance=0 +PktLag=250 +PktLagVariance=20 PktLoss=10 -PktOrder=0 +PktOrder=5 PktDup=0 [/Script/UnrealEd.HierarchicalLODSettings] diff --git a/Plugins/AbilityFramework/AbilityFramework.uplugin b/Plugins/AbilityFramework/AbilityFramework.uplugin index cc4aedc..49c5851 100644 --- a/Plugins/AbilityFramework/AbilityFramework.uplugin +++ b/Plugins/AbilityFramework/AbilityFramework.uplugin @@ -12,7 +12,7 @@ "SupportURL": "", "CanContainContent": true, "IsBetaVersion": true, - "Installed": false, + "Installed": true, "Modules": [ { "Name": "AbilityFramework", diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 65fe389..da00098 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -325,6 +325,15 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper MulticastRemoveEffectCue(CueParams); } } +// if (role < ENetRole::ROLE_Authority +// || mode == ENetMode::NM_Standalone) + { + FAFEffectRepInfo* RepInfo = GameEffectContainer.GetReplicationInfo(HandleIn); + if (RepInfo) + { + RepInfo->OnExpired(); + } + } TArray handles = GameEffectContainer.RemoveEffect(InProperty); for (const FGAEffectHandle& Handle : handles) { @@ -338,8 +347,17 @@ void UAFAbilityComponent::ClientExpireEffect_Implementation(FAFPredictionHandle } void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, - const FGAEffectContext& InContext) + const FGAEffectContext& InContext, const FGAEffectHandle& InHandle) { + { + FAFEffectRepInfo* RepInfo = GameEffectContainer.GetReplicationInfo(InHandle); + if (RepInfo && + (RepInfo->Type == ERepInfoType::LocallyPredicted + || RepInfo->Type == ERepInfoType::Server)) + { + RepInfo->OnExpired(); + } + } //if (GetOwnerRole() == ENetRole::ROLE_Authority // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) { @@ -369,6 +387,7 @@ void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProper MulticastRemoveEffectCue(CueParams); } } + TArray handles = GameEffectContainer.RemoveEffect(InProperty); for(const FGAEffectHandle& Handle : handles) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index bca3f82..7130e2c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -459,7 +459,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); /* RemoveEffect is used to remove effect by force. */ - void RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); + void RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); const TSet& GetAllEffectsHandles() const diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index f117ce3..20354f0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -4,9 +4,9 @@ #include "Effects/GAEffectCue.h" #include "AFCueSet.h" #include "AFCueManager.h" -#if WITH_EDITOR -#include "Editor.H" -#endif +//#if WITH_EDITOR +//#include "Editor.H" +//#endif UAFCueManager* UAFCueManager::ManagerInstance = nullptr; //UWorld* UAFCueManager::CurrentWorld = nullptr; @@ -27,9 +27,9 @@ UAFCueManager* UAFCueManager::Get() } void UAFCueManager::Initialize() { -#if WITH_EDITOR - FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); -#endif //WITH_EDITOR +#if WITH_EDITORONLY_DATA +// FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); +#endif //WITH_EDITORONLY_DATA FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index e575c37..d592747 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -273,7 +273,7 @@ void UGAAbilityBase::OnCooldownEffectExpired() if (CooldownEffectHandle.IsValid()) { - CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); + //CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); } } /* Functions for activation effect delegates */ @@ -317,7 +317,7 @@ void UGAAbilityBase::NativeFinishAbility() OnConfirmDelegate.RemoveAll(this); //if (ActivationEffect.Handle.IsValid()) { - AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext); + AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); } //remove effect. } @@ -331,7 +331,7 @@ void UGAAbilityBase::NativeCancelActivation() UAFAbilityComponent* AttrComp = ActivationEffect.Handle.GetContext().InstigatorComp.Get(); if (AbilityComponent) { - AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext); + AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); } } @@ -377,7 +377,7 @@ bool UGAAbilityBase::ApplyCooldownEffect() } void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) { - AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); + //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); OnCooldownEnd(InHandle); } void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index 47e74e2..c2f543d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -65,10 +65,10 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) // ... add any modules that your module loads dynamically here ... } ); - if (Target.Type == TargetRules.TargetType.Editor) - { - PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); - } + //if (Target.Type == TargetRules.TargetType.Editor) + //{ + // PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); + //} } } } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp index 78b0df8..3360292 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp @@ -189,6 +189,9 @@ FAFEffectTimeHandle FAFEffectTimerManager::AddTimer(double InDuration, double In void FAbilityFramework::StartupModule() { +#if WITH_EDITOR + //FModuleManager::Get().LoadModule(TEXT("AbilityFrameworkEditor")); +#endif //WITH_EDITOR //FAFEffectTimerManager::Get(); // This code will execute after your module is loaded into memory (but after global variables are initialized, of course.) } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index e8cc419..284edee 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -115,8 +115,13 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, effect->PredictionHandle = Ability->GetPredictionHandle(); } } - - return Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); + FGAEffectHandle Handle = Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); + if (InEffect.Duration > 0 || InEffect.Period > 0) + { + InEffect.AddHandle(Context.Target.Get(), Handle); + } + + return Handle; } FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, class UObject* Target, class APawn* Instigator, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index cb650e3..f6d5bf7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -47,10 +47,8 @@ FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, floa void FAFEffectRepInfo::Init() { FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnExpired); - Timer.SetTimer(ExpiredHandle, delDuration, - Duration, false); + ENetRole role = OwningComoponent->GetOwnerRole(); + ENetMode mode = OwningComoponent->GetOwner()->GetNetMode(); FTimerDelegate PeriodDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnPeriod); Timer.SetTimer(PeriodHandle, PeriodDuration, @@ -60,6 +58,18 @@ void FAFEffectRepInfo::OnExpired() { UE_LOG(AbilityFramework, Log, TEXT("Client FAFEffectRepInfo. OnExpired")); OwningComoponent->ExecuteEffectEvent(OnExpiredEvent); + + FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnExpired ")); + EffectInfoLog += EffectTag.ToString(); + AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); + FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); + Timer.ClearTimer(ExpiredHandle); + Timer.ClearTimer(PeriodHandle); + OwningComoponent->ExecuteEffectEvent(OnRemovedEvent); + + OwningComoponent->RemoveEffectEvent(OnExpiredEvent); + OwningComoponent->RemoveEffectEvent(OnPeriodEvent); + OwningComoponent->RemoveEffectEvent(OnRemovedEvent); } void FAFEffectRepInfo::OnPeriod() { @@ -73,6 +83,8 @@ void FAFEffectRepInfo::OnRemoved() FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); + OwningComoponent->ExecuteEffectEvent(OnRemovedEvent); + OwningComoponent->RemoveEffectEvent(OnExpiredEvent); OwningComoponent->RemoveEffectEvent(OnPeriodEvent); OwningComoponent->RemoveEffectEvent(OnRemovedEvent); @@ -85,6 +97,8 @@ void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InAr FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); + OwningComoponent->ExecuteEffectEvent(OnRemovedEvent); + OwningComoponent->RemoveEffectEvent(OnExpiredEvent); OwningComoponent->RemoveEffectEvent(OnPeriodEvent); OwningComoponent->RemoveEffectEvent(OnRemovedEvent); @@ -93,14 +107,12 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra { if (PredictionHandle.IsValid() && InArraySerializer.PredictedEffectInfos.Contains(PredictionHandle)) { + //remove predicted effect and move on. FGAEffectContainer& cont = const_cast(InArraySerializer); auto RemovePredicate = [&](const FAFEffectRepInfo& EmitterHandle) { return EmitterHandle.Handle == Handle; }; //cont.ActiveEffectInfos.Remove(*this); cont.ActiveEffectInfos.RemoveAll(RemovePredicate); return; - //remove replicated rep info ? - //keep client side handle. - //possibly override client predicted repinfo with informations from server. } else { @@ -109,6 +121,7 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra OwningComoponent = InArraySerializer.OwningComponent; InArraySerializer.EffectInfos.Add(Handle, this); InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); + Type = ERepInfoType::RemotePredicted; //OwningComoponent->ExecuteEffectEvent(OnAppliedEvent); @@ -463,6 +476,15 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c //add replication handle (and send it to server ?) const UWorld* World = OwningComponent->GetWorld(); FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); + if(bIsServer) + { + RepInfo->Type = ERepInfoType::Server; + } + else + { + RepInfo->Type = ERepInfoType::LocallyPredicted; + } + RepInfo->Spec = InProperty.GetClass(); RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; @@ -543,10 +565,7 @@ void FGAEffectContainer::AddEffect(FGAEffectProperty& InProperty, const FGAEffec FObjectKey key(InProperty.GetClass()); TArray& handles = EffectByClass.FindOrAdd(key); handles.Add(HandleIn); - if(EffectByClass.Num() == 0) - { - int asasd = 0; - } + if (bInfinite) { InfiniteEffects.Add(HandleIn); @@ -610,6 +629,9 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn , const FGAEffectProperty& InProperty) { RemoveFromAttribute(HandleIn); + + const_cast(InProperty).RemoveHandle(HandleIn); + ActiveEffectHandles.Remove(HandleIn); InfiniteEffects.Remove(HandleIn); TArray* handles = EffectByClass.Find(FObjectKey(InProperty.GetClass())); @@ -629,7 +651,6 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn EffectInfoLog += Out->EffectTag.ToString(); AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); MarkItemDirty(*Out); - Out->OnRemoved(); ActiveEffectInfos.Remove(*Out); MarkArrayDirty(); delete Out; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 66d4688..509b817 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -357,7 +357,12 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. */ - TMap Handles; +protected: + //possibly multiple handles per target ? + TMap Handles; + TMap HandleToTarget; + TMap Contexts; +public: FGAEffectProperty() : ApplicationRequirement(nullptr), Application(nullptr), @@ -389,6 +394,43 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty void Initialize(); void InitializeIfNotInitialized(); + + void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) + { + FObjectKey key(Target); + Handles.Add(key, InHandle); + HandleToTarget.Add(InHandle, Target); + } + + void RemoveHandle(const FGAEffectHandle& InHandle) + { + UObject* Target = nullptr; + HandleToTarget.RemoveAndCopyValue(InHandle, Target); + if(Target) + { + FObjectKey key(Target); + Handles.Remove(key); + Contexts.Remove(InHandle); + } + } + + FGAEffectHandle FindTargetEffect(UObject* Target) + { + FObjectKey key(Target); + if (FGAEffectHandle* handle = Handles.Find(key)) + return *handle; + + return FGAEffectHandle(); + } + + FGAEffectHandle FindTargetEffect(UObject* Target) const + { + FObjectKey key(Target); + if (const FGAEffectHandle* handle = Handles.Find(key)) + return *handle; + + return FGAEffectHandle(); + } void SetPredictionHandle(const FAFPredictionHandle& InHandle) { PredictionHandle = InHandle; @@ -591,13 +633,25 @@ struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer /* Simplified and minimal version of game effect replicated back to clients. */ - +UENUM() +enum class ERepInfoType : uint8 +{ + LocallyPredicted, + RemotePredicted, + Server +}; USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem { GENERATED_USTRUCT_BODY() public: + UPROPERTY() + ERepInfoType Type; + + UPROPERTY() + TSubclassOf Spec; + //tags are generally unique per effect type. UPROPERTY() FGameplayTag EffectTag; @@ -616,6 +670,8 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem float Duration; UPROPERTY() float ReplicationTime; + UPROPERTY() + float LastPeriodTime; UPROPERTY() FGameplayTag OnExpiredEvent; @@ -628,6 +684,11 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem FTimerHandle PeriodHandle; class UAFAbilityComponent* OwningComoponent; + UGAGameEffectSpec* GetSpec() const + { + return Spec.GetDefaultObject(); + } + //UPROPERTY() // FGAEffectContext Context; @@ -640,6 +701,13 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); + float GetPeriodTime(float InWorldTime) + { + if (InWorldTime > (LastPeriodTime + PeriodTime)) + LastPeriodTime = InWorldTime; + return InWorldTime - LastPeriodTime; + } + float GetRemainingTime(float InWorldTime) const { return Duration - (InWorldTime - AppliedTime); @@ -835,6 +903,11 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer UWorld* GetWorld() const; + FAFEffectRepInfo* GetReplicationInfo(const FGAEffectHandle& InHandle) + { + return EffectInfos.FindRef(InHandle); + } + ///Helpers float GetRemainingTime(const FGAEffectHandle& InHandle) const { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp index b4beef4..7ab732b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp @@ -1076,7 +1076,7 @@ class GameEffectsTestSuite float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); TestEqual("Source Stamina Finished: ", FinishedVal, 150.0f); FGAEffectContext Context = UGABlueprintLibrary::MakeContext(DestActor, SourceActor, DestActor, SourceActor, FHitResult(ForceInit)); - DestComponent->RemoveEffect(Effect, Context); + //DestComponent->RemoveEffect(Effect, Context); float PostRemovedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); TestEqual("Source Stamina Finished: ", PostRemovedVal, 100.0f); } diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp index ca4698b..3493cac 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp @@ -301,19 +301,19 @@ UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* In if (AbilityBP == NULL) { const UEdGraphSchema_K2* K2Schema = GetDefault(); - +#if WITH_EDITORONLY_DATA // Only allow a gameplay ability graph if there isn't one in a parent blueprint UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAAbilityGraph::StaticClass(), UGAAbilityGraphSchema::StaticClass()); -#if WITH_EDITORONLY_DATA + if (NewBP->UbergraphPages.Num()) { FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); } -#endif + FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); NewBP->LastEditedDocuments.Add(NewGraph); NewGraph->bAllowDeletion = false; - +#endif UBlueprintEditorSettings* Settings = GetMutableDefault(); if(Settings && Settings->bSpawnDefaultBlueprintNodes) { diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp index 77cc91b..1bd6caf 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp @@ -76,7 +76,10 @@ void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequenc /** IModuleInterface implementation */ void FAbilityFrameworkEditor::StartupModule() { - BlueprintEditorTabBinding = MakeShared(); + if(GEditor) + BlueprintEditorTabBinding = MakeShared(); + + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); PropertyModule.RegisterCustomPropertyTypeLayout("GAAttribute", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAAttributeDetailCustomization::MakeInstance)); diff --git a/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin b/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin new file mode 100644 index 0000000..520ef96 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin @@ -0,0 +1,37 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "AbilityFrameworkDebugger", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "AbilityFrameworkDebugger", + "Type": "Developer", + "LoadingPhase": "Default" + } + ], + "Plugins": [ + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "AbilityManager", + "Enabled": true + }, + { + "Name": "DraggableWindow", + "Enabled": true + } + ] +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp index 7d07745..50a1ca6 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp @@ -45,7 +45,11 @@ void SAFDEffects::InitializeEffects() { TSharedPtr Row = MakeShareable(new FAFDEffectRow); Row->Handle = RepInfo.Handle; + Row->RepInfo = const_cast(&RepInfo); + Row->AbilityComponent = AbilityComponent; Row->EffectClassName = RepInfo.Handle.GetEffectSpec()->GetName(); + Row->TimeRemaining = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetTimeRemaining)); + Row->PeriodTime = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetPeriodTime)); Effects.Add(Row); } //ListView->RebuildList(); @@ -59,12 +63,26 @@ TSharedRef SAFDEffects::GenerateListRow(TSharedPtr Eff [ SNew(SGridPanel) .FillColumn(0, 1) + /*.FillColumn(1,1) + .FillColumn(2,1)*/ + SGridPanel::Slot(0, 0) .HAlign(EHorizontalAlignment::HAlign_Fill) [ SNew(STextBlock) .Text(FText::FromString(EffectRow->EffectClassName)) ] + + SGridPanel::Slot(1, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(EffectRow->TimeRemaining) + ] + + SGridPanel::Slot(2, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(EffectRow->PeriodTime) + ] ]; } @@ -72,9 +90,14 @@ void SAFDEffects::OnEffectApplied(FGAEffectHandle InHandle) { TSharedPtr Row = MakeShareable(new FAFDEffectRow); Row->Handle = InHandle; + Row->RepInfo = AbilityComponent->GameEffectContainer.GetReplicationInfo(InHandle); + Row->AbilityComponent = AbilityComponent; Row->EffectClassName = InHandle.GetEffectSpec()->GetName(); + Row->TimeRemaining = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetTimeRemaining)); + Row->PeriodTime = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetPeriodTime)); UE_LOG(LogTemp, Warning, TEXT("SAFDEffects::OnEffectAppliede")); Effects.Add(Row); + ListView->RebuildList(); } void SAFDEffects::OnEffectRemoved(FGAEffectHandle InHandle) diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h index 7843397..9ebe342 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h @@ -5,13 +5,31 @@ #include "CoreMinimal.h" #include "Widgets/SCompoundWidget.h" +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" #include "AFAbilityInterface.h" #include "AFAbilityComponent.h" -struct FAFDEffectRow +struct FAFDEffectRow : public TSharedFromThis { FString EffectClassName; FGAEffectHandle Handle; + FAFEffectRepInfo* RepInfo; + TAttribute TimeRemaining; + TAttribute PeriodTime; + TWeakObjectPtr AbilityComponent; + + FText GetTimeRemaining() const + { + //return FText::AsNumber(0); + return FText::AsNumber(AbilityComponent->GameEffectContainer.GetRemainingTime(Handle)); + } + + FText GetPeriodTime() const + { + //return FText::AsNumber(0); + return FText::AsNumber(RepInfo->GetPeriodTime(static_cast(FPlatformTime::Seconds()))); + } const bool operator==(const FAFDEffectRow& Other) const { diff --git a/Plugins/AbilityManager/AbilityManager.uplugin b/Plugins/AbilityManager/AbilityManager.uplugin new file mode 100644 index 0000000..6915221 --- /dev/null +++ b/Plugins/AbilityManager/AbilityManager.uplugin @@ -0,0 +1,29 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "AbilityManager", + "Description": "Manages input and UI for abilities. Sample implementation with most common functionality.", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "AbilityManager", + "Type": "Runtime", + "LoadingPhase": "Default" + } + ], + "Plugins": [ + { + "Name": "AbilityFramework", + "Enabled": true + } + ] +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/DraggableWindow.uplugin b/Plugins/DraggableWindow/DraggableWindow.uplugin new file mode 100644 index 0000000..3b1b4c9 --- /dev/null +++ b/Plugins/DraggableWindow/DraggableWindow.uplugin @@ -0,0 +1,23 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "DraggableWindow", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "DraggableWindow", + "Type": "Developer", + "LoadingPhase": "Default" + } + ] +} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/ARGameMode.cpp index 8b19f70..264ae10 100644 --- a/Source/ActionRPGGame/ARGameMode.cpp +++ b/Source/ActionRPGGame/ARGameMode.cpp @@ -8,7 +8,7 @@ #include "Abilities/ARAbilityBase.h" //#include "IpConnec" //#include "OnlineSubsystemUtils/IpConnection.h" -#include "IPAddress.h" +//#include "IPAddress.h" #include "SDraggableWindowWidget.h" AARGameMode::AARGameMode() { @@ -20,11 +20,11 @@ void AARGameMode::BeginPlay() { if (UNetConnection* Conn = GetNetConnection()) { - UE_LOG(LogTemp, Warning, TEXT("Your message, %s \n"), *FString::FromInt(Conn->GetAddrAsInt())); + // UE_LOG(LogTemp, Warning, TEXT("Your message, %s \n"), *FString::FromInt(Conn->GetAddrAsInt())); } } - TSharedPtr desktop = SNew(SDraggableDesktopWidget); - GEngine->GameViewport->AddViewportWidgetContent(desktop.ToSharedRef()); + //TSharedPtr desktop = SNew(SDraggableDesktopWidget); + //GEngine->GameViewport->AddViewportWidgetContent(desktop.ToSharedRef()); //TSharedPtr window = SNew(SDraggableWindowWidget); //GEngine->GameViewport->AddViewportWidgetContent(window.ToSharedRef()); diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 6c4d72f..8a44f10 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -55,5 +55,10 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AbilityManager", "DraggableWindow" }); - } + if (Target.Type == TargetRules.TargetType.Editor) + { + PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" }); + PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); + } + } } diff --git a/Source/ActionRPGGame/ActionRPGGame.cpp b/Source/ActionRPGGame/ActionRPGGame.cpp index de18043..c2b4241 100644 --- a/Source/ActionRPGGame/ActionRPGGame.cpp +++ b/Source/ActionRPGGame/ActionRPGGame.cpp @@ -5,6 +5,9 @@ #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "Abilities/GAAbilityBase.h" +#if WITH_EDITOR +#include "IAbilityFrameworkEditor.h" +#endif void FActionRPGGameModule::StartupModule() { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); @@ -19,6 +22,10 @@ void FActionRPGGameModule::StartupModule() { Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); } +#if WITH_EDITOR + FModuleManager::Get().LoadModule(TEXT("AbilityFrameworkEditor")); + //FModuleManager::LoadModuleChecked(TEXT("AbilityFrameworkEditor")); +#endif //WITH_EDITOR }; IMPLEMENT_PRIMARY_GAME_MODULE(FActionRPGGameModule, ActionRPGGame, "ActionRPGGame"); \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index fef4e90..35fccaf 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -14,7 +14,7 @@ UARUIAbilityManagerComponent::UARUIAbilityManagerComponent() { // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; + PrimaryComponentTick.bCanEverTick = false; // ... } @@ -23,6 +23,7 @@ UARUIAbilityManagerComponent::UARUIAbilityManagerComponent() // Called when the game starts void UARUIAbilityManagerComponent::BeginPlay() { + Super::BeginPlay(); //initiazile Model (hhueheu). AbilitySet.SetNum(2); AbilitySet[0].SetNum(6); @@ -80,7 +81,7 @@ void UARUIAbilityManagerComponent::BeginPlay() { AbilityComp->BP_BindAbilityToAction(Tag); } - Super::BeginPlay(); + } diff --git a/Source/ActionRPGGameEditor.Target.cs b/Source/ActionRPGGameEditor.Target.cs index 6bd6d2e..8a3d1a2 100644 --- a/Source/ActionRPGGameEditor.Target.cs +++ b/Source/ActionRPGGameEditor.Target.cs @@ -9,5 +9,6 @@ public ActionRPGGameEditorTarget(TargetInfo Target) : base(Target) { Type = TargetType.Editor; ExtraModuleNames.Add("ActionRPGGame"); - } + ExtraModuleNames.Add("ActionRPGGameEditor"); + } } diff --git a/Source/ActionRPGGameEditor/ActionRPGGameEditor.Build.cs b/Source/ActionRPGGameEditor/ActionRPGGameEditor.Build.cs new file mode 100644 index 0000000..7075209 --- /dev/null +++ b/Source/ActionRPGGameEditor/ActionRPGGameEditor.Build.cs @@ -0,0 +1,37 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class ActionRPGGameEditor : ModuleRules +{ + public ActionRPGGameEditor(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; + PublicIncludePaths.AddRange( + new string[] { + // ... add public include paths required here ... + } + ); + + PrivateIncludePaths.AddRange( + new string[] { + // ... add other private include paths required here ... + } + ); + PublicDependencyModuleNames.AddRange(new string[] { + "Core", + "CoreUObject", + "Engine", + "InputCore", + "Slate", + "SlateCore", + "UMG", + "GameplayTags", + "AbilityFramework", + "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" + }); + + PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); + + } +} diff --git a/Source/ActionRPGGameEditor/ActionRPGGameEditor.cpp b/Source/ActionRPGGameEditor/ActionRPGGameEditor.cpp new file mode 100644 index 0000000..0526ce7 --- /dev/null +++ b/Source/ActionRPGGameEditor/ActionRPGGameEditor.cpp @@ -0,0 +1,14 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "ActionRPGGameEditor.h" +#include "Modules/ModuleManager.h" +#include "Misc/CommandLine.h" +#include "IAbilityFrameworkEditor.h" + +void FActionRPGGameEditorModule::StartupModule() +{ + //FModuleManager::Get().LoadModule("Kismet"); + FModuleManager::LoadModuleChecked(TEXT("AbilityFrameworkEditor")); +}; +IMPLEMENT_PRIMARY_GAME_MODULE(FActionRPGGameEditorModule, ActionRPGGameEditor, "ActionRPGGameEditor"); + \ No newline at end of file diff --git a/Source/ActionRPGGameEditor/ActionRPGGameEditor.h b/Source/ActionRPGGameEditor/ActionRPGGameEditor.h new file mode 100644 index 0000000..aa288ee --- /dev/null +++ b/Source/ActionRPGGameEditor/ActionRPGGameEditor.h @@ -0,0 +1,9 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +class FActionRPGGameEditorModule : public FDefaultGameModuleImpl +{ + virtual void StartupModule() override; +}; \ No newline at end of file From f4a086c4b88b74f667468e8d82773fe61fedabf1 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 30 Dec 2017 02:37:10 +0100 Subject: [PATCH 022/187] improvements to debugger and draggable window --- .../AbilityFramework/AFAbilityComponent.cpp | 11 + .../AbilityFramework/AFAbilityComponent.h | 4 + .../AbilityFramework/Effects/GAGameEffect.cpp | 44 +-- .../AbilityFramework/Effects/GAGameEffect.h | 19 +- .../Source/AbilityFramework/GAGlobalTypes.h | 2 + .../AbilityFrameworkDebugger.uplugin | 2 +- .../AbilityFrameworkDebugger/AFDManager.cpp | 19 +- .../AbilityFrameworkDebugger/AFDManager.h | 8 +- .../AbilityFrameworkDebugger.Build.cs | 6 +- .../AbilityFrameworkDebugger.cpp | 15 +- .../AbilityFrameworkDebugger.h | 4 + .../SAFDDesktopWidget.cpp | 4 +- Plugins/AbilityManager/AbilityManager.uplugin | 5 + .../AMAbilityManagerComponent.cpp | 20 -- .../AMAbilityManagerComponent.h | 3 +- .../AMAbilityInputProperty.cpp | 36 +++ .../AMAbilityInputProperty.h | 18 ++ .../AbilityManagerEditor.Build.cs | 60 ++++ .../AbilityManagerEditor.cpp | 20 ++ .../AbilityManagerEditor.h | 15 + .../DraggableWindow/DWBPFunctionLibrary.cpp | 14 + .../DraggableWindow/DWBPFunctionLibrary.h | 26 ++ .../Source/DraggableWindow/DWManager.cpp | 74 +++++ .../Source/DraggableWindow/DWManager.h | 35 +++ .../Source/DraggableWindow/DWTypes.cpp | 3 + .../Source/DraggableWindow/DWTypes.h | 41 +++ .../DraggableWindow/DraggableWindow.Build.cs | 6 +- .../DraggableWindow/DraggableWindow.cpp | 17 +- .../Source/DraggableWindow/DraggableWindow.h | 6 + .../SDraggableWindowWidget.cpp | 275 ++++++++++++++---- .../DraggableWindow/SDraggableWindowWidget.h | 63 ++-- Source/ActionRPGGame/ARCharacter.cpp | 8 +- Source/ActionRPGGame/ARCharacter.h | 2 +- Source/ActionRPGGame/ARPlayerController.cpp | 4 +- .../Abilities/ARUIAbilityManagerComponent.cpp | 15 - .../Weapons/ARWeaponManagerComponent.cpp | 4 +- 36 files changed, 740 insertions(+), 168 deletions(-) create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index da00098..32c7493 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -806,6 +806,13 @@ void UAFAbilityComponent::UninitializeComponent() //EffectTimerManager.Reset(); //GameEffectContainer } +void UAFAbilityComponent::BindInputs(class UInputComponent* InputComponent) +{ + for (const FGameplayTag& Tag : AbilityInputs) + { + BindAbilityToAction(InputComponent, Tag); + } +} void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InInput, bool bBlock) { AbilityContainer.SetBlockedInput(InInput, bBlock); @@ -813,10 +820,14 @@ void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InInput, bool bBlo void UAFAbilityComponent::BP_BindAbilityToAction(FGameplayTag ActionName) { UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + check(InputComponent); + BindAbilityToAction(InputComponent, ActionName); } void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName) { + check(InputComponent); + if (!InputComponent) return; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 7130e2c..67466a2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -271,6 +271,9 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UPROPERTY(EditAnywhere, Category = "Config") FGAAttribute DeathAttribute; + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray AbilityInputs; + UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer DefaultTags; @@ -793,6 +796,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, //TSharedPtr AbilityLoadedHandle; void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId); void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); + void BindInputs(class UInputComponent* InputComponent); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") void BP_BindAbilityToAction(FGameplayTag ActionName); void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index f6d5bf7..863d9ab 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -57,37 +57,37 @@ void FAFEffectRepInfo::Init() void FAFEffectRepInfo::OnExpired() { UE_LOG(AbilityFramework, Log, TEXT("Client FAFEffectRepInfo. OnExpired")); - OwningComoponent->ExecuteEffectEvent(OnExpiredEvent); + OwningComoponent->ExecuteEffectEvent(GetSpec()->OnExpiredEvent); FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnExpired ")); - EffectInfoLog += EffectTag.ToString(); + EffectInfoLog += GetEffectTag().ToString(); AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); - OwningComoponent->ExecuteEffectEvent(OnRemovedEvent); + OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); - OwningComoponent->RemoveEffectEvent(OnExpiredEvent); - OwningComoponent->RemoveEffectEvent(OnPeriodEvent); - OwningComoponent->RemoveEffectEvent(OnRemovedEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnRemovedEvent); } void FAFEffectRepInfo::OnPeriod() { - OwningComoponent->ExecuteEffectEvent(OnPeriodEvent); + OwningComoponent->ExecuteEffectEvent(GetSpec()->OnPeriodEvent); } void FAFEffectRepInfo::OnRemoved() { FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnRemoved ")); - EffectInfoLog += EffectTag.ToString(); + EffectInfoLog += GetEffectTag().ToString(); AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); - OwningComoponent->ExecuteEffectEvent(OnRemovedEvent); + OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); - OwningComoponent->RemoveEffectEvent(OnExpiredEvent); - OwningComoponent->RemoveEffectEvent(OnPeriodEvent); - OwningComoponent->RemoveEffectEvent(OnRemovedEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnRemovedEvent); } void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) @@ -97,11 +97,13 @@ void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InAr FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); - OwningComoponent->ExecuteEffectEvent(OnRemovedEvent); + OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); - OwningComoponent->RemoveEffectEvent(OnExpiredEvent); - OwningComoponent->RemoveEffectEvent(OnPeriodEvent); - OwningComoponent->RemoveEffectEvent(OnRemovedEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); + OwningComoponent->RemoveEffectEvent(GetSpec()->OnRemovedEvent); + + OwningComoponent->OnEffectRemoved.Broadcast(Handle); } void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) { @@ -119,6 +121,7 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra //remove predicted effect. } OwningComoponent = InArraySerializer.OwningComponent; + AppliedTime = OwningComoponent->GetWorld()->GetTimeSeconds(); InArraySerializer.EffectInfos.Add(Handle, this); InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); Type = ERepInfoType::RemotePredicted; @@ -134,6 +137,8 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra FTimerDelegate PeriodDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnPeriod); Timer.SetTimer(PeriodHandle, PeriodDuration, PeriodTime, true); + Handle.EffectPtr = MakeShareable(new FGAEffect(Spec.GetDefaultObject(), Context)); + OwningComoponent->OnEffectAppliedToTarget.Broadcast(Handle); } void FAFEffectRepInfo::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) @@ -485,12 +490,9 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c RepInfo->Type = ERepInfoType::LocallyPredicted; } RepInfo->Spec = InProperty.GetClass(); - RepInfo->OnExpiredEvent = InProperty.GetSpec()->OnExpiredEvent; - RepInfo->OnPeriodEvent = InProperty.GetSpec()->OnPeriodEvent; - RepInfo->OnRemovedEvent = InProperty.GetSpec()->OnRemovedEvent; + RepInfo->Context = InHandle.GetContext(); RepInfo->Handle = InHandle; RepInfo->PredictionHandle = InProperty.PredictionHandle; - RepInfo->EffectTag = InProperty.GetSpec()->EffectTag; RepInfo->Init(); MarkItemDirty(*RepInfo); ActiveEffectInfos.Add(*RepInfo); @@ -648,7 +650,7 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn if (Out) { FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); - EffectInfoLog += Out->EffectTag.ToString(); + EffectInfoLog += Out->GetEffectTag().ToString(); AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); MarkItemDirty(*Out); ActiveEffectInfos.Remove(*Out); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 509b817..9f82703 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -652,9 +652,9 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem UPROPERTY() TSubclassOf Spec; - //tags are generally unique per effect type. UPROPERTY() - FGameplayTag EffectTag; + FGAEffectContext Context; + //Handle to effect, which is using this info. UPROPERTY() FGAEffectHandle Handle; @@ -662,7 +662,7 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem UPROPERTY() FAFPredictionHandle PredictionHandle; - UPROPERTY() + UPROPERTY(NotReplicated) float AppliedTime; UPROPERTY() float PeriodTime; @@ -670,15 +670,9 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem float Duration; UPROPERTY() float ReplicationTime; - UPROPERTY() + UPROPERTY(NotReplicated) float LastPeriodTime; - UPROPERTY() - FGameplayTag OnExpiredEvent; - UPROPERTY() - FGameplayTag OnPeriodEvent; - UPROPERTY() - FGameplayTag OnRemovedEvent; FTimerHandle ExpiredHandle; FTimerHandle PeriodHandle; @@ -701,6 +695,11 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); + FGameplayTag GetEffectTag() + { + return GetSpec()->EffectTag; + } + float GetPeriodTime(float InWorldTime) { if (InWorldTime > (LastPeriodTime + PeriodTime)) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 187a13b..8264e31 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -304,6 +304,8 @@ USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectHandle { GENERATED_BODY() +public: + friend struct FAFEffectRepInfo; protected: //just to be safe we don't run out of numbers.. UPROPERTY() diff --git a/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin b/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin index 520ef96..b3a3879 100644 --- a/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin +++ b/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin @@ -16,7 +16,7 @@ "Modules": [ { "Name": "AbilityFrameworkDebugger", - "Type": "Developer", + "Type": "Runtime", "LoadingPhase": "Default" } ], diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp index 2ba3971..3ef1ce4 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp @@ -6,6 +6,7 @@ #include "Engine/GameViewportClient.h" #include "Slate.h" #include "SlateCore.h" +#include "DWManager.h" FAFDManager* FAFDManager::Instance = nullptr; @@ -21,12 +22,20 @@ void FAFDManager::Init() { Dekstop = SNew(SAFDDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); GEngine->GameViewport->AddViewportWidgetContent(Dekstop.ToSharedRef()); +} - WindowDesktop = SNew(SDraggableDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); - GEngine->GameViewport->AddViewportWidgetContent(WindowDesktop.ToSharedRef()); +FDWWWindowHandle FAFDManager::AddDebugWindow(TSharedPtr InWindowContent) +{ + return FDWManager::Get().CreateWindow(InWindowContent); } -FDWWWindowHandle FAFDManager::AddNewWindow(TSharedPtr InWindow) +#if WITH_EDITORONLY_DATA +void FAFDManager::PIEDestroy() { - return WindowDesktop->AddWindow(InWindow); -} \ No newline at end of file + if (Instance) + { + delete Instance; + Instance = nullptr; + } +} +#endif \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h index 90a0d43..c309907 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h @@ -12,7 +12,6 @@ class ABILITYFRAMEWORKDEBUGGER_API FAFDManager private: static FAFDManager* Instance; TSharedPtr Dekstop; - TSharedPtr WindowDesktop; protected: void Init(); public: @@ -27,7 +26,12 @@ class ABILITYFRAMEWORKDEBUGGER_API FAFDManager return*Instance; } - FDWWWindowHandle AddNewWindow(TSharedPtr InWindow); +#if WITH_EDITORONLY_DATA + static void PIEDestroy(); +#endif + + + FDWWWindowHandle AddDebugWindow(TSharedPtr InWindowContent); FAFDManager(); ~FAFDManager(); diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs index 14db1b5..5d1bd03 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs @@ -58,5 +58,9 @@ public AbilityFrameworkDebugger(ReadOnlyTargetRules Target) : base(Target) // ... add any modules that your module loads dynamically here ... } ); - } + if (Target.Type == TargetRules.TargetType.Editor) + { + PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); + } + } } diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp index 6a252ba..e0ac611 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp @@ -3,7 +3,9 @@ #include "AbilityFrameworkDebugger.h" #include "HAL/IConsoleManager.h" #include "AFDManager.h" - +#if WITH_EDITORONLY_DATA +#include "Editor.H" +#endif #define LOCTEXT_NAMESPACE "FAbilityFrameworkDebuggerModule" void FAbilityFrameworkDebuggerModule::StartupModule() @@ -15,6 +17,10 @@ void FAbilityFrameworkDebuggerModule::StartupModule() FConsoleCommandDelegate::CreateStatic(OpenAbilityDebugger), ECVF_Default ); + +#if WITH_EDITORONLY_DATA + FEditorDelegates::EndPIE.AddRaw(this, &FAbilityFrameworkDebuggerModule::HandlePIEEnd); +#endif //WITH_EDITORONLY_DATA } void FAbilityFrameworkDebuggerModule::ShutdownModule() @@ -28,7 +34,12 @@ void FAbilityFrameworkDebuggerModule::OpenAbilityDebugger() { FAFDManager::Get(); } - +#if WITH_EDITORONLY_DATA +void FAbilityFrameworkDebuggerModule::HandlePIEEnd(bool InVal) +{ + FAFDManager::PIEDestroy(); +} +#endif #undef LOCTEXT_NAMESPACE IMPLEMENT_MODULE(FAbilityFrameworkDebuggerModule, AbilityFrameworkDebugger) \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h index 34de4ca..d50fefe 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h @@ -15,4 +15,8 @@ class FAbilityFrameworkDebuggerModule : public IModuleInterface /** IModuleInterface implementation */ virtual void StartupModule() override; virtual void ShutdownModule() override; + +#if WITH_EDITORONLY_DATA + void HandlePIEEnd(bool InVal); +#endif }; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp index 8b02163..d2091b4 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp @@ -196,10 +196,8 @@ END_SLATE_FUNCTION_BUILD_OPTIMIZATION FReply SAFDDesktopWidget::OnNewDebugWindowClicked() { - TSharedPtr window = SNew(SDraggableWindowWidget); - FDWWWindowHandle Handle = FAFDManager::Get().AddNewWindow(window); TSharedPtr wid = SNew(SAFDMainWidget); - window->AddContent(wid); + FDWWWindowHandle Handle = FAFDManager::Get().AddDebugWindow(wid); wid->SetWindowHandle(Handle); return FReply::Handled(); } \ No newline at end of file diff --git a/Plugins/AbilityManager/AbilityManager.uplugin b/Plugins/AbilityManager/AbilityManager.uplugin index 6915221..bfa155d 100644 --- a/Plugins/AbilityManager/AbilityManager.uplugin +++ b/Plugins/AbilityManager/AbilityManager.uplugin @@ -18,6 +18,11 @@ "Name": "AbilityManager", "Type": "Runtime", "LoadingPhase": "Default" + }, + { + "Name": "AbilityManagerEditor", + "Type": "Editor", + "LoadingPhase": "Default" } ], "Plugins": [ diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 003e5dc..3fde467 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -42,26 +42,6 @@ void UAMAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickT // ... } -void UAMAbilityManagerComponent::BindInputs() -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - for (const FGameplayTag& Tag : InputsToBind) - { - AbilityComp->BP_BindAbilityToAction(Tag); - } -} - UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) { return AbilitySet.Num() >= MaxGroups ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index 899d85d..fd4ee30 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -76,6 +76,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent UPROPERTY(EditAnywhere) uint8 MaxGroups; + //Map input bindings to particular slot and group. UPROPERTY(EditAnywhere) FAMAbilityInputContainer InputSetup; @@ -99,7 +100,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - void BindInputs(); + UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp new file mode 100644 index 0000000..f87f7b0 --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp @@ -0,0 +1,36 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "AMAbilityInputProperty.h" +#include "AbilityManagerEditor.h" +#include "IDetailsView.h" +#include "PropertyEditorModule.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" +#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" +#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" +#include "Editor/PropertyEditor/Private/SDetailsView.h" +//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h +#include "STextCombobox.h" +#include "STreeView.h" +#include "SButton.h" +#include "STextBlock.h" + +#include "EditorClassUtils.h" + + +TSharedRef FAMAbilityInputProperty::MakeInstance() +{ + return MakeShareable(new FAMAbilityInputProperty); +} + +FAMAbilityInputProperty::~FAMAbilityInputProperty() +{ + +} + +void FAMAbilityInputProperty::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} +void FAMAbilityInputProperty::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h new file mode 100644 index 0000000..c31729d --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h @@ -0,0 +1,18 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FAMAbilityInputProperty : public IPropertyTypeCustomization +{ +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FAMAbilityInputProperty(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; +}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs new file mode 100644 index 0000000..c61e045 --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs @@ -0,0 +1,60 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class AbilityManagerEditor : ModuleRules +{ + public AbilityManagerEditor(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "AbilityManagerEditor/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "AbilityManagerEditor/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "UnrealEd", + "PropertyEditor", + "GameplayTags", + "GameplayTasks", + "AbilityFramework", + "AbilityManager" + // ... add private dependencies that you statically link with here ... + } + ); + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp new file mode 100644 index 0000000..06b8d0e --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityManagerEditor.h" + +#define LOCTEXT_NAMESPACE "FAbilityManagerEditor" + +void FAbilityManagerEditorModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FAbilityManagerEditorModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FAbilityManagerEditorModule, AbilityManagerEditor) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h new file mode 100644 index 0000000..0879ce8 --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FAbilityManagerEditorModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp new file mode 100644 index 0000000..1e86c07 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "DWBPFunctionLibrary.h" +#include "DWManager.h" + + +FDWWWindowHandle UDWBPFunctionLibrary::CreateWindow() +{ + return FDWManager::Get().CreateWindow(); +} +FDWWWindowHandle UDWBPFunctionLibrary::CreateWindowWithContent(UUserWidget* InWindowContent) +{ + return FDWManager::Get().CreateWindow(InWindowContent->TakeWidget()); +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h new file mode 100644 index 0000000..25a797a --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Kismet/BlueprintFunctionLibrary.h" +#include "UserWidget.h" +#include "DWTypes.h" + +#include "DWBPFunctionLibrary.generated.h" + +/** + * + */ +UCLASS() +class DRAGGABLEWINDOW_API UDWBPFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() + +public: + UFUNCTION(BlueprintCallable, Category = "Draggable Window") + static FDWWWindowHandle CreateWindow(); + + UFUNCTION(BlueprintCallable, Category = "Draggable Window") + static FDWWWindowHandle CreateWindowWithContent(UUserWidget* InWindowContent); +}; diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp new file mode 100644 index 0000000..23fbfc6 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp @@ -0,0 +1,74 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "DWManager.h" +#include "EngineGlobals.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" + +FDWManager* FDWManager::Instance = nullptr; +void FDWManager::Init() +{ + Desktop = SNew(SDraggableDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); + GEngine->GameViewport->AddViewportWidgetContent(Desktop.ToSharedRef(), 2000); +} +void FDWManager::CleanUp() +{ + Desktop->Clean(); + Desktop.Reset(); + WindowHandles.Empty(); + WindowHandles.Shrink(); +} +void FDWManager::RemoveWindow(const FDWWWindowHandle& InHandle) +{ + Desktop->RemoveWindow(InHandle.Window.Pin()); + WindowHandles.Remove(InHandle); +} +FDWManager& FDWManager::Get() +{ + if (!Instance) + { + Instance = new FDWManager(); + Instance->Init(); + } + return *Instance; +} +#if WITH_EDITORONLY_DATA +void FDWManager::PIEDestroy() +{ + if (Instance) + { + Instance->CleanUp(); + delete Instance; + Instance = nullptr; + } +} +#endif //WITH_EDITORONLY_DATA +FDWManager::FDWManager() +{ +} + +FDWManager::~FDWManager() +{ +} + +FDWWWindowHandle FDWManager::CreateWindow() +{ + TSharedPtr NewWindow = SNew(SDraggableWindowWidget); + FDWWWindowHandle Handle = Desktop->AddWindow(NewWindow); + WindowHandles.Add(Handle); + return Handle; +} +FDWWWindowHandle FDWManager::CreateWindow(TSharedPtr InWindowContent) +{ + TSharedPtr NewWindow = SNew(SDraggableWindowWidget); + NewWindow->AddContent(InWindowContent); + FDWWWindowHandle Handle = Desktop->AddWindow(NewWindow); + WindowHandles.Add(Handle); + return Handle; +} +FDWWWindowHandle FDWManager::AddWindow(TSharedPtr InWindowWidget) +{ + FDWWWindowHandle Handle = Desktop->AddWindow(InWindowWidget); + WindowHandles.Add(Handle); + return Handle; +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h new file mode 100644 index 0000000..555a046 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h @@ -0,0 +1,35 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SDraggableWindowWidget.h" + +/** + * + */ +class DRAGGABLEWINDOW_API FDWManager +{ +public: + friend class SDraggableWindowWidget; + friend class SDraggableDesktopWidget; +private: + static FDWManager* Instance; + TSharedPtr Desktop; + TSet WindowHandles; + void Init(); + void CleanUp(); + void RemoveWindow(const FDWWWindowHandle& InHandle); + FDWManager(); +public: + static FDWManager& Get(); +#if WITH_EDITORONLY_DATA + static void PIEDestroy(); +#endif //WITH_EDITORONLY_DATA + ~FDWManager(); + + FDWWWindowHandle CreateWindow(); + FDWWWindowHandle CreateWindow(TSharedPtr InWindowContent); + FDWWWindowHandle AddWindow(TSharedPtr InWindowWidget); +}; +typedef FDWManager FDraggableWindowManager; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp new file mode 100644 index 0000000..3fe94f4 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp @@ -0,0 +1,3 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "DWTypes.h" \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h new file mode 100644 index 0000000..d5e8c26 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h @@ -0,0 +1,41 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "DWTypes.generated.h" + +USTRUCT(BlueprintType) +struct FDWWWindowHandle +{ + GENERATED_BODY() + TWeakPtr Window; +protected: + uint32 Handle; +public: + FDWWWindowHandle() + {}; + FDWWWindowHandle(uint32 InHandle) + : Handle(InHandle) + { + + } + + ~FDWWWindowHandle() + { + Handle = 0; + Window.Reset(); + } + + static FDWWWindowHandle Make(TSharedPtr InWindow); + + friend uint32 GetTypeHash(const FDWWWindowHandle& InHandle) + { + return InHandle.Handle; + } + + const bool operator==(const FDWWWindowHandle& InHandle) const + { + return Handle == InHandle.Handle; + } +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs index 773b006..28f6bba 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs @@ -53,5 +53,9 @@ public DraggableWindow(ReadOnlyTargetRules Target) : base(Target) // ... add any modules that your module loads dynamically here ... } ); - } + if (Target.Type == TargetRules.TargetType.Editor) + { + PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); + } + } } diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp index c3765cb..e401549 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp @@ -1,12 +1,20 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. #include "DraggableWindow.h" - +#include "DWManager.h" +#if WITH_EDITORONLY_DATA +#include "Editor.H" +#endif #define LOCTEXT_NAMESPACE "FDraggableWindowModule" void FDraggableWindowModule::StartupModule() { // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module + +#if WITH_EDITORONLY_DATA + FEditorDelegates::EndPIE.AddRaw(this, &FDraggableWindowModule::HandlePIEEnd); +#endif //WITH_EDITORONLY_DATA + } void FDraggableWindowModule::ShutdownModule() @@ -14,7 +22,12 @@ void FDraggableWindowModule::ShutdownModule() // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, // we call this function before unloading the module. } - +#if WITH_EDITORONLY_DATA +void FDraggableWindowModule::HandlePIEEnd(bool InVal) +{ + FDWManager::PIEDestroy(); +} +#endif #undef LOCTEXT_NAMESPACE IMPLEMENT_MODULE(FDraggableWindowModule, DraggableWindow) \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h index 072d102..457f438 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h @@ -2,9 +2,12 @@ #pragma once +#include "Engine.h" #include "CoreMinimal.h" #include "ModuleManager.h" +DECLARE_STATS_GROUP(TEXT("DraggebleWindow"), STATGROUP_DraggebleWindow, STATCAT_Advanced); + class FDraggableWindowModule : public IModuleInterface { public: @@ -12,4 +15,7 @@ class FDraggableWindowModule : public IModuleInterface /** IModuleInterface implementation */ virtual void StartupModule() override; virtual void ShutdownModule() override; +#if WITH_EDITORONLY_DATA + void HandlePIEEnd(bool InVal); +#endif }; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index 3560b8a..5aea774 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -7,6 +7,10 @@ #include "SlateCore.h" #include "SBorder.h" #include "Widgets/Layout/SGridPanel.h" +#include "Widgets/Layout/SBackgroundBlur.h" +#include "DWManager.h" + +DECLARE_CYCLE_STAT(TEXT("DraggebleWindow.Tick"), STAT_DraggebleWindowTick, STATGROUP_DraggebleWindow); FDWWWindowHandle FDWWWindowHandle::Make(TSharedPtr InWindow) { @@ -14,12 +18,22 @@ FDWWWindowHandle FDWWWindowHandle::Make(TSharedPtr NewHandle++; FDWWWindowHandle Handle(NewHandle); Handle.Window = InWindow; + InWindow->SetHandle(Handle); return NewHandle; } - +void SDraggableDesktopWidget::Clean() +{ + for (TSharedPtr& Window : Windows) + { + Window.Reset(); + } + Windows.Empty(); + Windows.Shrink(); +} BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION void SDraggableDesktopWidget::Construct(const FArguments& InArgs) { + SetVisibility(EVisibility::SelfHitTestInvisible); Container = SNew(SOverlay).Visibility(EVisibility::SelfHitTestInvisible); ChildSlot [ @@ -39,10 +53,19 @@ FDWWWindowHandle SDraggableDesktopWidget::AddWindow(TSharedPtr InWindow) +{ + Container->RemoveSlot(InWindow.ToSharedRef()); + Windows.Remove(InWindow); + InWindow.Reset(); +} + void SWindowBox::Construct(const FArguments& InArgs) { WidthOverride = InArgs._WidthOverride.Get(); @@ -131,15 +154,11 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) { CurrentSize = FVector2D(1, 1); ResizingState = EDDWState::NoResize; - + SetVisibility(EVisibility::SelfHitTestInvisible); FSimpleDelegate OnPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnPressed); FSimpleDelegate OnReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnReleased); TAttribute posAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetPosition)); - TAttribute sizeAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetSize)); - - TAttribute widthAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetWidth)); - TAttribute heightAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetHeight)); FSimpleDelegate OnHorizontalPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizePressed); FSimpleDelegate OnHorizontalReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeReleased); @@ -157,11 +176,25 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) FSimpleDelegate OnBottomLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizePressed); FSimpleDelegate OnBottomLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizeReleased); + FSimpleDelegate OnTopRightPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopRightResizePressed); + FSimpleDelegate OnTopRightReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopRightResizeReleased); + + FSimpleDelegate OnTopLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopLeftResizePressed); + FSimpleDelegate OnTopLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopLeftResizeReleased); + + + FSimpleDelegate OnCloseButtonPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnCloseButtonPressed); + CurrentHeight = 200; CurrentWidth = 200; - bDragging = false; - + FSlateBrush brush; + brush.DrawAs = ESlateBrushDrawType::Type::NoDrawType; + ButtonStyle.Normal = brush; + ButtonStyle.Hovered = brush; + ButtonStyle.Pressed = brush; + ButtonStyle.Disabled = brush; + BackgroundColor = FSlateColor(FLinearColor(0, 0, 0, 1)); ChildSlot [ SNew(SCanvas) @@ -180,6 +213,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .WidthOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnTopLeftPressedDel) + .OnReleased(OnTopLeftReleasedDel) + .Cursor(EMouseCursor::ResizeSouthEast) ] ] + SGridPanel::Slot(1 ,0) @@ -188,8 +225,11 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .HeightOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) .OnPressed(OnVerticalTopPressedDel) .OnReleased(OnVerticalTopReleasedDel) + .Cursor(EMouseCursor::ResizeUpDown) + ] ] + SGridPanel::Slot(2, 0) @@ -199,6 +239,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .WidthOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnTopRightPressedDel) + .OnReleased(OnTopRightReleasedDel) + .Cursor(EMouseCursor::ResizeSouthWest) ] ] + SGridPanel::Slot(0, 1) @@ -207,8 +251,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .WidthOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) .OnPressed(OnHorizontalLeftPressedDel) .OnReleased(OnHorizontalLeftReleasedDel) + .Cursor(EMouseCursor::ResizeLeftRight) ] ] + SGridPanel::Slot(1, 1) @@ -216,33 +262,67 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .VAlign(EVerticalAlignment::VAlign_Fill) [ SAssignNew(WindowBox, SWindowBox) + .Visibility(EVisibility::SelfHitTestInvisible) //.HeightOverride(heightAttr) //.WidthOverride(widthAttr) [ SNew(SVerticalBox) + .Visibility(EVisibility::SelfHitTestInvisible) + SVerticalBox::Slot() .AutoHeight() - .MaxHeight(32) + .MaxHeight(24) [ - SNew(SHorizontalBox) - + SHorizontalBox::Slot() + SNew(SOverlay) + + SOverlay::Slot() + [ + SNew(SBackgroundBlur) + .BlurRadius(4) + .BlurStrength(16) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + + SOverlay::Slot() [ - SNew(SButton) + SAssignNew(WindowBar, SButton) .OnPressed(OnPressedDel) .OnReleased(OnReleasedDel) + .VAlign(EVerticalAlignment::VAlign_Center) + .HAlign(EHorizontalAlignment::HAlign_Right) + .ContentPadding(FMargin(0)) + .ButtonStyle(&ButtonStyle) + [ + SNew(SButton) + .OnPressed(OnCloseButtonPressedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("X")) + ] + ] ] ] + SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) .FillHeight(1.0f) [ SNew(SBox) .HAlign(EHorizontalAlignment::HAlign_Fill) .VAlign(EVerticalAlignment::VAlign_Fill) [ - SAssignNew(Content, SOverlay) + SNew(SOverlay) + + SOverlay::Slot() + [ + SNew(SBackgroundBlur) + .BlurRadius(4) + .BlurStrength(8) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + +SOverlay::Slot() + [ + SAssignNew(Content, SOverlay) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + ] ] ] @@ -254,8 +334,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .WidthOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) .OnPressed(OnHorizontalPressedDel) .OnReleased(OnHorizontalReleasedDel) + .Cursor(EMouseCursor::ResizeLeftRight) ] ] + SGridPanel::Slot(0, 2) @@ -265,8 +347,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .WidthOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) .OnPressed(OnBottomLeftPressedDel) .OnReleased(OnBottomLeftReleasedDel) + .Cursor(EMouseCursor::ResizeSouthWest) ] ] + SGridPanel::Slot(1, 2) @@ -275,8 +359,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .HeightOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) .OnPressed(OnVerticalBottomPressedDel) .OnReleased(OnVerticalBottomReleasedDel) + .Cursor(EMouseCursor::ResizeUpDown) ] ] + SGridPanel::Slot(2, 2) @@ -286,8 +372,10 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .WidthOverride(3) [ SNew(SButton) + .ButtonStyle(&ButtonStyle) .OnPressed(OnBottomRightPressedDel) .OnReleased(OnBottomRightReleasedDel) + .Cursor(EMouseCursor::ResizeSouthEast) ] ] ] @@ -306,6 +394,9 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) } END_SLATE_FUNCTION_BUILD_OPTIMIZATION +SDraggableWindowWidget::~SDraggableWindowWidget() +{ +} FVector2D SDraggableWindowWidget::ComputeDesiredSize(float) const { return SCompoundWidget::ComputeDesiredSize(1); @@ -313,29 +404,43 @@ FVector2D SDraggableWindowWidget::ComputeDesiredSize(float) const } void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) { + SCOPE_CYCLE_COUNTER(STAT_DraggebleWindowTick); SCompoundWidget::Tick(AllottedGeometry, InCurrentTime, InDeltaTime); FVector2D LastPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); FVector2D CurrentPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); float dist = FVector2D::Distance(CurrentPosition, LastPosition);// *InDeltaTime; - if (bDragging) + switch (ResizingState) { - FVector2D locaPos = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); + case EDDWState::Dragging: + { + FVector2D locaPos = CurrentPosition; + locaPos = locaPos - DragPosition; //FVector2D(50, 12); + if ( (locaPos.X + DragPosition.X) <= 20) + { + CurrentCursorPosition.X = 20; + } + if ( (locaPos.Y + DragPosition.Y) <= 20) + { + CurrentCursorPosition.Y = 20; + } CurrentCursorPosition = locaPos; + + break; } - if(ResizingState == EDDWState::HorizontalRight) - { + case EDDWState::HorizontalRight: + { float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; - if(dist != 0) + if (dist != 0) { CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); } - CurrentX = CurrentXX; CurrentWidth = CurrentWidth + CurrentXX; WindowBox->SetWidthOverride(CurrentWidth); + break; } - else if (ResizingState == EDDWState::HorizontalLeft) + case EDDWState::HorizontalLeft: { float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; if (dist != 0) @@ -346,13 +451,25 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl CurrentCursorPosition.X -= CurrentXX; CurrentWidth = CurrentWidth + CurrentXX; WindowBox->SetWidthOverride(CurrentWidth); + break; } - else if(ResizingState == EDDWState::VerticalTop) - { - + case EDDWState::VerticalTop: + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentXX = CurrentCursorPosition.Y - CurrentPosition.Y; + //CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + CurrentCursorPosition.Y -= CurrentXX; + //CurrentX = CurrentY; + CurrentHeight = CurrentHeight + CurrentXX; + WindowBox->SetHeightOverride(CurrentHeight); + break; } - else if (ResizingState == EDDWState::VerticalBottom) - { + case EDDWState::VerticalBottom: + { float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; if (dist != 0) { @@ -361,9 +478,10 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl //CurrentX = CurrentY; CurrentHeight = CurrentHeight + CurrentY; WindowBox->SetHeightOverride(CurrentHeight); + break; } - else if(ResizingState == EDDWState::DiagonalBottomRight) - { + case EDDWState::DiagonalBottomRight: + { float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; if (dist != 0) @@ -371,14 +489,14 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); } - CurrentX = CurrentXX; CurrentWidth = CurrentWidth + CurrentXX; CurrentHeight = CurrentHeight + CurrentY; WindowBox->SetHeightOverride(CurrentHeight); WindowBox->SetWidthOverride(CurrentWidth); + break; } - else if(ResizingState == EDDWState::DiagonalBottomLeft) - { + case EDDWState::DiagonalBottomLeft: + { float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; if (dist != 0) @@ -386,14 +504,53 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); } - CurrentX = CurrentXX; CurrentCursorPosition.X -= CurrentXX; CurrentWidth = CurrentWidth + CurrentXX; CurrentHeight = CurrentHeight + CurrentY; WindowBox->SetHeightOverride(CurrentHeight); WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::DiagonalTopRight: + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; + CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); + } + CurrentCursorPosition.Y -= CurrentY; + //CurrentX = CurrentY; + CurrentHeight = CurrentHeight + CurrentY; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::DiagonalTopLeft: + { + float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + if (dist != 0) + { + CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; + CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; + } + CurrentCursorPosition.Y -= CurrentY; + CurrentCursorPosition.X -= CurrentXX; + CurrentHeight = CurrentHeight + CurrentY; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::NoResize: + { break; + } + default: + break; } - } void SDraggableWindowWidget::AddContent(TSharedPtr InWidget) { @@ -404,14 +561,31 @@ void SDraggableWindowWidget::AddContent(TSharedPtr InWidget) InWidget.ToSharedRef() ]; } +void SDraggableWindowWidget::SetHandle(const FDWWWindowHandle& InHandle) +{ + Handle = InHandle; +} +void SDraggableWindowWidget::OnCloseButtonPressed() +{ + FDWManager::Get().RemoveWindow(Handle); +} void SDraggableWindowWidget::OnPressed() { - bDragging = true; - //CurrentCursorPosition = FSlateApplication::Get().GetCursorPos(); + FGeometry geom = GetCachedGeometry(); + FVector2D CurrentPosition = geom.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed Pre DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); + DragPosition = CurrentPosition - CurrentCursorPosition; + //DragPosition.X = FMath::Clamp(DragPosition.X, CurrentCursorPosition.X, CurrentCursorPosition.X + CurrentWidth); + //DragPosition.Y = FMath::Clamp(DragPosition.Y, CurrentCursorPosition.Y, CurrentCursorPosition.Y + 24); + + UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentPosition X: %f Y: %f"), CurrentPosition.X, CurrentPosition.Y); + UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentCursorPosition X: %f Y: %f"), CurrentCursorPosition.X, CurrentCursorPosition.Y); + UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); + ResizingState = EDDWState::Dragging; } void SDraggableWindowWidget::OnReleased() { - bDragging = false; + ResizingState = EDDWState::NoResize; } void SDraggableWindowWidget::OnHorizontalResizePressed() @@ -474,26 +648,25 @@ void SDraggableWindowWidget::OnBottomLeftResizeReleased() ResizingState = EDDWState::NoResize; } -FVector2D SDraggableWindowWidget::GetPosition() const +void SDraggableWindowWidget::OnTopRightResizePressed() { - return CurrentCursorPosition; + ResizingState = EDDWState::DiagonalTopRight; } -FVector2D SDraggableWindowWidget::GetSize() const +void SDraggableWindowWidget::OnTopRightResizeReleased() { - return CurrentSize; + ResizingState = EDDWState::NoResize; } -FOptionalSize SDraggableWindowWidget::GetHeight() const + +void SDraggableWindowWidget::OnTopLeftResizePressed() { - return CurrentHeight; + ResizingState = EDDWState::DiagonalTopLeft; } -FOptionalSize SDraggableWindowWidget::GetWidth() const +void SDraggableWindowWidget::OnTopLeftResizeReleased() { - return CurrentWidth; + ResizingState = EDDWState::NoResize; } -FText SDraggableWindowWidget::GetCurrentX() const + +FVector2D SDraggableWindowWidget::GetPosition() const { - FString ret = FString("Right") + FString::FormatAsNumber(CurrentSize.X) + FString("\n") - + FString("CurrentWidth ") + FString::FormatAsNumber(CurrentWidth) + FString("\n") - + FString("CurrentX ") + FString::FormatAsNumber(CurrentX) + FString("\n"); - return FText::FromString(ret); + return CurrentCursorPosition; } diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h index e00b084..9182264 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h @@ -5,25 +5,15 @@ #include "CoreMinimal.h" #include "Input/Events.h" #include "Widgets/SCompoundWidget.h" +#include "SlateCore.h" +#include "Styling/SlateTypes.h" #include "SOverlay.h" #include "SGridPanel.h" #include "SBox.h" +#include "SBorder.h" +#include "SButton.h" #include "SConstraintCanvas.h" -struct FDWWWindowHandle -{ - TWeakPtr Window; -protected: - uint32 Handle; -public: - FDWWWindowHandle() - {}; - FDWWWindowHandle(uint32 InHandle) - : Handle(InHandle) - { - - } - static FDWWWindowHandle Make(TSharedPtr InWindow); -}; +#include "DWTypes.h" enum class EDDWState : uint8 { Dragging = 0, @@ -40,15 +30,19 @@ enum class EDDWState : uint8 }; class DRAGGABLEWINDOW_API SDraggableDesktopWidget : public SCompoundWidget { + SLATE_BEGIN_ARGS(SDraggableDesktopWidget) {} SLATE_END_ARGS() - +public: + friend class FDWManager; /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - + void Construct(const FArguments& InArgs); +protected: TArray> Windows; TSharedPtr Container; + void Clean(); FDWWWindowHandle AddWindow(TSharedPtr InWindow); + void RemoveWindow(TSharedPtr InWindow); }; class SWindowBox : public SPanel @@ -120,29 +114,41 @@ class SWindowBox : public SPanel */ class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget { -public: SLATE_BEGIN_ARGS(SDraggableWindowWidget){} + SLATE_ATTRIBUTE(bool, HideOnClose) SLATE_END_ARGS() +public: + friend struct FDWWWindowHandle; + friend class SDraggableDesktopWidget; + friend class FDWManager; protected: EDDWState ResizingState; - bool bDragging; - + FVector2D CurrentSize; FVector2D CurrentCursorPosition; + FVector2D DragPosition; TSharedPtr Content; TSharedPtr WindowBox; float CurrentHeight; float CurrentWidth; - float CurrentX; + FButtonStyle ButtonStyle; + TAttribute BackgroundColor; + TSharedPtr WindowBar; + FDWWWindowHandle Handle; public: /** Constructs this widget with InArgs */ void Construct(const FArguments& InArgs); + ~SDraggableWindowWidget(); +protected: virtual FVector2D ComputeDesiredSize(float) const override; virtual void Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) override; void AddContent(TSharedPtr InWidget); -protected: + + void SetHandle(const FDWWWindowHandle& InHandle); + void OnCloseButtonPressed(); + void OnPressed(); void OnReleased(); @@ -165,10 +171,11 @@ class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget void OnBottomLeftResizePressed(); void OnBottomLeftResizeReleased(); - FVector2D GetPosition() const; - FVector2D GetSize() const; + void OnTopRightResizePressed(); + void OnTopRightResizeReleased(); - FOptionalSize GetHeight() const; - FOptionalSize GetWidth() const; - FText GetCurrentX() const; + void OnTopLeftResizePressed(); + void OnTopLeftResizeReleased(); + + FVector2D GetPosition() const; }; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 10664ed..e7d2bf4 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -7,6 +7,8 @@ #include "GameFramework/CharacterMovementComponent.h" #include "GameFramework/Controller.h" #include "GameFramework/SpringArmComponent.h" +#include "ARPlayerController.h" +#include "ARUIAbilityManagerComponent.h" ////////////////////////////////////////////////////////////////////////// // AARCharacter @@ -69,9 +71,13 @@ void AARCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputC PlayerInputComponent->BindAxis("LookUp", this, &APawn::AddControllerPitchInput); PlayerInputComponent->BindAxis("LookUpRate", this, &AARCharacter::LookUpAtRate); - + Abilities->BindInputs(PlayerInputComponent); } +void AARCharacter::PossessedBy(AController* NewController) +{ + Super::PossessedBy(NewController); +} void AARCharacter::TurnAtRate(float Rate) { // calculate delta for this frame from the rate information diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 2d31f86..fce5e16 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -63,7 +63,7 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface // APawn interface virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; // End of APawn interface - + virtual void PossessedBy(AController* NewController) override; public: /** Returns CameraBoom subobject **/ FORCEINLINE class USpringArmComponent* GetCameraBoom() const { return CameraBoom; } diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index d1434fd..dd10ba5 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -41,7 +41,7 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); - WeaponManager->BindInputs(); + //WeaponManager->BindInputs(); //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); @@ -51,12 +51,14 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr); } + //UIAbilityManagerComponent->BindInputs(); } void AARPlayerController::SetupInputComponent() { Super::SetupInputComponent(); InputComponent->BindAction("SwitchAbilitySet", IE_Pressed, this, &AARPlayerController::InputSwitchAbilitySet); + } void AARPlayerController::InputSwitchAbilitySet() diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index 35fccaf..bfb880d 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -66,25 +66,10 @@ void UARUIAbilityManagerComponent::BeginPlay() WeaponCrosshairWidget->AddToViewport(); } } - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - for (const FGameplayTag& Tag : AbilityInputs) - { - AbilityComp->BP_BindAbilityToAction(Tag); - } } - // Called every frame void UARUIAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 1572d21..bfb9dde 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -50,8 +50,8 @@ void UARWeaponManagerComponent::BeginPlay() //for (const FGameplayTag& Tag : AbilityInputs) { - AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[0]); - AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[1]); + //AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[0]); + //AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[1]); } // ... From b77285678e3a26f52ab15753d6e464f6c15b5462 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 6 Jan 2018 09:24:32 +0100 Subject: [PATCH 023/187] draggable window fixes --- Config/DefaultEngine.ini | 2 + .../SDraggableWindowWidget.cpp | 150 ++++++++++-------- .../DraggableWindow/SDraggableWindowWidget.h | 3 + 3 files changed, 88 insertions(+), 67 deletions(-) diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index d3b9082..29400d2 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -149,4 +149,6 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 +[/Script/Engine.ProxyLODMeshSimplificationSettings] +r.ProxyLODMeshReductionModule=ProxyLODMeshReduction diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index 5aea774..cb25953 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -9,6 +9,10 @@ #include "Widgets/Layout/SGridPanel.h" #include "Widgets/Layout/SBackgroundBlur.h" #include "DWManager.h" +#include "EngineGlobals.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" +#include "SceneViewport.h" DECLARE_CYCLE_STAT(TEXT("DraggebleWindow.Tick"), STAT_DraggebleWindowTick, STATGROUP_DraggebleWindow); @@ -102,7 +106,6 @@ void SWindowBox::OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedC const EVisibility& MyCurrentVisibility = this->GetVisibility(); if (ArrangedChildren.Accepts(MyCurrentVisibility)) { - //const FOptionalSize CurrentMaxAspectRatio = MaxAspectRatio.Get(); const FMargin SlotPadding(ChildSlot.SlotPadding.Get()); bool bAlignChildren = true; @@ -123,7 +126,6 @@ void SWindowBox::OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedC ChildSlot.GetWidget(), FVector2D(XAlignmentResult.Offset, YAlignmentResult.Offset), FVector2D(AlignedSizeX, AlignedSizeY) - //FVector2D(WidthOverride.Get().Get(), HeightOverride.Get().Get()) ) ); } @@ -272,32 +274,32 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) .AutoHeight() .MaxHeight(24) [ - SNew(SOverlay) - + SOverlay::Slot() - [ - SNew(SBackgroundBlur) - .BlurRadius(4) - .BlurStrength(16) - .Visibility(EVisibility::SelfHitTestInvisible) - ] - + SOverlay::Slot() + SNew(SOverlay) + + SOverlay::Slot() + [ + SNew(SBackgroundBlur) + .BlurRadius(4) + .BlurStrength(16) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + + SOverlay::Slot() + [ + SAssignNew(WindowBar, SButton) + .OnPressed(OnPressedDel) + .OnReleased(OnReleasedDel) + .VAlign(EVerticalAlignment::VAlign_Center) + .HAlign(EHorizontalAlignment::HAlign_Right) + .ContentPadding(FMargin(0)) + .ButtonStyle(&ButtonStyle) [ - SAssignNew(WindowBar, SButton) - .OnPressed(OnPressedDel) - .OnReleased(OnReleasedDel) - .VAlign(EVerticalAlignment::VAlign_Center) - .HAlign(EHorizontalAlignment::HAlign_Right) - .ContentPadding(FMargin(0)) - .ButtonStyle(&ButtonStyle) + SNew(SButton) + .OnPressed(OnCloseButtonPressedDel) [ - SNew(SButton) - .OnPressed(OnCloseButtonPressedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("X")) - ] + SNew(STextBlock) + .Text(FText::FromString("X")) ] ] + ] ] + SVerticalBox::Slot() @@ -379,19 +381,9 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) ] ] ] - // Populate the widget ]; WindowBox->SetHeightOverride(CurrentHeight); WindowBox->SetWidthOverride(CurrentWidth); - /*Content->AddSlot() - [ - SNew(SButton) - [ - SNew(STextBlock) - .Text(this, &SDraggableWindowWidget::GetCurrentX) - ] - ];*/ - } END_SLATE_FUNCTION_BUILD_OPTIMIZATION SDraggableWindowWidget::~SDraggableWindowWidget() @@ -400,7 +392,6 @@ SDraggableWindowWidget::~SDraggableWindowWidget() FVector2D SDraggableWindowWidget::ComputeDesiredSize(float) const { return SCompoundWidget::ComputeDesiredSize(1); - //return FVector2D(CurrentWidth, CurrentHeight); } void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) { @@ -408,30 +399,56 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl SCompoundWidget::Tick(AllottedGeometry, InCurrentTime, InDeltaTime); FVector2D LastPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); + FVector2D CurrentPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); - float dist = FVector2D::Distance(CurrentPosition, LastPosition);// *InDeltaTime; + + float dist = FVector2D::Distance(CurrentPosition, LastPosition); switch (ResizingState) { case EDDWState::Dragging: { + FVector2D AbsPos = FSlateApplicationBase::Get().GetCursorPos(); FVector2D locaPos = CurrentPosition; - locaPos = locaPos - DragPosition; //FVector2D(50, 12); - if ( (locaPos.X + DragPosition.X) <= 20) + locaPos = locaPos - DragPosition; + AbsPosition = AbsPos - AbsDragPosition; + + FVector2D WindowPosition = GEngine->GameViewport->GetWindow()->GetPositionInScreen(); + FVector2D WindowSize = GEngine->GameViewport->GetWindow()->GetSizeInScreen(); + + const float ApplicationScale = FSlateApplication::Get().GetApplicationScale(); + FVector2D AbsSize = AllottedGeometry.LocalToAbsolute(FVector2D(CurrentWidth, CurrentHeight)); + FVector2D localSize = WindowSize + WindowPosition; + float distanceX = localSize.X - (AbsPosition.X + (CurrentWidth - AbsDragPosition.X)); + UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: WindowEdges X: %f Y: %f"), localSize.X, WindowPosition.Y + WindowSize.Y); + UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: AbsPos X: %f Y: %f"), locaPos.X, locaPos.Y); + UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: distanceX: %f"), distanceX); + + UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: AbsPosCalc X: %f Y: %f"), ((AbsPos.X)) + ((AbsSize.X - AbsDragPosition.X)* ApplicationScale), ((AbsPos.Y) + (CurrentHeight - DragPosition.Y))); + UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: CurrentWidth - DragPosition. X: %f Y: %f"), (((AbsSize.X) - AbsDragPosition.X)* ApplicationScale), ((CurrentHeight - DragPosition.Y))); + UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: DragPosition. X: %f Y: %f"), ((AbsDragPosition.X)), ((AbsDragPosition.Y))); + //(DragPosition.X)) + if ((locaPos.X >= 0) && (((AbsPos.X) + ((AbsSize.X - AbsDragPosition.X)* ApplicationScale)) <= (localSize.X))) { - CurrentCursorPosition.X = 20; + CurrentCursorPosition.X = locaPos.X; } - if ( (locaPos.Y + DragPosition.Y) <= 20) + if ((locaPos.Y >= 0) && (((AbsPos.Y) + ((AbsSize.Y - AbsDragPosition.Y)* ApplicationScale)) <= (localSize.Y))) { - CurrentCursorPosition.Y = 20; + CurrentCursorPosition.Y = locaPos.Y; + } + if (locaPos.X <= 0) + { + CurrentCursorPosition.X = 0; + } + if (locaPos.Y <= 0) + { + CurrentCursorPosition.Y = 0; } - CurrentCursorPosition = locaPos; - break; } case EDDWState::HorizontalRight: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; if (dist != 0) { CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); @@ -442,12 +459,12 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl } case EDDWState::HorizontalLeft: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; if (dist != 0) { CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; } - //float CurrentXX = LastPosition.X - CurrentPosition.X; + CurrentCursorPosition.X -= CurrentXX; CurrentWidth = CurrentWidth + CurrentXX; WindowBox->SetWidthOverride(CurrentWidth); @@ -455,35 +472,34 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl } case EDDWState::VerticalTop: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; - float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; + float CurrentY = 0; if (dist != 0) { CurrentXX = CurrentCursorPosition.Y - CurrentPosition.Y; - //CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } CurrentCursorPosition.Y -= CurrentXX; - //CurrentX = CurrentY; CurrentHeight = CurrentHeight + CurrentXX; WindowBox->SetHeightOverride(CurrentHeight); break; } case EDDWState::VerticalBottom: { - float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentY = 0; if (dist != 0) { CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); } - //CurrentX = CurrentY; + CurrentHeight = CurrentHeight + CurrentY; WindowBox->SetHeightOverride(CurrentHeight); break; } case EDDWState::DiagonalBottomRight: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; - float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; + float CurrentY = 0; if (dist != 0) { CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); @@ -497,8 +513,8 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl } case EDDWState::DiagonalBottomLeft: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; - float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; + float CurrentY = 0; if (dist != 0) { CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; @@ -513,15 +529,15 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl } case EDDWState::DiagonalTopRight: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; - float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; + float CurrentY = 0; if (dist != 0) { CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); } CurrentCursorPosition.Y -= CurrentY; - //CurrentX = CurrentY; + CurrentHeight = CurrentHeight + CurrentY; CurrentWidth = CurrentWidth + CurrentXX; WindowBox->SetHeightOverride(CurrentHeight); @@ -530,8 +546,8 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl } case EDDWState::DiagonalTopLeft: { - float CurrentXX = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; - float CurrentY = 0;// dist * sign;// CurrentPosition.X - LastPosition.X; + float CurrentXX = 0; + float CurrentY = 0; if (dist != 0) { CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; @@ -572,15 +588,15 @@ void SDraggableWindowWidget::OnCloseButtonPressed() void SDraggableWindowWidget::OnPressed() { FGeometry geom = GetCachedGeometry(); - FVector2D CurrentPosition = geom.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); + FVector2D CurrentPosAbs = FSlateApplicationBase::Get().GetLastCursorPos(); + FVector2D CurrentPosition = geom.AbsoluteToLocal(CurrentPosAbs); //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed Pre DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); DragPosition = CurrentPosition - CurrentCursorPosition; - //DragPosition.X = FMath::Clamp(DragPosition.X, CurrentCursorPosition.X, CurrentCursorPosition.X + CurrentWidth); - //DragPosition.Y = FMath::Clamp(DragPosition.Y, CurrentCursorPosition.Y, CurrentCursorPosition.Y + 24); + AbsDragPosition = CurrentPosAbs - AbsPosition; - UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentPosition X: %f Y: %f"), CurrentPosition.X, CurrentPosition.Y); - UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentCursorPosition X: %f Y: %f"), CurrentCursorPosition.X, CurrentCursorPosition.Y); - UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentPosition X: %f Y: %f"), CurrentPosition.X, CurrentPosition.Y); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentCursorPosition X: %f Y: %f"), CurrentCursorPosition.X, CurrentCursorPosition.Y); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); ResizingState = EDDWState::Dragging; } void SDraggableWindowWidget::OnReleased() diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h index 9182264..8badad2 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h @@ -35,6 +35,7 @@ class DRAGGABLEWINDOW_API SDraggableDesktopWidget : public SCompoundWidget SLATE_END_ARGS() public: friend class FDWManager; + friend class SDraggableWindowWidget; /** Constructs this widget with InArgs */ void Construct(const FArguments& InArgs); protected: @@ -127,6 +128,8 @@ class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget FVector2D CurrentSize; FVector2D CurrentCursorPosition; FVector2D DragPosition; + FVector2D AbsPosition; + FVector2D AbsDragPosition; TSharedPtr Content; TSharedPtr WindowBox; From 2639d16e426a07d80912232d8c8c7742717fbe53 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 22 Jan 2018 21:50:43 +0100 Subject: [PATCH 024/187] plugin updates --- Config/DefaultEngine.ini | 9 +- .../AbilityFrameworkDebugger/AFDManager.cpp | 2 +- .../DraggableWindow/DWBPFunctionLibrary.cpp | 8 +- .../DraggableWindow/DWBPFunctionLibrary.h | 4 +- .../Source/DraggableWindow/DWManager.cpp | 16 +- .../Source/DraggableWindow/DWManager.h | 9 +- .../DraggableWindow/DraggableWindow.Build.cs | 3 +- .../Source/DraggableWindow/DraggableWindow.h | 2 +- .../SDraggableWindowWidget.cpp | 74 +++-- .../DraggableWindow/SDraggableWindowWidget.h | 7 + .../Source/SpectrAI/SpectrAI.Build.cs | 60 ++++ Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp | 20 ++ Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h | 15 + .../Source/SpectrAI/SpectrAIController.cpp | 62 ++++ .../Source/SpectrAI/SpectrAIController.h | 304 ++++++++++++++++++ .../Source/SpectrAI/SpectrContext.cpp | 7 + .../SpectrAI/Source/SpectrAI/SpectrContext.h | 20 ++ Plugins/SpectrAI/SpectrAI.uplugin | 23 ++ 18 files changed, 589 insertions(+), 56 deletions(-) create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h create mode 100644 Plugins/SpectrAI/SpectrAI.uplugin diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 29400d2..76e28ea 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -22,6 +22,8 @@ r.SupportStationarySkylight=False r.SupportLowQualityLightmaps=False r.ClearCoatNormal=True r.DefaultFeature.LensFlare=True +r.GenerateLandscapeGIData=True +r.TemporalAA.Upsampling=False [/Script/Engine.StreamingSettings] s.AsyncLoadingThreadEnabled=True @@ -108,6 +110,9 @@ PktDup=0 [/Script/UnrealEd.HierarchicalLODSettings] bForceSettingsInAllMaps=False +[/Script/Engine.ProxyLODMeshSimplificationSettings] +r.ProxyLODMeshReductionModule=ProxyLODMeshReduction + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -148,7 +153,3 @@ SyncSceneSmoothingFactor=0.000000 AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 - -[/Script/Engine.ProxyLODMeshSimplificationSettings] -r.ProxyLODMeshReductionModule=ProxyLODMeshReduction - diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp index 3ef1ce4..dc9608a 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp @@ -26,7 +26,7 @@ void FAFDManager::Init() FDWWWindowHandle FAFDManager::AddDebugWindow(TSharedPtr InWindowContent) { - return FDWManager::Get().CreateWindow(InWindowContent); + return FDWManager::Get().CreateWindow(InWindowContent, "Debug"); } #if WITH_EDITORONLY_DATA diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp index 1e86c07..48e6f7b 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp @@ -4,11 +4,11 @@ #include "DWManager.h" -FDWWWindowHandle UDWBPFunctionLibrary::CreateWindow() +FDWWWindowHandle UDWBPFunctionLibrary::CreateWindow(const FString& WindowName) { - return FDWManager::Get().CreateWindow(); + return FDWManager::Get().CreateWindow(WindowName); } -FDWWWindowHandle UDWBPFunctionLibrary::CreateWindowWithContent(UUserWidget* InWindowContent) +FDWWWindowHandle UDWBPFunctionLibrary::CreateWindowWithContent(UUserWidget* InWindowContent, const FString& WindowName) { - return FDWManager::Get().CreateWindow(InWindowContent->TakeWidget()); + return FDWManager::Get().CreateWindow(InWindowContent->TakeWidget(), WindowName); } \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h index 25a797a..1914c37 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h @@ -19,8 +19,8 @@ class DRAGGABLEWINDOW_API UDWBPFunctionLibrary : public UBlueprintFunctionLibrar public: UFUNCTION(BlueprintCallable, Category = "Draggable Window") - static FDWWWindowHandle CreateWindow(); + static FDWWWindowHandle CreateWindow(const FString& WindowName); UFUNCTION(BlueprintCallable, Category = "Draggable Window") - static FDWWWindowHandle CreateWindowWithContent(UUserWidget* InWindowContent); + static FDWWWindowHandle CreateWindowWithContent(UUserWidget* InWindowContent, const FString& WindowName); }; diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp index 23fbfc6..bf1b797 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp @@ -51,24 +51,22 @@ FDWManager::~FDWManager() { } -FDWWWindowHandle FDWManager::CreateWindow() +FDWWWindowHandle FDWManager::CreateWindow(const FString& WindowName) { TSharedPtr NewWindow = SNew(SDraggableWindowWidget); - FDWWWindowHandle Handle = Desktop->AddWindow(NewWindow); - WindowHandles.Add(Handle); - return Handle; + return AddWindow(NewWindow, WindowName); } -FDWWWindowHandle FDWManager::CreateWindow(TSharedPtr InWindowContent) +FDWWWindowHandle FDWManager::CreateWindow(TSharedPtr InWindowContent, const FString& WindowName) { + TSharedPtr NewWindow = SNew(SDraggableWindowWidget); NewWindow->AddContent(InWindowContent); - FDWWWindowHandle Handle = Desktop->AddWindow(NewWindow); - WindowHandles.Add(Handle); - return Handle; + return AddWindow(NewWindow, WindowName); } -FDWWWindowHandle FDWManager::AddWindow(TSharedPtr InWindowWidget) +FDWWWindowHandle FDWManager::AddWindow(TSharedPtr InWindowWidget, const FString& WindowName) { FDWWWindowHandle Handle = Desktop->AddWindow(InWindowWidget); WindowHandles.Add(Handle); + WindowsByName.Add(FName(*WindowName), Handle); return Handle; } \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h index 555a046..046d245 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h @@ -17,10 +17,13 @@ class DRAGGABLEWINDOW_API FDWManager static FDWManager* Instance; TSharedPtr Desktop; TSet WindowHandles; + //name of window, window handle + TMap WindowsByName; void Init(); void CleanUp(); void RemoveWindow(const FDWWWindowHandle& InHandle); FDWManager(); + public: static FDWManager& Get(); #if WITH_EDITORONLY_DATA @@ -28,8 +31,8 @@ class DRAGGABLEWINDOW_API FDWManager #endif //WITH_EDITORONLY_DATA ~FDWManager(); - FDWWWindowHandle CreateWindow(); - FDWWWindowHandle CreateWindow(TSharedPtr InWindowContent); - FDWWWindowHandle AddWindow(TSharedPtr InWindowWidget); + FDWWWindowHandle CreateWindow(const FString& WindowName); + FDWWWindowHandle CreateWindow(TSharedPtr InWindowContent, const FString& WindowName); + FDWWWindowHandle AddWindow(TSharedPtr InWindowWidget, const FString& WindowName); }; typedef FDWManager FDraggableWindowManager; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs index 28f6bba..60f34c5 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs @@ -27,7 +27,7 @@ public DraggableWindow(ReadOnlyTargetRules Target) : base(Target) PublicDependencyModuleNames.AddRange( new string[] { - "Core", + "Core", // ... add other public dependencies that you statically link with here ... } ); @@ -36,6 +36,7 @@ public DraggableWindow(ReadOnlyTargetRules Target) : base(Target) PrivateDependencyModuleNames.AddRange( new string[] { + "Core", "CoreUObject", "Engine", "InputCore", diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h index 457f438..106e834 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h @@ -6,7 +6,7 @@ #include "CoreMinimal.h" #include "ModuleManager.h" -DECLARE_STATS_GROUP(TEXT("DraggebleWindow"), STATGROUP_DraggebleWindow, STATCAT_Advanced); + class FDraggableWindowModule : public IModuleInterface { diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index cb25953..fe62648 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -284,21 +284,35 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) ] + SOverlay::Slot() [ - SAssignNew(WindowBar, SButton) - .OnPressed(OnPressedDel) - .OnReleased(OnReleasedDel) - .VAlign(EVerticalAlignment::VAlign_Center) - .HAlign(EHorizontalAlignment::HAlign_Right) - .ContentPadding(FMargin(0)) - .ButtonStyle(&ButtonStyle) + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .FillWidth(0.8f) + .AutoWidth() [ - SNew(SButton) - .OnPressed(OnCloseButtonPressedDel) + SNew(STextBlock) + .Text(FText::FromString("Window Title")) + ] + + SHorizontalBox::Slot() + .FillWidth(0.2f) + .AutoWidth() + [ + SAssignNew(WindowBar, SButton) + .OnPressed(OnPressedDel) + .OnReleased(OnReleasedDel) + .VAlign(EVerticalAlignment::VAlign_Center) + .HAlign(EHorizontalAlignment::HAlign_Right) + .ContentPadding(FMargin(0)) + .ButtonStyle(&ButtonStyle) [ - SNew(STextBlock) - .Text(FText::FromString("X")) + SNew(SButton) + .OnPressed(OnCloseButtonPressedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("X")) + ] ] ] + ] ] @@ -409,40 +423,33 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl case EDDWState::Dragging: { FVector2D AbsPos = FSlateApplicationBase::Get().GetCursorPos(); - FVector2D locaPos = CurrentPosition; - locaPos = locaPos - DragPosition; + + CurrentPosition = CurrentPosition - DragPosition; AbsPosition = AbsPos - AbsDragPosition; FVector2D WindowPosition = GEngine->GameViewport->GetWindow()->GetPositionInScreen(); - FVector2D WindowSize = GEngine->GameViewport->GetWindow()->GetSizeInScreen(); + FVector2D WindowSize = GEngine->GameViewport->GetWindow()->GetSizeInScreen() - 8; const float ApplicationScale = FSlateApplication::Get().GetApplicationScale(); FVector2D AbsSize = AllottedGeometry.LocalToAbsolute(FVector2D(CurrentWidth, CurrentHeight)); FVector2D localSize = WindowSize + WindowPosition; - float distanceX = localSize.X - (AbsPosition.X + (CurrentWidth - AbsDragPosition.X)); - UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: WindowEdges X: %f Y: %f"), localSize.X, WindowPosition.Y + WindowSize.Y); - UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: AbsPos X: %f Y: %f"), locaPos.X, locaPos.Y); - UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: distanceX: %f"), distanceX); - - UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: AbsPosCalc X: %f Y: %f"), ((AbsPos.X)) + ((AbsSize.X - AbsDragPosition.X)* ApplicationScale), ((AbsPos.Y) + (CurrentHeight - DragPosition.Y))); - UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: CurrentWidth - DragPosition. X: %f Y: %f"), (((AbsSize.X) - AbsDragPosition.X)* ApplicationScale), ((CurrentHeight - DragPosition.Y))); - UE_LOG(LogTemp, Warning, TEXT("EDDWState::Dragging: DragPosition. X: %f Y: %f"), ((AbsDragPosition.X)), ((AbsDragPosition.Y))); - //(DragPosition.X)) - if ((locaPos.X >= 0) && (((AbsPos.X) + ((AbsSize.X - AbsDragPosition.X)* ApplicationScale)) <= (localSize.X))) + CurrentCursorPosition = CurrentPosition; + + if (CurrentPosition.X <= 0) { - CurrentCursorPosition.X = locaPos.X; + CurrentCursorPosition.X = 0; } - if ((locaPos.Y >= 0) && (((AbsPos.Y) + ((AbsSize.Y - AbsDragPosition.Y)* ApplicationScale)) <= (localSize.Y))) + if (CurrentPosition.Y <= 0) { - CurrentCursorPosition.Y = locaPos.Y; + CurrentCursorPosition.Y = 0; } - if (locaPos.X <= 0) + if ((AbsPos.X + ((AbsSize.X - AbsDragPosition.X) * ApplicationScale)) >= localSize.X) { - CurrentCursorPosition.X = 0; + CurrentCursorPosition.X = localSize.X - CurrentWidth; } - if (locaPos.Y <= 0) + if ((AbsPos.Y + ((AbsSize.Y - AbsDragPosition.Y) * ApplicationScale)) >= localSize.Y) { - CurrentCursorPosition.Y = 0; + CurrentCursorPosition.Y = localSize.Y - CurrentHeight; } break; } @@ -686,3 +693,8 @@ FVector2D SDraggableWindowWidget::GetPosition() const { return CurrentCursorPosition; } + +FText SDraggableWindowWidget::GetTitle() const +{ + return WindowTitle; +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h index 8badad2..95bbca8 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h @@ -14,6 +14,9 @@ #include "SButton.h" #include "SConstraintCanvas.h" #include "DWTypes.h" + +DECLARE_STATS_GROUP(TEXT("DraggebleWindow"), STATGROUP_DraggebleWindow, STATCAT_Advanced); + enum class EDDWState : uint8 { Dragging = 0, @@ -139,6 +142,8 @@ class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget TAttribute BackgroundColor; TSharedPtr WindowBar; FDWWWindowHandle Handle; + + FText WindowTitle; public: /** Constructs this widget with InArgs */ void Construct(const FArguments& InArgs); @@ -181,4 +186,6 @@ class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget void OnTopLeftResizeReleased(); FVector2D GetPosition() const; + + FText GetTitle() const; }; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs new file mode 100644 index 0000000..c69bf3f --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs @@ -0,0 +1,60 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class SpectrAI : ModuleRules +{ + public SpectrAI(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "SpectrAI/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "SpectrAI/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "Core", + "CoreUObject", + "Engine", + "InputCore", + "Slate", + "SlateCore", + "AIModule", + "GameplayTags", + "GameplayTasks" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp new file mode 100644 index 0000000..44a9f01 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "SpectrAI.h" + +#define LOCTEXT_NAMESPACE "FSpectrAIModule" + +void FSpectrAIModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FSpectrAIModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FSpectrAIModule, SpectrAI) \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h new file mode 100644 index 0000000..a266684 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FSpectrAIModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp new file mode 100644 index 0000000..0716396 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp @@ -0,0 +1,62 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrAIController.h" + +bool operator>(float Rhs, const FSpectrDecision& Lhs) +{ + return Rhs > Lhs.Score; +} + + +ASpectrAIController::ASpectrAIController() +{ + Goal.Add(TEXT("WoodCollected"), true); + + CurrentState.Add(TEXT("HasWood"), false); + CurrentState.Add(TEXT("HasAxe"), false); + + FSpectrAction ChopWood; + ChopWood.Name = "ChopWood"; + ChopWood.PreCondition.Add(TEXT("HasWood"), false); + ChopWood.PreCondition.Add(TEXT("WoodChopped"), false); + ChopWood.PreCondition.Add(TEXT("HasAxe"), true); + ChopWood.Effects.Add(TEXT("WoodChopped"), true); + + FSpectrAction PickLogs; + PickLogs.Name = "PickLogs"; + PickLogs.PreCondition.Add(TEXT("HasWood"), false); + PickLogs.Effects.Add(TEXT("HasWood"), true); + PickLogs.Effects.Add(TEXT("WoodCollected"), false); + + FSpectrAction DropLogs; + DropLogs.Name = "DropLogs"; + DropLogs.PreCondition.Add(TEXT("HasWood"), true); + DropLogs.Effects.Add(TEXT("HasWood"), false); + DropLogs.Effects.Add(TEXT("WoodCollected"), true); + + //FSpectrAction ChopWood; + //ChopWood.Name = "ChopWood"; + //ChopWood.PreCondition.Add(TEXT("HasWood"), false); + //ChopWood.PreCondition.Add(TEXT("HasAxe"), true); + //ChopWood.Effects.Add(TEXT("HasWood"), true); + + + FSpectrAction PickItem_Axe; + PickItem_Axe.Name = "PickItem_Axe"; + PickItem_Axe.PreCondition.Add(TEXT("HasAxe"), false); + PickItem_Axe.Effects.Add(TEXT("HasAxe"), true); + + Spectr.ActionList.Add(ChopWood); + Spectr.ActionList.Add(PickItem_Axe); + Spectr.ActionList.Add(PickLogs); + Spectr.ActionList.Add(DropLogs); + + TArray ActionQueue; + Spectr.Plan(Goal, CurrentState, ActionQueue); + + float Dupa2 = 0; + if (Dupa2 > 0) + { + + } +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h new file mode 100644 index 0000000..626f298 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h @@ -0,0 +1,304 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AIController.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "Queue.h" +#include "SpectrAIController.generated.h" + +//Consideration (calculates score) +//--normalized 0-1 +//--calculated against curve + +//Qualifier +//--Contains Considerations +//--defines how score Considerations should be combined +//--return score. + +//Decision (what should I do?) +//--contain exactly ONE action to execute if decision wins + +//Decision Score Evaluator (Selector) +//--containts multiple considerations +//--all condsiderations are calculated with given context +//--they are summed (or multiplied) +//--contains single decision to execute. + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrConsideration +{ + GENERATED_BODY() +public: + virtual float Score() const { return 0; } + virtual ~FSpectrConsideration() + {} +}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrQualifier +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Considerations; +public: + virtual ~FSpectrQualifier() + {} + virtual float Qualify() const + { + float TotalScore = 0; + for (const FSpectrConsideration& Consideration : Considerations) + { + TotalScore += Consideration.Score(); + } + return TotalScore; + } +}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrDecision +{ + GENERATED_BODY() +public: + mutable float Score; + void SetScore(float InScore) const + { + Score = InScore; + } +}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrEvaluator +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FSpectrQualifier Qualifier; + + UPROPERTY(EditAnywhere) + FSpectrDecision Decision; + + mutable float Score; + + float Evaluate() const + { + Score = 0; + float score = Qualifier.Qualify(); + Decision.SetScore(score); + Score = score; + return score; + } +}; + +bool operator>(float Rhs, const FSpectrDecision& Lhs); + +USTRUCT(BlueprintType) +struct FSpectrAction +{ + GENERATED_BODY() +public: + FString Name; + TMap PreCondition; + TMap Effects; + + //precondition + //Score to cosnider how viable given action will be + UPROPERTY(EditAnywhere) + FSpectrQualifier Qualifier; +}; + +/* + High level goal we try to create plan for. +*/ +struct FSpectrGoal +{ + /* + All of these tags must be present on Actor State to satisfy this goal. + */ + TMap RequiredConditions; + + /* Qualify if planner should for a plan for this Goal. */ + FSpectrQualifier Qualifier; +}; + +USTRUCT(BlueprintType) +struct FSpectrPlanner +{ + GENERATED_BODY() +public: + void Plan(const FSpectrAction& InAction, const FSpectrGoal& Goal) + { + TQueue < FSpectrAction, EQueueMode::Mpsc > ActionQueue; + } +}; + +/* +Actions:: +--ChopLog + --Preconditions + AI.HasTool + AI.HasLogs + --Effects + AI.HasLogs + + +Actor: + FSpectrGoal:: + --CollectWood + Precondition: + --AI.HasLogs +*/ + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrAI +{ + GENERATED_BODY() +public: + TArray ActionList; + + //Precondition, List of action for this precondition; + TMap> ActionMap; + + void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, + TArray& ActionQueue) + { + bool bDone = false; + for (const FSpectrAction& Action : ActionList) + { + if (CheckGoal(Action.PreCondition, InCurrent)) + { + TMap NewState = AddGoalChanges(InCurrent, Action.Effects); + ActionQueue.Add(Action); + if (CheckGoal(InTargetGoal, NewState)) + { + return; + } + if (!bDone) + { + bDone = true; + BuildGraph(InTargetGoal, NewState, ActionQueue); + break; + } + } + } + } + + bool CheckGoal(const TMap& InTest, const TMap& InCurrent) + { + bool bAchieved = false; + + for (TPair Test : InTest) + { + if (InCurrent.Contains(Test.Key)) + { + if (InCurrent[Test.Key] == Test.Value) + { + bAchieved = true; + } + else + { + bAchieved = false; + break; //all or nothing. + } + } + } + + + return bAchieved; + } + + TMap AddGoalChanges(const TMap& InCurrent, const TMap& InChange) + { + TMap NewSet; + + NewSet.Append(InCurrent); + + for (TPair Change : InChange) + { + if (NewSet.Contains(Change.Key)) + { + bool* dd = NewSet.Find(Change.Key); + *dd = Change.Value; + } + else + { + NewSet.Add(Change.Key, Change.Value); + } + } + + return NewSet; + } + + void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, TArray& InActionQueue) + { + BuildGraph(InTargetGoal, InCurrentState, InActionQueue); + } +}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrSelector +{ + GENERATED_BODY() +public: + + UPROPERTY(EditAnywhere) + TArray Evaluators; + + void Choose() + { + TArray SortedDecisions; //actually there will be only one highest scoring PoC + for (const FSpectrEvaluator& Evaluator : Evaluators) + { + if (SortedDecisions.Num() == 0) + { + Evaluator.Evaluate(); + SortedDecisions.Add(Evaluator.Decision); + } + else + { + if (Evaluator.Evaluate() > SortedDecisions[0]) + { + SortedDecisions[0] = Evaluator.Decision; + } + } + } + } +}; + +/* + Current state of the worl from perspective of single AI Actor. +*/ +UCLASS() +class SPECTRAI_API USpectrWorldState : public UObject +{ + GENERATED_BODY() + FGameplayTagContainer ConditionStates; +}; + +/* + Stores Context of world. Should be instanced per AI. + Should be filled by external (or internal) changes like stimuly from senses, + distance to interesting objects, or internal state of character (do I have this item in Inveotry ?). + +*/ + +/** + * + */ +UCLASS() +class SPECTRAI_API ASpectrAIController : public AAIController +{ + GENERATED_BODY() +public: + + TMap Goal; + TMap CurrentState; + FSpectrAI Spectr; + + ASpectrAIController(); + UPROPERTY(EditAnywhere) + FSpectrSelector Selector; +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp new file mode 100644 index 0000000..988813d --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrContext.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h new file mode 100644 index 0000000..9296b75 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "SpectrContext.generated.h" + +/** + * + */ +UCLASS() +class SPECTRAI_API USpectrContext : public UObject +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAI/SpectrAI.uplugin b/Plugins/SpectrAI/SpectrAI.uplugin new file mode 100644 index 0000000..8175de1 --- /dev/null +++ b/Plugins/SpectrAI/SpectrAI.uplugin @@ -0,0 +1,23 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "SpectrAI", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "SpectrAI", + "Type": "Runtime", + "LoadingPhase": "Default" + } + ] +} \ No newline at end of file From 57c11c36da02a9732843724bfb759ccf43dbf018 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 23 Jan 2018 00:08:43 +0100 Subject: [PATCH 025/187] prototype update --- .../Source/SpectrAI/SpectrAIController.cpp | 37 +++++----- .../Source/SpectrAI/SpectrAIController.h | 72 ++++++++++++++++--- 2 files changed, 81 insertions(+), 28 deletions(-) diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp index 0716396..6d0273c 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp @@ -14,45 +14,46 @@ ASpectrAIController::ASpectrAIController() CurrentState.Add(TEXT("HasWood"), false); CurrentState.Add(TEXT("HasAxe"), false); - - FSpectrAction ChopWood; + CurrentState.Add(TEXT("WoodCollected"), false); + FTestContext Context; + FChopTreeAction ChopWood; ChopWood.Name = "ChopWood"; + ChopWood.CustomConditon = true; ChopWood.PreCondition.Add(TEXT("HasWood"), false); - ChopWood.PreCondition.Add(TEXT("WoodChopped"), false); + //ChopWood.PreCondition.Add(TEXT("WoodChopped"), false); ChopWood.PreCondition.Add(TEXT("HasAxe"), true); - ChopWood.Effects.Add(TEXT("WoodChopped"), true); + ChopWood.Effects.Add(TEXT("HasWood"), true); - FSpectrAction PickLogs; + FPickLogAction PickLogs; PickLogs.Name = "PickLogs"; + PickLogs.CustomConditon = false; PickLogs.PreCondition.Add(TEXT("HasWood"), false); PickLogs.Effects.Add(TEXT("HasWood"), true); - PickLogs.Effects.Add(TEXT("WoodCollected"), false); FSpectrAction DropLogs; DropLogs.Name = "DropLogs"; + DropLogs.CustomConditon = true; DropLogs.PreCondition.Add(TEXT("HasWood"), true); DropLogs.Effects.Add(TEXT("HasWood"), false); DropLogs.Effects.Add(TEXT("WoodCollected"), true); - //FSpectrAction ChopWood; - //ChopWood.Name = "ChopWood"; - //ChopWood.PreCondition.Add(TEXT("HasWood"), false); - //ChopWood.PreCondition.Add(TEXT("HasAxe"), true); - //ChopWood.Effects.Add(TEXT("HasWood"), true); - - FSpectrAction PickItem_Axe; + PickItem_Axe.CustomConditon = true; PickItem_Axe.Name = "PickItem_Axe"; PickItem_Axe.PreCondition.Add(TEXT("HasAxe"), false); PickItem_Axe.Effects.Add(TEXT("HasAxe"), true); - Spectr.ActionList.Add(ChopWood); - Spectr.ActionList.Add(PickItem_Axe); - Spectr.ActionList.Add(PickLogs); - Spectr.ActionList.Add(DropLogs); + + Spectr.ActionList.Add(MakeShareable(&PickLogs)); + Spectr.ActionList.Add(MakeShareable(&DropLogs)); + Spectr.ActionList.Add(MakeShareable(&ChopWood)); + Spectr.ActionList.Add(MakeShareable(&PickItem_Axe)); TArray ActionQueue; - Spectr.Plan(Goal, CurrentState, ActionQueue); + TMap MergedState; + MergedState.Append(CurrentState); + MergedState.Append(Goal); + Spectr.Plan(Goal, CurrentState, ActionQueue, Context); float Dupa2 = 0; if (Dupa2 > 0) diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h index 626f298..2e4622f 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h @@ -94,7 +94,18 @@ struct SPECTRAI_API FSpectrEvaluator }; bool operator>(float Rhs, const FSpectrDecision& Lhs); +struct FTestContext +{ + bool bTreeInRange; + bool bLogInRange; + + FTestContext() + : bTreeInRange(true) + , bLogInRange(false) + { + } +}; USTRUCT(BlueprintType) struct FSpectrAction { @@ -103,11 +114,51 @@ struct FSpectrAction FString Name; TMap PreCondition; TMap Effects; - + bool CustomConditon; //precondition //Score to cosnider how viable given action will be UPROPERTY(EditAnywhere) FSpectrQualifier Qualifier; + + virtual ~FSpectrAction() {}; + virtual void Execute(FTestContext& Context) {} + + virtual bool EvaluateCondition(FTestContext& Context) const + { + return CustomConditon; + } +}; + +USTRUCT(BlueprintType) +struct FPickLogAction : public FSpectrAction +{ + GENERATED_BODY() +public: + virtual ~FPickLogAction() {}; + virtual void Execute(FTestContext& Context) + { + Context.bLogInRange = false; + } + virtual bool EvaluateCondition(FTestContext& Context) const override + { + return Context.bLogInRange; + } +}; + +USTRUCT(BlueprintType) +struct FChopTreeAction : public FSpectrAction +{ + GENERATED_BODY() +public: + virtual ~FChopTreeAction() {}; + virtual void Execute(FTestContext& Context) + { + Context.bTreeInRange = false; + } + virtual bool EvaluateCondition(FTestContext& Context) const override + { + return Context.bTreeInRange; + } }; /* @@ -157,21 +208,21 @@ struct SPECTRAI_API FSpectrAI { GENERATED_BODY() public: - TArray ActionList; + TArray> ActionList; //Precondition, List of action for this precondition; TMap> ActionMap; void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, - TArray& ActionQueue) + TArray& ActionQueue, FTestContext& Context) { bool bDone = false; - for (const FSpectrAction& Action : ActionList) + for (const TSharedPtr& Action : ActionList) { - if (CheckGoal(Action.PreCondition, InCurrent)) + if (Action->EvaluateCondition(Context) && CheckGoal(Action->PreCondition, InCurrent)) { - TMap NewState = AddGoalChanges(InCurrent, Action.Effects); - ActionQueue.Add(Action); + TMap NewState = AddGoalChanges(InCurrent, Action->Effects); + ActionQueue.Add(*Action); if (CheckGoal(InTargetGoal, NewState)) { return; @@ -179,7 +230,7 @@ struct SPECTRAI_API FSpectrAI if (!bDone) { bDone = true; - BuildGraph(InTargetGoal, NewState, ActionQueue); + BuildGraph(InTargetGoal, NewState, ActionQueue, Context); break; } } @@ -232,9 +283,10 @@ struct SPECTRAI_API FSpectrAI return NewSet; } - void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, TArray& InActionQueue) + void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, TArray& InActionQueue, + FTestContext& Context) { - BuildGraph(InTargetGoal, InCurrentState, InActionQueue); + BuildGraph(InTargetGoal, InCurrentState, InActionQueue, Context); } }; From 91bded1f97d72bf5fe2fc7adfde2667bcd5248cc Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 23 Jan 2018 22:51:24 +0100 Subject: [PATCH 026/187] starting sample to Spectr --- Config/DefaultGameplayTags.ini | 25 +- .../Source/SpectrAI/SpectrAIController.cpp | 57 +---- .../Source/SpectrAI/SpectrAIController.h | 231 +----------------- .../SpectrAI/Source/SpectrAI/SpectrAction.cpp | 16 ++ .../SpectrAI/Source/SpectrAI/SpectrAction.h | 38 +++ .../Source/SpectrAI/SpectrBrainComponent.cpp | 23 ++ .../Source/SpectrAI/SpectrBrainComponent.h | 157 ++++++++++++ .../SpectrAI/Source/SpectrAI/SpectrContext.h | 2 +- .../SpectrAITest/STestAction_ChopFirewood.cpp | 7 + .../SpectrAITest/STestAction_ChopFirewood.h | 20 ++ .../SpectrAITest/STestAction_ChopWood.cpp | 7 + .../SpectrAITest/STestAction_ChopWood.h | 20 ++ .../STestAction_CollectBranches.cpp | 7 + .../STestAction_CollectBranches.h | 20 ++ .../SpectrAITest/STestAction_CollectOre.cpp | 7 + .../SpectrAITest/STestAction_CollectOre.h | 20 ++ .../SpectrAITest/STestAction_DropFirewood.cpp | 7 + .../SpectrAITest/STestAction_DropFirewood.h | 20 ++ .../SpectrAITest/STestAction_DropOre.cpp | 7 + .../Source/SpectrAITest/STestAction_DropOre.h | 20 ++ .../SpectrAITest/STestAction_DropWood.cpp | 7 + .../SpectrAITest/STestAction_DropWood.h | 20 ++ .../SpectrAITest/STestAction_MakeAxe.cpp | 7 + .../Source/SpectrAITest/STestAction_MakeAxe.h | 20 ++ .../SpectrAITest/STestAction_MakePick.cpp | 7 + .../SpectrAITest/STestAction_MakePick.h | 20 ++ .../SpectrAITest/STestAction_MineOre.cpp | 7 + .../Source/SpectrAITest/STestAction_MineOre.h | 20 ++ .../SpectrAITest/STestAction_PickItemAxe.cpp | 7 + .../SpectrAITest/STestAction_PickItemAxe.h | 20 ++ .../SpectrAITest/STestAction_PickItemPick.cpp | 7 + .../SpectrAITest/STestAction_PickItemPick.h | 20 ++ .../Source/SpectrAITest/STestBranch.cpp | 27 ++ .../Source/SpectrAITest/STestBranch.h | 28 +++ .../Source/SpectrAITest/STestForge.cpp | 27 ++ .../Source/SpectrAITest/STestForge.h | 28 +++ .../Source/SpectrAITest/STestStorage.cpp | 27 ++ .../Source/SpectrAITest/STestStorage.h | 28 +++ .../Source/SpectrAITest/STestTree.cpp | 27 ++ .../Source/SpectrAITest/STestTree.h | 28 +++ .../Source/SpectrAITest/SpectrAITest.Build.cs | 61 +++++ .../Source/SpectrAITest/SpectrAITest.cpp | 20 ++ .../Source/SpectrAITest/SpectrAITest.h | 15 ++ Plugins/SpectrAITest/SpectrAITest.uplugin | 29 +++ 44 files changed, 918 insertions(+), 300 deletions(-) create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h create mode 100644 Plugins/SpectrAITest/SpectrAITest.uplugin diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 36a060e..4bf0491 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -5,26 +5,6 @@ WarnOnInvalidTags=True FastReplication=False NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 --GameplayTagList=(Tag="Ability.Corruption",DevComment="") --GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") --GameplayTagList=(Tag="Ability.Input.NextWeapon",DevComment="") --GameplayTagList=(Tag="Ability.Input.PreviousWeapon",DevComment="") --GameplayTagList=(Tag="Ability.Input.SwitchAbilities",DevComment="") --GameplayTagList=(Tag="Ability.Rifle",DevComment="") --GameplayTagList=(Tag="Ability.Rifle.Activate",DevComment="") --GameplayTagList=(Tag="Ability.Rifle.Ammo",DevComment="") --GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") --GameplayTagList=(Tag="Ability.Rifle.Reload",DevComment="") --GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") --GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") --GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") --GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") --GameplayTagList=(Tag="Damage",DevComment="") --GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") --GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") --GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") --GameplayTagList=(Tag="Input.UI.WeaponNext",DevComment="") --GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.Input.Jump",DevComment="") @@ -39,6 +19,11 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") ++GameplayTagList=(Tag="AI.HaveAxe",DevComment="") ++GameplayTagList=(Tag="AI.HaveOre",DevComment="") ++GameplayTagList=(Tag="AI.HavePick",DevComment="") ++GameplayTagList=(Tag="AI.HaveWood",DevComment="") ++GameplayTagList=(Tag="AI.WoodCollected",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +GameplayTagList=(Tag="Damage",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp index 6d0273c..285f183 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp @@ -1,63 +1,14 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "SpectrAIController.h" - +#include "SpectrBrainComponent.h" bool operator>(float Rhs, const FSpectrDecision& Lhs) { return Rhs > Lhs.Score; } - -ASpectrAIController::ASpectrAIController() +ASpectrAIController::ASpectrAIController(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) { - Goal.Add(TEXT("WoodCollected"), true); - - CurrentState.Add(TEXT("HasWood"), false); - CurrentState.Add(TEXT("HasAxe"), false); - CurrentState.Add(TEXT("WoodCollected"), false); - FTestContext Context; - FChopTreeAction ChopWood; - ChopWood.Name = "ChopWood"; - ChopWood.CustomConditon = true; - ChopWood.PreCondition.Add(TEXT("HasWood"), false); - //ChopWood.PreCondition.Add(TEXT("WoodChopped"), false); - ChopWood.PreCondition.Add(TEXT("HasAxe"), true); - ChopWood.Effects.Add(TEXT("HasWood"), true); - - FPickLogAction PickLogs; - PickLogs.Name = "PickLogs"; - PickLogs.CustomConditon = false; - PickLogs.PreCondition.Add(TEXT("HasWood"), false); - PickLogs.Effects.Add(TEXT("HasWood"), true); - - FSpectrAction DropLogs; - DropLogs.Name = "DropLogs"; - DropLogs.CustomConditon = true; - DropLogs.PreCondition.Add(TEXT("HasWood"), true); - DropLogs.Effects.Add(TEXT("HasWood"), false); - DropLogs.Effects.Add(TEXT("WoodCollected"), true); - - FSpectrAction PickItem_Axe; - PickItem_Axe.CustomConditon = true; - PickItem_Axe.Name = "PickItem_Axe"; - PickItem_Axe.PreCondition.Add(TEXT("HasAxe"), false); - PickItem_Axe.Effects.Add(TEXT("HasAxe"), true); - - - Spectr.ActionList.Add(MakeShareable(&PickLogs)); - Spectr.ActionList.Add(MakeShareable(&DropLogs)); - Spectr.ActionList.Add(MakeShareable(&ChopWood)); - Spectr.ActionList.Add(MakeShareable(&PickItem_Axe)); - - TArray ActionQueue; - TMap MergedState; - MergedState.Append(CurrentState); - MergedState.Append(Goal); - Spectr.Plan(Goal, CurrentState, ActionQueue, Context); - - float Dupa2 = 0; - if (Dupa2 > 0) - { - - } + SpectrBrain = ObjectInitializer.CreateDefaultSubobject(this, TEXT("SpectrBrain")); } \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h index 2e4622f..a4b42cc 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h @@ -4,9 +4,6 @@ #include "CoreMinimal.h" #include "AIController.h" -#include "GameplayTags.h" -#include "GameplayTagContainer.h" -#include "Queue.h" #include "SpectrAIController.generated.h" //Consideration (calculates score) @@ -106,60 +103,6 @@ struct FTestContext } }; -USTRUCT(BlueprintType) -struct FSpectrAction -{ - GENERATED_BODY() -public: - FString Name; - TMap PreCondition; - TMap Effects; - bool CustomConditon; - //precondition - //Score to cosnider how viable given action will be - UPROPERTY(EditAnywhere) - FSpectrQualifier Qualifier; - - virtual ~FSpectrAction() {}; - virtual void Execute(FTestContext& Context) {} - - virtual bool EvaluateCondition(FTestContext& Context) const - { - return CustomConditon; - } -}; - -USTRUCT(BlueprintType) -struct FPickLogAction : public FSpectrAction -{ - GENERATED_BODY() -public: - virtual ~FPickLogAction() {}; - virtual void Execute(FTestContext& Context) - { - Context.bLogInRange = false; - } - virtual bool EvaluateCondition(FTestContext& Context) const override - { - return Context.bLogInRange; - } -}; - -USTRUCT(BlueprintType) -struct FChopTreeAction : public FSpectrAction -{ - GENERATED_BODY() -public: - virtual ~FChopTreeAction() {}; - virtual void Execute(FTestContext& Context) - { - Context.bTreeInRange = false; - } - virtual bool EvaluateCondition(FTestContext& Context) const override - { - return Context.bTreeInRange; - } -}; /* High level goal we try to create plan for. @@ -175,168 +118,6 @@ struct FSpectrGoal FSpectrQualifier Qualifier; }; -USTRUCT(BlueprintType) -struct FSpectrPlanner -{ - GENERATED_BODY() -public: - void Plan(const FSpectrAction& InAction, const FSpectrGoal& Goal) - { - TQueue < FSpectrAction, EQueueMode::Mpsc > ActionQueue; - } -}; - -/* -Actions:: ---ChopLog - --Preconditions - AI.HasTool - AI.HasLogs - --Effects - AI.HasLogs - - -Actor: - FSpectrGoal:: - --CollectWood - Precondition: - --AI.HasLogs -*/ - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrAI -{ - GENERATED_BODY() -public: - TArray> ActionList; - - //Precondition, List of action for this precondition; - TMap> ActionMap; - - void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, - TArray& ActionQueue, FTestContext& Context) - { - bool bDone = false; - for (const TSharedPtr& Action : ActionList) - { - if (Action->EvaluateCondition(Context) && CheckGoal(Action->PreCondition, InCurrent)) - { - TMap NewState = AddGoalChanges(InCurrent, Action->Effects); - ActionQueue.Add(*Action); - if (CheckGoal(InTargetGoal, NewState)) - { - return; - } - if (!bDone) - { - bDone = true; - BuildGraph(InTargetGoal, NewState, ActionQueue, Context); - break; - } - } - } - } - - bool CheckGoal(const TMap& InTest, const TMap& InCurrent) - { - bool bAchieved = false; - - for (TPair Test : InTest) - { - if (InCurrent.Contains(Test.Key)) - { - if (InCurrent[Test.Key] == Test.Value) - { - bAchieved = true; - } - else - { - bAchieved = false; - break; //all or nothing. - } - } - } - - - return bAchieved; - } - - TMap AddGoalChanges(const TMap& InCurrent, const TMap& InChange) - { - TMap NewSet; - - NewSet.Append(InCurrent); - - for (TPair Change : InChange) - { - if (NewSet.Contains(Change.Key)) - { - bool* dd = NewSet.Find(Change.Key); - *dd = Change.Value; - } - else - { - NewSet.Add(Change.Key, Change.Value); - } - } - - return NewSet; - } - - void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, TArray& InActionQueue, - FTestContext& Context) - { - BuildGraph(InTargetGoal, InCurrentState, InActionQueue, Context); - } -}; - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrSelector -{ - GENERATED_BODY() -public: - - UPROPERTY(EditAnywhere) - TArray Evaluators; - - void Choose() - { - TArray SortedDecisions; //actually there will be only one highest scoring PoC - for (const FSpectrEvaluator& Evaluator : Evaluators) - { - if (SortedDecisions.Num() == 0) - { - Evaluator.Evaluate(); - SortedDecisions.Add(Evaluator.Decision); - } - else - { - if (Evaluator.Evaluate() > SortedDecisions[0]) - { - SortedDecisions[0] = Evaluator.Decision; - } - } - } - } -}; - -/* - Current state of the worl from perspective of single AI Actor. -*/ -UCLASS() -class SPECTRAI_API USpectrWorldState : public UObject -{ - GENERATED_BODY() - FGameplayTagContainer ConditionStates; -}; - -/* - Stores Context of world. Should be instanced per AI. - Should be filled by external (or internal) changes like stimuly from senses, - distance to interesting objects, or internal state of character (do I have this item in Inveotry ?). - -*/ - /** * */ @@ -345,12 +126,10 @@ class SPECTRAI_API ASpectrAIController : public AAIController { GENERATED_BODY() public: - - TMap Goal; - TMap CurrentState; - FSpectrAI Spectr; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + class USpectrBrainComponent* SpectrBrain; - ASpectrAIController(); - UPROPERTY(EditAnywhere) - FSpectrSelector Selector; + ASpectrAIController(const FObjectInitializer& ObjectInitializer); + + }; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp new file mode 100644 index 0000000..544777a --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrAction.h" + + + + +void USpectrAction::Execute_Implementation(class USpectrContext* InContext) +{ + +} + +bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InContext) +{ + return true; +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h new file mode 100644 index 0000000..07d4e69 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "SpectrAction.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAI_API USpectrAction : public UObject +{ + GENERATED_BODY() +public: + /* + Tag Name of requirent condition in agent state, Desiared State Value + */ + UPROPERTY(EditAnywhere, Category = "State Configuration") + TMap PreConditions; + + /* + Tag Name of change applied to agent state is effect is executed, Desiared State Value + */ + UPROPERTY(EditAnywhere, Category = "State Configuration") + TMap Effects; + + UFUNCTION(BlueprintNativeEvent) + void Execute(class USpectrContext* InContext); + virtual void Execute_Implementation(class USpectrContext* InContext); + + UFUNCTION(BlueprintNativeEvent) + bool EvaluateCondition(class USpectrContext* InContext); + virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext); +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp new file mode 100644 index 0000000..ff5a742 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrBrainComponent.h" +#include "SpectrContext.h" + +USpectrBrainComponent::USpectrBrainComponent() +{ + if(Context) + CurrentContext = Cast(CreateDefaultSubobject(TEXT("CurrentContext"), Context, Context, true, false, false)); +} + +void USpectrBrainComponent::StarPlanning() +{ + TArray> OutActionList; + SpectrAI.Plan(Goal, CurrentState, OutActionList, ActionList, CurrentContext); + + for (const TSubclassOf& Action : OutActionList) + { + FString name = Action.GetDefaultObject()->GetName(); + + UE_LOG(LogTemp, Log, TEXT("Action Name: %s \n"), *name); + } +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h new file mode 100644 index 0000000..b251616 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -0,0 +1,157 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "BrainComponent.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "Queue.h" +#include "SpectrAction.h" +#include "SpectrBrainComponent.generated.h" + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrAI +{ + GENERATED_BODY() +public: + //Precondition, List of action for this precondition; + TMap> > ActionMap; + + void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, + TArray>& ActionQueue, const TArray>& ActionList, + class USpectrContext* InContext) + { + bool bDone = false; + for (const TSubclassOf& Action : ActionList) + { + if (Action.GetDefaultObject()->EvaluateCondition(InContext) && CheckGoal(Action.GetDefaultObject()->PreConditions, InCurrent)) + { + TMap NewState = AddGoalChanges(InCurrent, Action.GetDefaultObject()->Effects); + ActionQueue.Add(Action); + if (CheckGoal(InTargetGoal, NewState)) + { + return; + } + if (!bDone) + { + bDone = true; + BuildGraph(InTargetGoal, NewState, ActionQueue, ActionList, InContext); + break; + } + } + } + } + + bool CheckGoal(const TMap& InTest, const TMap& InCurrent) + { + bool bAchieved = false; + + for (TPair Test : InTest) + { + if (InCurrent.Contains(Test.Key)) + { + if (InCurrent[Test.Key] == Test.Value) + { + bAchieved = true; + } + else + { + bAchieved = false; + break; //all or nothing. + } + } + } + + + return bAchieved; + } + + TMap AddGoalChanges(const TMap& InCurrent, const TMap& InChange) + { + TMap NewSet; + + NewSet.Append(InCurrent); + + for (TPair Change : InChange) + { + if (NewSet.Contains(Change.Key)) + { + bool* dd = NewSet.Find(Change.Key); + *dd = Change.Value; + } + else + { + NewSet.Add(Change.Key, Change.Value); + } + } + + return NewSet; + } + + void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, + TArray>& InActionQueue, const TArray>& ActionList, + class USpectrContext* InContext) + { + BuildGraph(InTargetGoal, InCurrentState, InActionQueue, ActionList, InContext); + } +}; + +//USTRUCT(BlueprintType) +//struct SPECTRAI_API FSpectrSelector +//{ +// GENERATED_BODY() +//public: +// +// UPROPERTY(EditAnywhere) +// TArray Evaluators; +// +// void Choose() +// { +// TArray SortedDecisions; //actually there will be only one highest scoring PoC +// for (const FSpectrEvaluator& Evaluator : Evaluators) +// { +// if (SortedDecisions.Num() == 0) +// { +// Evaluator.Evaluate(); +// SortedDecisions.Add(Evaluator.Decision); +// } +// else +// { +// if (Evaluator.Evaluate() > SortedDecisions[0]) +// { +// SortedDecisions[0] = Evaluator.Decision; +// } +// } +// } +// } +//}; + + +/** + * + */ +UCLASS() +class SPECTRAI_API USpectrBrainComponent : public UActorComponent +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TMap Goal; + UPROPERTY(EditAnywhere) + TMap CurrentState; + UPROPERTY(EditAnywhere) + TArray> ActionList; + + UPROPERTY(EditAnywhere) + TSubclassOf Context; + + class USpectrContext* CurrentContext; + + FSpectrAI SpectrAI; + + USpectrBrainComponent(); + UFUNCTION(BlueprintCallable) + void StarPlanning(); + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h index 9296b75..8822a25 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h @@ -9,7 +9,7 @@ /** * */ -UCLASS() +UCLASS(BlueprintType, Blueprintable) class SPECTRAI_API USpectrContext : public UObject { GENERATED_BODY() diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp new file mode 100644 index 0000000..b68a39f --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_ChopFirewood.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h new file mode 100644 index 0000000..a5ea064 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_ChopFirewood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_ChopFirewood : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp new file mode 100644 index 0000000..001a874 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_ChopWood.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h new file mode 100644 index 0000000..8f58cfd --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_ChopWood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_ChopWood : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp new file mode 100644 index 0000000..876aefc --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_CollectBranches.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h new file mode 100644 index 0000000..bae50a2 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_CollectBranches.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_CollectBranches : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp new file mode 100644 index 0000000..3800d2d --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_CollectOre.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h new file mode 100644 index 0000000..212463b --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_CollectOre.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_CollectOre : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp new file mode 100644 index 0000000..51b3f40 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_DropFirewood.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h new file mode 100644 index 0000000..e8df383 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_DropFirewood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_DropFirewood : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp new file mode 100644 index 0000000..d017aad --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_DropOre.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h new file mode 100644 index 0000000..2883ff4 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_DropOre.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_DropOre : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp new file mode 100644 index 0000000..0cafb3b --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_DropWood.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h new file mode 100644 index 0000000..04fb1c8 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_DropWood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_DropWood : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp new file mode 100644 index 0000000..c9b4702 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_MakeAxe.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h new file mode 100644 index 0000000..030d66c --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_MakeAxe.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_MakeAxe : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp new file mode 100644 index 0000000..a50a2b5 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_MakePick.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h new file mode 100644 index 0000000..b694046 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_MakePick.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_MakePick : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp new file mode 100644 index 0000000..6c91e77 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_MineOre.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h new file mode 100644 index 0000000..6472f2e --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_MineOre.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_MineOre : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp new file mode 100644 index 0000000..9726888 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_PickItemAxe.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h new file mode 100644 index 0000000..a9cdda9 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_PickItemAxe.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_PickItemAxe : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp new file mode 100644 index 0000000..4d1578b --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_PickItemPick.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h new file mode 100644 index 0000000..a22eaff --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_PickItemPick.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_PickItemPick : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp new file mode 100644 index 0000000..9296a87 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestBranch.h" + + +// Sets default values +ASTestBranch::ASTestBranch() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestBranch::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestBranch::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h new file mode 100644 index 0000000..2c1755a --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestBranch.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestBranch : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestBranch(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp new file mode 100644 index 0000000..22d4aa4 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestForge.h" + + +// Sets default values +ASTestForge::ASTestForge() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestForge::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestForge::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h new file mode 100644 index 0000000..21f2f0e --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestForge.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestForge : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestForge(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp new file mode 100644 index 0000000..a28db48 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestStorage.h" + + +// Sets default values +ASTestStorage::ASTestStorage() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestStorage::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestStorage::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h new file mode 100644 index 0000000..fcf1463 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestStorage.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestStorage : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestStorage(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp new file mode 100644 index 0000000..cc09e79 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestTree.h" + + +// Sets default values +ASTestTree::ASTestTree() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestTree::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestTree::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h new file mode 100644 index 0000000..1c0cb6c --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestTree.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestTree : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestTree(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs new file mode 100644 index 0000000..f899150 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs @@ -0,0 +1,61 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class SpectrAITest : ModuleRules +{ + public SpectrAITest(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "SpectrAITest/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "SpectrAITest/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "Core", + "CoreUObject", + "Engine", + "InputCore", + "Slate", + "SlateCore", + "AIModule", + "GameplayTags", + "GameplayTasks", + "SpectrAI" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp new file mode 100644 index 0000000..ebd2517 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "SpectrAITest.h" + +#define LOCTEXT_NAMESPACE "FSpectrAITestModule" + +void FSpectrAITestModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FSpectrAITestModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FSpectrAITestModule, SpectrAITest) \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h new file mode 100644 index 0000000..8f51c72 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FSpectrAITestModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Plugins/SpectrAITest/SpectrAITest.uplugin b/Plugins/SpectrAITest/SpectrAITest.uplugin new file mode 100644 index 0000000..fbc88e1 --- /dev/null +++ b/Plugins/SpectrAITest/SpectrAITest.uplugin @@ -0,0 +1,29 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "SpectrAITest", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "SpectrAITest", + "Type": "Developer", + "LoadingPhase": "Default" + } + ], + "Plugins": [ + { + "Name": "SpectrAI", + "Enabled": true + } + ] +} \ No newline at end of file From 58ba1064d599fefbee7e752d07adda67bec7498e Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 24 Jan 2018 00:39:57 +0100 Subject: [PATCH 027/187] Spectr update --- .../Source/SpectrAI/SpectrAIController.h | 14 ----- .../Source/SpectrAI/SpectrBrainComponent.h | 29 +++++++++-- .../SpectrAI/Source/SpectrAI/SpectrGoal.cpp | 7 +++ Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h | 51 +++++++++++++++++++ 4 files changed, 84 insertions(+), 17 deletions(-) create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h index a4b42cc..476d990 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h @@ -104,20 +104,6 @@ struct FTestContext } }; -/* - High level goal we try to create plan for. -*/ -struct FSpectrGoal -{ - /* - All of these tags must be present on Actor State to satisfy this goal. - */ - TMap RequiredConditions; - - /* Qualify if planner should for a plan for this Goal. */ - FSpectrQualifier Qualifier; -}; - /** * */ diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index b251616..e042890 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -10,6 +10,12 @@ #include "SpectrAction.h" #include "SpectrBrainComponent.generated.h" +//Node representing single step in plan. +struct FSpectrNode +{ + +}; + USTRUCT(BlueprintType) struct SPECTRAI_API FSpectrAI { @@ -25,6 +31,7 @@ struct SPECTRAI_API FSpectrAI bool bDone = false; for (const TSubclassOf& Action : ActionList) { + UE_LOG(LogTemp, Log, TEXT("-Build Plan - Action Name: %s \n"), *Action.GetDefaultObject()->GetName()); if (Action.GetDefaultObject()->EvaluateCondition(InContext) && CheckGoal(Action.GetDefaultObject()->PreConditions, InCurrent)) { TMap NewState = AddGoalChanges(InCurrent, Action.GetDefaultObject()->Effects); @@ -46,17 +53,23 @@ struct SPECTRAI_API FSpectrAI bool CheckGoal(const TMap& InTest, const TMap& InCurrent) { bool bAchieved = false; - + for (TPair Test : InCurrent) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Check Current Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + for (TPair Test : InTest) { if (InCurrent.Contains(Test.Key)) { if (InCurrent[Test.Key] == Test.Value) { + UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Passed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); bAchieved = true; } else { + UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Failed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); bAchieved = false; break; //all or nothing. } @@ -72,7 +85,12 @@ struct SPECTRAI_API FSpectrAI TMap NewSet; NewSet.Append(InCurrent); - + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE START")); + for (TPair Test : InCurrent) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE END")); for (TPair Change : InChange) { if (NewSet.Contains(Change.Key)) @@ -85,7 +103,12 @@ struct SPECTRAI_API FSpectrAI NewSet.Add(Change.Key, Change.Value); } } - + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST START")); + for (TPair Test : NewSet) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST END")); return NewSet; } diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp new file mode 100644 index 0000000..3b2ccbf --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrGoal.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h new file mode 100644 index 0000000..0cfda69 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h @@ -0,0 +1,51 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "SpectrGoal.generated.h" + +/** + * + */ +UCLASS() +class SPECTRAI_API USpectrGoal : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TMap Goal; + + //What to change in state if goal has been achieved ? + UPROPERTY(EditAnywhere) + TMap FinishedState; + + //What Should we do if this goal is selected ? + virtual void SetupState() + { + + } + + //Called when goal has been selected, just before plan is executed. + virtual void GoalStarted() + { + + } + + //called just after plan finished execution + virtual void GoalFinished() + { + + } + + //called if plan for some reason cannot be finished and is aborted. + virtual void GoalAborted() + { + + } + + +}; From 175acaedbc4c6879bc77cd2a15b7bc1b8db47be4 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 24 Jan 2018 00:42:42 +0100 Subject: [PATCH 028/187] Spectr goal --- Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h index 0cfda69..b28e378 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h @@ -22,9 +22,14 @@ class SPECTRAI_API USpectrGoal : public UObject //What to change in state if goal has been achieved ? UPROPERTY(EditAnywhere) TMap FinishedState; - + + virtual float QualifyGoal(class USpectrContext* InContext) + { + return -1.0f; + } + //What Should we do if this goal is selected ? - virtual void SetupState() + virtual void GoalSelected() { } From 73abfce936179ece566d0ceae59b7085c2d24c4a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 24 Jan 2018 14:26:08 +0100 Subject: [PATCH 029/187] Chaged action search from forward to reverse. --- .../AFEK2Node_AsyncEffectTaskCall.cpp | 1 - .../GAEK2Node_LatentAbilityTaskCall.cpp | 1 - .../Source/SpectrAI/SpectrBrainComponent.h | 51 +++++++++++++------ 3 files changed, 36 insertions(+), 17 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp index de15873..61b6b5f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp @@ -4,7 +4,6 @@ #include "Kismet/KismetArrayLibrary.h" #include "GameplayTask.h" #include "Effects/EffectTasks/AFEffectTask.h" -#include "AFBlueprintFunctionLibrary.h" #include "Effects/GAEffectExtension.h" #include "KismetCompiler.h" #include "BlueprintEditorUtils.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp index b039916..8fbc0f2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -4,7 +4,6 @@ #include "Kismet/KismetArrayLibrary.h" #include "GameplayTask.h" #include "Abilities/Tasks/GAAbilityTask.h" -#include "AFBlueprintFunctionLibrary.h" #include "Abilities/GAAbilityBase.h" #include "KismetCompiler.h" #include "BlueprintEditorUtils.h" diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index e042890..56c52c1 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -32,37 +32,41 @@ struct SPECTRAI_API FSpectrAI for (const TSubclassOf& Action : ActionList) { UE_LOG(LogTemp, Log, TEXT("-Build Plan - Action Name: %s \n"), *Action.GetDefaultObject()->GetName()); - if (Action.GetDefaultObject()->EvaluateCondition(InContext) && CheckGoal(Action.GetDefaultObject()->PreConditions, InCurrent)) + if (Action.GetDefaultObject()->EvaluateCondition(InContext) + && CheckGoal(Action.GetDefaultObject()->Effects, InTargetGoal)) { - TMap NewState = AddGoalChanges(InCurrent, Action.GetDefaultObject()->Effects); + TMap UpdatedGoalState = UpdateState(Action.GetDefaultObject()->Effects, + InTargetGoal); + TMap NewGoal = AddGoalChanges(UpdatedGoalState, + Action.GetDefaultObject()->PreConditions); ActionQueue.Add(Action); - if (CheckGoal(InTargetGoal, NewState)) + if (CheckGoal(UpdatedGoalState, NewGoal)) { return; } if (!bDone) { bDone = true; - BuildGraph(InTargetGoal, NewState, ActionQueue, ActionList, InContext); + BuildGraph(NewGoal, NewGoal, ActionQueue, ActionList, InContext); break; } } } } - bool CheckGoal(const TMap& InTest, const TMap& InCurrent) + bool CheckGoal(const TMap& InEffects, const TMap& InGoal) { bool bAchieved = false; - for (TPair Test : InCurrent) + for (TPair Test : InGoal) { UE_LOG(LogTemp, Log, TEXT("---Build Plan - Check Current Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); } - for (TPair Test : InTest) + for (TPair Test : InEffects) { - if (InCurrent.Contains(Test.Key)) + if (InGoal.Contains(Test.Key)) { - if (InCurrent[Test.Key] == Test.Value) + if (InGoal[Test.Key] == Test.Value) { UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Passed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); bAchieved = true; @@ -80,23 +84,40 @@ struct SPECTRAI_API FSpectrAI return bAchieved; } - TMap AddGoalChanges(const TMap& InCurrent, const TMap& InChange) + TMap UpdateState(const TMap& InEffects, + const TMap& InCurrentState) + { + TMap NewState; + NewState.Append(InCurrentState); + for (TPair Effect : InEffects) + { + if (NewState.Contains(Effect.Key)) + { + bool* dd = NewState.Find(Effect.Key); + *dd = Effect.Value; + } + } + return NewState; + } + + TMap AddGoalChanges(const TMap& InCurrentGoal, + const TMap& InGoalChange) { TMap NewSet; - NewSet.Append(InCurrent); + NewSet.Append(InCurrentGoal); UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE START")); - for (TPair Test : InCurrent) + for (TPair Test : InCurrentGoal) { UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); } UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE END")); - for (TPair Change : InChange) + for (TPair Change : InGoalChange) { if (NewSet.Contains(Change.Key)) { - bool* dd = NewSet.Find(Change.Key); - *dd = Change.Value; + /*bool* dd = NewSet.Find(Change.Key); + *dd = Change.Value;*/ } else { From 91bbafbd21bbb3a805a94b6617c61f95d26c3da3 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 25 Jan 2018 00:24:25 +0100 Subject: [PATCH 030/187] spectr update --- .../SpectrAI/Source/SpectrAI/SpectrAction.h | 2 + .../Source/SpectrAI/SpectrBrainComponent.h | 133 +++++++++++++++--- 2 files changed, 113 insertions(+), 22 deletions(-) diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h index 07d4e69..6b9d26a 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h @@ -16,6 +16,8 @@ class SPECTRAI_API USpectrAction : public UObject { GENERATED_BODY() public: + UPROPERTY(EditAnywhere, Category = "State Configuration") + int32 Cost; /* Tag Name of requirent condition in agent state, Desiared State Value */ diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index 56c52c1..9cf801f 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -13,7 +13,18 @@ //Node representing single step in plan. struct FSpectrNode { - + int32 Cost; + int32 RemainingCost; + TWeakPtr Parent; + TMap State; + TSubclassOf Action; + TArray> Children; + FSpectrNode() {} + FSpectrNode(const TMap& InState, int32 InCost, int32 InRemainingCost) + : Cost(InCost) + , RemainingCost(InRemainingCost) + , State(InState) + {} }; USTRUCT(BlueprintType) @@ -24,36 +35,103 @@ struct SPECTRAI_API FSpectrAI //Precondition, List of action for this precondition; TMap> > ActionMap; - void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, - TArray>& ActionQueue, const TArray>& ActionList, - class USpectrContext* InContext) + void BuildGraph2(TArray>& InNodes, const TArray>& ActionList, TSharedPtr PathParent) { - bool bDone = false; - for (const TSubclassOf& Action : ActionList) + for (TSharedPtr Node : InNodes) { - UE_LOG(LogTemp, Log, TEXT("-Build Plan - Action Name: %s \n"), *Action.GetDefaultObject()->GetName()); - if (Action.GetDefaultObject()->EvaluateCondition(InContext) - && CheckGoal(Action.GetDefaultObject()->Effects, InTargetGoal)) + for (TSubclassOf Action : ActionList) { - TMap UpdatedGoalState = UpdateState(Action.GetDefaultObject()->Effects, - InTargetGoal); - TMap NewGoal = AddGoalChanges(UpdatedGoalState, - Action.GetDefaultObject()->PreConditions); - ActionQueue.Add(Action); - if (CheckGoal(UpdatedGoalState, NewGoal)) + if (CheckGoal(Action.GetDefaultObject()->Effects, Node->State)) { - return; - } - if (!bDone) - { - bDone = true; - BuildGraph(NewGoal, NewGoal, ActionQueue, ActionList, InContext); + TMap NewState = Action.GetDefaultObject()->PreConditions; // AddGoalChanges(Action.GetDefaultObject()->PreConditions, Node->State); + TSharedPtr Node2 = MakeShareable(new FSpectrNode(NewState, 0, 0)); + Node2->Action = Action; + Node->Children.Add(Node2); + + if (PathParent.IsValid()) + { + PathParent->Cost += Action.GetDefaultObject()->Cost; + } + else + { + //first iteration; + PathParent = Node; + PathParent->Cost += Action.GetDefaultObject()->Cost; + } + BuildGraph2(Node->Children, ActionList, PathParent); break; } } } } + void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, + TArray>& ActionQueue, const TArray>& ActionList, + class USpectrContext* InContext) + { + + TArray> OpenNodes; + TArray> ClosedNodes; + + TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); + + //OpenNodes.Push(Node); + TArray> AvailableActions = ActionList; + + + //first find all nodes which will fullfil intial goal + for (const TSubclassOf& Action : ActionList) + { + if (CheckGoal(Action.GetDefaultObject()->Effects, InTargetGoal)) + { + TMap NewState = Action.GetDefaultObject()->PreConditions;// AddGoalChanges(Action.GetDefaultObject()->PreConditions, Node->State); + TSharedPtr Node2 = MakeShareable(new FSpectrNode(NewState, 0, 0)); + Node2->Action = Action; + OpenNodes.Add(Node2); + + //remove action which will fullfil initial goal state. + AvailableActions.Remove(Action); + } + } + BuildGraph2(OpenNodes, AvailableActions, nullptr); + + + for (TSharedPtr Node : OpenNodes) + { + + } + //TArray> AvailableActions; + //AvailableActions.Append(ActionList); + //TArray> UsedList; + //bool bDone = false; + //while (AvailableActions.Num() > 0) + //{ + // TSubclassOf Action = AvailableActions.Pop(); + // UsedList.Push(Action); + // UE_LOG(LogTemp, Log, TEXT("-Build Plan - Action Name: %s \n"), *Action.GetDefaultObject()->GetName()); + // if (Action.GetDefaultObject()->EvaluateCondition(InContext) + // && CheckGoal(Action.GetDefaultObject()->Effects, InTargetGoal)) + // { + // TMap NewGoal = AddGoalChanges(InTargetGoal, + // Action.GetDefaultObject()->PreConditions); + // + // ActionQueue.Add(Action); + // /*if (CheckGoal(UpdatedGoalState, NewGoal)) + // { + // return; + // }*/ + // UsedList.Append(AvailableActions); + // UsedList.Remove(Action); + // if (!bDone) + // { + // bDone = true; + // BuildGraph(NewGoal, NewGoal, ActionQueue, UsedList, InContext); + // break; + // } + // } + //} + } + bool CheckGoal(const TMap& InEffects, const TMap& InGoal) { bool bAchieved = false; @@ -132,7 +210,18 @@ struct SPECTRAI_API FSpectrAI UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST END")); return NewSet; } - + void InitializeMap(const TArray>& ActionList) + { + for (const TSubclassOf Action : ActionList) + { + for (const TPair& Effect : Action.GetDefaultObject()->Effects) + { + TArray>& ActionArray = ActionMap.FindOrAdd(Effect.Key); + ActionArray.Add(Action); + } + + } + } void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, TArray>& InActionQueue, const TArray>& ActionList, class USpectrContext* InContext) From aa953921c28ee8e3b66eb106c4dad405cb55cae1 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 25 Jan 2018 21:11:44 +0100 Subject: [PATCH 031/187] Spectr prototyping plan searching --- .../Source/SpectrAI/SpectrBrainComponent.cpp | 9 +- .../Source/SpectrAI/SpectrBrainComponent.h | 132 ++++++++---------- 2 files changed, 64 insertions(+), 77 deletions(-) diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp index ff5a742..4130742 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp @@ -2,7 +2,14 @@ #include "SpectrBrainComponent.h" #include "SpectrContext.h" - +bool operator==(const FSpectrNode& Other, const TSubclassOf& Action) +{ + return Other.Action == Action; +} +bool operator==(FSpectrNode* Other, const TSubclassOf& Action) +{ + return Other->Action == Action; +} USpectrBrainComponent::USpectrBrainComponent() { if(Context) diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index 9cf801f..2e890cf 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -25,8 +25,21 @@ struct FSpectrNode , RemainingCost(InRemainingCost) , State(InState) {} + + bool operator==(const FSpectrNode& Other) const + { + return Action == Other.Action; + } + bool operator==(const TSubclassOf& Other) const + { + return Action == Other; + } + }; +bool operator==(const FSpectrNode& Other, const TSubclassOf& Action); +bool operator==(FSpectrNode* Other, const TSubclassOf& Action); + USTRUCT(BlueprintType) struct SPECTRAI_API FSpectrAI { @@ -35,35 +48,6 @@ struct SPECTRAI_API FSpectrAI //Precondition, List of action for this precondition; TMap> > ActionMap; - void BuildGraph2(TArray>& InNodes, const TArray>& ActionList, TSharedPtr PathParent) - { - for (TSharedPtr Node : InNodes) - { - for (TSubclassOf Action : ActionList) - { - if (CheckGoal(Action.GetDefaultObject()->Effects, Node->State)) - { - TMap NewState = Action.GetDefaultObject()->PreConditions; // AddGoalChanges(Action.GetDefaultObject()->PreConditions, Node->State); - TSharedPtr Node2 = MakeShareable(new FSpectrNode(NewState, 0, 0)); - Node2->Action = Action; - Node->Children.Add(Node2); - - if (PathParent.IsValid()) - { - PathParent->Cost += Action.GetDefaultObject()->Cost; - } - else - { - //first iteration; - PathParent = Node; - PathParent->Cost += Action.GetDefaultObject()->Cost; - } - BuildGraph2(Node->Children, ActionList, PathParent); - break; - } - } - } - } void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, TArray>& ActionQueue, const TArray>& ActionList, class USpectrContext* InContext) @@ -74,62 +58,58 @@ struct SPECTRAI_API FSpectrAI TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); - //OpenNodes.Push(Node); + OpenNodes.Push(Node); TArray> AvailableActions = ActionList; - - //first find all nodes which will fullfil intial goal - for (const TSubclassOf& Action : ActionList) + //reverse A*, or something similiar to it at least.. + while (OpenNodes.Num()) { - if (CheckGoal(Action.GetDefaultObject()->Effects, InTargetGoal)) + TSharedPtr CurrentNode = OpenNodes.Pop(); + ClosedNodes.Push(CurrentNode); + + for (const TSubclassOf& Action : AvailableActions) { - TMap NewState = Action.GetDefaultObject()->PreConditions;// AddGoalChanges(Action.GetDefaultObject()->PreConditions, Node->State); - TSharedPtr Node2 = MakeShareable(new FSpectrNode(NewState, 0, 0)); - Node2->Action = Action; - OpenNodes.Add(Node2); - //remove action which will fullfil initial goal state. - AvailableActions.Remove(Action); - } - } - BuildGraph2(OpenNodes, AvailableActions, nullptr); - + if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) + { + return Item.Get() == Action; + })) + { + continue; + } - for (TSharedPtr Node : OpenNodes) - { + if (!(CurrentNode->Action == Action)) + { + if (CheckGoal(Action.GetDefaultObject()->Effects, CurrentNode->State)) + { + TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action.GetDefaultObject()->PreConditions, Action.GetDefaultObject()->Cost, 0)); + Node2->Action = Action; + OpenNodes.Add(Node2); + if (CurrentNode->Children.Num() == 0) + { + CurrentNode->Children.Add(Node2); + } + else + { + if ( !(CurrentNode->Children[0]->Cost < Action.GetDefaultObject()->Cost) ) + { + CurrentNode->Children.Empty(); + CurrentNode->Children.Add(Node2); + } + else + { + //action has been discarded, remove it from OpenNodes + OpenNodes.Remove(Node2); + //and add to closed nodes. No reason to ever consider it again. + ClosedNodes.Add(Node2); + } + } + } + } + } } - //TArray> AvailableActions; - //AvailableActions.Append(ActionList); - //TArray> UsedList; - //bool bDone = false; - //while (AvailableActions.Num() > 0) - //{ - // TSubclassOf Action = AvailableActions.Pop(); - // UsedList.Push(Action); - // UE_LOG(LogTemp, Log, TEXT("-Build Plan - Action Name: %s \n"), *Action.GetDefaultObject()->GetName()); - // if (Action.GetDefaultObject()->EvaluateCondition(InContext) - // && CheckGoal(Action.GetDefaultObject()->Effects, InTargetGoal)) - // { - // TMap NewGoal = AddGoalChanges(InTargetGoal, - // Action.GetDefaultObject()->PreConditions); - // - // ActionQueue.Add(Action); - // /*if (CheckGoal(UpdatedGoalState, NewGoal)) - // { - // return; - // }*/ - // UsedList.Append(AvailableActions); - // UsedList.Remove(Action); - // if (!bDone) - // { - // bDone = true; - // BuildGraph(NewGoal, NewGoal, ActionQueue, UsedList, InContext); - // break; - // } - // } - //} } bool CheckGoal(const TMap& InEffects, const TMap& InGoal) From 61e581571e0bb5118838d59ee8b9f5c082dcd783 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 27 Jan 2018 13:23:43 +0100 Subject: [PATCH 032/187] spectr- prototyping movement --- Config/DefaultEngine.ini | 16 +- .../SpectrAI/Source/SpectrAI/SpectrAction.cpp | 18 +- .../SpectrAI/Source/SpectrAI/SpectrAction.h | 42 +++- .../Source/SpectrAI/SpectrBrainComponent.cpp | 93 +++++++- .../Source/SpectrAI/SpectrBrainComponent.h | 203 +++++++++++------- .../SpectrAITest/STestAIControllerBase.cpp | 7 + .../SpectrAITest/STestAIControllerBase.h | 20 ++ .../Source/SpectrAITest/STestAction_GoTo.cpp | 7 + .../Source/SpectrAITest/STestAction_GoTo.h | 20 ++ .../SpectrAITest/STestAction_PickItemAxe.cpp | 36 +++- .../SpectrAITest/STestAction_PickItemAxe.h | 14 +- .../Source/SpectrAITest/STestAxePickup.cpp | 27 +++ .../Source/SpectrAITest/STestAxePickup.h | 28 +++ 13 files changed, 433 insertions(+), 98 deletions(-) create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 76e28ea..bfba6b0 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -92,9 +92,6 @@ AssetManagerClassName=/Script/AbilityFramework.AFAssetManager [/Script/Engine.UserInterfaceSettings] bLoadWidgetsOnDedicatedServer=False -[/Script/Engine.NavigationSystem] -DataGatheringMode=Lazy - [/Script/AIModule.AISystem] HotSpotManagerClassName=/Script/AIModule.AIHotSpotManager bAllowStrafing=True @@ -153,3 +150,16 @@ SyncSceneSmoothingFactor=0.000000 AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 + +[/Script/Engine.NavigationSystem] +bAutoCreateNavigationData=True +bAllowClientSideNavigation=False +bInitialBuildingLocked=False +bSkipAgentHeightCheckWhenPickingNavData=False +DataGatheringMode=Lazy +bGenerateNavigationOnlyAroundNavigationInvokers=False +ActiveTilesUpdateInterval=1.000000 ++SupportedAgents=(Name="Default",Color=(B=0,G=255,R=140,A=164),DefaultQueryExtent=(X=50.000000,Y=50.000000,Z=250.000000),NavigationDataClassName=/Script/Engine.RecastNavMesh,AgentRadius=35.000000,AgentHeight=144.000000,AgentStepHeight=-1.000000,NavWalkingSearchHeightScale=0.500000,PreferredNavData=Class'"/Script/Engine.RecastNavMesh"',bCanCrouch=True,bCanJump=True,bCanWalk=True,bCanSwim=True,bCanFly=False) +DirtyAreasUpdateFreq=60.000000 + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp index 544777a..106e629 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp @@ -1,16 +1,28 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "SpectrAction.h" +#include "SpectrBrainComponent.h" +void USpectrAction::NativeMoveTo(class USpectrBrainComponent* Brain) +{ - -void USpectrAction::Execute_Implementation(class USpectrContext* InContext) +} +void USpectrAction::Execute_Implementation(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) { } +float USpectrAction::Score_Implementation(class USpectrContext* InContext, class AAIController* AIController) +{ + return Cost; +} -bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InContext) +bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController) { return true; +} + +void USpectrAction::NativeFinished() +{ + OwningBrain->OnActionFinished(this); } \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h index 6b9d26a..2a4a97f 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h @@ -30,11 +30,45 @@ class SPECTRAI_API USpectrAction : public UObject UPROPERTY(EditAnywhere, Category = "State Configuration") TMap Effects; + UPROPERTY() + USpectrBrainComponent* OwningBrain; + + /* Override to check if action in rnage of Target/Location to execute */ + virtual bool NativeIsInRange() + { + return true; + } + + virtual void NativeMoveTo(class USpectrBrainComponent* Brain); + + virtual void NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) {} + + virtual void NativeExecute() {}; + + virtual float NativeSscore(class USpectrContext* InContext, class AAIController* AIController) + { + return Cost; + } + + virtual float NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) + { + return true; + } + + void NativeFinished() + { + + } + + UFUNCTION(BlueprintNativeEvent) + void Execute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + virtual void Execute_Implementation(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + UFUNCTION(BlueprintNativeEvent) - void Execute(class USpectrContext* InContext); - virtual void Execute_Implementation(class USpectrContext* InContext); + float Score(class USpectrContext* InContext, class AAIController* AIController); + virtual float Score_Implementation(class USpectrContext* InContext, class AAIController* AIController); UFUNCTION(BlueprintNativeEvent) - bool EvaluateCondition(class USpectrContext* InContext); - virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext); + bool EvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); + virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController); }; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp index 4130742..8cfc425 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp @@ -2,29 +2,100 @@ #include "SpectrBrainComponent.h" #include "SpectrContext.h" -bool operator==(const FSpectrNode& Other, const TSubclassOf& Action) +#include "AIController.h" + + +bool operator==(const FSpectrNode& Other, const USpectrAction*& Action) { return Other.Action == Action; } -bool operator==(FSpectrNode* Other, const TSubclassOf& Action) -{ - return Other->Action == Action; -} + USpectrBrainComponent::USpectrBrainComponent() { + FSMState = ESpectrState::Idle; if(Context) CurrentContext = Cast(CreateDefaultSubobject(TEXT("CurrentContext"), Context, Context, true, false, false)); } +void USpectrBrainComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + //check for new goals + //evaluate if new goal is worth pursuing over the current one. +} +void USpectrBrainComponent::BeginPlay() +{ + Super::BeginPlay(); + if (AAIController* AIController = Cast(GetOwner())) + { + AIController->GetPathFollowingComponent()->OnRequestFinished.AddUObject(this, &USpectrBrainComponent::OnMoveFinished); + } + for (const TSubclassOf& ActionClass : ActionList) + { + USpectrAction* Action = NewObject(this, ActionClass); + Actions.Add(Action); + } +} void USpectrBrainComponent::StarPlanning() { - TArray> OutActionList; - SpectrAI.Plan(Goal, CurrentState, OutActionList, ActionList, CurrentContext); - - for (const TSubclassOf& Action : OutActionList) + TArray OutActionList; + if (AAIController* AIController = Cast(GetOwner())) { - FString name = Action.GetDefaultObject()->GetName(); - + SpectrAI.Plan(Goal, CurrentState, OutActionList, Actions, CurrentContext, AIController); + } + for (int32 Idx = OutActionList.Num() - 1; Idx >= 0; Idx--) + { + FString name = OutActionList[Idx]->GetName(); + PendingPlan.Add(OutActionList[Idx]); UE_LOG(LogTemp, Log, TEXT("Action Name: %s \n"), *name); } + ExecutePlan(); +} + +void USpectrBrainComponent::ExecutePlan() +{ + if (PendingPlan.Num() && PendingPlan[0]) + { + CurrentAction = PendingPlan[0]; + PendingPlan.RemoveAt(0, 1, true); + } + if (AAIController* AIController = Cast(GetOwner())) + { + //Not in range + if (!CurrentAction->NativeIsInRange()) + { + FSMState = ESpectrState::Move; + CurrentAction->NativeMoveTo(this); + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(CurrentAction, &USpectrAction::NativeOnMoveFinished, CurrentContext, AIController, this); + PendingMoveEvent = Delegate; + } + else //in range, just execute action. + { + FSMState = ESpectrState::Action; + CurrentAction->Execute(CurrentContext, AIController, this); + } + // + } +} +void USpectrBrainComponent::OnActionFinished(USpectrAction* InAction) +{ + +} +void USpectrBrainComponent::OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result) +{ + PendingMoveEvent.ExecuteIfBound(); + //ExecutePlan(); +} + +void USpectrBrainComponent::MoveToLocation() +{ + FSMState = ESpectrState::Move; +} +void USpectrBrainComponent::MoveToActor(AActor* Target) +{ + FSMState = ESpectrState::Move; + if (AAIController* AIController = Cast(GetOwner())) + { + AIController->MoveToActor(Target, 500); + } } \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index 2e890cf..a2dd361 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -8,16 +8,27 @@ #include "GameplayTagContainer.h" #include "Queue.h" #include "SpectrAction.h" +#include "Navigation/PathFollowingComponent.h" +#include "AITypes.h" + #include "SpectrBrainComponent.generated.h" +enum class ESpectrState : uint8 +{ + Idle = 0, + Action = 1, + Move = 2 +}; + //Node representing single step in plan. struct FSpectrNode { int32 Cost; + float Score; int32 RemainingCost; TWeakPtr Parent; TMap State; - TSubclassOf Action; + USpectrAction* Action; TArray> Children; FSpectrNode() {} FSpectrNode(const TMap& InState, int32 InCost, int32 InRemainingCost) @@ -26,19 +37,24 @@ struct FSpectrNode , State(InState) {} + bool Equals(USpectrAction* InAction) + { + return Action == InAction; + } + bool operator==(const FSpectrNode& Other) const { return Action == Other.Action; } - bool operator==(const TSubclassOf& Other) const + bool operator==(const USpectrAction*& Other) const { return Action == Other; } }; -bool operator==(const FSpectrNode& Other, const TSubclassOf& Action); -bool operator==(FSpectrNode* Other, const TSubclassOf& Action); +bool operator==(const FSpectrNode& Other, const USpectrAction*& Action); + USTRUCT(BlueprintType) struct SPECTRAI_API FSpectrAI @@ -48,70 +64,6 @@ struct SPECTRAI_API FSpectrAI //Precondition, List of action for this precondition; TMap> > ActionMap; - void BuildGraph(const TMap& InTargetGoal, const TMap& InCurrent, - TArray>& ActionQueue, const TArray>& ActionList, - class USpectrContext* InContext) - { - - TArray> OpenNodes; - TArray> ClosedNodes; - - TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); - - OpenNodes.Push(Node); - - TArray> AvailableActions = ActionList; - - //reverse A*, or something similiar to it at least.. - while (OpenNodes.Num()) - { - TSharedPtr CurrentNode = OpenNodes.Pop(); - ClosedNodes.Push(CurrentNode); - - for (const TSubclassOf& Action : AvailableActions) - { - - if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) - { - return Item.Get() == Action; - })) - { - continue; - } - - if (!(CurrentNode->Action == Action)) - { - if (CheckGoal(Action.GetDefaultObject()->Effects, CurrentNode->State)) - { - TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action.GetDefaultObject()->PreConditions, Action.GetDefaultObject()->Cost, 0)); - Node2->Action = Action; - OpenNodes.Add(Node2); - - if (CurrentNode->Children.Num() == 0) - { - CurrentNode->Children.Add(Node2); - } - else - { - if ( !(CurrentNode->Children[0]->Cost < Action.GetDefaultObject()->Cost) ) - { - CurrentNode->Children.Empty(); - CurrentNode->Children.Add(Node2); - } - else - { - //action has been discarded, remove it from OpenNodes - OpenNodes.Remove(Node2); - //and add to closed nodes. No reason to ever consider it again. - ClosedNodes.Add(Node2); - } - } - } - } - } - } - } - bool CheckGoal(const TMap& InEffects, const TMap& InGoal) { bool bAchieved = false; @@ -202,11 +154,91 @@ struct SPECTRAI_API FSpectrAI } } - void Plan(const TMap& InTargetGoal, const TMap& InCurrentState, - TArray>& InActionQueue, const TArray>& ActionList, - class USpectrContext* InContext) + void Plan(const TMap& InTargetGoal, const TMap& InCurrentState + , TArray& InActionQueue + , const TArray& ActionList + , class USpectrContext* InContext + , class AAIController* AIController) { - BuildGraph(InTargetGoal, InCurrentState, InActionQueue, ActionList, InContext); + TArray> OpenNodes; + TArray> ClosedNodes; + + TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); + + //actually made action when constructing node path. + //and then execute it in reverse (from last item in array to first). + //so we don't was time traversing node tree and then reordering actions.. + TArray ActionPlan; + + OpenNodes.Push(Node); + + TArray AvailableActions = ActionList; + + //reverse A*, or something similiar to it at least.. + while (OpenNodes.Num()) + { + TSharedPtr CurrentNode = OpenNodes.Pop(); + ClosedNodes.Push(CurrentNode); + + for (USpectrAction*& Action : AvailableActions) + { + //or instead of pushing to closed actions... we can remove them for Available Actions hmm ? + if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) + { + return Item->Equals(Action); + })) + { + continue; + } + + if (!(CurrentNode->Action == Action)) + { + if (CheckGoal(Action->Effects, CurrentNode->State)) + { + //action scored Zero, so it probabaly can't be used anyway. + if (!Action->EvaluateCondition(InContext, AIController)) + { + continue; + } + float Score = Action->Score(InContext, AIController); + + TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action->PreConditions, Action->Cost, 0)); + Node2->Action = Action; + Node2->Score = Score; + OpenNodes.Add(Node2); + + if (CurrentNode->Children.Num() == 0) + { + CurrentNode->Children.Add(Node2); + ActionPlan.Add(Action); + } + else + { + //add new action, only if it is cheaper than current one. + //very primitive we need to check if the actuall path will be cheaper. + //so compare current cost of the path with + if (Score > Node2->Score) + { + ActionPlan.Remove(CurrentNode->Children[0]->Action); + CurrentNode->Children.Empty(); + CurrentNode->Children.Add(Node2); + + ActionPlan.Add(Action); + } + else + { + //action has been discarded, remove it from OpenNodes + OpenNodes.Remove(Node2); + //and add to closed nodes. No reason to ever consider it again. + ClosedNodes.Add(Node2); + } + } + } + } + } + } + + InActionQueue = ActionPlan; } }; @@ -249,6 +281,8 @@ class SPECTRAI_API USpectrBrainComponent : public UActorComponent { GENERATED_BODY() public: + ESpectrState FSMState; + UPROPERTY(EditAnywhere) TMap Goal; UPROPERTY(EditAnywhere) @@ -256,6 +290,17 @@ class SPECTRAI_API USpectrBrainComponent : public UActorComponent UPROPERTY(EditAnywhere) TArray> ActionList; + UPROPERTY() + TArray PendingPlan; + + UPROPERTY() + USpectrAction* CurrentAction; + + //maybe it will be better to instance actions per actor. + //this way we cloud change state of action without affecting other actors. + UPROPERTY() + TArray Actions; + UPROPERTY(EditAnywhere) TSubclassOf Context; @@ -263,8 +308,20 @@ class SPECTRAI_API USpectrBrainComponent : public UActorComponent FSpectrAI SpectrAI; + //Map of pending move events. + FSimpleDelegate PendingMoveEvent; + USpectrBrainComponent(); + virtual void BeginPlay() override; + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; UFUNCTION(BlueprintCallable) void StarPlanning(); - + + void ExecutePlan(); + + void OnActionFinished(USpectrAction* InAction); + void OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result); + + void MoveToLocation(); + void MoveToActor(AActor* Target); }; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp new file mode 100644 index 0000000..7b04f84 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAIControllerBase.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h new file mode 100644 index 0000000..f79cf73 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAIController.h" +#include "STestAIControllerBase.generated.h" + +/** + * + */ +UCLASS() +class SPECTRAITEST_API ASTestAIControllerBase : public ASpectrAIController +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp new file mode 100644 index 0000000..365c590 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_GoTo.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h new file mode 100644 index 0000000..393bce0 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_GoTo.generated.h" + +/** + * + */ +UCLASS() +class SPECTRAITEST_API USTestAction_GoTo : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp index 9726888..36ca832 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp @@ -1,7 +1,41 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "STestAction_PickItemAxe.h" +#include "AIController.h" +#include "SpectrBrainComponent.h" +#include "STestAxePickup.h" +#include "EngineUtils.h" +void USTestAction_PickItemAxe::Execute_Implementation(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + APawn* Pawn = AIController->GetPawn(); + + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetItem = *ActorIt; + break; + } + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetItem->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance > MinDistance) + { + Brain->MoveToActor(TargetItem); + return; + } +} - +bool USTestAction_PickItemAxe::EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController) +{ + bool bFound = false; + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetItem = *ActorIt; + bFound = true; + break; + } + return bFound; +} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h index a9cdda9..f7135ae 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h @@ -13,8 +13,16 @@ UCLASS(BlueprintType, Blueprintable) class SPECTRAITEST_API USTestAction_PickItemAxe : public USpectrAction { GENERATED_BODY() +protected: + /* Minimum distance from item to pick it. */ + UPROPERTY(EditAnywhere) + float MinDistance; + UPROPERTY() + AActor* TargetItem; +public: + virtual void Execute_Implementation(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; - - - + virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController); }; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp new file mode 100644 index 0000000..a25fb52 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAxePickup.h" + + +// Sets default values +ASTestAxePickup::ASTestAxePickup() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestAxePickup::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestAxePickup::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h new file mode 100644 index 0000000..970ff76 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestAxePickup.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestAxePickup : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestAxePickup(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; From 7f0ad436a49c240b984e3f250dbd0265908df024 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 28 Jan 2018 17:14:26 +0100 Subject: [PATCH 033/187] spectr update --- .../Source/SpectrAI/SpectrAIController.cpp | 6 +- .../Source/SpectrAI/SpectrAIController.h | 83 ++----------------- .../SpectrAI/Source/SpectrAI/SpectrAction.cpp | 38 ++++++++- .../SpectrAI/Source/SpectrAI/SpectrAction.h | 58 ++++++++----- .../Source/SpectrAI/SpectrBrainComponent.cpp | 61 +++++++++++--- .../Source/SpectrAI/SpectrBrainComponent.h | 67 +++++---------- .../Source/SpectrAI/SpectrConsideration.cpp | 7 ++ .../Source/SpectrAI/SpectrConsideration.h | 20 +++++ .../Source/SpectrAI/SpectrEvaluator.cpp | 7 ++ .../Source/SpectrAI/SpectrEvaluator.h | 72 ++++++++++++++++ Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h | 6 +- .../SpectrAIEditor/SpectrAIEditor.Build.cs | 64 ++++++++++++++ .../Source/SpectrAIEditor/SpectrAIEditor.cpp | 20 +++++ .../Source/SpectrAIEditor/SpectrAIEditor.h | 15 ++++ .../SpectrGoalCustomization.cpp | 12 +++ .../SpectrAIEditor/SpectrGoalCustomization.h | 17 ++++ Plugins/SpectrAI/SpectrAI.uplugin | 19 +++-- .../SpectrAITest/STestAction_ChopFirewood.cpp | 51 +++++++++++- .../SpectrAITest/STestAction_ChopFirewood.h | 20 ++++- .../SpectrAITest/STestAction_ChopWood.h | 2 +- .../SpectrAITest/STestAction_DropFirewood.cpp | 49 ++++++++++- .../SpectrAITest/STestAction_DropFirewood.h | 20 ++++- .../SpectrAITest/STestAction_PickItemAxe.cpp | 47 +++++++---- .../SpectrAITest/STestAction_PickItemAxe.h | 14 +++- 24 files changed, 576 insertions(+), 199 deletions(-) create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp index 285f183..c5103bd 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp @@ -2,13 +2,11 @@ #include "SpectrAIController.h" #include "SpectrBrainComponent.h" -bool operator>(float Rhs, const FSpectrDecision& Lhs) -{ - return Rhs > Lhs.Score; -} + ASpectrAIController::ASpectrAIController(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { SpectrBrain = ObjectInitializer.CreateDefaultSubobject(this, TEXT("SpectrBrain")); + AIPerception = ObjectInitializer.CreateDefaultSubobject(this, TEXT("AIPerception")); } \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h index 476d990..19287ea 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "AIController.h" +#include "Perception/AIPerceptionComponent.h" #include "SpectrAIController.generated.h" //Consideration (calculates score) @@ -24,85 +25,7 @@ //--they are summed (or multiplied) //--contains single decision to execute. -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrConsideration -{ - GENERATED_BODY() -public: - virtual float Score() const { return 0; } - virtual ~FSpectrConsideration() - {} -}; - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrQualifier -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Considerations; -public: - virtual ~FSpectrQualifier() - {} - virtual float Qualify() const - { - float TotalScore = 0; - for (const FSpectrConsideration& Consideration : Considerations) - { - TotalScore += Consideration.Score(); - } - return TotalScore; - } -}; - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrDecision -{ - GENERATED_BODY() -public: - mutable float Score; - void SetScore(float InScore) const - { - Score = InScore; - } -}; -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrEvaluator -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - FSpectrQualifier Qualifier; - - UPROPERTY(EditAnywhere) - FSpectrDecision Decision; - - mutable float Score; - - float Evaluate() const - { - Score = 0; - float score = Qualifier.Qualify(); - Decision.SetScore(score); - Score = score; - return score; - } -}; - -bool operator>(float Rhs, const FSpectrDecision& Lhs); -struct FTestContext -{ - bool bTreeInRange; - bool bLogInRange; - - FTestContext() - : bTreeInRange(true) - , bLogInRange(false) - { - - } -}; /** * @@ -115,6 +38,10 @@ class SPECTRAI_API ASpectrAIController : public AAIController UPROPERTY(VisibleAnywhere, BlueprintReadOnly) class USpectrBrainComponent* SpectrBrain; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + class UAIPerceptionComponent* AIPerception; + + ASpectrAIController(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp index 106e629..e57eba5 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp @@ -6,17 +6,34 @@ void USpectrAction::NativeMoveTo(class USpectrBrainComponent* Brain) { - + MoveTo(Brain); +} +void USpectrAction::NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +{ + OnMoveFinished(InContext, AIController, Brain); } -void USpectrAction::Execute_Implementation(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +void USpectrAction::FinishMove(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +{ + NativeOnMoveFinished(InContext, AIController, Brain); +} +void USpectrAction::MoveTo_Implementation(class USpectrBrainComponent* Brain) { } + +float USpectrAction::NativeScore(class USpectrContext* InContext, class AAIController* AIController) +{ + return Score(InContext, AIController); +} + float USpectrAction::Score_Implementation(class USpectrContext* InContext, class AAIController* AIController) { return Cost; } - +bool USpectrAction::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + return EvaluateCondition(InContext, AIController); +} bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController) { return true; @@ -25,4 +42,19 @@ bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InCon void USpectrAction::NativeFinished() { OwningBrain->OnActionFinished(this); +} + +void USpectrAction::NativeExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +{ + OnExecute(InContext, AIController, Brain); +} + +void USpectrAction::ActionFinished() +{ + NativeFinished(); +} + +void USpectrAction::MoveToTarget(AActor* Target, float MinimumDistance) +{ + OwningBrain->MoveToActor(Target, MinimumDistance); } \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h index 2a4a97f..b6ac82b 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h @@ -9,8 +9,11 @@ #include "SpectrAction.generated.h" /** - * + * Default implmenetations of Native* functions call to either blueprint events + * or blueprint Native functions which can be overriden from blueprint. + * Though they do provide default implementation (where possible). */ + UCLASS(BlueprintType, Blueprintable) class SPECTRAI_API USpectrAction : public UObject { @@ -30,39 +33,50 @@ class SPECTRAI_API USpectrAction : public UObject UPROPERTY(EditAnywhere, Category = "State Configuration") TMap Effects; - UPROPERTY() + UPROPERTY(BlueprintReadOnly, Category = "Spectr AI") USpectrBrainComponent* OwningBrain; /* Override to check if action in rnage of Target/Location to execute */ - virtual bool NativeIsInRange() + virtual bool NativeIsInRange(class AAIController* AIController) { return true; } virtual void NativeMoveTo(class USpectrBrainComponent* Brain); - virtual void NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) {} + virtual void NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - virtual void NativeExecute() {}; + UFUNCTION(BlueprintNativeEvent) + void MoveTo(class USpectrBrainComponent* Brain); + virtual void MoveTo_Implementation(class USpectrBrainComponent* Brain); - virtual float NativeSscore(class USpectrContext* InContext, class AAIController* AIController) - { - return Cost; - } + UFUNCTION(BlueprintImplementableEvent, Category = "Spectr AI") + void OnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - virtual float NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) - { - return true; - } + UFUNCTION(BlueprintCallable, Category = "Spectr AI") + void FinishMove(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - void NativeFinished() - { + /* + Call Super::NativeExecute if you want to execute OnExecuted BP event, or call it manually. - } + Remember to call NativeFinished() somewhere, to indicate that Action finished execution. + */ + virtual void NativeExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - UFUNCTION(BlueprintNativeEvent) - void Execute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - virtual void Execute_Implementation(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + virtual float NativeScore(class USpectrContext* InContext, class AAIController* AIController); + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); + + /* + Remember to call it always after Action has finished execution. Otherwise Action Queue will be stuck. + */ + void NativeFinished(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Spectr AI") + void OnExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + + UFUNCTION(BlueprintCallable, Category = "Spectr AI") + void ActionFinished(); UFUNCTION(BlueprintNativeEvent) float Score(class USpectrContext* InContext, class AAIController* AIController); @@ -71,4 +85,10 @@ class SPECTRAI_API USpectrAction : public UObject UFUNCTION(BlueprintNativeEvent) bool EvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController); + + + + + UFUNCTION(BlueprintCallable) + void MoveToTarget(AActor* Target, float MinimumDistance); }; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp index 8cfc425..ac3d1a3 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp @@ -10,7 +10,8 @@ bool operator==(const FSpectrNode& Other, const USpectrAction*& Action) return Other.Action == Action; } -USpectrBrainComponent::USpectrBrainComponent() +USpectrBrainComponent::USpectrBrainComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) { FSMState = ESpectrState::Idle; if(Context) @@ -33,6 +34,7 @@ void USpectrBrainComponent::BeginPlay() for (const TSubclassOf& ActionClass : ActionList) { USpectrAction* Action = NewObject(this, ActionClass); + Action->OwningBrain = this; Actions.Add(Action); } } @@ -46,23 +48,48 @@ void USpectrBrainComponent::StarPlanning() for (int32 Idx = OutActionList.Num() - 1; Idx >= 0; Idx--) { FString name = OutActionList[Idx]->GetName(); + PendingPlan.Add(OutActionList[Idx]); + PendingPlan2.Enqueue(OutActionList[Idx]); + UE_LOG(LogTemp, Log, TEXT("Action Name: %s \n"), *name); } - ExecutePlan(); + ExecutePlan(nullptr); +} + +void USpectrBrainComponent::SelectGoal() +{ + } -void USpectrBrainComponent::ExecutePlan() +void USpectrBrainComponent::ExecutePlan(class USpectrAction* PreviousAction) { - if (PendingPlan.Num() && PendingPlan[0]) + if (PendingPlan2.IsEmpty()) + { + //plan finished + StarPlanning(); //plan again + //in reality look for new goal. + return; + } + while (!PendingPlan2.IsEmpty()) + { + USpectrAction* OutAction; + PendingPlan2.Dequeue(OutAction); + if (OutAction != PreviousAction) + { + CurrentAction = OutAction; + break; + } + } + /*if (PendingPlan.Num() && PendingPlan[0]) { CurrentAction = PendingPlan[0]; PendingPlan.RemoveAt(0, 1, true); - } + }*/ if (AAIController* AIController = Cast(GetOwner())) { //Not in range - if (!CurrentAction->NativeIsInRange()) + if (!CurrentAction->NativeIsInRange(AIController)) { FSMState = ESpectrState::Move; CurrentAction->NativeMoveTo(this); @@ -72,18 +99,30 @@ void USpectrBrainComponent::ExecutePlan() else //in range, just execute action. { FSMState = ESpectrState::Action; - CurrentAction->Execute(CurrentContext, AIController, this); + CurrentAction->NativeExecute(CurrentContext, AIController, this); } // } } -void USpectrBrainComponent::OnActionFinished(USpectrAction* InAction) +void USpectrBrainComponent::AbortPlan(const FString& Reason) { +} +void USpectrBrainComponent::OnActionFinished(USpectrAction* InAction) +{ + ExecutePlan(InAction); } void USpectrBrainComponent::OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result) { - PendingMoveEvent.ExecuteIfBound(); + if (AAIController* AIController = Cast(GetOwner())) + { + if (CurrentAction) + { + CurrentAction->NativeOnMoveFinished(CurrentContext, AIController, this); + } + } + //PendingMoveEvent.ExecuteIfBound(); + //PendingMoveEvent.Unbind(); //ExecutePlan(); } @@ -91,11 +130,11 @@ void USpectrBrainComponent::MoveToLocation() { FSMState = ESpectrState::Move; } -void USpectrBrainComponent::MoveToActor(AActor* Target) +void USpectrBrainComponent::MoveToActor(AActor* Target, float MinDistance) { FSMState = ESpectrState::Move; if (AAIController* AIController = Cast(GetOwner())) { - AIController->MoveToActor(Target, 500); + AIController->MoveToActor(Target, MinDistance); } } \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index a2dd361..11eb7f5 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -3,7 +3,7 @@ #pragma once #include "CoreMinimal.h" -#include "BrainComponent.h" +#include "GameplayTasksComponent.h" #include "GameplayTags.h" #include "GameplayTagContainer.h" #include "Queue.h" @@ -196,11 +196,11 @@ struct SPECTRAI_API FSpectrAI if (CheckGoal(Action->Effects, CurrentNode->State)) { //action scored Zero, so it probabaly can't be used anyway. - if (!Action->EvaluateCondition(InContext, AIController)) + if (!Action->NativeEvaluateCondition(InContext, AIController)) { continue; } - float Score = Action->Score(InContext, AIController); + float Score = Action->NativeScore(InContext, AIController); TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action->PreConditions, Action->Cost, 0)); Node2->Action = Action; @@ -242,42 +242,11 @@ struct SPECTRAI_API FSpectrAI } }; -//USTRUCT(BlueprintType) -//struct SPECTRAI_API FSpectrSelector -//{ -// GENERATED_BODY() -//public: -// -// UPROPERTY(EditAnywhere) -// TArray Evaluators; -// -// void Choose() -// { -// TArray SortedDecisions; //actually there will be only one highest scoring PoC -// for (const FSpectrEvaluator& Evaluator : Evaluators) -// { -// if (SortedDecisions.Num() == 0) -// { -// Evaluator.Evaluate(); -// SortedDecisions.Add(Evaluator.Decision); -// } -// else -// { -// if (Evaluator.Evaluate() > SortedDecisions[0]) -// { -// SortedDecisions[0] = Evaluator.Decision; -// } -// } -// } -// } -//}; - - /** * */ UCLASS() -class SPECTRAI_API USpectrBrainComponent : public UActorComponent +class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent { GENERATED_BODY() public: @@ -289,39 +258,47 @@ class SPECTRAI_API USpectrBrainComponent : public UActorComponent TMap CurrentState; UPROPERTY(EditAnywhere) TArray> ActionList; + UPROPERTY() + TArray Actions; + + UPROPERTY(EditAnywhere, Instanced) + TArray Goals; + UPROPERTY(EditAnywhere, Instanced) + class USpectrGoal* CurrentGoal; + UPROPERTY() TArray PendingPlan; + TQueue PendingPlan2; + UPROPERTY() USpectrAction* CurrentAction; - //maybe it will be better to instance actions per actor. - //this way we cloud change state of action without affecting other actors. - UPROPERTY() - TArray Actions; + UPROPERTY(EditAnywhere) TSubclassOf Context; - - class USpectrContext* CurrentContext; + UPROPERTY() + class USpectrContext* CurrentContext; FSpectrAI SpectrAI; //Map of pending move events. FSimpleDelegate PendingMoveEvent; - USpectrBrainComponent(); + USpectrBrainComponent(const FObjectInitializer& ObjectInitializer); virtual void BeginPlay() override; virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; UFUNCTION(BlueprintCallable) void StarPlanning(); - void ExecutePlan(); - + void SelectGoal(); + void ExecutePlan(class USpectrAction* PreviousAction); + void AbortPlan(const FString& Reason); void OnActionFinished(USpectrAction* InAction); void OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result); void MoveToLocation(); - void MoveToActor(AActor* Target); + void MoveToActor(AActor* Target, float MinDistance); }; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp new file mode 100644 index 0000000..88cf50e --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrConsideration.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h new file mode 100644 index 0000000..da8ec6e --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "SpectrConsideration.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class SPECTRAI_API USpectrConsideration : public UObject +{ + GENERATED_BODY() + +public: + virtual float Score() const { return 0; } + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp new file mode 100644 index 0000000..37d9944 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrEvaluator.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h new file mode 100644 index 0000000..673ff31 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h @@ -0,0 +1,72 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "SpectrConsideration.h" +#include "SpectrEvaluator.generated.h" + + +//USTRUCT(BlueprintType) +//struct SPECTRAI_API FSpectrConsideration +//{ +// GENERATED_BODY() +//public: +// virtual float Score() const { return 0; } +// virtual ~FSpectrConsideration() +// {} +//}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrQualifier +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; +public: + virtual ~FSpectrQualifier() + {} + virtual float Qualify() const + { + float TotalScore = 0; + for (USpectrConsideration* Consideration : Considerations) + { + TotalScore += Consideration->Score(); + } + return TotalScore; + } +}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrEvaluator +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FSpectrQualifier Qualifier; + + mutable float Score; + + float Evaluate() const + { + Score = 0; + float score = Qualifier.Qualify(); + Score = score; + return score; + } +}; + +/** + * + */ +//UCLASS() +//class SPECTRAI_API USpectrEvaluator : public UObject +//{ +// GENERATED_BODY() +// +// +// +// +//}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h index b28e378..fafc316 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h @@ -6,12 +6,13 @@ #include "UObject/NoExportTypes.h" #include "GameplayTags.h" #include "GameplayTagContainer.h" +#include "SpectrEvaluator.h" #include "SpectrGoal.generated.h" /** * */ -UCLASS() +UCLASS(BlueprintType, Blueprintable, EditInLineNew) class SPECTRAI_API USpectrGoal : public UObject { GENERATED_BODY() @@ -23,6 +24,9 @@ class SPECTRAI_API USpectrGoal : public UObject UPROPERTY(EditAnywhere) TMap FinishedState; + UPROPERTY(EditAnywhere) + FSpectrEvaluator ScoreEvaluator; + virtual float QualifyGoal(class USpectrContext* InContext) { return -1.0f; diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs new file mode 100644 index 0000000..7ef7a9b --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs @@ -0,0 +1,64 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class SpectrAIEditor : ModuleRules +{ + public SpectrAIEditor(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "SpectrAIEditor/Public", + "SpectrAI/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "SpectrAIEditor/Private", + "SpectrAI/Private" + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "Core", + "CoreUObject", + "Engine", + "InputCore", + "Slate", + "SlateCore", + "AIModule", + "UnrealEd", + "PropertyEditor", + "GameplayTags", + "GameplayTasks", + "SpectrAI" + // ... add private dependencies that you statically link with here ... + } + ); + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp new file mode 100644 index 0000000..7e6a50e --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "SpectrAIEditor.h" + +#define LOCTEXT_NAMESPACE "FSpectrAIEditor" + +void FSpectrAIEditorModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FSpectrAIEditorModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FSpectrAIEditorModule, SpectrAIEditor) \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h new file mode 100644 index 0000000..7b2e8e7 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FSpectrAIEditorModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp new file mode 100644 index 0000000..6269568 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp @@ -0,0 +1,12 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "SpectrGoalCustomization.h" + +TSharedRef FSpectrGoalCustomization::MakeInstance() +{ + return MakeShareable(new FSpectrGoalCustomization()); +} +void FSpectrGoalCustomization::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h new file mode 100644 index 0000000..767e7f9 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h @@ -0,0 +1,17 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrGoal.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FSpectrGoalCustomization : public IDetailCustomization +{ +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAI/SpectrAI.uplugin b/Plugins/SpectrAI/SpectrAI.uplugin index 8175de1..0dea0d0 100644 --- a/Plugins/SpectrAI/SpectrAI.uplugin +++ b/Plugins/SpectrAI/SpectrAI.uplugin @@ -13,11 +13,16 @@ "CanContainContent": true, "IsBetaVersion": false, "Installed": false, - "Modules": [ - { - "Name": "SpectrAI", - "Type": "Runtime", - "LoadingPhase": "Default" - } - ] + "Modules": [ + { + "Name": "SpectrAI", + "Type": "Runtime", + "LoadingPhase": "Default" + }, + { + "Name": "SpectrAIEditor", + "Type": "Editor", + "LoadingPhase": "Default" + } + ] } \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp index b68a39f..793d1af 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp @@ -1,7 +1,54 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "STestAction_ChopFirewood.h" +#include "AIController.h" +#include "SpectrBrainComponent.h" +#include "STestTree.h" +#include "EngineUtils.h" +bool USTestAction_ChopFirewood::NativeIsInRange(class AAIController* AIController) +{ + //We can evaluate again here if we have target, and if it worth going. + //we can either find better fit or abort plan at this point. + bool bInRange = false; + if (TargetTree) + { + APawn* Pawn = AIController->GetPawn(); + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetTree->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance < MinDistance) + { + bInRange = true; + } + } + return bInRange; +} +void USTestAction_ChopFirewood::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + Brain->MoveToActor(TargetTree, MinDistance); +} +void USTestAction_ChopFirewood::NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeExecute(InContext, AIController, Brain); +} +//void USTestAction_ChopFirewood::NativeExecute(class USpectrContext* InContext +// , class AAIController* AIController +// , class USpectrBrainComponent* Brain) +//{ +// NativeFinished(); +//} - - +bool USTestAction_ChopFirewood::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + bool bFound = false; + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetTree = *ActorIt; + bFound = true; + break; + } + return bFound; +} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h index a5ea064..d2378c8 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h @@ -13,8 +13,24 @@ UCLASS(BlueprintType, Blueprintable) class SPECTRAITEST_API USTestAction_ChopFirewood : public USpectrAction { GENERATED_BODY() - - + + UPROPERTY() + AActor* TargetTree; + UPROPERTY(EditAnywhere) + float MinDistance; + +public: + virtual bool NativeIsInRange(class AAIController* AIController) override; + virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; + virtual void NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + //virtual void NativeExecute(class USpectrContext* InContext + // , class AAIController* AIController + // , class USpectrBrainComponent* Brain) override; + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); }; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h index 8f58cfd..4428927 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h @@ -13,7 +13,7 @@ UCLASS(BlueprintType, Blueprintable) class SPECTRAITEST_API USTestAction_ChopWood : public USpectrAction { GENERATED_BODY() - + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp index 51b3f40..e23a260 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp @@ -1,7 +1,52 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "STestAction_DropFirewood.h" +#include "AIController.h" +#include "SpectrBrainComponent.h" +#include "STestStorage.h" +#include "EngineUtils.h" +bool USTestAction_DropFirewood::NativeIsInRange(class AAIController* AIController) +{ + bool bInRange = false; + if (TargetDropPoint) + { + APawn* Pawn = AIController->GetPawn(); + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetDropPoint->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance < MinDistance) + { + bInRange = true; + } + } + return bInRange; +} +void USTestAction_DropFirewood::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + Brain->MoveToActor(TargetDropPoint, MinDistance); +} +void USTestAction_DropFirewood::NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeExecute(InContext, AIController, Brain); +} +void USTestAction_DropFirewood::NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeFinished(); +} - - +bool USTestAction_DropFirewood::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + bool bFound = false; + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetDropPoint = *ActorIt; + bFound = true; + break; + } + return bFound; +} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h index e8df383..9a8cb95 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h @@ -13,8 +13,24 @@ UCLASS(BlueprintType, Blueprintable) class SPECTRAITEST_API USTestAction_DropFirewood : public USpectrAction { GENERATED_BODY() - - + + UPROPERTY() + AActor* TargetDropPoint; + UPROPERTY(EditAnywhere) + float MinDistance; + +public: + virtual bool NativeIsInRange(class AAIController* AIController) override; + virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; + virtual void NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual void NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); }; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp index 36ca832..eeb7171 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp @@ -6,29 +6,40 @@ #include "STestAxePickup.h" #include "EngineUtils.h" -void USTestAction_PickItemAxe::Execute_Implementation(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) +bool USTestAction_PickItemAxe::NativeIsInRange(class AAIController* AIController) { - APawn* Pawn = AIController->GetPawn(); - - - for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + bool bInRange = false; + if (TargetItem) { - TargetItem = *ActorIt; - break; - } - FVector Position = Pawn->GetActorLocation(); - FVector TargetPosition = TargetItem->GetActorLocation(); - float Distance = FVector::Dist(Position, TargetPosition); - if (Distance > MinDistance) - { - Brain->MoveToActor(TargetItem); - return; + APawn* Pawn = AIController->GetPawn(); + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetItem->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance < MinDistance) + { + bInRange = true; + } } + return bInRange; +} +void USTestAction_PickItemAxe::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + Brain->MoveToActor(TargetItem, MinDistance); +} +void USTestAction_PickItemAxe::NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeExecute(InContext, AIController, Brain); +} +void USTestAction_PickItemAxe::NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeFinished(); } -bool USTestAction_PickItemAxe::EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController) +bool USTestAction_PickItemAxe::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) { bool bFound = false; for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h index f7135ae..e1a25f0 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h +++ b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h @@ -20,9 +20,15 @@ class SPECTRAITEST_API USTestAction_PickItemAxe : public USpectrAction UPROPERTY() AActor* TargetItem; public: - virtual void Execute_Implementation(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) override; + virtual bool NativeIsInRange(class AAIController* AIController) override; + virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; + virtual void NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; - virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController); + virtual void NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); }; From 2164baad3edb8f23f8cb4d43cabbde85388922f0 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 28 Jan 2018 23:21:56 +0100 Subject: [PATCH 034/187] abilities update --- .../AFBlueprintFunctionLibrary.cpp | 46 ++++++++++ .../AFBlueprintFunctionLibrary.h | 17 ++++ .../AbilityFrameworkDebugger/AFDCharacter.cpp | 34 ++++++++ .../AbilityFrameworkDebugger/AFDCharacter.h | 31 +++++++ .../AFDCharacterAttributes.cpp | 7 ++ .../AFDCharacterAttributes.h | 27 ++++++ .../AbilityFrameworkDebugger/AFDDummyPawn.cpp | 84 +++++++++++++++++++ .../AbilityFrameworkDebugger/AFDDummyPawn.h | 65 ++++++++++++++ .../AbilityFrameworkDebugger/AFDGameMode.cpp | 7 ++ .../AbilityFrameworkDebugger/AFDGameMode.h | 20 +++++ .../SDraggableWindowWidget.cpp | 36 ++++---- .../Source/SpectrAI/SpectrBrainComponent.h | 15 +++- Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h | 3 + 13 files changed, 372 insertions(+), 20 deletions(-) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..96bb5a8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp @@ -0,0 +1,46 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" + +#include "Abilities/GAAbilityBase.h" +#include "Effects/GAEffectField.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "AFBlueprintFunctionLibrary.h" + +void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, + const FGameplayTag& AbilityTag, FGameplayTag ActionTag) +{ + IAFAbilityInterface* Interface = Cast(Target); + if (!Interface) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Invalid Target")); + return; + } + UAFAbilityComponent* Comp = Interface->GetAbilityComp(); + if (!Comp) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Target %s InvalidComponent"), *Target->GetName()); + return; + } + + Comp->NativeInputPressed(ActionTag); +} +void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, + const FGameplayTag& AbilityTag, FGameplayTag ActionTag) +{ + IAFAbilityInterface* Interface = Cast(Target); + if (!Interface) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Invalid Target")); + return; + } + UAFAbilityComponent* Comp = Interface->GetAbilityComp(); + if (!Comp) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Target %s InvalidComponent"), *Target->GetName()); + return; + } + + Comp->NativeInputReleased(ActionTag); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h new file mode 100644 index 0000000..700bfb5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h @@ -0,0 +1,17 @@ +#pragma once +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "AFBlueprintFunctionLibrary.generated.h" +/* + Some static helper functions, to interact with Attribute system. +*/ +UCLASS() +class ABILITYFRAMEWORK_API UAFBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + static void TriggerAbilityPressedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + static void TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp new file mode 100644 index 0000000..a249885 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDCharacter.h" + + +// Sets default values +AAFDCharacter::AAFDCharacter() +{ + // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AAFDCharacter::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AAFDCharacter::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + +// Called to bind functionality to input +void AAFDCharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) +{ + Super::SetupPlayerInputComponent(PlayerInputComponent); + +} + diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h new file mode 100644 index 0000000..dcfddd9 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Character.h" +#include "AFDCharacter.generated.h" + +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API AAFDCharacter : public ACharacter +{ + GENERATED_BODY() + +public: + // Sets default values for this character's properties + AAFDCharacter(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + // Called to bind functionality to input + virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; + + + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp new file mode 100644 index 0000000..5c645c8 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDCharacterAttributes.h" + + + + diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h new file mode 100644 index 0000000..ce37f0c --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Attributes/GAAttributesBase.h" +#include "AFDCharacterAttributes.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API UAFDCharacterAttributes : public UGAAttributesBase +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Health; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Energy; + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Stamina; + + UPROPERTY(EditAnywhere, Category = "Base") + FAFAttributeBase Armor; + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp new file mode 100644 index 0000000..e3c67df --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp @@ -0,0 +1,84 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDDummyPawn.h" +#include "Attributes/GAAttributesBase.h" + +// Sets default values +AAFDDummyPawn::AAFDDummyPawn(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + // Set this pawn to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + + Arrow = ObjectInitializer.CreateDefaultSubobject(this, TEXT("Arrow")); + Collision = ObjectInitializer.CreateDefaultSubobject(this, TEXT("Collision")); + Abilities = ObjectInitializer.CreateDefaultSubobject(this, TEXT("Abilities")); + + SetRootComponent(Arrow); + Collision->AttachToComponent(RootComponent, FAttachmentTransformRules::KeepRelativeTransform); +} + +// Called when the game starts or when spawned +void AAFDDummyPawn::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AAFDDummyPawn::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + +// Called to bind functionality to input +void AAFDDummyPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) +{ + Super::SetupPlayerInputComponent(PlayerInputComponent); + +} +/* AFAbilityInterface Implementation START */ +class UGAAttributesBase* AAFDDummyPawn::GetAttributes() +{ + return Abilities->GetAttributes(); +} + +class UAFAbilityComponent* AAFDDummyPawn::GetAbilityComp() +{ + return Abilities; +} + +float AAFDDummyPawn::GetAttributeValue(FGAAttribute AttributeIn) const +{ + return Abilities->GetAttributeValue(AttributeIn); +} +void AAFDDummyPawn::ModifyAttribute(FGAEffectMod& ModIn + , const FGAEffectHandle& HandleIn + , struct FGAEffectProperty& InProperty) +{ + GetAttributes()->ModifyAttribute(ModIn, HandleIn, InProperty); +} + +FAFAttributeBase* AAFDDummyPawn::GetAttribute(FGAAttribute AttributeIn) +{ + return Abilities->GetAttribute(AttributeIn); +}; + +void AAFDDummyPawn::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) +{ + Abilities->RemoveBonus(AttributeIn, HandleIn, InMod); +}; + +float AAFDDummyPawn::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return Abilities->NativeGetAttributeValue(AttributeIn); +}; + +FGAEffectHandle AAFDDummyPawn::ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext) +{ + return Abilities->ApplyEffectToTarget(EffectIn, InProperty, InContext); +}; +/* AFAbilityInterface Implementation END */ \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h new file mode 100644 index 0000000..498923a --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h @@ -0,0 +1,65 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Pawn.h" +#include "Components/ArrowComponent.h" +#include "Components/CapsuleComponent.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" +#include "AFDDummyPawn.generated.h" + +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API AAFDDummyPawn : public APawn, public IAFAbilityInterface +{ + GENERATED_BODY() +protected: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components") + UArrowComponent* Arrow; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components") + UCapsuleComponent* Collision; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components") + UAFAbilityComponent* Abilities; +public: + // Sets default values for this pawn's properties + AAFDDummyPawn(const FObjectInitializer& ObjectInitializer); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + // Called to bind functionality to input + virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; + + /* AFAbilityInterface Implementation START */ + virtual FVector GetSocketLocation(FName SocketNameIn) override { return FVector::ZeroVector; }; + + virtual class UGAAttributesBase* GetAttributes() override; + + virtual class UAFAbilityComponent* GetAbilityComp() override; + + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; + + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) override; + + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; + + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; + + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; + + virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext) override; + + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override {}; + /* AFAbilityInterface Implementation END */ +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp new file mode 100644 index 0000000..e64ba5c --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDGameMode.h" + + + + diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h new file mode 100644 index 0000000..e93d3fe --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/GameModeBase.h" +#include "AFDGameMode.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API AAFDGameMode : public AGameModeBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index fe62648..54e4175 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -284,25 +284,24 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) ] + SOverlay::Slot() [ - SNew(SHorizontalBox) - + SHorizontalBox::Slot() - .FillWidth(0.8f) - .AutoWidth() + SAssignNew(WindowBar, SButton) + .OnPressed(OnPressedDel) + .OnReleased(OnReleasedDel) + .VAlign(EVerticalAlignment::VAlign_Center) + .HAlign(EHorizontalAlignment::HAlign_Right) + .ContentPadding(FMargin(0)) + .ButtonStyle(&ButtonStyle) [ - SNew(STextBlock) - .Text(FText::FromString("Window Title")) - ] - + SHorizontalBox::Slot() - .FillWidth(0.2f) - .AutoWidth() - [ - SAssignNew(WindowBar, SButton) - .OnPressed(OnPressedDel) - .OnReleased(OnReleasedDel) - .VAlign(EVerticalAlignment::VAlign_Center) - .HAlign(EHorizontalAlignment::HAlign_Right) - .ContentPadding(FMargin(0)) - .ButtonStyle(&ButtonStyle) + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .FillWidth(0.8f) + .AutoWidth() + [ + SNew(STextBlock) + .Visibility(EVisibility::SelfHitTestInvisible) + .Text(FText::FromString("Window Title")) + ] + + SHorizontalBox::Slot() [ SNew(SButton) .OnPressed(OnCloseButtonPressedDel) @@ -312,7 +311,6 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) ] ] ] - ] ] diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index 11eb7f5..85100e5 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -242,6 +242,17 @@ struct SPECTRAI_API FSpectrAI } }; +USTRUCT(BlueprintType) +struct FGoalSpec +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Instanced) + class USpectrGoal* Goal; + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; +}; + /** * */ @@ -260,10 +271,12 @@ class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent TArray> ActionList; UPROPERTY() TArray Actions; + UPROPERTY(EditAnywhere) + TArray Goals2; UPROPERTY(EditAnywhere, Instanced) TArray Goals; - UPROPERTY(EditAnywhere, Instanced) + UPROPERTY() class USpectrGoal* CurrentGoal; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h index fafc316..f2b5ca8 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h @@ -24,6 +24,9 @@ class SPECTRAI_API USpectrGoal : public UObject UPROPERTY(EditAnywhere) TMap FinishedState; + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; + UPROPERTY(EditAnywhere) FSpectrEvaluator ScoreEvaluator; From 2e578750dd9868367154f63fbc29c16ebaea68c8 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 29 Jan 2018 20:07:09 +0100 Subject: [PATCH 035/187] fixed ability activation crash --- Config/DefaultEngine.ini | 22 +++++++++--------- Config/DefaultGame.ini | 23 ++++++------------- Config/DefaultGameplayTags.ini | 2 ++ .../AbilityFramework/AFAbilityComponent.cpp | 3 ++- .../Abilities/GAAbilityBase.cpp | 3 ++- .../AbilityFramework/Effects/GAGameEffect.cpp | 4 ++-- .../Source/AbilityFramework/GAGlobalTypes.cpp | 2 +- .../AFDAbilityGiveTrigger.cpp | 3 +++ .../AFDAbilityGiveTrigger.h | 9 +++++--- 9 files changed, 36 insertions(+), 35 deletions(-) diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index bfba6b0..aeb6fb7 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -110,6 +110,17 @@ bForceSettingsInAllMaps=False [/Script/Engine.ProxyLODMeshSimplificationSettings] r.ProxyLODMeshReductionModule=ProxyLODMeshReduction +[/Script/Engine.NavigationSystem] +bAutoCreateNavigationData=True +bAllowClientSideNavigation=False +bInitialBuildingLocked=False +bSkipAgentHeightCheckWhenPickingNavData=False +DataGatheringMode=Lazy +bGenerateNavigationOnlyAroundNavigationInvokers=False +ActiveTilesUpdateInterval=1.000000 ++SupportedAgents=(Name="Default",Color=(B=0,G=255,R=140,A=164),DefaultQueryExtent=(X=50.000000,Y=50.000000,Z=250.000000),NavigationDataClassName=/Script/Engine.RecastNavMesh,AgentRadius=35.000000,AgentHeight=144.000000,AgentStepHeight=-1.000000,NavWalkingSearchHeightScale=0.500000,PreferredNavData=Class'"/Script/Engine.RecastNavMesh"',bCanCrouch=True,bCanJump=True,bCanWalk=True,bCanSwim=True,bCanFly=False) +DirtyAreasUpdateFreq=60.000000 + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -151,15 +162,4 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 -[/Script/Engine.NavigationSystem] -bAutoCreateNavigationData=True -bAllowClientSideNavigation=False -bInitialBuildingLocked=False -bSkipAgentHeightCheckWhenPickingNavData=False -DataGatheringMode=Lazy -bGenerateNavigationOnlyAroundNavigationInvokers=False -ActiveTilesUpdateInterval=1.000000 -+SupportedAgents=(Name="Default",Color=(B=0,G=255,R=140,A=164),DefaultQueryExtent=(X=50.000000,Y=50.000000,Z=250.000000),NavigationDataClassName=/Script/Engine.RecastNavMesh,AgentRadius=35.000000,AgentHeight=144.000000,AgentStepHeight=-1.000000,NavWalkingSearchHeightScale=0.500000,PreferredNavData=Class'"/Script/Engine.RecastNavMesh"',bCanCrouch=True,bCanJump=True,bCanWalk=True,bCanSwim=True,bCanFly=False) -DirtyAreasUpdateFreq=60.000000 - diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index 94d0dab..ce73a2e 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -5,29 +5,20 @@ ProjectName=Third Person Game Template [/Script/AbilityFramework.AFCueManager] DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet +[/Script/UnrealEd.ProjectPackagingSettings] +IncludeAppLocalPrerequisites=True +ApplocalPrerequisitesDirectory=(Path="$(EngineDir)/Binaries/ThirdParty/AppLocalDependencies") +bGenerateChunks=True + [/Script/Engine.AssetManagerSettings] -PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps"))) -PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game"))) --PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) --PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/AbilityFrameworkDebugger")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) bOnlyCookProductionAssets=False +bShouldManagerDetermineTypeAndName=False bShouldGuessTypeAndNameInEditor=True bShouldAcquireMissingChunksOnLoad=False -[/Script/UnrealEd.ProjectPackagingSettings] -IncludeAppLocalPrerequisites=True -ApplocalPrerequisitesDirectory=(Path="$(EngineDir)/Binaries/ThirdParty/AppLocalDependencies") -bGenerateChunks=True diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 4bf0491..d95a620 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -19,6 +19,8 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") +GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Base",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Base.Activation",DevComment="") +GameplayTagList=(Tag="AI.HaveAxe",DevComment="") +GameplayTagList=(Tag="AI.HaveOre",DevComment="") +GameplayTagList=(Tag="AI.HavePick",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 32c7493..e20f6c6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -907,9 +907,10 @@ void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { PredHandle = FAFPredictionHandle::GenerateClientHandle(this); + AbilityContainer.HandleInputPressed(ActionName, PredHandle); } ServerNativeInputPressed(ActionName, PredHandle); - AbilityContainer.HandleInputPressed(ActionName, PredHandle); + } void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index d592747..4dd0d09 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -315,9 +315,10 @@ void UGAAbilityBase::NativeFinishAbility() AbilityComponent->ExecutingAbility = nullptr; OnConfirmDelegate.Clear(); OnConfirmDelegate.RemoveAll(this); - //if (ActivationEffect.Handle.IsValid()) + if (!ActivationEffectHandle.IsValid()) { AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + ActivationEffectHandle.Reset(); } //remove effect. } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 863d9ab..c417bd2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -60,12 +60,12 @@ void FAFEffectRepInfo::OnExpired() OwningComoponent->ExecuteEffectEvent(GetSpec()->OnExpiredEvent); FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnExpired ")); - EffectInfoLog += GetEffectTag().ToString(); + EffectInfoLog += Spec.GetDefaultObject()->EffectTag.ToString(); // GetEffectTag().ToString(); AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); Timer.ClearTimer(ExpiredHandle); Timer.ClearTimer(PeriodHandle); - OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); + //OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index 9da2ce3..bdd6957 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -130,7 +130,7 @@ bool FGAEffectHandle::IsValid() const //} void FGAEffectHandle::Reset() { - Handle = 0; + Handle = INDEX_NONE; EffectPtr.Reset(); } diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp index a76a2ab..dcf743c 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp @@ -14,9 +14,12 @@ AAFDAbilityGiveTrigger::AAFDAbilityGiveTrigger() RootComponent = RootComp; Icon = CreateDefaultSubobject(IconName); + Icon->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); Trigger = CreateDefaultSubobject(TriggerName); Trigger->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); + //Trigger2 = CreateDefaultSubobject(TriggerName); + //Trigger2->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); } // Called when the game starts or when spawned diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h index f010fce..22a0f42 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h @@ -5,6 +5,7 @@ #include "CoreMinimal.h" #include "GameFramework/Actor.h" #include "Components/BoxComponent.h" +#include "Components/ShapeComponent.h" #include "GameplayTags.h" #include "AMTypes.h" #include "AMAbilityManagerComponent.h" @@ -33,15 +34,17 @@ class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor { GENERATED_BODY() protected: - UPROPERTY(BlueprintReadOnly) + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) USceneComponent* RootComp; - UPROPERTY(BlueprintReadOnly) + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) UBillboardComponent* Icon; - UPROPERTY(EditAnywhere, BlueprintReadOnly) + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) UBoxComponent* Trigger; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + UShapeComponent* Trigger2; UPROPERTY(EditAnywhere, Category = "Config") FAFDAbilityConfig AbilityConfig; From 2482976f8906840982b4fd2828c07419ed3d6b72 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 29 Jan 2018 23:08:50 +0100 Subject: [PATCH 036/187] change how periodic abilities should be created and fixed ability cancelation --- Config/DefaultGameplayTags.ini | 2 ++ .../AbilityFramework/AFAbilityComponent.cpp | 35 +++++++++++-------- .../Abilities/GAAbilityBase.cpp | 10 +++++- 3 files changed, 31 insertions(+), 16 deletions(-) diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index d95a620..772389f 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -21,6 +21,8 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base.Activation",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Periodic.Period",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Periodic.Removed",DevComment="") +GameplayTagList=(Tag="AI.HaveAxe",DevComment="") +GameplayTagList=(Tag="AI.HaveOre",DevComment="") +GameplayTagList=(Tag="AI.HavePick",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index e20f6c6..396d7ef 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -930,28 +930,33 @@ void UAFAbilityComponent::BP_InputReleased(FGameplayTag ActionName) void UAFAbilityComponent::NativeInputReleased(FGameplayTag ActionName) { - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - { - //if (Ability->AbilityComponent == this) - { - AbilityContainer.HandleInputReleased(ActionName); - } - } - ServerNativeInputReleased(ActionName); - } - else + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { - //UE_LOG(AbilityFramework, Log, TEXT("UAFAbilityComponent::NativeInputReleased: %s"), *AbilityTag.GetTagName().ToString()); - AbilityContainer.HandleInputReleased(ActionName); } + ServerNativeInputReleased(ActionName); + //if (GetOwnerRole() < ENetRole::ROLE_Authority) + //{ + // //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) + // { + // //if (Ability->AbilityComponent == this) + // { + // + // } + // } + // ServerNativeInputReleased(ActionName); + //} + //else + //{ + // //UE_LOG(AbilityFramework, Log, TEXT("UAFAbilityComponent::NativeInputReleased: %s"), *AbilityTag.GetTagName().ToString()); + + // AbilityContainer.HandleInputReleased(ActionName); + //} } void UAFAbilityComponent::ServerNativeInputReleased_Implementation(FGameplayTag ActionName) { - NativeInputReleased(ActionName); + AbilityContainer.HandleInputReleased(ActionName); } bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag ActionName) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 4dd0d09..f937c5e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -329,10 +329,18 @@ void UGAAbilityBase::CancelActivation() } void UGAAbilityBase::NativeCancelActivation() { - UAFAbilityComponent* AttrComp = ActivationEffect.Handle.GetContext().InstigatorComp.Get(); + if (!ActivationEffectHandle.IsValid()) + return; + + UAFAbilityComponent* AttrComp = ActivationEffectHandle.GetContext().InstigatorComp.Get(); + AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); if (AbilityComponent) { AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + AbilityState = EAFAbilityState::Waiting; + ActivationEffectHandle.Reset(); } } From 0d3316806ff53e73375357665327ce779ed027be Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 30 Jan 2018 00:33:07 +0100 Subject: [PATCH 037/187] if ability is already bound to input, first remove ability and then add new one --- .../AbilityFramework/AFAbilityComponent.cpp | 85 ++++++++++++------- .../AbilityFramework/AFAbilityComponent.h | 24 ++++-- .../AMAbilityManagerComponent.cpp | 2 +- Source/ActionRPGGame/ARPlayerController.cpp | 8 +- .../Abilities/ARUIAbilityManagerComponent.cpp | 2 +- 5 files changed, 78 insertions(+), 43 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 396d7ef..936682d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -647,6 +647,7 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf(AbilitiesComp->GetOwner(), AbilityIn); ability->AbilityComponent = AbilitiesComp.Get(); if (AbilitiesComp.IsValid()) @@ -662,9 +663,10 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOfGetNetMode() == ENetMode::NM_Standalone || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) { @@ -682,10 +684,13 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf& InInputTag) { - return AbilityContainer.IsAbilityBoundToAction(InAbilityTag, InInputTag); + bool bIs = false; + for (const FGameplayTag& Tag : InInputTag) + { + if (AbilityContainer.IsAbilityBoundToAction(InAbilityTag, Tag)) + { + bIs = true; + break; + } + } + return bIs; } void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { @@ -935,23 +949,6 @@ void UAFAbilityComponent::NativeInputReleased(FGameplayTag ActionName) AbilityContainer.HandleInputReleased(ActionName); } ServerNativeInputReleased(ActionName); - //if (GetOwnerRole() < ENetRole::ROLE_Authority) - //{ - // //if (UGAAbilityBase* Ability = AbilityContainer.GetAbility(AbilityTag)) - // { - // //if (Ability->AbilityComponent == this) - // { - // - // } - // } - // ServerNativeInputReleased(ActionName); - //} - //else - //{ - // //UE_LOG(AbilityFramework, Log, TEXT("UAFAbilityComponent::NativeInputReleased: %s"), *AbilityTag.GetTagName().ToString()); - - // AbilityContainer.HandleInputReleased(ActionName); - //} } void UAFAbilityComponent::ServerNativeInputReleased_Implementation(FGameplayTag ActionName) @@ -963,16 +960,28 @@ bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag Action return true; } void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar) + AActor* InAvatar, TArray InInputTag) { - NativeAddAbilityFromTag(InAbilityTag, InAvatar); + NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); } void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar) + AActor* InAvatar, const TArray& InInputTag) { + if (IsAbilityBoundToAction(InAbilityTag, InInputTag)) + { + //remove ability if it is already bound to this input; + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeRemoveAbility(InAbilityTag); + } + else + { + NativeRemoveAbility(InAbilityTag); + } + } if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar); + ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); } else { @@ -1001,13 +1010,30 @@ void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, } void UAFAbilityComponent::ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar) + AActor* InAvatar, const TArray& InInputTag) { - NativeAddAbilityFromTag(InAbilityTag, InAvatar); + NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); } bool UAFAbilityComponent::ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar) + AActor* InAvatar, const TArray& InInputTag) +{ + return true; +} +void UAFAbilityComponent::BP_RemoveAbility(FGameplayTag TagIn) +{ + +} +void UAFAbilityComponent::NativeRemoveAbility(const FGameplayTag& InAbilityTag) +{ + AbilityContainer.RemoveAbility(InAbilityTag); +} +void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(FGameplayTag InAbilityTag) +{ + NativeRemoveAbility(InAbilityTag); +} + +bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(FGameplayTag InAbilityTag) { return true; } @@ -1033,10 +1059,7 @@ void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, } } -void UAFAbilityComponent::BP_RemoveAbility(FGameplayTag TagIn) -{ - -} + UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(FGameplayTag TagIn) { UGAAbilityBase* retVal = AbilityContainer.GetAbility(TagIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 67466a2..be28a05 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -806,7 +806,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, const FAFOnAbilityReady& InputDelegate); - bool IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + bool IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); UFUNCTION(Server, Reliable, WithValidation) @@ -848,26 +848,34 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, */ UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability From Tag"), Category = "AbilityFramework|Abilities") void BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar); + AActor* InAvatar, TArray InInputTag); void NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar); + AActor* InAvatar, const TArray& InInputTag); UFUNCTION(Server, Reliable, WithValidation) void ServerNativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar); + AActor* InAvatar, const TArray& InInputTag); void ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar); + AActor* InAvatar, const TArray& InInputTag); bool ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar); + AActor* InAvatar, const TArray& InInputTag); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") + void BP_RemoveAbility(FGameplayTag TagIn); + + void NativeRemoveAbility(const FGameplayTag& InAbilityTag); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeRemoveAbility(const FGameplayTag& InAbilityTag); + + void ServerNativeRemoveAbility_Implementation(FGameplayTag InAbilityTag); + + bool ServerNativeRemoveAbility_Validate(FGameplayTag InAbilityTag); //TODO: Make it procted - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") - void BP_RemoveAbility(FGameplayTag TagIn); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 3fde467..e9c7ee6 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -92,7 +92,7 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit IAbilityInput, InGroup, InSlot); AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr);// , /*Input*/ ShootInput); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, IAbilityInput);// , /*Input*/ ShootInput); } void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index dd10ba5..5f9e11b 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -45,11 +45,15 @@ void AARPlayerController::SetPawn(APawn* InPawn) //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); - AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr); + TArray NextWeap; + NextWeap.Add(InputNextWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr, NextWeap); FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); - AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr); + TArray PrevWeap; + PrevWeap.Add(InputPreviousWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); } //UIAbilityManagerComponent->BindInputs(); } diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp index bfb880d..138062f 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp @@ -127,7 +127,7 @@ void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbil InAbilityTag, IAbilityInput, InAbilitySet, AbilityIndex); AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, ReadyDelegate); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr); + //AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr); } void UARUIAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, int32 InAbilitySet, int32 InAbilityIndex) From cf3b77c68be5981d1960bbebfc8d3209b05feb32 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 30 Jan 2018 00:48:02 +0100 Subject: [PATCH 038/187] ability check fixed --- .../AbilityFramework/AFAbilityComponent.cpp | 31 ++++++++++--------- .../AbilityFramework/AFAbilityComponent.h | 4 +-- 2 files changed, 18 insertions(+), 17 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 936682d..596a662 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -692,11 +692,16 @@ void FGASAbilityContainer::RemoveAbility(const FGameplayTag& AbilityIn) AbilitiesItems.RemoveAt(Index); MarkArrayDirty(); } -bool FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +FGameplayTag FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) { - bool bHave = false; - - return bHave; + FGameplayTag Ability; + FGameplayTag* AbilityTag = ActionToAbility.Find(InInputTag); + if (AbilityTag) + { + Ability = *AbilityTag + } + + return Ability; } void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { @@ -877,18 +882,13 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c ServerSetAbilityToAction(InAbilityTag, InInputTag); } } -bool UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag) +FGameplayTag UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag) { - bool bIs = false; for (const FGameplayTag& Tag : InInputTag) { - if (AbilityContainer.IsAbilityBoundToAction(InAbilityTag, Tag)) - { - bIs = true; - break; - } + return AbilityContainer.IsAbilityBoundToAction(Tag); + break; } - return bIs; } void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { @@ -967,16 +967,17 @@ void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, AActor* InAvatar, const TArray& InInputTag) { - if (IsAbilityBoundToAction(InAbilityTag, InInputTag)) + FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); + if (AlreadyBound.IsValid()) { //remove ability if it is already bound to this input; if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeRemoveAbility(InAbilityTag); + ServerNativeRemoveAbility(AlreadyBound); } else { - NativeRemoveAbility(InAbilityTag); + NativeRemoveAbility(AlreadyBound); } } if (GetOwnerRole() < ENetRole::ROLE_Authority) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index be28a05..06b3a6e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -162,7 +162,7 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer void RemoveAbility(const FGameplayTag& AbilityIn); void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); - bool IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InInputTag); void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); UGAAbilityBase* GetAbility(FGameplayTag TagIn); @@ -806,7 +806,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, const FAFOnAbilityReady& InputDelegate); - bool IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); UFUNCTION(Server, Reliable, WithValidation) From 5d326020c2ea8c7a18c3dff0fdf0f5575cac078a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 30 Jan 2018 00:53:44 +0100 Subject: [PATCH 039/187] fix --- .../Source/AbilityFramework/AFAbilityComponent.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 596a662..40e78b2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -698,7 +698,7 @@ FGameplayTag FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& In FGameplayTag* AbilityTag = ActionToAbility.Find(InInputTag); if (AbilityTag) { - Ability = *AbilityTag + Ability = *AbilityTag; } return Ability; From 138255693b2af3caac91f289debc68d12f182614 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 30 Jan 2018 00:54:21 +0100 Subject: [PATCH 040/187] fix --- .../Source/AbilityFramework/AFAbilityComponent.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 40e78b2..b4ce862 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -889,6 +889,7 @@ FGameplayTag UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InA return AbilityContainer.IsAbilityBoundToAction(Tag); break; } + return FGameplayTag(); } void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { From 30083df76812144c2a02de3556140dd1c7cccbba Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 30 Jan 2018 20:58:32 +0100 Subject: [PATCH 041/187] Effect Cues will now use tags and asset manager to load, instead of custom mapping asset --- .../AbilityFramework/AFAbilityComponent.cpp | 52 ++--- .../Source/AbilityFramework/AFCueManager.cpp | 205 ++++++++++++------ .../Source/AbilityFramework/AFCueManager.h | 4 + .../AbilityFramework/Effects/GAEffectCue.cpp | 91 ++++++++ .../AbilityFramework/Effects/GAEffectCue.h | 24 +- 5 files changed, 270 insertions(+), 106 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index b4ce862..cb9d58b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -217,28 +217,22 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn //here, we should start attribute change prediction //either change attribute or apply effect which will do so - - //if (mode == ENetMode::NM_Standalone - // || role >= ENetRole::ROLE_Authority) + //execute cue from effect regardless if we have target object or not. + if (InContext.TargetComp.IsValid()) { - //execute cue from effect regardless if we have target object or not. - if (InContext.TargetComp.IsValid()) - { - FGAEffectHandle Handle; - Handle = InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); - if (!PropertyByHandle.Contains(Handle)) - PropertyByHandle.Add(Handle, &InProperty); + FGAEffectHandle Handle; + Handle = InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + if (!PropertyByHandle.Contains(Handle)) + PropertyByHandle.Add(Handle, &InProperty); - OnEffectAppliedToTarget.Broadcast(Handle); - if(InProperty.Duration == 0 - && InProperty.Period == 0) - { - OnEffectRemoved.Broadcast(Handle); - } - return Handle; + OnEffectAppliedToTarget.Broadcast(Handle); + if(InProperty.Duration == 0 + && InProperty.Period == 0) + { + OnEffectRemoved.Broadcast(Handle); } + return Handle; } - return FGAEffectHandle(); } @@ -483,8 +477,8 @@ void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProp DOREPLIFETIME(UAFAbilityComponent, GameEffectContainer); DOREPLIFETIME(UAFAbilityComponent, ActiveCues); - - DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); + DOREPLIFETIME(UAFAbilityComponent, AbilityContainer); + //DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); DOREPLIFETIME_CONDITION(UAFAbilityComponent, RepMontage, COND_SkipOwner); //DOREPLIFETIME(UAFAbilityComponent, RepMontage); } @@ -968,25 +962,17 @@ void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, AActor* InAvatar, const TArray& InInputTag) { - FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); - if (AlreadyBound.IsValid()) - { - //remove ability if it is already bound to this input; - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNativeRemoveAbility(AlreadyBound); - } - else - { - NativeRemoveAbility(AlreadyBound); - } - } if (GetOwnerRole() < ENetRole::ROLE_Authority) { ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); } else { + FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); + if (AlreadyBound.IsValid()) + { + NativeRemoveAbility(AlreadyBound); + } if (UAssetManager* Manager = UAssetManager::GetIfValid()) { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index 20354f0..f1167b7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -147,91 +147,152 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, { if (!CurrentWorld) CurrentWorld = CueParams.Instigator->GetWorld(); - for (const FGameplayTag& Tag : CueParams.CueTags) + + + if (UAssetManager* Manager = UAssetManager::GetIfValid()) { - TSubclassOf CueClass = CueSet->Cues.FindRef(Tag); - if (!CueClass) - continue; - - ENetRole mode = CueParams.Instigator->GetRemoteRole(); - FString role; - switch (mode) + for (const FGameplayTag& CueTag : Tags) { - case ROLE_None: - role = "ROLE_None"; - break; - case ROLE_SimulatedProxy: - role = "ROLE_SimulatedProxy"; - break; - case ROLE_AutonomousProxy: - role = "ROLE_AutonomousProxy"; - break; - case ROLE_Authority: - role = "ROLE_Authority"; - break; - case ROLE_MAX: - role = "ROLE_MAX"; - break; - default: - break; - } - FString prefix = ""; - //if (mode == ENetMode::NM_Client) - //{ - // prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - //} + AGAEffectCue* actor = nullptr; - UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), - *prefix, - *Tag.ToString(), - CueParams.Instigator.IsValid() ? *CueParams.Instigator->GetName() : TEXT("Invalid Instigator"), - *CueParams.HitResult.Location.ToString(), - *CurrentWorld->GetName(), - *role - ); + TUniquePtr>& Cues = InstancedCues.FindOrAdd(CueTag); + if (Cues.IsValid()) + { + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(CueTag); - FActorSpawnParameters SpawnParams; - FVector Location = CueParams.HitResult.Location; - FRotator Rotation = FRotator::ZeroRotator; - AGAEffectCue* actor = nullptr; - TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); - if (!Cues.IsValid()) - { - Cues = MakeUnique>(); - } - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(Tag); + if (!UseCuesQueue.IsValid()) + { + UseCuesQueue = MakeUnique>(); + } + { + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); + } + return;//don't try to load asset, we already have pooled instance. + } + - if (!UseCuesQueue.IsValid()) - { - UseCuesQueue = MakeUnique>(); - } - - if (Cues->IsEmpty()) - { - actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); - Cues->Enqueue(actor); - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("AbilityTagSearch", CueTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams); + + Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } } - else + } +} + +void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag + , FPrimaryAssetId InPrimaryAssetId + , FGAEffectCueParams CueParams) +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); + TSubclassOf cls = Cast(loaded); + if (cls) { - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); + TSubclassOf CueClass = cls; + if (!CueClass) + return; + + ENetRole mode = CueParams.Instigator->GetRemoteRole(); + FString role; + switch (mode) + { + case ROLE_None: + role = "ROLE_None"; + break; + case ROLE_SimulatedProxy: + role = "ROLE_SimulatedProxy"; + break; + case ROLE_AutonomousProxy: + role = "ROLE_AutonomousProxy"; + break; + case ROLE_Authority: + role = "ROLE_Authority"; + break; + case ROLE_MAX: + role = "ROLE_MAX"; + break; + default: + break; + } + + FString prefix = ""; + //if (mode == ENetMode::NM_Client) + //{ + // prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + //} + + UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), + *prefix, + *InCueTag.ToString(), + CueParams.Instigator.IsValid() ? *CueParams.Instigator->GetName() : TEXT("Invalid Instigator"), + *CueParams.HitResult.Location.ToString(), + *CurrentWorld->GetName(), + *role + ); + + FActorSpawnParameters SpawnParams; + FVector Location = CueParams.HitResult.Location; + FRotator Rotation = FRotator::ZeroRotator; + AGAEffectCue* actor = nullptr; + + TUniquePtr>& Cues = InstancedCues.FindOrAdd(InCueTag); + if (!Cues.IsValid()) + { + Cues = MakeUnique>(); + } + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(InCueTag); + + if (!UseCuesQueue.IsValid()) + { + UseCuesQueue = MakeUnique>(); + } + + if (Cues->IsEmpty()) + { + actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); + Cues->Enqueue(actor); + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); + } + else + { + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); + } + + if (actor) + { + actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), + CueParams.Causer.Get(), CueParams.HitResult, CueParams); + } } - - //actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); - if (actor) + { - actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - CueParams.Causer.Get(), CueParams.HitResult, CueParams); + Manager->UnloadPrimaryAsset(InPrimaryAssetId); } - /*UseCues->Dequeue(actor); - Cues->Enqueue(actor);*/ } } + void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h index 97efa3b..a327a93 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h @@ -47,4 +47,8 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject const FGAEffectCueParams& CueParams); void HandleRemoveCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams); +protected: + void OnFinishedLoad(FGameplayTag InCueTag + , FPrimaryAssetId InPrimaryAssetId + , FGAEffectCueParams CueParams); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp index 1eb194e..2a806f9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp @@ -22,8 +22,94 @@ AGAEffectCue::AGAEffectCue(const FObjectInitializer& ObjectInitializer) } void AGAEffectCue::PostInitProperties() { + UpdateAssetRegistryInfo(); Super::PostInitProperties(); } + +void AGAEffectCue::Serialize(FArchive& Ar) +{ + if (Ar.IsSaving()) + { + UpdateAssetRegistryInfo(); + } + + Super::Serialize(Ar); + + if (Ar.IsLoading()) + { + UpdateAssetRegistryInfo(); + } +} +#if WITH_EDITORONLY_DATA +void AGAEffectCue::UpdateAssetBundleData() +{ + AssetBundleData.Reset(); + + // By default parse the metadata + if (UAssetManager::IsValid()) + { + UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); + } +} + +void AGAEffectCue::PreSave(const class ITargetPlatform* TargetPlatform) +{ + Super::PreSave(TargetPlatform); + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid()) + { + // Bundles may have changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +} +#endif +void AGAEffectCue::PostLoad() +{ + Super::PostLoad(); + +#if WITH_EDITORONLY_DATA + FAssetBundleData OldData = AssetBundleData; + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid() && OldData != AssetBundleData) + { + // Bundles changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +#endif +} +FPrimaryAssetId AGAEffectCue::GetPrimaryAssetId() const +{ + FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); + + const AGAEffectCue* A = this; + return FPrimaryAssetId(FPrimaryAssetType("EffectCue"), dupa1); + //if (HasAnyFlags(RF_ClassDefaultObject)) + { + UClass* SearchNativeClass = GetClass(); + + while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) + { + SearchNativeClass = SearchNativeClass->GetSuperClass(); + } + + if (SearchNativeClass && SearchNativeClass != GetClass()) + { + // If blueprint, return native class and asset name + + } + + // Native CDO, return nothing + return FPrimaryAssetId(); + } + + // Data assets use Class and ShortName by default, there's no inheritance so class works fine + //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); +} + void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) { Sequence = InSequence; @@ -71,4 +157,9 @@ void AGAEffectCue::NativeOnRemoved() SequencePlayer->Stop(); OnRemoved(); +} + +void AGAEffectCue::UpdateAssetRegistryInfo() +{ + AbilityTagSearch = CueTag.GetTagName(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h index a47006b..995ba45 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h @@ -5,16 +5,35 @@ #include "GameFramework/Actor.h" #include "MovieSceneSequencePlayer.h" #include "GAGlobalTypes.h" +#include "GameplayTags.h" +#include "AssetBundleData.h" +#include "Engine/AssetManager.h" #include "GAEffectCue.generated.h" class UActorSequencePlayer; UCLASS() class ABILITYFRAMEWORK_API AGAEffectCue : public AActor { GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Cue") + FGameplayTag CueTag; + UPROPERTY(AssetRegistrySearchable) + FName AbilityTagSearch; + UPROPERTY() + FAssetBundleData AssetBundleData; public: // Sets default values for this actor's properties AGAEffectCue(const FObjectInitializer& ObjectInitializer); - virtual void PostInitProperties() override; + void PostInitProperties() override; + + void Serialize(FArchive& Ar) override; + +#if WITH_EDITORONLY_DATA + void UpdateAssetBundleData(); + void PreSave(const class ITargetPlatform* TargetPlatform) override; +#endif //WITH_EDITORONLY_DATA + void PostLoad() override; + FPrimaryAssetId GetPrimaryAssetId() const override; // Called when the game starts or when spawned virtual void BeginPlay() override; @@ -60,4 +79,7 @@ class ABILITYFRAMEWORK_API AGAEffectCue : public AActor FMovieSceneSequencePlaybackSettings PlaybackSettings; FTimerHandle PeriodTimer; + +protected: + void UpdateAssetRegistryInfo(); }; From 7a7e997368b6f79c4fc28201ec7bbbd6a3966033 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 30 Jan 2018 23:36:52 +0100 Subject: [PATCH 042/187] loading effect cues from asset registry --- Config/DefaultGame.ini | 1 + Config/DefaultGameplayTags.ini | 1 + .../Source/AbilityFramework/AFCueManager.cpp | 8 ++------ .../Source/AbilityFramework/Effects/GAEffectCue.cpp | 7 ++++++- .../Source/AbilityFramework/Effects/GAEffectCue.h | 2 +- 5 files changed, 11 insertions(+), 8 deletions(-) diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index ce73a2e..f26d702 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -16,6 +16,7 @@ bGenerateChunks=True +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/AbilityFrameworkDebugger")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="EffectCue",AssetBaseClass=/Script/AbilityFramework.GAEffectCue,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/AbilityFrameworkDebugger")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) bOnlyCookProductionAssets=False bShouldManagerDetermineTypeAndName=False bShouldGuessTypeAndNameInEditor=True diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 772389f..6a873e4 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -21,6 +21,7 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base.Activation",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Periodic.Cue",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Periodic.Period",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Periodic.Removed",DevComment="") +GameplayTagList=(Tag="AI.HaveAxe",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index f1167b7..6369b09 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -180,9 +180,9 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, TArray AssetData; FARFilter Filter; - Filter.TagsAndValues.Add("AbilityTagSearch", CueTag.ToString()); + Filter.TagsAndValues.Add("EffectCueTagSearch", CueTag.ToString()); AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("EffectCue"), AssetData[0].AssetName); FPrimaryAssetTypeInfo Info; if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) { @@ -300,10 +300,6 @@ void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, CurrentWorld = CueParams.Instigator->GetWorld(); for (const FGameplayTag& Tag : CueParams.CueTags) { - TSubclassOf CueClass = CueSet->Cues.FindRef(Tag); - if (!CueClass) - continue; - AGAEffectCue* actor = nullptr; TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); if (!Cues.IsValid()) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp index 2a806f9..dc65290 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp @@ -44,6 +44,7 @@ void AGAEffectCue::Serialize(FArchive& Ar) void AGAEffectCue::UpdateAssetBundleData() { AssetBundleData.Reset(); + UpdateAssetRegistryInfo(); // By default parse the metadata if (UAssetManager::IsValid()) @@ -117,6 +118,10 @@ void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) // Called when the game starts or when spawned void AGAEffectCue::BeginPlay() { + if (!SequencePlayer) + { + SequencePlayer = NewObject(this, UActorSequencePlayer::StaticClass(), "SequencerPlayer"); + } SequencePlayer->Initialize(Sequence, PlaybackSettings); Super::BeginPlay(); @@ -161,5 +166,5 @@ void AGAEffectCue::NativeOnRemoved() void AGAEffectCue::UpdateAssetRegistryInfo() { - AbilityTagSearch = CueTag.GetTagName(); + EffectCueTagSearch = CueTag.GetTagName(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h index 995ba45..0301b04 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h @@ -18,7 +18,7 @@ class ABILITYFRAMEWORK_API AGAEffectCue : public AActor UPROPERTY(EditAnywhere, Category = "Cue") FGameplayTag CueTag; UPROPERTY(AssetRegistrySearchable) - FName AbilityTagSearch; + FName EffectCueTagSearch; UPROPERTY() FAssetBundleData AssetBundleData; public: From 4806b3e9cdd3f8f9a0ed7f0b8143eccfe0079ae3 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 31 Jan 2018 12:28:10 +0100 Subject: [PATCH 043/187] removed dead code --- .../AbilityFramework/AFAbilityComponent.cpp | 20 +- .../AbilityFramework/AFAbilityComponent.h | 2 - .../Source/AbilityFramework/AFCueManager.cpp | 10 +- .../Source/AbilityFramework/AFCueManager.h | 6 - .../Source/AbilityFramework/AFCueSet.cpp | 8 - .../Source/AbilityFramework/AFCueSet.h | 23 -- .../SpectrBrainComponent.h | 317 ++++++++++++++++++ 7 files changed, 322 insertions(+), 64 deletions(-) delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h create mode 100644 enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index cb9d58b..9832052 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -19,7 +19,6 @@ #include "MessageEndpointBuilder.h" #include "Effects/GAEffectExtension.h" #include "Effects/GAEffectCue.h" -#include "AFCueSet.h" #include "AFCueManager.h" #include "Effects/GABlueprintLibrary.h" #include "Async.h" @@ -412,24 +411,7 @@ void UAFAbilityComponent::MulticastApplyEffectCue_Implementation( FGAEffectCuePa *GetOwner()->GetName(), *CueParams.Instigator->GetName() ); - - //for (const FGameplayTag& Tag : CueParams.CueTags) - //{ - // TSubclassOf CueClass = TestCueSet->Cues.FindRef(Tag); - // if (!CueClass) - // continue; - - // FActorSpawnParameters SpawnParams; - // FVector Location = CueParams.HitResult.Location; - // FRotator Rotation = FRotator::ZeroRotator; - // AGAEffectCue* actor = nullptr; - // - // actor = GetWorld()->SpawnActor(CueClass, Location, Rotation, SpawnParams); - // actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - // CueParams.Causer.Get(), CueParams.HitResult); - - //} - + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams); } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 06b3a6e..8a55a27 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -261,8 +261,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, //FAFEffectTimerManager EffectTimerManager; - UPROPERTY(EditAnywhere) - class UAFCueSet* TestCueSet; UPROPERTY(EditAnywhere, Category = "Test") FGameplayTag TagTest; /* diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index 6369b09..b6d5700 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -2,7 +2,6 @@ #include "AbilityFramework.h" #include "Effects/GAEffectCue.h" -#include "AFCueSet.h" #include "AFCueManager.h" //#if WITH_EDITOR //#include "Editor.H" @@ -21,7 +20,6 @@ UAFCueManager* UAFCueManager::Get() RF_MarkAsRootSet); ManagerInstance->AddToRoot(); ManagerInstance->Initialize(); - ManagerInstance->LoadCueSet(); return ManagerInstance; } @@ -33,10 +31,6 @@ void UAFCueManager::Initialize() FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); } -void UAFCueManager::LoadCueSet() -{ - CueSet = DefaultCueSet.LoadSynchronous(); -} #if WITH_EDITOR void UAFCueManager::HandleOnPIEEnd(bool InVal) { @@ -171,6 +165,10 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, Cues->Dequeue(actor); UseCuesQueue->Enqueue(actor); } + if (actor) + { + actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.GetActor(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); + } return;//don't try to load asset, we already have pooled instance. } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h index a327a93..aed97c7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h @@ -20,11 +20,6 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject //UPROPERTY() static UAFCueManager* ManagerInstance; UWorld* CurrentWorld; - UPROPERTY(config, EditAnywhere, Category = "Cue Set") - TAssetPtr DefaultCueSet; - - UPROPERTY() - UAFCueSet* CueSet; //store per instigator ? Causer ? or global pool ? //stores unused instanced cues. @@ -34,7 +29,6 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject TMap>>> UsedCues; public: void Initialize(); - void LoadCueSet(); #if WITH_EDITOR //handle clearing up cache when PIE mode is ending. void HandleOnPIEEnd(bool InVal); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp deleted file mode 100644 index f946e48..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFCueSet.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h deleted file mode 100644 index fd829bc..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueSet.h +++ /dev/null @@ -1,23 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Engine/DataAsset.h" -#include "GameplayTags.h" -#include "AFCueSet.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFCueSet : public UDataAsset -{ - GENERATED_BODY() - -public: - UPROPERTY(EditAnywhere) - TMap> Cues; - - -}; diff --git a/enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h b/enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h new file mode 100644 index 0000000..85100e5 --- /dev/null +++ b/enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h @@ -0,0 +1,317 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameplayTasksComponent.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "Queue.h" +#include "SpectrAction.h" +#include "Navigation/PathFollowingComponent.h" +#include "AITypes.h" + +#include "SpectrBrainComponent.generated.h" + +enum class ESpectrState : uint8 +{ + Idle = 0, + Action = 1, + Move = 2 +}; + +//Node representing single step in plan. +struct FSpectrNode +{ + int32 Cost; + float Score; + int32 RemainingCost; + TWeakPtr Parent; + TMap State; + USpectrAction* Action; + TArray> Children; + FSpectrNode() {} + FSpectrNode(const TMap& InState, int32 InCost, int32 InRemainingCost) + : Cost(InCost) + , RemainingCost(InRemainingCost) + , State(InState) + {} + + bool Equals(USpectrAction* InAction) + { + return Action == InAction; + } + + bool operator==(const FSpectrNode& Other) const + { + return Action == Other.Action; + } + bool operator==(const USpectrAction*& Other) const + { + return Action == Other; + } + +}; + +bool operator==(const FSpectrNode& Other, const USpectrAction*& Action); + + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrAI +{ + GENERATED_BODY() +public: + //Precondition, List of action for this precondition; + TMap> > ActionMap; + + bool CheckGoal(const TMap& InEffects, const TMap& InGoal) + { + bool bAchieved = false; + for (TPair Test : InGoal) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Check Current Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + + for (TPair Test : InEffects) + { + if (InGoal.Contains(Test.Key)) + { + if (InGoal[Test.Key] == Test.Value) + { + UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Passed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); + bAchieved = true; + } + else + { + UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Failed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); + bAchieved = false; + break; //all or nothing. + } + } + } + + + return bAchieved; + } + + TMap UpdateState(const TMap& InEffects, + const TMap& InCurrentState) + { + TMap NewState; + NewState.Append(InCurrentState); + for (TPair Effect : InEffects) + { + if (NewState.Contains(Effect.Key)) + { + bool* dd = NewState.Find(Effect.Key); + *dd = Effect.Value; + } + } + return NewState; + } + + TMap AddGoalChanges(const TMap& InCurrentGoal, + const TMap& InGoalChange) + { + TMap NewSet; + + NewSet.Append(InCurrentGoal); + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE START")); + for (TPair Test : InCurrentGoal) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE END")); + for (TPair Change : InGoalChange) + { + if (NewSet.Contains(Change.Key)) + { + /*bool* dd = NewSet.Find(Change.Key); + *dd = Change.Value;*/ + } + else + { + NewSet.Add(Change.Key, Change.Value); + } + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST START")); + for (TPair Test : NewSet) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST END")); + return NewSet; + } + void InitializeMap(const TArray>& ActionList) + { + for (const TSubclassOf Action : ActionList) + { + for (const TPair& Effect : Action.GetDefaultObject()->Effects) + { + TArray>& ActionArray = ActionMap.FindOrAdd(Effect.Key); + ActionArray.Add(Action); + } + + } + } + void Plan(const TMap& InTargetGoal, const TMap& InCurrentState + , TArray& InActionQueue + , const TArray& ActionList + , class USpectrContext* InContext + , class AAIController* AIController) + { + TArray> OpenNodes; + TArray> ClosedNodes; + + TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); + + //actually made action when constructing node path. + //and then execute it in reverse (from last item in array to first). + //so we don't was time traversing node tree and then reordering actions.. + TArray ActionPlan; + + OpenNodes.Push(Node); + + TArray AvailableActions = ActionList; + + //reverse A*, or something similiar to it at least.. + while (OpenNodes.Num()) + { + TSharedPtr CurrentNode = OpenNodes.Pop(); + ClosedNodes.Push(CurrentNode); + + for (USpectrAction*& Action : AvailableActions) + { + //or instead of pushing to closed actions... we can remove them for Available Actions hmm ? + if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) + { + return Item->Equals(Action); + })) + { + continue; + } + + if (!(CurrentNode->Action == Action)) + { + if (CheckGoal(Action->Effects, CurrentNode->State)) + { + //action scored Zero, so it probabaly can't be used anyway. + if (!Action->NativeEvaluateCondition(InContext, AIController)) + { + continue; + } + float Score = Action->NativeScore(InContext, AIController); + + TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action->PreConditions, Action->Cost, 0)); + Node2->Action = Action; + Node2->Score = Score; + OpenNodes.Add(Node2); + + if (CurrentNode->Children.Num() == 0) + { + CurrentNode->Children.Add(Node2); + ActionPlan.Add(Action); + } + else + { + //add new action, only if it is cheaper than current one. + //very primitive we need to check if the actuall path will be cheaper. + //so compare current cost of the path with + if (Score > Node2->Score) + { + ActionPlan.Remove(CurrentNode->Children[0]->Action); + CurrentNode->Children.Empty(); + CurrentNode->Children.Add(Node2); + + ActionPlan.Add(Action); + } + else + { + //action has been discarded, remove it from OpenNodes + OpenNodes.Remove(Node2); + //and add to closed nodes. No reason to ever consider it again. + ClosedNodes.Add(Node2); + } + } + } + } + } + } + + InActionQueue = ActionPlan; + } +}; + +USTRUCT(BlueprintType) +struct FGoalSpec +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Instanced) + class USpectrGoal* Goal; + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; +}; + +/** + * + */ +UCLASS() +class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent +{ + GENERATED_BODY() +public: + ESpectrState FSMState; + + UPROPERTY(EditAnywhere) + TMap Goal; + UPROPERTY(EditAnywhere) + TMap CurrentState; + UPROPERTY(EditAnywhere) + TArray> ActionList; + UPROPERTY() + TArray Actions; + UPROPERTY(EditAnywhere) + TArray Goals2; + + UPROPERTY(EditAnywhere, Instanced) + TArray Goals; + UPROPERTY() + class USpectrGoal* CurrentGoal; + + + UPROPERTY() + TArray PendingPlan; + + TQueue PendingPlan2; + + UPROPERTY() + USpectrAction* CurrentAction; + + + + UPROPERTY(EditAnywhere) + TSubclassOf Context; + UPROPERTY() + class USpectrContext* CurrentContext; + + FSpectrAI SpectrAI; + + //Map of pending move events. + FSimpleDelegate PendingMoveEvent; + + USpectrBrainComponent(const FObjectInitializer& ObjectInitializer); + virtual void BeginPlay() override; + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; + UFUNCTION(BlueprintCallable) + void StarPlanning(); + + void SelectGoal(); + void ExecutePlan(class USpectrAction* PreviousAction); + void AbortPlan(const FString& Reason); + void OnActionFinished(USpectrAction* InAction); + void OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result); + + void MoveToLocation(); + void MoveToActor(AActor* Target, float MinDistance); +}; From 74f53896a4a17462b16ea8fd281d9e533f106639 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 31 Jan 2018 15:31:46 +0100 Subject: [PATCH 044/187] spectr added delay between planning --- .../Source/SpectrAI/SpectrBrainComponent.cpp | 41 ++- .../Source/SpectrAI/SpectrBrainComponent.h | 6 + .../SpectrBrainComponent.h | 317 ------------------ 3 files changed, 44 insertions(+), 320 deletions(-) delete mode 100644 enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp index ac3d1a3..9a38a52 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp @@ -3,7 +3,8 @@ #include "SpectrBrainComponent.h" #include "SpectrContext.h" #include "AIController.h" - +#include "Engine/World.h" +#include "TimerManager.h" bool operator==(const FSpectrNode& Other, const USpectrAction*& Action) { @@ -40,6 +41,12 @@ void USpectrBrainComponent::BeginPlay() } void USpectrBrainComponent::StarPlanning() { + //no point of running planner on clients. + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + return; + } + TArray OutActionList; if (AAIController* AIController = Cast(GetOwner())) { @@ -54,9 +61,37 @@ void USpectrBrainComponent::StarPlanning() UE_LOG(LogTemp, Log, TEXT("Action Name: %s \n"), *name); } - ExecutePlan(nullptr); + if (OutActionList.Num() == 0) + { + FTimerManager& Timer = GetWorld()->GetTimerManager(); + FTimerDelegate del = FTimerDelegate::CreateUObject(this, &USpectrBrainComponent::NextPlan); + Timer.SetTimer(NextPlanTimerHandle, del, 0.2f, false, 0.2f); + } + else + { + ExecutePlan(nullptr); + } + +} +void USpectrBrainComponent::NextPlan() +{ + TArray OutActionList; + if (AAIController* AIController = Cast(GetOwner())) + { + SpectrAI.Plan(Goal, CurrentState, OutActionList, Actions, CurrentContext, AIController); + } + if (OutActionList.Num() == 0) + { + FTimerManager& Timer = GetWorld()->GetTimerManager(); + FTimerDelegate del = FTimerDelegate::CreateUObject(this, &USpectrBrainComponent::NextPlan); + Timer.SetTimer(NextPlanTimerHandle, del, 0.2f, false, 0.2f); + } + else + { + ExecutePlan(nullptr); + } + } - void USpectrBrainComponent::SelectGoal() { diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h index 85100e5..332e97b 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h @@ -300,11 +300,15 @@ class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent //Map of pending move events. FSimpleDelegate PendingMoveEvent; + FTimerHandle NextPlanTimerHandle; + USpectrBrainComponent(const FObjectInitializer& ObjectInitializer); virtual void BeginPlay() override; virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; UFUNCTION(BlueprintCallable) void StarPlanning(); + UFUNCTION() + void NextPlan(); void SelectGoal(); void ExecutePlan(class USpectrAction* PreviousAction); @@ -314,4 +318,6 @@ class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent void MoveToLocation(); void MoveToActor(AActor* Target, float MinDistance); + + }; diff --git a/enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h b/enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h deleted file mode 100644 index 85100e5..0000000 --- a/enc_temp_folder/2e36b8f0a2caf8de3d0a095dcc5c868/SpectrBrainComponent.h +++ /dev/null @@ -1,317 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameplayTasksComponent.h" -#include "GameplayTags.h" -#include "GameplayTagContainer.h" -#include "Queue.h" -#include "SpectrAction.h" -#include "Navigation/PathFollowingComponent.h" -#include "AITypes.h" - -#include "SpectrBrainComponent.generated.h" - -enum class ESpectrState : uint8 -{ - Idle = 0, - Action = 1, - Move = 2 -}; - -//Node representing single step in plan. -struct FSpectrNode -{ - int32 Cost; - float Score; - int32 RemainingCost; - TWeakPtr Parent; - TMap State; - USpectrAction* Action; - TArray> Children; - FSpectrNode() {} - FSpectrNode(const TMap& InState, int32 InCost, int32 InRemainingCost) - : Cost(InCost) - , RemainingCost(InRemainingCost) - , State(InState) - {} - - bool Equals(USpectrAction* InAction) - { - return Action == InAction; - } - - bool operator==(const FSpectrNode& Other) const - { - return Action == Other.Action; - } - bool operator==(const USpectrAction*& Other) const - { - return Action == Other; - } - -}; - -bool operator==(const FSpectrNode& Other, const USpectrAction*& Action); - - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrAI -{ - GENERATED_BODY() -public: - //Precondition, List of action for this precondition; - TMap> > ActionMap; - - bool CheckGoal(const TMap& InEffects, const TMap& InGoal) - { - bool bAchieved = false; - for (TPair Test : InGoal) - { - UE_LOG(LogTemp, Log, TEXT("---Build Plan - Check Current Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); - } - - for (TPair Test : InEffects) - { - if (InGoal.Contains(Test.Key)) - { - if (InGoal[Test.Key] == Test.Value) - { - UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Passed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); - bAchieved = true; - } - else - { - UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Failed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); - bAchieved = false; - break; //all or nothing. - } - } - } - - - return bAchieved; - } - - TMap UpdateState(const TMap& InEffects, - const TMap& InCurrentState) - { - TMap NewState; - NewState.Append(InCurrentState); - for (TPair Effect : InEffects) - { - if (NewState.Contains(Effect.Key)) - { - bool* dd = NewState.Find(Effect.Key); - *dd = Effect.Value; - } - } - return NewState; - } - - TMap AddGoalChanges(const TMap& InCurrentGoal, - const TMap& InGoalChange) - { - TMap NewSet; - - NewSet.Append(InCurrentGoal); - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE START")); - for (TPair Test : InCurrentGoal) - { - UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); - } - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE END")); - for (TPair Change : InGoalChange) - { - if (NewSet.Contains(Change.Key)) - { - /*bool* dd = NewSet.Find(Change.Key); - *dd = Change.Value;*/ - } - else - { - NewSet.Add(Change.Key, Change.Value); - } - } - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST START")); - for (TPair Test : NewSet) - { - UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); - } - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST END")); - return NewSet; - } - void InitializeMap(const TArray>& ActionList) - { - for (const TSubclassOf Action : ActionList) - { - for (const TPair& Effect : Action.GetDefaultObject()->Effects) - { - TArray>& ActionArray = ActionMap.FindOrAdd(Effect.Key); - ActionArray.Add(Action); - } - - } - } - void Plan(const TMap& InTargetGoal, const TMap& InCurrentState - , TArray& InActionQueue - , const TArray& ActionList - , class USpectrContext* InContext - , class AAIController* AIController) - { - TArray> OpenNodes; - TArray> ClosedNodes; - - TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); - - //actually made action when constructing node path. - //and then execute it in reverse (from last item in array to first). - //so we don't was time traversing node tree and then reordering actions.. - TArray ActionPlan; - - OpenNodes.Push(Node); - - TArray AvailableActions = ActionList; - - //reverse A*, or something similiar to it at least.. - while (OpenNodes.Num()) - { - TSharedPtr CurrentNode = OpenNodes.Pop(); - ClosedNodes.Push(CurrentNode); - - for (USpectrAction*& Action : AvailableActions) - { - //or instead of pushing to closed actions... we can remove them for Available Actions hmm ? - if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) - { - return Item->Equals(Action); - })) - { - continue; - } - - if (!(CurrentNode->Action == Action)) - { - if (CheckGoal(Action->Effects, CurrentNode->State)) - { - //action scored Zero, so it probabaly can't be used anyway. - if (!Action->NativeEvaluateCondition(InContext, AIController)) - { - continue; - } - float Score = Action->NativeScore(InContext, AIController); - - TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action->PreConditions, Action->Cost, 0)); - Node2->Action = Action; - Node2->Score = Score; - OpenNodes.Add(Node2); - - if (CurrentNode->Children.Num() == 0) - { - CurrentNode->Children.Add(Node2); - ActionPlan.Add(Action); - } - else - { - //add new action, only if it is cheaper than current one. - //very primitive we need to check if the actuall path will be cheaper. - //so compare current cost of the path with - if (Score > Node2->Score) - { - ActionPlan.Remove(CurrentNode->Children[0]->Action); - CurrentNode->Children.Empty(); - CurrentNode->Children.Add(Node2); - - ActionPlan.Add(Action); - } - else - { - //action has been discarded, remove it from OpenNodes - OpenNodes.Remove(Node2); - //and add to closed nodes. No reason to ever consider it again. - ClosedNodes.Add(Node2); - } - } - } - } - } - } - - InActionQueue = ActionPlan; - } -}; - -USTRUCT(BlueprintType) -struct FGoalSpec -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Instanced) - class USpectrGoal* Goal; - UPROPERTY(EditAnywhere, Instanced) - TArray Considerations; -}; - -/** - * - */ -UCLASS() -class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent -{ - GENERATED_BODY() -public: - ESpectrState FSMState; - - UPROPERTY(EditAnywhere) - TMap Goal; - UPROPERTY(EditAnywhere) - TMap CurrentState; - UPROPERTY(EditAnywhere) - TArray> ActionList; - UPROPERTY() - TArray Actions; - UPROPERTY(EditAnywhere) - TArray Goals2; - - UPROPERTY(EditAnywhere, Instanced) - TArray Goals; - UPROPERTY() - class USpectrGoal* CurrentGoal; - - - UPROPERTY() - TArray PendingPlan; - - TQueue PendingPlan2; - - UPROPERTY() - USpectrAction* CurrentAction; - - - - UPROPERTY(EditAnywhere) - TSubclassOf Context; - UPROPERTY() - class USpectrContext* CurrentContext; - - FSpectrAI SpectrAI; - - //Map of pending move events. - FSimpleDelegate PendingMoveEvent; - - USpectrBrainComponent(const FObjectInitializer& ObjectInitializer); - virtual void BeginPlay() override; - virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; - UFUNCTION(BlueprintCallable) - void StarPlanning(); - - void SelectGoal(); - void ExecutePlan(class USpectrAction* PreviousAction); - void AbortPlan(const FString& Reason); - void OnActionFinished(USpectrAction* InAction); - void OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result); - - void MoveToLocation(); - void MoveToActor(AActor* Target, float MinDistance); -}; From 9e2745ea0509ab0e32a9c51a0cd8e04771018f7a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 1 Feb 2018 21:16:09 +0100 Subject: [PATCH 045/187] added base weapon class and removed dead code --- Config/DefaultGameplayTags.ini | 2 + .../Abilities/GAAbilityBase.cpp | 1 + .../Abilities/GAAbilityBase.h | 11 +- .../AbilityFrameworkEditor.cpp | 9 - .../AFDAbilityGiveTrigger.h | 12 +- .../AMAbilityManagerComponent.cpp | 15 +- .../AMAbilityManagerComponent.h | 27 +- Source/ActionRPGGame/ARCharacter.cpp | 1 - Source/ActionRPGGame/ARPlayerController.cpp | 6 +- Source/ActionRPGGame/ARPlayerController.h | 2 - Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 90 ++----- Source/ActionRPGGame/UI/ARAbilityWidget.h | 13 +- Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp | 3 - Source/ActionRPGGame/UI/ARUMGWidgetBase.h | 2 - .../UI/Abilities/ARAbilityInfoWidget.cpp | 1 - .../Abilities/ARAbilitySlotConfigWidget.cpp | 11 +- .../Abilities/ARUIAbilityManagerComponent.cpp | 247 ------------------ .../Abilities/ARUIAbilityManagerComponent.h | 113 -------- Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 54 ++++ Source/ActionRPGGame/Weapons/ARWeaponBase.h | 41 +++ .../Weapons/ARWeaponManagerComponent.cpp | 34 ++- .../Weapons/ARWeaponManagerComponent.h | 54 ++-- 22 files changed, 229 insertions(+), 520 deletions(-) delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponBase.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponBase.h diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 6a873e4..4fee96c 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -21,6 +21,8 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base.Activation",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Charged",DevComment="") ++GameplayTagList=(Tag="AFD.Ability.Charged.Activate",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Periodic.Cue",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Periodic.Period",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Periodic.Removed",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index f937c5e..8bc3f10 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -342,6 +342,7 @@ void UGAAbilityBase::NativeCancelActivation() AbilityState = EAFAbilityState::Waiting; ActivationEffectHandle.Reset(); } + OnActivationCancel(); } bool UGAAbilityBase::IsWaitingForConfirm() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 6ab63e9..fad1398 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -350,8 +350,11 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask /* - Called When activation effect expired. - In case of instant effects, called right after OnActivate. + * @call Order: + * Previous Function: UGAAbilityBase::StartActivation + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility + * + * Called on both Client and Server to indicate that ability is finished. */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnActivationFinished(); @@ -448,10 +451,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask * @call Order: * Previous Function: UGAAbilityBase::NativeFinishAbility * Next Function: (Blueprint) Custom Functions - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point - * finish ability. * - * Called to finish ability and start clean up. + * Called when ability is finished. */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnAbilityFinished(); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp index 1bd6caf..b2fede4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp @@ -107,15 +107,6 @@ void FAbilityFrameworkEditor::StartupModule() //BlueprintEditorTabBinding = MakeShared(); OnInitializeSequenceHandle = UGAEffectCueSequence::OnInitializeSequence().AddStatic(FAbilityFrameworkEditor::OnInitializeSequence); - - if (ISettingsModule* SettingsModule = FModuleManager::GetModulePtr("Settings")) - { - SettingsModule->RegisterSettings("Project", "Game", "Cue Manager", - FText::FromString("Cue Manager"), - FText::FromString("Cue Manager Settings"), - GetMutableDefault() - ); - } } void FAbilityFrameworkEditor::ShutdownModule() { diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h index 22a0f42..ad8794f 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h @@ -11,18 +11,18 @@ #include "AMAbilityManagerComponent.h" #include "AFDAbilityGiveTrigger.generated.h" -USTRUCT() +USTRUCT(BlueprintType) struct FAFDAbilityConfig { GENERATED_BODY() public: - UPROPERTY(EditAnywhere, Category = "Config") + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") EAMGroup Group; - UPROPERTY(EditAnywhere, Category = "Config") + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") EAMSlot Slot; - UPROPERTY(EditAnywhere, Category = "Config") + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") FGameplayTag AbilityTag; - UPROPERTY(EditAnywhere, Category = "Config") + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") TArray InputTag; }; @@ -46,7 +46,7 @@ class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor UPROPERTY(VisibleAnywhere, BlueprintReadOnly) UShapeComponent* Trigger2; - UPROPERTY(EditAnywhere, Category = "Config") + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") FAFDAbilityConfig AbilityConfig; UPROPERTY() diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index e9c7ee6..aaeeee9 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -41,7 +41,16 @@ void UAMAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickT // ... } +void UAMAbilityManagerComponent::BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent) +{ + if (!AbilityComponent) + return; + for (const FGameplayTag& Input : InputsToBind) + { + AbilityComponent->BindAbilityToAction(InputComponent, Input); + } +} UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) { return AbilitySet.Num() >= MaxGroups ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; @@ -74,7 +83,7 @@ void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, { AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; } -void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) +void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -92,7 +101,7 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit IAbilityInput, InGroup, InSlot); AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr, IAbilityInput);// , /*Input*/ ShootInput); + AbilityComp->NativeAddAbilityFromTag(InAbilityTag, InAvatar, IAbilityInput);// , /*Input*/ ShootInput); } void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) @@ -123,6 +132,7 @@ void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArra SetAbilityTag(InGroup, InSlot, InAbilityTag); SetInputTag(InGroup, InSlot, InAbilityInput); AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(InAbilityTag); } } @@ -143,6 +153,7 @@ void UAMAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, SetAbility(InGroup, InSlot, Ability); SetAbilityTag(InGroup, InSlot, InAbilityTag); SetInputTag(InGroup, InSlot, InAbilityInput); + ExecuteAbilityReadyEvent(InAbilityTag); } void UAMAbilityManagerComponent::NextGroup() diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index fd4ee30..725dc4d 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -9,6 +9,8 @@ #include "Abilities/GAAbilityBase.h" #include "AMAbilityManagerComponent.generated.h" + + /* - Group - Set @@ -89,6 +91,9 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent TArray> AbilityTagsSet; TArray>> AbilitySet; + + TMap AbilityReadyEvents; + public: // Sets default values for this component's properties UAMAbilityManagerComponent(); @@ -100,7 +105,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + void BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent); UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); @@ -113,7 +118,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Ability"), Category = "Ability Manager") void BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); - void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); + void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr); UFUNCTION() void OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); @@ -146,4 +151,22 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent UFUNCTION(BlueprintCallable) void SelectGroup(EAMGroup InGroup); + + + void AddOnAbilityReadyEvent(const FGameplayTag& Ability, const FSimpleDelegate& Delegate) + { + if (!AbilityReadyEvents.Contains(Ability)) + { + AbilityReadyEvents.Add(Ability, Delegate); + } + } + + void ExecuteAbilityReadyEvent(const FGameplayTag& Ability) + { + if (FSimpleDelegate* Event = AbilityReadyEvents.Find(Ability)) + { + Event->ExecuteIfBound(); + AbilityReadyEvents.Remove(Ability); + } + } }; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index e7d2bf4..e0beff5 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -8,7 +8,6 @@ #include "GameFramework/Controller.h" #include "GameFramework/SpringArmComponent.h" #include "ARPlayerController.h" -#include "ARUIAbilityManagerComponent.h" ////////////////////////////////////////////////////////////////////////// // AARCharacter diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 5f9e11b..7a6ce61 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -2,7 +2,6 @@ #include "ARPlayerController.h" #include "ARUIComponent.h" -#include "ARUIAbilityManagerComponent.h" #include "AFAbilityComponent.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" @@ -17,7 +16,6 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial : Super(ObjectInitializer) { UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); - UIAbilityManagerComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIAbilityManagerComponent"); WeaponManager = ObjectInitializer.CreateDefaultSubobject(this, "WeaponManager"); AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); @@ -41,7 +39,8 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); - //WeaponManager->BindInputs(); + AbilityManager->BindInputs(InputComponent, AbilityComp); + WeaponManager->BindInputs(InputComponent, AbilityComp); //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); @@ -67,7 +66,6 @@ void AARPlayerController::SetupInputComponent() void AARPlayerController::InputSwitchAbilitySet() { - UIAbilityManagerComponent->SwitchSet(); } void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 57de46f..da6fd69 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -17,8 +17,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController public: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIComponent* UIComponent; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") - class UARUIAbilityManagerComponent* UIAbilityManagerComponent; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARWeaponManagerComponent* WeaponManager; diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index 5d527c5..96f3e05 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -3,7 +3,7 @@ #include "ARAbilityWidget.h" #include "AFAbilityInterface.h" #include "AFAbilityComponent.h" -#include "ARUIAbilityManagerComponent.h" +#include "AMAbilityManagerComponent.h" #include "Abilities/GAAbilityBase.h" #include "ARAbilityBase.h" @@ -15,73 +15,73 @@ float UARAbilityWidget::GetActivationRemainingTime() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationRemainingTime() : 0; } float UARAbilityWidget::GetActivationRemainingTimeNormalized() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationRemainingTimeNormalized() : 0; } float UARAbilityWidget::GetActivationCurrentTime() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationCurrentTime() : 0; } float UARAbilityWidget::GetActivationCurrentTimeNormalized() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationCurrentTimeNormalized() : 0; } float UARAbilityWidget::GetActivationEndTime() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationEndTime() : 0; } float UARAbilityWidget::GetCooldownRemainingTime() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownRemainingTime() : 0; } float UARAbilityWidget::GetCooldownRemainingTimeNormalized() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownRemainingTimeNormalized() : 0; } float UARAbilityWidget::GetCooldownCurrentTime() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownCurrentTime() : 0; } float UARAbilityWidget::GetCooldownCurrentTimeNormalized() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownCurrentTimeNormalized() : 0; } float UARAbilityWidget::GetCooldownEndTime() { - if (!OwningComponent) + if (!AbilityManager) return 0; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownEndTime() : 0; } UTexture2D* UARAbilityWidget::GetIcon() @@ -89,48 +89,10 @@ UTexture2D* UARAbilityWidget::GetIcon() if (Icon) return Icon; - if (!OwningComponent) + if (!AbilityManager) return nullptr; - UARAbilityBase* Ability = OwningComponent->GetAbility(AbilitySetIndex, AbilityIndex); - return Ability ? Ability->UIData->Icon : nullptr; -} - -void UARAbilityWidget::Setbility(const FGameplayTag& InAbility) -{ - AbilityTag = InAbility; - FAssetData AssetData = FARGlobals::GetAbilityAssetByTag(InAbility); - TSubclassOf cls;// = nullptr; - if (AssetData.IsValid()) - { - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - FPrimaryAssetId PrimaryAssetId = FARGlobals::MakeAbilityAssetId(AssetData); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info))// && !Info.bHasBlueprintClasses) - { - cls = Manager->GetPrimaryAssetObjectClass(PrimaryAssetId); - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityWidget::OnFinishedLoad, PrimaryAssetId); - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); - } - } - } -} -void UARAbilityWidget::OnFinishedLoad(FPrimaryAssetId PrimaryAssetId) -{ - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - UObject* loaded = Manager->GetPrimaryAssetObject(PrimaryAssetId); - TSubclassOf cls = Cast(loaded); - if (cls) - { - UARAbilityBase* CDO = cls.GetDefaultObject(); - Icon = CDO->UIData->Icon; - } - { - Manager->UnloadPrimaryAsset(PrimaryAssetId); - } - } -} + return nullptr; + /*UARAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->UIData->Icon : nullptr;*/ +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index aeaaa0a..afca7c5 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -7,6 +7,7 @@ #include "GameplayTags.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" +#include "AMTypes.h" #include "ARAbilityWidget.generated.h" /** @@ -17,11 +18,13 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase { GENERATED_BODY() public: + UPROPERTY() + class UAMAbilityManagerComponent* AbilityManager; UPROPERTY(EditAnywhere, Category = "Config") - int32 AbilitySetIndex; + EAMGroup Group; UPROPERTY(EditAnywhere, Category = "Config") - int32 AbilityIndex; + EAMSlot AbilitySlot; UPROPERTY(EditAnywhere, Category = "Config") UTexture2D* Icon; UPROPERTY(EditAnywhere, Category = "Config") @@ -51,10 +54,4 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") UTexture2D* GetIcon(); - - UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|UI|Abilities") - void Setbility(const FGameplayTag& InAbility); - - UFUNCTION() - void OnFinishedLoad(FPrimaryAssetId PrimaryAssetId); }; diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp b/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp index a67fcaa..e2cd6e7 100644 --- a/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp +++ b/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp @@ -1,7 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARUMGWidgetBase.h" -#include "ARUIAbilityManagerComponent.h" #include "ARPlayerController.h" @@ -10,7 +9,6 @@ void UARUMGWidgetBase::NativePreConstruct() { if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) { - OwningComponent = MyPC->UIAbilityManagerComponent; UIComponent = MyPC->UIComponent; } Super::NativePreConstruct(); @@ -19,7 +17,6 @@ void UARUMGWidgetBase::NativeConstruct() { if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) { - OwningComponent = MyPC->UIAbilityManagerComponent; UIComponent = MyPC->UIComponent; } Super::NativeConstruct(); diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.h b/Source/ActionRPGGame/UI/ARUMGWidgetBase.h index 0ed49ef..1b785f6 100644 --- a/Source/ActionRPGGame/UI/ARUMGWidgetBase.h +++ b/Source/ActionRPGGame/UI/ARUMGWidgetBase.h @@ -14,8 +14,6 @@ class ACTIONRPGGAME_API UARUMGWidgetBase : public UUserWidget { GENERATED_BODY() public: - UPROPERTY(BlueprintReadOnly) - class UARUIAbilityManagerComponent* OwningComponent; UPROPERTY(BlueprintReadOnly) class UARUIComponent* UIComponent; public: diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp index 112a552..724863a 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp @@ -3,6 +3,5 @@ #include "ARAbilityInfoWidget.h" #include "AFAbilityInterface.h" #include "AFAbilityComponent.h" -#include "ARUIAbilityManagerComponent.h" #include "Abilities/GAAbilityBase.h" #include "ARPlayerController.h" diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp index 680da53..4426f48 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp @@ -6,7 +6,6 @@ #include "Blueprint/WidgetBlueprintLibrary.h" #include "ARGlobals.h" #include "AFAbilityComponent.h" -#include "ARUIAbilityManagerComponent.h" #include "Abilities/GAAbilityBase.h" @@ -23,7 +22,7 @@ void UARAbilitySlotConfigWidget::NativeOnDragDetected(const FGeometry& InGeometr UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); if (DragDropOp) { - APlayerController* MyPC = Cast(OwningComponent->GetOwner()); + /*APlayerController* MyPC = Cast(OwningComponent->GetOwner()); UARAbilityWidget* DragIcon = CreateWidget(MyPC, OwningComponent->DragVisualClass); DragIcon->AbilityIndex = AbilityIndex; DragIcon->AbilitySetIndex = AbilitySetIndex; @@ -32,15 +31,15 @@ void UARAbilitySlotConfigWidget::NativeOnDragDetected(const FGeometry& InGeometr DragDropOp->Payload = this; DragDropOp->DefaultDragVisual = DragIcon; - OutOperation = DragDropOp; + OutOperation = DragDropOp;*/ } } bool UARAbilitySlotConfigWidget::NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) { - UARAbilityWidget* Payload = Cast(InOperation->Payload); - Setbility(Payload->AbilityTag); + //UARAbilityWidget* Payload = Cast(InOperation->Payload); + //Setbility(Payload->AbilityTag); - OwningComponent->NativeEquipAbility(Payload->AbilityTag, AbilitySetIndex, AbilityIndex); + //OwningComponent->NativeEquipAbility(Payload->AbilityTag, AbilitySetIndex, AbilityIndex); return false; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp deleted file mode 100644 index 138062f..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.cpp +++ /dev/null @@ -1,247 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARUIAbilityManagerComponent.h" -#include "ARAbilityInfoWidget.h" -#include "ARWeaponInfoWidget.h" -#include "ARPlayerController.h" -#include "AFAbilityComponent.h" -#include "AssetRegistryModule.h" -#include "Engine/AssetManager.h" -#include "ARAbilityBase.h" -#include "ARAbilityUIData.h" -// Sets default values for this component's properties -UARUIAbilityManagerComponent::UARUIAbilityManagerComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = false; - - // ... -} - - -// Called when the game starts -void UARUIAbilityManagerComponent::BeginPlay() -{ - Super::BeginPlay(); - //initiazile Model (hhueheu). - AbilitySet.SetNum(2); - AbilitySet[0].SetNum(6); - AbilitySet[1].SetNum(6); - - AbilityTagsSet.SetNum(2); - AbilityTagsSet[0].SetNum(6); - AbilityTagsSet[1].SetNum(6); - - //InputBindingsSet.SetNum(2); - //InputBindingsSet[0].SetNum(6); - //InputBindingsSet[1].SetNum(6); - - ActiveSet = 0; - - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - if (AbilitySetConfigClass) - { - AbilitySetConfigWidget = CreateWidget(Cast(GetOwner()), AbilitySetConfigClass); - //AbilitySetConfigWidget->InitializeWidget(this); - AbilitySetConfigWidget->AddToViewport(); - } - if (AbilityWidgetClass) - { - AbilityWidget = CreateWidget(Cast(GetOwner()), AbilityWidgetClass); - //AbilityWidget->InitializeWidget(this); - } - if (WeaponWidgetClass) - { - WeaponWidget = CreateWidget(Cast(GetOwner()), WeaponWidgetClass); - //WeaponWidget->InitializeWidget(this); - } - - if (WeaponCrosshairWidgetClass) - { - WeaponCrosshairWidget = CreateWidget(Cast(GetOwner()), WeaponCrosshairWidgetClass); - WeaponCrosshairWidget->AddToViewport(); - } - } - - -} - -// Called every frame -void UARUIAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} - -UARAbilityBase* UARUIAbilityManagerComponent::GetAbility(int32 SetIndex, int32 AbilityIndex) -{ - if(AbilitySet[SetIndex][AbilityIndex].IsValid()) - return AbilitySet[SetIndex][AbilityIndex].Get(); - return nullptr; -} -void UARUIAbilityManagerComponent::SetAbility(int32 SetIndex, int32 AbilityIndex, UARAbilityBase* InAbility) -{ - AbilitySet[SetIndex][AbilityIndex] = InAbility; -} -FGameplayTag UARUIAbilityManagerComponent::GetAbilityTag(int32 SetIndex, int32 AbilityIndex) -{ - return AbilityTagsSet[SetIndex][AbilityIndex]; -} -void UARUIAbilityManagerComponent::SetAbilityTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag) -{ - AbilityTagsSet[SetIndex][AbilityIndex] = InAbilityTag; -} - -FGameplayTag UARUIAbilityManagerComponent::GetInputTag(int32 SetIndex, int32 AbilityIndex) -{ - return InputBindingsSet[SetIndex][AbilityIndex]; -} -void UARUIAbilityManagerComponent::SetInputTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag) -{ - InputBindingsSet[SetIndex][AbilityIndex] = InAbilityTag; -} - -void UARUIAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 InAbilitySet - , int32 AbilityIndex) -{ - //fake implementation untill I add AssetManager support. - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - FGameplayTag IAbilityInput = GetInputTag(InAbilitySet, AbilityIndex); - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARUIAbilityManagerComponent::OnAbilityReady, - InAbilityTag, IAbilityInput, InAbilitySet, AbilityIndex); - AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, ReadyDelegate); - - //AbilityComp->NativeAddAbilityFromTag(InAbilityTag, nullptr); -} -void UARUIAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, - int32 InAbilitySet, int32 InAbilityIndex) -{ - NativeOnAbilityReady(InAbilityTag, InAbilityInput, InAbilitySet, InAbilityIndex); -} -void UARUIAbilityManagerComponent::NativeOnAbilityReady(const FGameplayTag& InAbilityTag, const FGameplayTag InAbilityInput, - int32 InAbilitySet, int32 InAbilityIndex) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - - UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARUIAbilityManagerComponent::OnAbilityInputReady, - InAbilityTag, InAbilityInput, InAbilitySet, InAbilityIndex); - - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - } - else - { - SetAbility(InAbilitySet, InAbilityIndex, Ability); - SetAbilityTag(InAbilitySet, InAbilityIndex, InAbilityTag); - SetInputTag(InAbilitySet, InAbilityIndex, InAbilityInput); - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); - } -} -void UARUIAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, - int32 InAbilitySet, int32 InAbilityIndex) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - SetAbility(InAbilitySet, InAbilityIndex, Ability); - SetAbilityTag(InAbilitySet, InAbilityIndex, InAbilityTag); - SetInputTag(InAbilitySet, InAbilityIndex, InAbilityInput); -} -void UARUIAbilityManagerComponent::SwitchSet() -{ - //in reality it should be vlidated on server as well - //although this system is independent from ability component. - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - - if (ActiveSet == 0) - { - const TArray& AbilityTags = AbilityTagsSet[0]; - const FARAbilityInputBinding& InputTags = InputBindingsSet[0]; - const FARAbilityInputBinding InputTags2 = InputBindingsSet[1]; - for (int32 Idx = 0; Idx < 6; Idx++) - { - AbilityComp->SetBlockedInput(InputTags[Idx], true); - AbilityComp->SetBlockedInput(InputTags2[Idx], false); - } - ActiveSet = 1; - OnAbilitySetChanged.Broadcast(1); - } - else if (ActiveSet == 1) - { - const TArray& AbilityTags = AbilityTagsSet[1]; - const FARAbilityInputBinding& InputTags = InputBindingsSet[1]; - const FARAbilityInputBinding& InputTags2 = InputBindingsSet[0]; - for (int32 Idx = 0; Idx < 6; Idx++) - { - AbilityComp->SetBlockedInput(InputTags[Idx], true); - AbilityComp->SetBlockedInput(InputTags2[Idx], false); - } - ActiveSet = 0; - OnAbilitySetChanged.Broadcast(0); - } -} - -void UARUIAbilityManagerComponent::FinishedLoadinFiles() -{ - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - TArray AssetData; - FARFilter Filter; - Filter.ClassNames.Add(TEXT("UGAAbilityBase"));// .Classes.Add(UStaticMesh::StaticClass()); - Filter.TagsAndValues.Add("Ability.Corruption"); - Filter.bRecursiveClasses = true; - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - - FARFilter Filter2; - Filter2.bRecursiveClasses = true; - Filter2.ClassNames.Add(TEXT("UGAAbilityBase"));// .Classes.Add(UStaticMesh::StaticClass()); - - TArray AssetData2; - AssetRegistryModule.Get().GetAssets(Filter2, AssetData2); - -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h b/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h deleted file mode 100644 index 96fe27c..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARUIAbilityManagerComponent.h +++ /dev/null @@ -1,113 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "GameplayTags.h" -#include "ARAbilityBase.h" -#include "ARAvailableAbilities.h" -#include "ARUIAbilityManagerComponent.generated.h" - - -USTRUCT(BlueprintType) -struct FARAbilityInputBinding -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray InputBinding; - - inline FGameplayTag& operator[](int32 InIndex) - { - return InputBinding[InIndex]; - } - - inline const FGameplayTag& operator[](int32 InIndex) const - { - return InputBinding[InIndex]; - } -}; -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAROnAbilitySetChanged, int32, AbilitySet); -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARUIAbilityManagerComponent : public UActorComponent -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Config") - TSubclassOf Abilities; - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf AbilitySetConfigClass; - UPROPERTY(BlueprintReadOnly) - UUserWidget* AbilitySetConfigWidget; - - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf AbilityWidgetClass; - UPROPERTY(BlueprintReadOnly) - UARAbilityInfoWidget* AbilityWidget; - - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf WeaponWidgetClass; - UPROPERTY(BlueprintReadOnly) - UARWeaponInfoWidget* WeaponWidget; - - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf WeaponCrosshairWidgetClass; - UPROPERTY(BlueprintReadOnly) - UUserWidget* WeaponCrosshairWidget; - - UPROPERTY(EditAnywhere, Category = "Input Config") - TArray AbilityInputs; - - int32 ActiveSet; - UPROPERTY(EditAnywhere, Category = "Input Config") - TArray InputBindingsSet; - - TArray> AbilityTagsSet; - TArray>> AbilitySet; -public: - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf DragVisualClass; - - UPROPERTY(BlueprintAssignable) - FAROnAbilitySetChanged OnAbilitySetChanged; -public: - // Sets default values for this component's properties - UARUIAbilityManagerComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - UARAbilityBase* GetAbility(int32 SetIndex, int32 AbilityIndex); - void SetAbility(int32 SetIndex, int32 AbilityIndex, UARAbilityBase* InAbility); - - FGameplayTag GetAbilityTag(int32 SetIndex, int32 AbilityIndex); - void SetAbilityTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag); - - FGameplayTag GetInputTag(int32 SetIndex, int32 AbilityIndex); - void SetInputTag(int32 SetIndex, int32 AbilityIndex, FGameplayTag InAbilityTag); - - void NativeEquipAbility(const FGameplayTag& InAbilityTag, int32 InAbilitySet - , int32 AbilityIndex); - UFUNCTION() - void OnAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, - int32 InAbilitySet, int32 InAbilityIndex); - - void NativeOnAbilityReady(const FGameplayTag& InAbilityTag, const FGameplayTag InAbilityInput, - int32 InAbilitySet, int32 InAbilityIndex); - - //only used in Client-Server mode. Abilities are additionaly binded on server - //so we need to wait for server response to make sure that ability is bound on server. - UFUNCTION() - void OnAbilityInputReady(FGameplayTag InAbilityTag, FGameplayTag InAbilityInput, - int32 InAbilitySet, int32 InAbilityIndex); - - void SwitchSet(); - UFUNCTION() - void FinishedLoadinFiles(); -}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp new file mode 100644 index 0000000..392305e --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp @@ -0,0 +1,54 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponBase.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" +#include "AMAbilityManagerComponent.h" +#include "ARWeaponManagerComponent.h" +#include "../ARCharacter.h" +// Sets default values +AARWeaponBase::AARWeaponBase() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AARWeaponBase::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AARWeaponBase::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} +void AARWeaponBase::Equip(EAMGroup Group, EAMSlot Slot + , class APawn* InPOwner + , class UAMAbilityManagerComponent* WeaponManager) +{ + UARWeaponManagerComponent* WManager = Cast(WeaponManager); + if (!WManager) + return; + + POwner = InPOwner; + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &AARWeaponBase::NativeOnWeaponEquiped); + WManager->AddOnAbilityReadyEvent(WeaponAbility, Delegate); + WManager->NativeEquipAbility(WeaponAbility, Group, Slot, this); +} +void AARWeaponBase::NativeOnWeaponEquiped() +{ + if (!POwner) + return; + + AARCharacter* Character = Cast(POwner); + if (!Character) + return; + + AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, SocketName); + //Ability is ready, Attach to pawn. +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Weapons/ARWeaponBase.h new file mode 100644 index 0000000..56b9603 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.h @@ -0,0 +1,41 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "GameplayTags.h" +#include "AMTypes.h" +#include "ARWeaponBase.generated.h" + +UCLASS() +class ACTIONRPGGAME_API AARWeaponBase : public AActor +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere) + FGameplayTag WeaponAbility; + UPROPERTY(EditAnywhere) + FName SocketName; + UPROPERTY() + APawn* POwner; + +public: + // Sets default values for this actor's properties + AARWeaponBase(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + virtual void Equip(EAMGroup Group, EAMSlot Slot + , class APawn* InPOwner + , class UAMAbilityManagerComponent* WeaponManager); + + UFUNCTION() + virtual void NativeOnWeaponEquiped(); + +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index bfb9dde..bcc6a74 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -4,7 +4,9 @@ #include "AFAbilityInterface.h" #include "AFAbilityComponent.h" #include "ARWeaponAbilityBase.h" -#include "../Weapons/ARWeaponManagerComponent.h" +#include "ARWeaponBase.h" +#include "Engine/World.h" + // Sets default values for this component's properties UARWeaponManagerComponent::UARWeaponManagerComponent() { @@ -47,13 +49,6 @@ void UARWeaponManagerComponent::BeginPlay() UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); if (!AbilityComp) return; - - //for (const FGameplayTag& Tag : AbilityInputs) - { - //AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[0]); - //AbilityComp->BP_BindAbilityToAction(InputSetup.GetInputs(EAMGroup::Group001, EAMSlot::Slot001)[1]); - } - // ... } @@ -69,7 +64,30 @@ UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() { return GetAbility(ActiveGroup, EAMSlot::Slot001); } +void UARWeaponManagerComponent::BP_EquipWeapon(EAMGroup Group, EAMSlot Slot) +{ + EquipWeapon(Group, Slot); +} +void UARWeaponManagerComponent::EquipWeapon(EAMGroup Group, EAMSlot Slot) +{ + if (WeaponClasses.Num() < 0) + return; + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + APawn* POwner = MyPC->GetPawn(); + IAFAbilityInterface* ABInt = Cast(POwner); + if (!ABInt) + return; + + UWorld* World = GetWorld(); + FActorSpawnParameters SpawnParams; + AARWeaponBase* Weapon = World->SpawnActor(WeaponClasses[0], SpawnParams); + Weapon->Equip(Group, Slot, POwner, this); + + Weapons.Add(Weapon); +} void UARWeaponManagerComponent::NextWeapon() { NextGroup(); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 767db89..da42916 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -17,21 +17,17 @@ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComponent { GENERATED_BODY() -//public: -// UPROPERTY(EditAnywhere, Category = "Input") -// FGameplayTag ShootInput; -// UPROPERTY(EditAnywhere, Category = "Input") -// FGameplayTag ReloadInput; -// -// TArray> AllWeapons; -// -// TMap> AllWeapons2; -// //Maps weapon slot to delegate to broadcast that weapon changed in given slot. -// TMap OnWeaponChanged; -// TWeakObjectPtr CurrentWeapon; -// -// UPROPERTY() -// EARWeaponSlot ActiveWeaponIndex; +protected: + UPROPERTY(EditAnywhere, Category = "Weapons") + TArray> WeaponClasses; + + //currently equipped weapons + UPROPERTY() + TArray Weapons; + + //currently active weapons. + UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") + class AARWeaponBase* CurrentWeapon; public: // Sets default values for this component's properties UARWeaponManagerComponent(); @@ -45,30 +41,14 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; UGAAbilityBase* GetCurrentWeapon(); - //void AddOnWeaponChangedEvent(const FGameplayTag& InTag, FAROnWeaponReady& InDelegate); - //void SendOnWeaponChangedEvent(const FGameplayTag& InTag, UARWeaponAbilityBase* InAbility); + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Equip Weapon"), Category = "Weapon Manager") + void BP_EquipWeapon(EAMGroup Group, EAMSlot Slot); + + virtual void EquipWeapon(EAMGroup Group, EAMSlot Slot); + UFUNCTION(BlueprintCallable) void NextWeapon(); UFUNCTION(BlueprintCallable) void PreviousWeapon(); - - //UFUNCTION(Server, Reliable, WithValidation) - // void ServerNextWeapon(int32 WeaponIndex); - //void ServerNextWeapon_Implementation(int32 WeaponIndex); - //bool ServerNextWeapon_Validate(int32 WeaponIndex); - //UFUNCTION(Client, Reliable) - // void ClientNextWeapon(int32 WeaponIndex); - //void ClientNextWeapon_Implementation(int32 WeaponIndex); - - //UFUNCTION(Server, Reliable, WithValidation) - // void ServerPreviousWeapon(int32 WeaponIndex); - //void ServerPreviousWeapon_Implementation(int32 WeaponIndex); - //bool ServerPreviousWeapon_Validate(int32 WeaponIndex); - // - //UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Weapon"), Category = "ActionRPGGame|UI|Weapon") - // void BP_EquipWeapon(const FGameplayTag& InAbilityTag, EARWeaponSlot SlotIndex); - - //void NativeEquipWeapon(const FGameplayTag& InAbilityTag, int32 SlotIndex); - //UFUNCTION() - // void OnWeaponReady(FGameplayTag InAbilityTag, int32 SlotIndex); }; From f7eaa32e836fe765682ebbbd5ee47f06f3648d48 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 3 Feb 2018 10:57:21 +0100 Subject: [PATCH 046/187] fixed window dragging --- .../Source/DraggableWindow/SDraggableWindowWidget.cpp | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index 54e4175..fe4e4f6 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -23,7 +23,7 @@ FDWWWindowHandle FDWWWindowHandle::Make(TSharedPtr FDWWWindowHandle Handle(NewHandle); Handle.Window = InWindow; InWindow->SetHandle(Handle); - return NewHandle; + return Handle; } void SDraggableDesktopWidget::Clean() { @@ -430,9 +430,9 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl const float ApplicationScale = FSlateApplication::Get().GetApplicationScale(); FVector2D AbsSize = AllottedGeometry.LocalToAbsolute(FVector2D(CurrentWidth, CurrentHeight)); + FVector2D GeomAbs = AllottedGeometry.GetAbsolutePosition(); FVector2D localSize = WindowSize + WindowPosition; CurrentCursorPosition = CurrentPosition; - if (CurrentPosition.X <= 0) { CurrentCursorPosition.X = 0; @@ -443,11 +443,13 @@ void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const doubl } if ((AbsPos.X + ((AbsSize.X - AbsDragPosition.X) * ApplicationScale)) >= localSize.X) { - CurrentCursorPosition.X = localSize.X - CurrentWidth; + FVector2D localSize2 = AllottedGeometry.AbsoluteToLocal(WindowSize + WindowPosition); + CurrentCursorPosition.X = localSize2.X - CurrentWidth; } if ((AbsPos.Y + ((AbsSize.Y - AbsDragPosition.Y) * ApplicationScale)) >= localSize.Y) { - CurrentCursorPosition.Y = localSize.Y - CurrentHeight; + FVector2D localSize2 = AllottedGeometry.AbsoluteToLocal(WindowSize + WindowPosition); + CurrentCursorPosition.Y = localSize2.Y - CurrentHeight; } break; } From 0fa9fff6caafc2149cb19a22d5e0c5a63b82ace0 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 4 Feb 2018 01:10:42 +0100 Subject: [PATCH 047/187] prototyping weapon Equiping/Weapon Ability, added prototype ability manager widget --- Config/DefaultGameplayTags.ini | 1 + Config/DefaultInput.ini | 47 +--------- .../AbilityFramework/AFAbilityComponent.cpp | 32 ++++++- .../AbilityFramework/Effects/GAEffectCue.cpp | 5 +- .../AMAbilityManagerComponent.cpp | 36 ++++---- .../AMAbilityManagerComponent.h | 32 ++++--- Source/ActionRPGGame/ARPlayerController.cpp | 11 ++- Source/ActionRPGGame/ARPlayerController.h | 2 +- .../Abilities/ARAbilityManagerComponent.cpp | 33 ++++++- .../Abilities/ARAbilityManagerComponent.h | 22 ++++- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 88 ++++--------------- Source/ActionRPGGame/UI/ARAbilityWidget.h | 32 +------ Source/ActionRPGGame/UI/ARUIComponent.cpp | 11 ++- Source/ActionRPGGame/UI/ARUIComponent.h | 7 ++ .../UI/Abilities/ARAbilityDragVisual.cpp | 7 ++ .../UI/Abilities/ARAbilityDragVisual.h | 27 ++++++ .../ARAbilityManagerSlotDragWidget.cpp | 31 +++++++ ...get.h => ARAbilityManagerSlotDragWidget.h} | 17 ++-- .../ARAbilityManagerSlotDropWidget.cpp | 15 ++++ .../ARAbilityManagerSlotDropWidget.h | 25 ++++++ .../UI/Abilities/ARAbilityManagerWidget.cpp | 7 ++ .../UI/Abilities/ARAbilityManagerWidget.h | 20 +++++ .../Abilities/ARAbilitySlotConfigWidget.cpp | 45 ---------- .../UI/Abilities/ARAbilitySlotWidget.cpp | 81 +++++++++++++++++ .../UI/Abilities/ARAbilitySlotWidget.h | 46 ++++++++++ .../UI/Weapons/ARWeaponBaseWidget.cpp | 7 ++ .../UI/Weapons/ARWeaponBaseWidget.h | 20 +++++ Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 23 ++++- Source/ActionRPGGame/Weapons/ARWeaponBase.h | 9 +- .../Weapons/ARWeaponManagerComponent.cpp | 83 ++++++++++++----- .../Weapons/ARWeaponManagerComponent.h | 9 +- 31 files changed, 561 insertions(+), 270 deletions(-) create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp rename Source/ActionRPGGame/UI/Abilities/{ARAbilitySlotConfigWidget.h => ARAbilityManagerSlotDragWidget.h} (63%) create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 4fee96c..16ddb24 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -17,6 +17,7 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Rifle.Damage",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Reload",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Shoot",DevComment="") ++GameplayTagList=(Tag="Ability.Shotgun",DevComment="") +GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") +GameplayTagList=(Tag="AFD.Ability.Base",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index b574e20..cc27d23 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -6,27 +6,6 @@ -AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.25,Exponent=1.f,Sensitivity=1.f)) -AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) -AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.f,Exponent=1.f,Sensitivity=0.07f)) --AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Left_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Grip1Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MotionController_Right_Grip2Axis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_Special_Left_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_Special_Left_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_LeftX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_LeftY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_RightX",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_RightY",AxisProperties=(DeadZone=0.250000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MouseX",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MouseY",AxisProperties=(DeadZone=0.000000,Sensitivity=0.070000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="MouseWheelAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_LeftTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) --AxisConfig=(AxisKeyName="Gamepad_RightTriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_X",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Left_Thumbstick_Y",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) +AxisConfig=(AxisKeyName="MotionController_Left_TriggerAxis",AxisProperties=(DeadZone=0.000000,Sensitivity=1.000000,Exponent=1.000000,bInvert=False)) @@ -59,38 +38,16 @@ bCaptureMouseOnLaunch=True DefaultViewportMouseCaptureMode=CapturePermanently_IncludingInitialMouseDown bDefaultViewportMouseLock=False DefaultViewportMouseLockMode=LockOnCapture --ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="SwitchAbilitySet",Key=B,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="ShowHideAbilities",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --ActionMappings=(ActionName="PreviousWeapon",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="SwitchAbilitySet",Key=B,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="ShowHideAbilities",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="InputAbilityManager",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.UI.WeaponPrevious",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) --AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) --AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) --AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) --AxisMappings=(AxisName="MoveForward",Key=Down,Scale=-1.000000) --AxisMappings=(AxisName="MoveForward",Key=Gamepad_LeftY,Scale=1.000000) --AxisMappings=(AxisName="MoveRight",Key=A,Scale=-1.000000) --AxisMappings=(AxisName="MoveRight",Key=D,Scale=1.000000) --AxisMappings=(AxisName="MoveRight",Key=Gamepad_LeftX,Scale=1.000000) --AxisMappings=(AxisName="TurnRate",Key=Gamepad_RightX,Scale=1.000000) --AxisMappings=(AxisName="TurnRate",Key=Left,Scale=-1.000000) --AxisMappings=(AxisName="TurnRate",Key=Right,Scale=1.000000) --AxisMappings=(AxisName="Turn",Key=MouseX,Scale=1.000000) --AxisMappings=(AxisName="LookUpRate",Key=Gamepad_RightY,Scale=1.000000) --AxisMappings=(AxisName="LookUp",Key=MouseY,Scale=-1.000000) ++ActionMappings=(ActionName="InputWeaponManager",Key=L,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) +AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) +AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 9832052..265834b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -689,10 +689,21 @@ void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbility ActionToAbility.Remove(Action); } - AbilitiesInputs.Remove(InAbilityTag); + //AbilitiesInputs.Remove(InAbilityTag); } void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { + if (ActionToAbility.Contains(InInputTag)) + { + FGameplayTag AbilityTag = ActionToAbility.FindRef(InInputTag); + UE_LOG(AbilityFramework, Log, TEXT("FGASAbilityContainer: Input %s is already abount to Ability %s"), + *InInputTag.ToString(), + *AbilityTag.ToString() + ); + + //return; + } + FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InInputTag); AbilityTag = InAbilityTag; @@ -834,6 +845,14 @@ void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, F void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag , const FAFOnAbilityReady& InputDelegate) { + for (const FGameplayTag& Tag : InInputTag) + { + if (AbilityContainer.IsAbilityBoundToAction(Tag).IsValid()) + { + RemoveAbilityFromAction(InAbilityTag, Tag); + } + } + for (const FGameplayTag& Tag : InInputTag) { SetAbilityToAction(InAbilityTag, Tag, InputDelegate); @@ -845,6 +864,8 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c //check if there is input under tag //clear it //then bind. + + AbilityContainer.SetAbilityToAction(InAbilityTag, InInputTag); ENetRole role = GetOwnerRole(); @@ -944,13 +965,20 @@ void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, AActor* InAvatar, const TArray& InInputTag) { + FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); if (GetOwnerRole() < ENetRole::ROLE_Authority) { ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); + if (AlreadyBound.IsValid()) + { + for (const FGameplayTag& Input : InInputTag) + { + AbilityContainer.RemoveAbilityFromAction(InAbilityTag, Input); + } + } } else { - FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); if (AlreadyBound.IsValid()) { NativeRemoveAbility(AlreadyBound); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp index dc65290..e742625 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp @@ -147,7 +147,10 @@ void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObj Timer.SetTimer(PeriodTimer, del, CueParams.Period, true); } BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); - SequencePlayer->Play(); + if (!SequencePlayer) + { + SequencePlayer->Play(); + } } void AGAEffectCue::NativeOnExecuted() diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index aaeeee9..534d8a6 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -25,12 +25,14 @@ void UAMAbilityManagerComponent::BeginPlay() } void UAMAbilityManagerComponent::InitializeComponent() { - AbilitySet.SetNum(MaxGroups); - AbilityTagsSet.SetNum(MaxGroups); - for(int32 Idx = 0; Idx < MaxGroups; Idx++) + uint8 GroupNum = Groups.Num(); + + AbilitySet.SetNum(GroupNum); + AbilityTagsSet.SetNum(GroupNum); + for(int32 Idx = 0; Idx < GroupNum; Idx++) { - AbilitySet[Idx].SetNum(1); - AbilityTagsSet[Idx].SetNum(1); + AbilitySet[Idx].SetNum(Groups[Idx].SlotNum); + AbilityTagsSet[Idx].SetNum(Groups[Idx].SlotNum); } } @@ -53,11 +55,11 @@ void UAMAbilityManagerComponent::BindInputs(UInputComponent* InputComponent, cla } UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) { - return AbilitySet.Num() >= MaxGroups ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; + return AbilitySet.Num() >= Groups.Num() ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; } void UAMAbilityManagerComponent::SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility) { - if (AbilitySet.Num() < MaxGroups) + if (AbilitySet.Num() < Groups.Num()) return; AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbility; @@ -71,9 +73,9 @@ void UAMAbilityManagerComponent::SetInputTag(EAMGroup InGroup, EAMSlot InSlot, T { } -void UAMAbilityManagerComponent::BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) +void UAMAbilityManagerComponent::BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) { - NativeEquipAbility(InAbilityTag, InGroup, InSlot); + NativeEquipAbility(InAbilityTag, InGroup, InSlot, nullptr, bBindInput); } FGameplayTag UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) { @@ -83,7 +85,7 @@ void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, { AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; } -void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar) +void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar, bool bBindInput) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -96,7 +98,11 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); if (!AbilityComp) return; - TArray IAbilityInput = GetInputTag(InGroup, InSlot); + TArray IAbilityInput; + + if(bBindInput) + IAbilityInput = GetInputTag(InGroup, InSlot); + FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReady, InAbilityTag, IAbilityInput, InGroup, InSlot); @@ -164,7 +170,7 @@ void UAMAbilityManagerComponent::NextGroup() { int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex++; - if(CurrentIndex > MaxGroups) + if(CurrentIndex > Groups.Num()) { ActiveGroup = EAMGroup::Group001; } @@ -173,7 +179,7 @@ void UAMAbilityManagerComponent::NextGroup() ActiveGroup = AMIntToEnum(CurrentIndex); } - if (ActiveGroup < AMIntToEnum(MaxGroups)) + if (ActiveGroup < AMIntToEnum(Groups.Num())) { } else @@ -211,7 +217,7 @@ void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponInde int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex++; ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex > MaxGroups) + if (CurrentIndex > Groups.Num()) { ActiveGroup = EAMGroup::Group001; } @@ -219,7 +225,7 @@ void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponInde { ActiveGroup = AMIntToEnum(CurrentIndex); } - if (ActiveGroup < AMIntToEnum(MaxGroups)) + if (ActiveGroup < AMIntToEnum(Groups.Num())) { } else diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index 725dc4d..7280e0e 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -20,14 +20,6 @@ */ //all the inputs assigned to SINGLE ability; -USTRUCT() -struct FAMAbilityInputs -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Inputs; -}; USTRUCT() struct FAMAbilityInputSlot @@ -35,11 +27,11 @@ struct FAMAbilityInputSlot GENERATED_BODY() public: UPROPERTY(EditAnywhere) - FAMAbilityInputs Inputs; + TArray Inputs; TArray operator()() { - return Inputs.Inputs; + return Inputs; } }; @@ -69,6 +61,14 @@ struct FAMAbilityInputContainer } }; +USTRUCT() +struct FAMAbilitySlotConfig +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + uint8 SlotNum; +}; UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent @@ -76,7 +76,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent GENERATED_BODY() protected: UPROPERTY(EditAnywhere) - uint8 MaxGroups; + TArray Groups; //Map input bindings to particular slot and group. UPROPERTY(EditAnywhere) @@ -86,8 +86,6 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent TArray InputsToBind; EAMGroup ActiveGroup; - //UPROPERTY(EditAnywhere, Category = "Input Config") - // TArray InputBindingsSet; TArray> AbilityTagsSet; TArray>> AbilitySet; @@ -116,9 +114,9 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Ability"), Category = "Ability Manager") - void BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); + void BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); - void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr); + void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); UFUNCTION() void OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); @@ -128,9 +126,9 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent EAMGroup InGroup, EAMSlot InSlot); UFUNCTION(BlueprintCallable) - void NextGroup(); + virtual void NextGroup(); UFUNCTION(BlueprintCallable) - void PreviousGroup(); + virtual void PreviousGroup(); UFUNCTION(Server, Reliable, WithValidation) void ServerNextGroup(int32 WeaponIndex); diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 7a6ce61..f41a11a 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -53,6 +53,8 @@ void AARPlayerController::SetPawn(APawn* InPawn) TArray PrevWeap; PrevWeap.Add(InputPreviousWeapon); AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); + + InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); } //UIAbilityManagerComponent->BindInputs(); } @@ -67,7 +69,10 @@ void AARPlayerController::SetupInputComponent() void AARPlayerController::InputSwitchAbilitySet() { } - +void AARPlayerController::InputShowHideAbilityManager() +{ + AbilityManager->ShowHideAbilityManager(); +} void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) { IAFAbilityInterface* ABInt = Cast(GetPawn()); @@ -85,10 +90,10 @@ void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGamepl void AARPlayerController::NextWeapon() { - WeaponManager->NextWeapon(); + //WeaponManager->NextWeapon(); } void AARPlayerController::PreviousWeapon() { - WeaponManager->PreviousWeapon(); + //WeaponManager->PreviousWeapon(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index da6fd69..ad007c0 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -39,7 +39,7 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController void SetupInputComponent(); void InputSwitchAbilitySet(); - + void InputShowHideAbilityManager(); UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapons") void NextWeapon(); UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapons") diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index 1632f8d..c2ac24d 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -1,7 +1,13 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARAbilityManagerComponent.h" +#include "Blueprint/UserWidget.h" +#include "GameFramework/PlayerController.h" +#include "Layout/Visibility.h" +#include "DWBPFunctionLibrary.h" +#include "SDraggableWindowWidget.h" +#include "../UI/Abilities/ARAbilityManagerWidget.h" // Sets default values for this component's properties UARAbilityManagerComponent::UARAbilityManagerComponent() @@ -18,9 +24,16 @@ UARAbilityManagerComponent::UARAbilityManagerComponent() void UARAbilityManagerComponent::BeginPlay() { Super::BeginPlay(); - + APlayerController* OwnerPC = Cast(GetOwner()); // ... - + if (ManagerWidgetClass) + { + ManagerWidget = CreateWidget(OwnerPC, ManagerWidgetClass); + ManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + ManagerWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(ManagerWidget, "Ability Manager"); + ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); + //ManagerWidget->AddToViewport(); + } } @@ -32,3 +45,19 @@ void UARAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickT // ... } +void UARAbilityManagerComponent::ShowHideAbilityManager() +{ + if (!ManagerWidget) + return; + + EVisibility Visibility = ManagerWindowHandle.Window.Pin()->GetVisibility(); + + if (Visibility == EVisibility::Collapsed) + { + ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::SelfHitTestInvisible); + } + else if (Visibility == EVisibility::SelfHitTestInvisible) + { + ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h index 3dd6b4d..52a8ee7 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -3,11 +3,14 @@ #pragma once #include "CoreMinimal.h" - #include "Components/ActorComponent.h" #include "GameplayTags.h" + #include "Abilities/GAAbilityBase.h" #include "AMAbilityManagerComponent.h" +#include "DWTypes.h" + + #include "ARAbilityManagerComponent.generated.h" @@ -15,11 +18,18 @@ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerComponent { GENERATED_BODY() -public: +protected: + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf DragVisualClass; + UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf DragVisualClass; + TSubclassOf ManagerWidgetClass; + + UPROPERTY() + class UARAbilityManagerWidget* ManagerWidget; + FDWWWindowHandle ManagerWindowHandle; public: // Sets default values for this component's properties UARAbilityManagerComponent(); @@ -32,6 +42,10 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + void ShowHideAbilityManager(); + inline TSubclassOf GetDragVisualClass() + { + return DragVisualClass; + } }; diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index 96f3e05..df26e91 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -11,79 +11,29 @@ #include "Input/Reply.h" #include "Input/Events.h" #include "Blueprint/WidgetBlueprintLibrary.h" +#include "../ARPlayerController.h" #include "ARGlobals.h" -float UARAbilityWidget::GetActivationRemainingTime() +void UARAbilityWidget::NativePreConstruct() { - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationRemainingTime() : 0; -} -float UARAbilityWidget::GetActivationRemainingTimeNormalized() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationRemainingTimeNormalized() : 0; -} -float UARAbilityWidget::GetActivationCurrentTime() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationCurrentTime() : 0; + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + UIComponent = MyPC->UIComponent; + AbilityManager = MyPC->AbilityManager; + } + Super::NativePreConstruct(); } -float UARAbilityWidget::GetActivationCurrentTimeNormalized() +void UARAbilityWidget::NativeConstruct() { - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationCurrentTimeNormalized() : 0; -} -float UARAbilityWidget::GetActivationEndTime() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationEndTime() : 0; + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + UIComponent = MyPC->UIComponent; + AbilityManager = MyPC->AbilityManager; + } + Super::NativeConstruct(); } -float UARAbilityWidget::GetCooldownRemainingTime() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownRemainingTime() : 0; -} -float UARAbilityWidget::GetCooldownRemainingTimeNormalized() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownRemainingTimeNormalized() : 0; -} -float UARAbilityWidget::GetCooldownCurrentTime() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownCurrentTime() : 0; -} -float UARAbilityWidget::GetCooldownCurrentTimeNormalized() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownCurrentTimeNormalized() : 0; -} -float UARAbilityWidget::GetCooldownEndTime() -{ - if (!AbilityManager) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownEndTime() : 0; -} + UTexture2D* UARAbilityWidget::GetIcon() { if (Icon) @@ -92,7 +42,7 @@ UTexture2D* UARAbilityWidget::GetIcon() if (!AbilityManager) return nullptr; - return nullptr; - /*UARAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->UIData->Icon : nullptr;*/ + //return nullptr; + UARAbilityBase* Ability = nullptr;// Cast(AbilityManager->GetAbility(Group, AbilitySlot)); + return Ability ? Ability->UIData->Icon : nullptr; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index afca7c5..8750211 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -8,6 +8,7 @@ #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "AMTypes.h" +#include "../Abilities/ARAbilityManagerComponent.h" #include "ARAbilityWidget.generated.h" /** @@ -19,38 +20,13 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase GENERATED_BODY() public: UPROPERTY() - class UAMAbilityManagerComponent* AbilityManager; + class UARAbilityManagerComponent* AbilityManager; - UPROPERTY(EditAnywhere, Category = "Config") - EAMGroup Group; - UPROPERTY(EditAnywhere, Category = "Config") - EAMSlot AbilitySlot; UPROPERTY(EditAnywhere, Category = "Config") UTexture2D* Icon; - UPROPERTY(EditAnywhere, Category = "Config") - FGameplayTag AbilityTag; - - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationRemainingTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationCurrentTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationEndTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownRemainingTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownCurrentTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownEndTime(); + virtual void NativePreConstruct() override; + virtual void NativeConstruct() override; UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") UTexture2D* GetIcon(); diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 8c73f7a..2b7c872 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -1,7 +1,8 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARUIComponent.h" - +#include "ARPlayerController.h" +#include "Blueprint/UserWidget.h" // Sets default values for this component's properties UARUIComponent::UARUIComponent() @@ -19,8 +20,14 @@ void UARUIComponent::BeginPlay() { Super::BeginPlay(); + AARPlayerController* MyPC = Cast(GetOwner()); // ... - + if (CrosshairClass) + { + CrosshairWidget = CreateWidget(MyPC, CrosshairClass); + CrosshairWidget->SetVisibility(ESlateVisibility::HitTestInvisible); + CrosshairWidget->AddToViewport(); + } } diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index dd25671..21af377 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -11,6 +11,13 @@ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARUIComponent : public UActorComponent { GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf CrosshairClass; + + UPROPERTY() + UUserWidget* CrosshairWidget; + public: // Sets default values for this component's properties diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp new file mode 100644 index 0000000..2f7a4c2 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityDragVisual.h" + + + + diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h new file mode 100644 index 0000000..209d342 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "AMTypes.h" +#include "ARAbilityDragVisual.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityDragVisual : public UUserWidget +{ + GENERATED_BODY() +public: + UPROPERTY() + class UARAbilityManagerComponent* AbilityManager; + UPROPERTY(EditAnywhere, Category = "Config") + EAMGroup Group; + UPROPERTY(EditAnywhere, Category = "Config") + EAMSlot AbilitySlot; + + + +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp new file mode 100644 index 0000000..b085552 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityManagerSlotDragWidget.h" +#include "Blueprint/WidgetBlueprintLibrary.h" + +#include "ARAbilityDragVisual.h" +#include "../../Abilities/ARAbilityManagerComponent.h" + +FReply UARAbilityManagerSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) +{ + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + //return FReply::Unhandled(); +} + +void UARAbilityManagerSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) +{ + UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); + if (DragDropOp) + { + APlayerController* MyPC = Cast(AbilityManager->GetOwner()); + UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); + DragIcon->AbilityManager = AbilityManager; + + DragDropOp->Payload = this; + DragDropOp->DefaultDragVisual = DragIcon; + + OutOperation = DragDropOp; + } +} diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.h similarity index 63% rename from Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h rename to Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.h index 9f91bee..242bff5 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.h @@ -4,25 +4,28 @@ #include "CoreMinimal.h" #include "UI/ARAbilityWidget.h" -#include "ARAbilitySlotConfigWidget.generated.h" +#include "AMTypes.h" +#include "ARAbilityManagerSlotDragWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARAbilitySlotConfigWidget : public UARAbilityWidget +class ACTIONRPGGAME_API UARAbilityManagerSlotDragWidget : public UARAbilityWidget { GENERATED_BODY() -public: - +protected: UPROPERTY(EditAnywhere, Category = "Config") - FGameplayTag InputBinding; + FGameplayTag AbilityTag; public: virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) override; virtual void NativeOnDragDetected(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; - virtual bool NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; + + inline const FGameplayTag& GetAbilityTag() const + { + return AbilityTag; + } }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp new file mode 100644 index 0000000..15dcede --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityManagerSlotDropWidget.h" + +#include "ARAbilityManagerSlotDragWidget.h" +#include "../../Abilities/ARAbilityManagerComponent.h" + +bool UARAbilityManagerSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UARAbilityManagerSlotDragWidget* Payload = Cast(InOperation->Payload); + + AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); + return false; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h new file mode 100644 index 0000000..f6361ee --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARAbilityWidget.h" +#include "AMTypes.h" +#include "ARAbilityManagerSlotDropWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityManagerSlotDropWidget : public UARAbilityWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Config") + EAMGroup AbilityGroup; + UPROPERTY(EditAnywhere, Category = "Config") + EAMSlot AbilitySlot; +public: + virtual bool NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp new file mode 100644 index 0000000..576b0bd --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityManagerWidget.h" + + + + diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h new file mode 100644 index 0000000..b2e0ded --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARAbilityManagerWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityManagerWidget : public UUserWidget +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp deleted file mode 100644 index 4426f48..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotConfigWidget.cpp +++ /dev/null @@ -1,45 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilitySlotConfigWidget.h" -#include "Input/Reply.h" -#include "Input/Events.h" -#include "Blueprint/WidgetBlueprintLibrary.h" -#include "ARGlobals.h" -#include "AFAbilityComponent.h" -#include "Abilities/GAAbilityBase.h" - - -FReply UARAbilitySlotConfigWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) -{ - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; - //return FReply::Unhandled(); -} - -void UARAbilitySlotConfigWidget::NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) -{ - UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); - if (DragDropOp) - { - /*APlayerController* MyPC = Cast(OwningComponent->GetOwner()); - UARAbilityWidget* DragIcon = CreateWidget(MyPC, OwningComponent->DragVisualClass); - DragIcon->AbilityIndex = AbilityIndex; - DragIcon->AbilitySetIndex = AbilitySetIndex; - DragIcon->OwningComponent = OwningComponent; - - DragDropOp->Payload = this; - DragDropOp->DefaultDragVisual = DragIcon; - - OutOperation = DragDropOp;*/ - } -} -bool UARAbilitySlotConfigWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - //UARAbilityWidget* Payload = Cast(InOperation->Payload); - //Setbility(Payload->AbilityTag); - - //OwningComponent->NativeEquipAbility(Payload->AbilityTag, AbilitySetIndex, AbilityIndex); - return false; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp new file mode 100644 index 0000000..d738f09 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp @@ -0,0 +1,81 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilitySlotWidget.h" + +#include "AMAbilityManagerComponent.h" +#include "Abilities/GAAbilityBase.h" + +#include "ARAbilityBase.h" +#include "ARAbilityUIData.h" + +float UARAbilitySlotWidget::GetActivationRemainingTime() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetActivationRemainingTime() : 0; +} +float UARAbilitySlotWidget::GetActivationRemainingTimeNormalized() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetActivationRemainingTimeNormalized() : 0; +} +float UARAbilitySlotWidget::GetActivationCurrentTime() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetActivationCurrentTime() : 0; +} +float UARAbilitySlotWidget::GetActivationCurrentTimeNormalized() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetActivationCurrentTimeNormalized() : 0; +} +float UARAbilitySlotWidget::GetActivationEndTime() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetActivationEndTime() : 0; +} + +float UARAbilitySlotWidget::GetCooldownRemainingTime() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetCooldownRemainingTime() : 0; +} +float UARAbilitySlotWidget::GetCooldownRemainingTimeNormalized() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetCooldownRemainingTimeNormalized() : 0; +} +float UARAbilitySlotWidget::GetCooldownCurrentTime() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetCooldownCurrentTime() : 0; +} +float UARAbilitySlotWidget::GetCooldownCurrentTimeNormalized() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetCooldownCurrentTimeNormalized() : 0; +} +float UARAbilitySlotWidget::GetCooldownEndTime() +{ + if (!AbilityManager) + return 0; + UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); + return Ability ? Ability->GetCooldownEndTime() : 0; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h new file mode 100644 index 0000000..33a64a5 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h @@ -0,0 +1,46 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARAbilityWidget.h" +#include "AMTypes.h" +#include "ARAbilitySlotWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilitySlotWidget : public UARAbilityWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Config") + EAMGroup Group; + UPROPERTY(EditAnywhere, Category = "Config") + EAMSlot AbilitySlot; +public: + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationRemainingTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationCurrentTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetActivationEndTime(); + + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownRemainingTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownCurrentTime(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") + float GetCooldownEndTime(); + + +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp new file mode 100644 index 0000000..2296d52 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponBaseWidget.h" + + + + diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h new file mode 100644 index 0000000..f31df22 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARWeaponBaseWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponBaseWidget : public UARUMGWidgetBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp index 392305e..87cd1fb 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp @@ -27,7 +27,7 @@ void AARWeaponBase::Tick(float DeltaTime) Super::Tick(DeltaTime); } -void AARWeaponBase::Equip(EAMGroup Group, EAMSlot Slot +void AARWeaponBase::OnAddToWeaponManager(EAMGroup Group, EAMSlot Slot , class APawn* InPOwner , class UAMAbilityManagerComponent* WeaponManager) { @@ -36,9 +36,24 @@ void AARWeaponBase::Equip(EAMGroup Group, EAMSlot Slot return; POwner = InPOwner; - FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &AARWeaponBase::NativeOnWeaponEquiped); - WManager->AddOnAbilityReadyEvent(WeaponAbility, Delegate); - WManager->NativeEquipAbility(WeaponAbility, Group, Slot, this); + //FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &AARWeaponBase::NativeOnWeaponEquiped); + WManager->AddOnAbilityReadyEvent(WeaponAbility, FSimpleDelegate()); + WManager->NativeEquipAbility(WeaponAbility, Group, Slot, this, false); +} +void AARWeaponBase::Equip() +{ + if (!POwner) + return; + + AARCharacter* Character = Cast(POwner); + if (!Character) + return; + + AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, SocketName); +} +void AARWeaponBase::UnEquip() +{ + } void AARWeaponBase::NativeOnWeaponEquiped() { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Weapons/ARWeaponBase.h index 56b9603..643c7f4 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.h @@ -31,11 +31,18 @@ class ACTIONRPGGAME_API AARWeaponBase : public AActor public: // Called every frame virtual void Tick(float DeltaTime) override; - virtual void Equip(EAMGroup Group, EAMSlot Slot + virtual void OnAddToWeaponManager(EAMGroup Group, EAMSlot Slot , class APawn* InPOwner , class UAMAbilityManagerComponent* WeaponManager); + virtual void Equip(); + virtual void UnEquip(); UFUNCTION() virtual void NativeOnWeaponEquiped(); + + const inline FGameplayTag& GetWeaponAbility() const + { + return WeaponAbility; + } }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index bcc6a74..fed06ee 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -13,22 +13,6 @@ UARWeaponManagerComponent::UARWeaponManagerComponent() // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; - AbilitySet.SetNum(MaxGroups); - if (MaxGroups > 0) - { - AbilitySet[0].SetNum(1); - AbilitySet[1].SetNum(1); - AbilitySet[2].SetNum(1); - AbilitySet[3].SetNum(1); - } - AbilityTagsSet.SetNum(MaxGroups); - if (MaxGroups > 0) - { - AbilityTagsSet[0].SetNum(1); - AbilityTagsSet[1].SetNum(1); - AbilityTagsSet[2].SetNum(1); - AbilityTagsSet[3].SetNum(1); - } // ... } @@ -64,11 +48,11 @@ UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() { return GetAbility(ActiveGroup, EAMSlot::Slot001); } -void UARWeaponManagerComponent::BP_EquipWeapon(EAMGroup Group, EAMSlot Slot) +void UARWeaponManagerComponent::BP_EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx) { - EquipWeapon(Group, Slot); + EquipWeapon(Group, Slot, Idx); } -void UARWeaponManagerComponent::EquipWeapon(EAMGroup Group, EAMSlot Slot) +void UARWeaponManagerComponent::EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx) { if (WeaponClasses.Num() < 0) return; @@ -83,16 +67,71 @@ void UARWeaponManagerComponent::EquipWeapon(EAMGroup Group, EAMSlot Slot) UWorld* World = GetWorld(); FActorSpawnParameters SpawnParams; - AARWeaponBase* Weapon = World->SpawnActor(WeaponClasses[0], SpawnParams); - Weapon->Equip(Group, Slot, POwner, this); - + AARWeaponBase* Weapon = World->SpawnActor(WeaponClasses[Idx], SpawnParams); + Weapon->OnAddToWeaponManager(Group, Slot, POwner, this); + AbilityToWeapon.Add(Weapon->GetWeaponAbility(), Weapon); + if (Group == EAMGroup::Group001) + { + CurrentWeapon = Weapon; + CurrentWeapon->Equip(); + } Weapons.Add(Weapon); } void UARWeaponManagerComponent::NextWeapon() { + FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); NextGroup(); + FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + if (!NextWeaponAbility.IsValid()) + return; + TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponAbility)); + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, + NextWeaponAbility, WeaponInput); + + AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, ReadyDelegate); + } + else + { + AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(NextWeaponAbility); + CurrentWeapon = AbilityToWeapon.FindRef(NextWeaponAbility); + CurrentWeapon->Equip(); + } } void UARWeaponManagerComponent::PreviousWeapon() { PreviousGroup(); +} + + +void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index da42916..d69a459 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -28,6 +28,8 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp //currently active weapons. UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") class AARWeaponBase* CurrentWeapon; + + TMap AbilityToWeapon; public: // Sets default values for this component's properties UARWeaponManagerComponent(); @@ -43,12 +45,15 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UGAAbilityBase* GetCurrentWeapon(); UFUNCTION(BlueprintCallable, meta=(DisplayName="Equip Weapon"), Category = "Weapon Manager") - void BP_EquipWeapon(EAMGroup Group, EAMSlot Slot); + void BP_EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx); - virtual void EquipWeapon(EAMGroup Group, EAMSlot Slot); + virtual void EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx); UFUNCTION(BlueprintCallable) void NextWeapon(); UFUNCTION(BlueprintCallable) void PreviousWeapon(); + + UFUNCTION() + void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); }; From 2cb5ca5471e6b62c32ee2881f0427de57addc91d Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 5 Feb 2018 00:39:46 +0100 Subject: [PATCH 048/187] prototyping weapons, added basic weapon replication, fixed some bugs in abilities --- Config/DefaultInput.ini | 2 +- .../AbilityFramework/AFAbilityComponent.cpp | 18 +- .../AbilityFramework/AFAbilityComponent.h | 2 +- .../Source/AbilityFramework/AFCueManager.cpp | 11 +- .../Abilities/GAAbilityBase.cpp | 5 + .../Abilities/GAAbilityBase.h | 3 + .../AbilityFramework.Build.cs | 8 +- .../AMAbilityManagerComponent.cpp | 85 +++++-- .../AMAbilityManagerComponent.h | 25 +- Source/ActionRPGGame/ARCharacter.cpp | 26 +- Source/ActionRPGGame/ARCharacter.h | 21 ++ Source/ActionRPGGame/ARItemPickupBase.cpp | 27 +++ Source/ActionRPGGame/ARItemPickupBase.h | 28 +++ Source/ActionRPGGame/ARPlayerController.cpp | 15 +- Source/ActionRPGGame/ARPlayerController.h | 6 +- .../Abilities/ARAbilityManagerComponent.cpp | 21 +- Source/ActionRPGGame/UI/ARUIComponent.cpp | 36 ++- Source/ActionRPGGame/UI/ARUIComponent.h | 6 +- .../UI/Inventory/ARInventoryManagerWidget.cpp | 7 + .../UI/Inventory/ARInventoryManagerWidget.h | 20 ++ .../UI/Weapons/ARWeaponBaseWidget.cpp | 20 ++ .../UI/Weapons/ARWeaponBaseWidget.h | 8 +- .../Weapons/ARWeaponManagerSlotDragWidget.cpp | 31 +++ .../Weapons/ARWeaponManagerSlotDragWidget.h | 29 +++ .../Weapons/ARWeaponManagerSlotDropWidget.cpp | 18 ++ .../Weapons/ARWeaponManagerSlotDropWidget.h | 26 ++ .../UI/Weapons/ARWeaponManagerWidget.cpp | 25 ++ .../UI/Weapons/ARWeaponManagerWidget.h | 23 ++ .../UI/Weapons/ARWeaponSlotWidget.cpp | 26 ++ .../UI/Weapons/ARWeaponSlotWidget.h | 31 +++ .../Weapons/ARWeaponAbilityBase.cpp | 6 - Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 6 +- .../Weapons/ARWeaponManagerComponent.cpp | 223 ++++++++++++++---- .../Weapons/ARWeaponManagerComponent.h | 30 ++- 34 files changed, 742 insertions(+), 132 deletions(-) create mode 100644 Source/ActionRPGGame/ARItemPickupBase.cpp create mode 100644 Source/ActionRPGGame/ARItemPickupBase.h create mode 100644 Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index cc27d23..0638191 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -47,7 +47,7 @@ DefaultViewportMouseLockMode=LockOnCapture +ActionMappings=(ActionName="InputAbilityManager",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.UI.WeaponPrevious",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="InputWeaponManager",Key=L,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="InputInventory",Key=I,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) +AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) +AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 265834b..a50b37f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -312,8 +312,8 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper CueParams.Period = InProperty.Period; CueParams.Duration = InProperty.Duration; - if (mode == ENetMode::NM_Standalone - || role >= ENetRole::ROLE_Authority) + //if (mode == ENetMode::NM_Standalone + // || role >= ENetRole::ROLE_Authority) { MulticastRemoveEffectCue(CueParams); } @@ -351,8 +351,8 @@ void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, RepInfo->OnExpired(); } } - //if (GetOwnerRole() == ENetRole::ROLE_Authority - // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + if (GetOwnerRole() == ENetRole::ROLE_Authority + || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) { InternalRemoveEffect(InProperty, InContext); } @@ -374,8 +374,8 @@ void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProper CueParams.Duration = InProperty.Duration; ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); - //if (mode == ENetMode::NM_Standalone - // || role >= ENetRole::ROLE_Authority) + if (mode == ENetMode::NM_Standalone + || role >= ENetRole::ROLE_Authority) { MulticastRemoveEffectCue(CueParams); } @@ -996,7 +996,7 @@ void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, FPrimaryAssetTypeInfo Info; if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbilityTag, PrimaryAssetId); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbilityTag, PrimaryAssetId, InAvatar); Manager->LoadPrimaryAsset(PrimaryAssetId, TArray(), @@ -1036,7 +1036,7 @@ bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(FGameplayTag InAbil return true; } void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, - FPrimaryAssetId InPrimaryAssetId) + FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar) { if (GetOwnerRole() < ENetRole::ROLE_Authority) { @@ -1048,7 +1048,7 @@ void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, TSubclassOf cls = Cast(loaded); if (cls) { - InstanceAbility(cls, nullptr); + InstanceAbility(cls, InAvatar); } { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 8a55a27..4f650af 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -792,7 +792,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, TMap BlockedInput; //TSharedPtr AbilityLoadedHandle; - void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId); + void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar); void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); void BindInputs(class UInputComponent* InputComponent); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index b6d5700..316df5a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -3,9 +3,9 @@ #include "AbilityFramework.h" #include "Effects/GAEffectCue.h" #include "AFCueManager.h" -//#if WITH_EDITOR -//#include "Editor.H" -//#endif +#if WITH_EDITOR +#include "Editor.h" +#endif UAFCueManager* UAFCueManager::ManagerInstance = nullptr; //UWorld* UAFCueManager::CurrentWorld = nullptr; @@ -26,7 +26,7 @@ UAFCueManager* UAFCueManager::Get() void UAFCueManager::Initialize() { #if WITH_EDITORONLY_DATA -// FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); + FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); #endif //WITH_EDITORONLY_DATA FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); @@ -77,6 +77,9 @@ void UAFCueManager::HandleOnPIEEnd(bool InVal) } } + + InstancedCues.Empty(); + UsedCues.Empty(); } #endif //WITH_EDITOR void UAFCueManager::HandlePreLoadMap(const FString& InMapName) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 8bc3f10..d1a13f6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -891,4 +891,9 @@ float UGAAbilityBase::BP_GetCooldownCurrentTimeNormalized() float UGAAbilityBase::BP_GetCooldownEndTime() { return GetCooldownEndTime(); +} + +AActor* UGAAbilityBase::BP_GetAvatar() +{ + return AvatarActor; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index fad1398..8711b5f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -636,4 +636,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask float BP_GetCooldownCurrentTimeNormalized(); UFUNCTION(BlueprintPure, DisplayName = "GetCooldownEndTime", Category = "AbilityFramework|Abilities|Helpers") float BP_GetCooldownEndTime(); + + UFUNCTION(BlueprintCallable, DisplayName = "Get Avatar", Category = "AbilityFramework|Abilities|Helpers") + AActor* BP_GetAvatar(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index c2f543d..47e74e2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -65,10 +65,10 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) // ... add any modules that your module loads dynamically here ... } ); - //if (Target.Type == TargetRules.TargetType.Editor) - //{ - // PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); - //} + if (Target.Type == TargetRules.TargetType.Editor) + { + PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); + } } } } \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 534d8a6..927f0a2 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -11,6 +11,7 @@ UAMAbilityManagerComponent::UAMAbilityManagerComponent() // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; bWantsInitializeComponent = true; + SetIsReplicated(true); // ... } @@ -19,7 +20,7 @@ UAMAbilityManagerComponent::UAMAbilityManagerComponent() void UAMAbilityManagerComponent::BeginPlay() { Super::BeginPlay(); - + //OnNextGroupDelegate = FGroupConfirmDelegate::(this, UAMAbilityManagerComponent::OnNextGroupConfirmed); // ... } @@ -199,12 +200,9 @@ void UAMAbilityManagerComponent::PreviousGroup() int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex--; ActiveGroup = AMIntToEnum(CurrentIndex); - if (ActiveGroup >= EAMGroup::Group001) + if (CurrentIndex < 0) { - } - else - { - ActiveGroup = EAMGroup::Group001; + ActiveGroup = AMIntToEnum(Groups.Num() - 1); } if (GetOwnerRole() < ENetRole::ROLE_Authority) { @@ -239,16 +237,21 @@ void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponInde //since it will be done trough ability. if (ActiveGroup != AMIntToEnum(WeaponIndex)) { - ClientNextGroup(AMEnumToInt(ActiveGroup)); + ClientNextGroup(AMEnumToInt(ActiveGroup), false); + } + else + { + ClientNextGroup(AMEnumToInt(ActiveGroup), true); } } bool UAMAbilityManagerComponent::ServerNextGroup_Validate(int32 WeaponIndex) { return true; } -void UAMAbilityManagerComponent::ClientNextGroup_Implementation(int32 WeaponIndex) +void UAMAbilityManagerComponent::ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) { ActiveGroup = AMIntToEnum(WeaponIndex); + OnNextGroupConfirmed(ActiveGroup, bPredictionSuccess); } void UAMAbilityManagerComponent::ServerPreviousGroup_Implementation(int32 WeaponIndex) @@ -256,28 +259,82 @@ void UAMAbilityManagerComponent::ServerPreviousGroup_Implementation(int32 Weapon int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex--; ActiveGroup = AMIntToEnum(CurrentIndex); - if (ActiveGroup >= EAMGroup::Group001) + if (CurrentIndex < 0) { + ActiveGroup = AMIntToEnum(Groups.Num() -1); } - else + if (ActiveGroup != AMIntToEnum(WeaponIndex)) { - ActiveGroup = EAMGroup::Group001; + ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); } - if (ActiveGroup != AMIntToEnum(WeaponIndex)) + else { - ClientPreviousGroup(AMEnumToInt(ActiveGroup)); + ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); } } bool UAMAbilityManagerComponent::ServerPreviousGroup_Validate(int32 WeaponIndex) { return true; } -void UAMAbilityManagerComponent::ClientPreviousGroup_Implementation(int32 WeaponIndex) +void UAMAbilityManagerComponent::ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) { ActiveGroup = AMIntToEnum(WeaponIndex); + OnPreviousGroupConfirmed(ActiveGroup, bPredictionSuccess); } void UAMAbilityManagerComponent::SelectGroup(EAMGroup InGroup) { + if (AMEnumToInt(InGroup) > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + return; + } + ActiveGroup = InGroup; +} + +class UAFAbilityComponent* UAMAbilityManagerComponent::GetAbilityComponent() +{ + UAFAbilityComponent* AbilityComponent = nullptr; + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return AbilityComponent; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return AbilityComponent; + + AbilityComponent = ABInt->GetAbilityComp(); + return AbilityComponent; +} + +bool UAMAbilityManagerComponent::IsServerOrStandalone() const +{ + AActor* Owner = GetOwner(); + if (Owner->GetNetMode() == ENetMode::NM_DedicatedServer + || Owner->GetNetMode() == ENetMode::NM_Standalone) + { + return true; + } + return false; +} +bool UAMAbilityManagerComponent::IsClientOrStandalone() const +{ + AActor* Owner = GetOwner(); + if (Owner->GetNetMode() == ENetMode::NM_Client + || Owner->GetNetMode() == ENetMode::NM_Standalone) + { + return true; + } + return false; +} +bool UAMAbilityManagerComponent::IsClient() const +{ + AActor* Owner = GetOwner(); + if (Owner->GetNetMode() == ENetMode::NM_Client + || Owner->Role < ENetRole::ROLE_Authority) + { + return true; + } + return false; } \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index 7280e0e..b4fec7f 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -4,6 +4,9 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + #include "AMTypes.h" #include "GameplayTags.h" #include "Abilities/GAAbilityBase.h" @@ -92,6 +95,11 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent TMap AbilityReadyEvents; + DECLARE_DELEGATE_TwoParams(FGroupConfirmDelegate, int32, bool) + + FGroupConfirmDelegate OnNextGroupDelegate; + FGroupConfirmDelegate OnPreviousGroupDelegate; + public: // Sets default values for this component's properties UAMAbilityManagerComponent(); @@ -135,18 +143,21 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent void ServerNextGroup_Implementation(int32 WeaponIndex); bool ServerNextGroup_Validate(int32 WeaponIndex); UFUNCTION(Client, Reliable) - void ClientNextGroup(int32 WeaponIndex); - void ClientNextGroup_Implementation(int32 WeaponIndex); + void ClientNextGroup(int32 WeaponIndex, bool bPredictionSuccess); + void ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); UFUNCTION(Server, Reliable, WithValidation) void ServerPreviousGroup(int32 WeaponIndex); void ServerPreviousGroup_Implementation(int32 WeaponIndex); bool ServerPreviousGroup_Validate(int32 WeaponIndex); UFUNCTION(Client, Reliable) - void ClientPreviousGroup(int32 WeaponIndex); - void ClientPreviousGroup_Implementation(int32 WeaponIndex); + void ClientPreviousGroup(int32 WeaponIndex, bool bPredictionSuccess); + void ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); + virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; + virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; + UFUNCTION(BlueprintCallable) void SelectGroup(EAMGroup InGroup); @@ -167,4 +178,10 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent AbilityReadyEvents.Remove(Ability); } } +protected: + class UAFAbilityComponent* GetAbilityComponent(); + + bool IsServerOrStandalone() const; + bool IsClientOrStandalone() const; + bool IsClient() const; }; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index e0beff5..d14b567 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -7,6 +7,9 @@ #include "GameFramework/CharacterMovementComponent.h" #include "GameFramework/Controller.h" #include "GameFramework/SpringArmComponent.h" +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + #include "ARPlayerController.h" ////////////////////////////////////////////////////////////////////////// @@ -45,6 +48,8 @@ AARCharacter::AARCharacter() Abilities = CreateDefaultSubobject(TEXT("Abilities")); + FollowCamera->TransformUpdated.AddUObject(this, &AARCharacter::OnCameraTransformUpdate); + // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) } @@ -165,4 +170,23 @@ void AARCharacter::RemoveTagContainer(const FGameplayTagContainer& TagsIn) { Abilities->RemoveTagContainer(TagsIn); } -/* IAFAbilityInterface- END */ \ No newline at end of file +/* IAFAbilityInterface- END */ + +void AARCharacter::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + + DOREPLIFETIME(AARCharacter, CameraTransform); +} + +void AARCharacter::Multicast_CameraTransform_Implementation(FARCameraTransform InCameraTransform) +{ + CameraTransform = InCameraTransform; +} +void AARCharacter::OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport) +{ + FARCameraTransform CamTransform; + CameraTransform.ForwardVector = FollowCamera->GetForwardVector(); + CameraTransform.Location = FollowCamera->GetComponentLocation(); + //Multicast_CameraTransform(CamTransform); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index fce5e16..b5bf071 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -9,6 +9,17 @@ #include "AFAbilityInterface.h" #include "ARCharacter.generated.h" +USTRUCT(BlueprintType) +struct FARCameraTransform +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly) + FVector ForwardVector; + UPROPERTY(BlueprintReadOnly) + FVector Location; +}; + UCLASS(config=Game) class AARCharacter : public ACharacter, public IAFAbilityInterface { @@ -28,6 +39,10 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface UPROPERTY(EditAnywhere, Category = "Default Abilities") TArray AbilitiesToGive; +public: + UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") + FARCameraTransform CameraTransform; + public: AARCharacter(); @@ -92,5 +107,11 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; /* IAFAbilityInterface- END */ + + UFUNCTION(NetMulticast, Unreliable) + void Multicast_CameraTransform(FARCameraTransform InCameraTransform); + void Multicast_CameraTransform_Implementation(FARCameraTransform InCameraTransform); + + void OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport); }; diff --git a/Source/ActionRPGGame/ARItemPickupBase.cpp b/Source/ActionRPGGame/ARItemPickupBase.cpp new file mode 100644 index 0000000..5496dfe --- /dev/null +++ b/Source/ActionRPGGame/ARItemPickupBase.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemPickupBase.h" + + +// Sets default values +AARItemPickupBase::AARItemPickupBase() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AARItemPickupBase::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AARItemPickupBase::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Source/ActionRPGGame/ARItemPickupBase.h b/Source/ActionRPGGame/ARItemPickupBase.h new file mode 100644 index 0000000..3b4055c --- /dev/null +++ b/Source/ActionRPGGame/ARItemPickupBase.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "ARItemPickupBase.generated.h" + +UCLASS() +class ACTIONRPGGAME_API AARItemPickupBase : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + AARItemPickupBase(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index f41a11a..ca0d04b 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -55,6 +55,7 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); + InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); } //UIAbilityManagerComponent->BindInputs(); } @@ -73,6 +74,10 @@ void AARPlayerController::InputShowHideAbilityManager() { AbilityManager->ShowHideAbilityManager(); } +void AARPlayerController::InputShowHideInventory() +{ + UIComponent->ShowHideInventory(); +} void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) { IAFAbilityInterface* ABInt = Cast(GetPawn()); @@ -87,13 +92,3 @@ void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGamepl AbilityComp->SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); } - -void AARPlayerController::NextWeapon() -{ - //WeaponManager->NextWeapon(); -} - -void AARPlayerController::PreviousWeapon() -{ - //WeaponManager->PreviousWeapon(); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index ad007c0..9fe3efb 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -40,10 +40,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController void InputSwitchAbilitySet(); void InputShowHideAbilityManager(); - UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapons") - void NextWeapon(); - UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapons") - void PreviousWeapon(); - + void InputShowHideInventory(); void OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag); }; diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index c2ac24d..850fc50 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -7,6 +7,7 @@ #include "DWBPFunctionLibrary.h" #include "SDraggableWindowWidget.h" + #include "../UI/Abilities/ARAbilityManagerWidget.h" // Sets default values for this component's properties @@ -24,15 +25,19 @@ UARAbilityManagerComponent::UARAbilityManagerComponent() void UARAbilityManagerComponent::BeginPlay() { Super::BeginPlay(); - APlayerController* OwnerPC = Cast(GetOwner()); - // ... - if (ManagerWidgetClass) + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) { - ManagerWidget = CreateWidget(OwnerPC, ManagerWidgetClass); - ManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); - ManagerWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(ManagerWidget, "Ability Manager"); - ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); - //ManagerWidget->AddToViewport(); + APlayerController* OwnerPC = Cast(GetOwner()); + // ... + if (ManagerWidgetClass) + { + ManagerWidget = CreateWidget(OwnerPC, ManagerWidgetClass); + ManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + ManagerWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(ManagerWidget, "Ability Manager"); + ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); + //ManagerWidget->AddToViewport(); + } } } diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 2b7c872..2357d2f 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -1,9 +1,10 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARUIComponent.h" -#include "ARPlayerController.h" #include "Blueprint/UserWidget.h" +#include "ARPlayerController.h" +#include "Inventory/ARInventoryManagerWidget.h" // Sets default values for this component's properties UARUIComponent::UARUIComponent() { @@ -20,13 +21,23 @@ void UARUIComponent::BeginPlay() { Super::BeginPlay(); - AARPlayerController* MyPC = Cast(GetOwner()); - // ... - if (CrosshairClass) + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) { - CrosshairWidget = CreateWidget(MyPC, CrosshairClass); - CrosshairWidget->SetVisibility(ESlateVisibility::HitTestInvisible); - CrosshairWidget->AddToViewport(); + AARPlayerController* MyPC = Cast(GetOwner()); + // ... + if (CrosshairClass) + { + CrosshairWidget = CreateWidget(MyPC, CrosshairClass); + CrosshairWidget->SetVisibility(ESlateVisibility::HitTestInvisible); + CrosshairWidget->AddToViewport(); + } + if (InventoryManagerClass) + { + InventoryManagerWidget = CreateWidget(MyPC, InventoryManagerClass); + InventoryManagerWidget->SetVisibility(ESlateVisibility::Collapsed); + InventoryManagerWidget->AddToViewport(); + } } } @@ -39,3 +50,14 @@ void UARUIComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorC // ... } +void UARUIComponent::ShowHideInventory() +{ + if (InventoryManagerWidget->GetVisibility() == ESlateVisibility::Collapsed) + { + InventoryManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + } + else if (InventoryManagerWidget->GetVisibility() == ESlateVisibility::SelfHitTestInvisible) + { + InventoryManagerWidget->SetVisibility(ESlateVisibility::Collapsed); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index 21af377..8c81ccf 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -18,6 +18,10 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY() UUserWidget* CrosshairWidget; + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf InventoryManagerClass; + UPROPERTY() + class UARInventoryManagerWidget* InventoryManagerWidget; public: // Sets default values for this component's properties @@ -32,5 +36,5 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + void ShowHideInventory(); }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp new file mode 100644 index 0000000..88439ed --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARInventoryManagerWidget.h" + + + + diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h new file mode 100644 index 0000000..09d0e55 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARInventoryManagerWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARInventoryManagerWidget : public UUserWidget +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp index 2296d52..22d6008 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp @@ -2,6 +2,26 @@ #include "ARWeaponBaseWidget.h" +#include "../../ARPlayerController.h" +#include "../../Weapons/ARWeaponManagerComponent.h" +void UARWeaponBaseWidget::NativePreConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + WeaponManager = MyPC->WeaponManager; + } + Super::NativePreConstruct(); +} +void UARWeaponBaseWidget::NativeConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + WeaponManager = MyPC->WeaponManager; + } + Super::NativeConstruct(); +} + + diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h index f31df22..9d37b27 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h @@ -13,7 +13,13 @@ UCLASS() class ACTIONRPGGAME_API UARWeaponBaseWidget : public UARUMGWidgetBase { GENERATED_BODY() - +protected: + UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") + class UARWeaponManagerComponent* WeaponManager; + +public: + void NativePreConstruct(); + void NativeConstruct(); diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp new file mode 100644 index 0000000..44fbec9 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponManagerSlotDragWidget.h" +#include "Blueprint/WidgetBlueprintLibrary.h" + +#include "ARAbilityDragVisual.h" +#include "../../Weapons/ARWeaponManagerComponent.h" + +FReply UARWeaponManagerSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) +{ + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + //return FReply::Unhandled(); +} + +void UARWeaponManagerSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) +{ + UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); + if (DragDropOp) + { + APlayerController* MyPC = Cast(WeaponManager->GetOwner()); + //UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); + //DragIcon->AbilityManager = AbilityManager; + + DragDropOp->Payload = this; + //DragDropOp->DefaultDragVisual = DragIcon; + + OutOperation = DragDropOp; + } +} diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h new file mode 100644 index 0000000..1fc7f7d --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Weapons/ARWeaponBaseWidget.h" +#include "ARWeaponManagerSlotDragWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponManagerSlotDragWidget : public UARWeaponBaseWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(BlueprintReadWrite, meta=(ExposeOnSpawn), Category = "Weapon Widget") + int32 WeaponIdx; +public: + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) override; + virtual void NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; + + inline int32 GetWeapon() + { + return WeaponIdx; + } +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp new file mode 100644 index 0000000..f80ca84 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp @@ -0,0 +1,18 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponManagerSlotDropWidget.h" + +#include "AFAbilityComponent.h" + +#include "../../Weapons/ARWeaponManagerComponent.h" +#include "../../Weapons/ARWeaponAbilityBase.h" +#include "ARWeaponManagerSlotDragWidget.h" + +bool UARWeaponManagerSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UARWeaponManagerSlotDragWidget* Payload = Cast(InOperation->Payload); + + WeaponManager->AddWeaponToManager(WeaponSlot, EAMSlot::Slot001, Payload->GetWeapon()); + return false; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h new file mode 100644 index 0000000..911bc37 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "ARWeaponBaseWidget.h" +#include "AMTypes.h" +#include "ARWeaponManagerSlotDropWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponManagerSlotDropWidget : public UARWeaponBaseWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Config") + EAMGroup WeaponSlot; +public: + virtual bool NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; + + + +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp new file mode 100644 index 0000000..67be10d --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponManagerWidget.h" + +#include "../../ARPlayerController.h" +#include "../../Weapons/ARWeaponManagerComponent.h" + + + +void UARWeaponManagerWidget::NativePreConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + WeaponManager = MyPC->WeaponManager; + } + Super::NativePreConstruct(); +} +void UARWeaponManagerWidget::NativeConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + WeaponManager = MyPC->WeaponManager; + } + Super::NativeConstruct(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h new file mode 100644 index 0000000..b4c4047 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARWeaponManagerWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponManagerWidget : public UUserWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") + class UARWeaponManagerComponent* WeaponManager; + +public: + void NativePreConstruct(); + void NativeConstruct(); +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp new file mode 100644 index 0000000..78f94c0 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponSlotWidget.h" + + + + +float UARWeaponSlotWidget::GetCurrentReloadTime() const +{ + return 0; +} + +float UARWeaponSlotWidget::GetCurrentReloadTimeNormalized() const +{ + return 0; +} + +float UARWeaponSlotWidget::GetMagazineAmmo() const +{ + return 0; +} + +float UARWeaponSlotWidget::GetRemaningAmmo() const +{ + return 0; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h new file mode 100644 index 0000000..5f5d4c2 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Weapons/ARWeaponBaseWidget.h" +#include "AMTypes.h" +#include "ARWeaponSlotWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponSlotWidget : public UARWeaponBaseWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") + EAMGroup WeaponSlot; + + + UFUNCTION(BlueprintPure, Category = "Weapon") + float GetCurrentReloadTime() const; + UFUNCTION(BlueprintPure, Category = "Weapon") + float GetCurrentReloadTimeNormalized() const; + UFUNCTION(BlueprintPure, Category = "Weapon") + float GetMagazineAmmo() const; + UFUNCTION(BlueprintPure, Category = "Weapon") + float GetRemaningAmmo() const; + +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp index fd3b7f2..3d9a7e5 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -6,10 +6,4 @@ void UARWeaponAbilityBase::OnAbilityInited() { - UWorld* world = GetWorld(); - if (!world) - return; - - FActorSpawnParameters SpawnParams; - AvatarActor = world->SpawnActor(WeaponAvatar, SpawnParams); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp index 87cd1fb..8a6cd9b 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp @@ -49,11 +49,15 @@ void AARWeaponBase::Equip() if (!Character) return; - AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, SocketName); + AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); } void AARWeaponBase::UnEquip() { + AARCharacter* Character = Cast(POwner); + if (!Character) + return; + DetachFromActor(FDetachmentTransformRules::KeepWorldTransform); } void AARWeaponBase::NativeOnWeaponEquiped() { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index fed06ee..0a631f1 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -48,90 +48,215 @@ UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() { return GetAbility(ActiveGroup, EAMSlot::Slot001); } -void UARWeaponManagerComponent::BP_EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx) + +void UARWeaponManagerComponent::AddToWeaponInventory(TSubclassOf InWeapon) { - EquipWeapon(Group, Slot, Idx); + WeaponClasses.Add(InWeapon); } -void UARWeaponManagerComponent::EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx) -{ - if (WeaponClasses.Num() < 0) - return; - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - APawn* POwner = MyPC->GetPawn(); - IAFAbilityInterface* ABInt = Cast(POwner); - if (!ABInt) - return; - UWorld* World = GetWorld(); +void UARWeaponManagerComponent::BP_AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) +{ + AddWeaponToManager(Group, Slot, Idx); +} +void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) +{ + if (IsClient()) + { + ServerAddWeaponToManager(Group, Slot, Idx); + if (Group == EAMGroup::Group001) + { + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); + //if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, + WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), WeaponInput); - FActorSpawnParameters SpawnParams; - AARWeaponBase* Weapon = World->SpawnActor(WeaponClasses[Idx], SpawnParams); - Weapon->OnAddToWeaponManager(Group, Slot, POwner, this); - AbilityToWeapon.Add(Weapon->GetWeaponAbility(), Weapon); - if (Group == EAMGroup::Group001) + AbilityComp->SetAbilityToAction(WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), WeaponInput, ReadyDelegate); + } + } + } + else { - CurrentWeapon = Weapon; - CurrentWeapon->Equip(); + if (WeaponClasses.Num() < 0) + return; + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + APawn* POwner = MyPC->GetPawn(); + IAFAbilityInterface* ABInt = Cast(POwner); + if (!ABInt) + return; + + UWorld* World = GetWorld(); + + FActorSpawnParameters SpawnParams; + AARWeaponBase* Weapon = World->SpawnActor(WeaponClasses[Idx], SpawnParams); + Weapon->OnAddToWeaponManager(Group, Slot, POwner, this); + AbilityToWeapon.Add(Weapon->GetWeaponAbility(), Weapon); + if (Group == EAMGroup::Group001) + { + CurrentWeapon = Weapon; + CurrentWeapon->Equip(); + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); + + { + AbilityComp->SetAbilityToAction(Weapon->GetWeaponAbility(), WeaponInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(Weapon->GetWeaponAbility()); + } + } + Weapons.Add(Weapon); } - Weapons.Add(Weapon); + } +void UARWeaponManagerComponent::ServerAddWeaponToManager_Implementation(EAMGroup Group, EAMSlot Slot, int32 Idx) +{ + AddWeaponToManager(Group, Slot, Idx); +} +bool UARWeaponManagerComponent::ServerAddWeaponToManager_Validate(EAMGroup Group, EAMSlot Slot, int32 Idx) +{ + return true; +} + void UARWeaponManagerComponent::NextWeapon() { FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); NextGroup(); FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) - return; - TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) + { + NextWeaponAbility = FindNextValid(); + } + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +} +void UARWeaponManagerComponent::PreviousWeapon() +{ + FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + PreviousGroup(); + FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + if (!NextWeaponAbility.IsValid()) + { + NextWeaponAbility = FindPreviousValid(); + } + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +} + + +void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags) +{ + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + + //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); +} +void UARWeaponManagerComponent::OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) +{ + if (bPredictionSuccess) return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) + //something gone wrong.. we need to change weapon to correct one. + //we probabaly already changed. So just get current group. + FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + + //and then get correct one from server. + FGameplayTag NextWeaponAbility = GetAbilityTag(ValidGroup, EAMSlot::Slot001); + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +} +void UARWeaponManagerComponent::OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) +{ + if (bPredictionSuccess) return; - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + //something gone wrong.. we need to change weapon to correct one. + //we probabaly already changed. So just get current group. + FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + + //and then get correct one from server. + FGameplayTag NextWeaponAbility = GetAbilityTag(ValidGroup, EAMSlot::Slot001); + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +} + +void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag) +{ + if (!NextWeaponTag.IsValid()) + { + return; + } + TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); if (!AbilityComp) return; - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponAbility)); + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponTag)); if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, - NextWeaponAbility, WeaponInput); + NextWeaponTag, WeaponInput); - AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, ReadyDelegate); + AbilityComp->SetAbilityToAction(NextWeaponTag, WeaponInput, ReadyDelegate); } else { - AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(NextWeaponAbility); - CurrentWeapon = AbilityToWeapon.FindRef(NextWeaponAbility); + AbilityComp->SetAbilityToAction(NextWeaponTag, WeaponInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(NextWeaponTag); + AARWeaponBase* PreviousWeapon = AbilityToWeapon.FindRef(PreviousWeaponTag); + PreviousWeapon->UnEquip(); + CurrentWeapon = AbilityToWeapon.FindRef(NextWeaponTag); CurrentWeapon->Equip(); } } -void UARWeaponManagerComponent::PreviousWeapon() +FGameplayTag UARWeaponManagerComponent::FindNextValid() { - PreviousGroup(); -} + FGameplayTag WeaponAbilityTag; + int32 Idx = AMEnumToInt(ActiveGroup); + while (!WeaponAbilityTag.IsValid()) + { + Idx++; + if (Idx > Groups.Num() - 1) + { + Idx = 0; + } + WeaponAbilityTag = GetAbilityTag(AMIntToEnum(Idx), EAMSlot::Slot001); + } + if (WeaponAbilityTag.IsValid()) + { + SelectGroup(AMIntToEnum(Idx)); + } + return WeaponAbilityTag; +} -void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags) +FGameplayTag UARWeaponManagerComponent::FindPreviousValid() { - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; + FGameplayTag WeaponAbilityTag; + int32 Idx = AMEnumToInt(ActiveGroup); + while (!WeaponAbilityTag.IsValid()) + { + Idx--; + if (Idx < 0) + { + Idx = 0; + } + WeaponAbilityTag = GetAbilityTag(AMIntToEnum(Idx), EAMSlot::Slot001); + } + if (WeaponAbilityTag.IsValid()) + { + SelectGroup(AMIntToEnum(Idx)); + } + return WeaponAbilityTag; +} - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; +void UARWeaponManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; + DOREPLIFETIME(UARWeaponManagerComponent, CurrentWeapon); +} - //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); +void UARWeaponManagerComponent::OnRep_CurrentWeapon() +{ + if (CurrentWeapon) + { + int sd = 0; + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index d69a459..d6f674d 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -18,7 +18,7 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp { GENERATED_BODY() protected: - UPROPERTY(EditAnywhere, Category = "Weapons") + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> WeaponClasses; //currently equipped weapons @@ -26,8 +26,10 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp TArray Weapons; //currently active weapons. - UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") + UPROPERTY(BlueprintReadOnly, ReplicatedUsing=OnRep_CurrentWeapon, Category = "Weapon Manager") class AARWeaponBase* CurrentWeapon; + UFUNCTION() + void OnRep_CurrentWeapon(); TMap AbilityToWeapon; public: @@ -44,10 +46,18 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; UGAAbilityBase* GetCurrentWeapon(); - UFUNCTION(BlueprintCallable, meta=(DisplayName="Equip Weapon"), Category = "Weapon Manager") - void BP_EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx); + UFUNCTION(BlueprintCallable, Category = "Weapon Manager") + void AddToWeaponInventory(TSubclassOf InWeapon); + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Add Weapon To Manager"), Category = "Weapon Manager") + void BP_AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); + + virtual void AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); - virtual void EquipWeapon(EAMGroup Group, EAMSlot Slot, int32 Idx); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); + virtual void ServerAddWeaponToManager_Implementation(EAMGroup Group, EAMSlot Slot, int32 Idx); + bool ServerAddWeaponToManager_Validate(EAMGroup Group, EAMSlot Slot, int32 Idx); UFUNCTION(BlueprintCallable) void NextWeapon(); @@ -55,5 +65,13 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp void PreviousWeapon(); UFUNCTION() - void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); + void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); +protected: + virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; + virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; + + void EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag); + + FGameplayTag FindNextValid(); + FGameplayTag FindPreviousValid(); }; From e0d326ba96e5049674b0364c746230bfaf1d77d6 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 5 Feb 2018 18:17:34 +0100 Subject: [PATCH 049/187] weapon replication fixes --- .../AbilityFramework/AFAbilityComponent.cpp | 10 +++++++- Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 13 ++++++---- Source/ActionRPGGame/Weapons/ARWeaponBase.h | 5 ++-- .../Weapons/ARWeaponManagerComponent.cpp | 25 +++++++++++++++++++ .../Weapons/ARWeaponManagerComponent.h | 6 +++++ 5 files changed, 51 insertions(+), 8 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index a50b37f..a3c5340 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -356,6 +356,14 @@ void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, { InternalRemoveEffect(InProperty, InContext); } + FGAEffectCueParams CueParams; + CueParams.Instigator = InContext.Instigator; + CueParams.Causer = InContext.Causer; + CueParams.HitResult = InContext.HitResult; + CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; + CueParams.Period = InProperty.Period; + CueParams.Duration = InProperty.Duration; + MulticastRemoveEffectCue(CueParams); } void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) @@ -377,7 +385,7 @@ void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProper if (mode == ENetMode::NM_Standalone || role >= ENetRole::ROLE_Authority) { - MulticastRemoveEffectCue(CueParams); + //MulticastRemoveEffectCue(CueParams); } } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp index 8a6cd9b..53c7f8c 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp @@ -32,12 +32,14 @@ void AARWeaponBase::OnAddToWeaponManager(EAMGroup Group, EAMSlot Slot , class UAMAbilityManagerComponent* WeaponManager) { UARWeaponManagerComponent* WManager = Cast(WeaponManager); + WeaponManagerComponent = WManager; + if (!WManager) return; POwner = InPOwner; - //FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &AARWeaponBase::NativeOnWeaponEquiped); - WManager->AddOnAbilityReadyEvent(WeaponAbility, FSimpleDelegate()); + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &AARWeaponBase::OnWeaponAbilityReady, Group); + WManager->AddOnAbilityReadyEvent(WeaponAbility, Delegate); WManager->NativeEquipAbility(WeaponAbility, Group, Slot, this, false); } void AARWeaponBase::Equip() @@ -59,7 +61,7 @@ void AARWeaponBase::UnEquip() DetachFromActor(FDetachmentTransformRules::KeepWorldTransform); } -void AARWeaponBase::NativeOnWeaponEquiped() +void AARWeaponBase::OnWeaponAbilityReady(EAMGroup Group) { if (!POwner) return; @@ -67,7 +69,8 @@ void AARWeaponBase::NativeOnWeaponEquiped() AARCharacter* Character = Cast(POwner); if (!Character) return; + if (!WeaponManagerComponent) + return; - AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, SocketName); - //Ability is ready, Attach to pawn. + WeaponManagerComponent->OnWeaponAbilityReady(WeaponAbility, Group); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Weapons/ARWeaponBase.h index 643c7f4..f58f286 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.h @@ -19,7 +19,8 @@ class ACTIONRPGGAME_API AARWeaponBase : public AActor FName SocketName; UPROPERTY() APawn* POwner; - + UPROPERTY() + UARWeaponManagerComponent* WeaponManagerComponent; public: // Sets default values for this actor's properties AARWeaponBase(); @@ -38,7 +39,7 @@ class ACTIONRPGGAME_API AARWeaponBase : public AActor virtual void UnEquip(); UFUNCTION() - virtual void NativeOnWeaponEquiped(); + virtual void OnWeaponAbilityReady(EAMGroup Group); const inline FGameplayTag& GetWeaponAbility() const diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 0a631f1..5b198ca 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -66,6 +66,11 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (Group == EAMGroup::Group001) { UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + FAFOnAbilityReady ReadyDel = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::ClientOnWeaponAbilityReady, + WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), Group); + + AbilityComp->AddOnAbilityReadyDelegate(WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), ReadyDel); + TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); //if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { @@ -259,4 +264,24 @@ void UARWeaponManagerComponent::OnRep_CurrentWeapon() { int sd = 0; } +} +void UARWeaponManagerComponent::OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, EAMGroup InGroup) +{ + UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); + if (!AbilityComponent) + return; + + UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(WeaponAbility)); + SetAbility(InGroup, EAMSlot::Slot001, Ability); + SetAbilityTag(InGroup, EAMSlot::Slot001, WeaponAbility); +} +void UARWeaponManagerComponent::ClientOnWeaponAbilityReady(FGameplayTag WeaponAbility, EAMGroup InGroup) +{ + UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); + if (!AbilityComponent) + return; + + UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(WeaponAbility)); + SetAbility(InGroup, EAMSlot::Slot001, Ability); + SetAbilityTag(InGroup, EAMSlot::Slot001, WeaponAbility); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index d6f674d..7bde2b8 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -66,6 +66,12 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UFUNCTION() void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); + + void OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, EAMGroup InGroup); + + UFUNCTION() + void ClientOnWeaponAbilityReady(FGameplayTag WeaponAbility, EAMGroup InGroup); + protected: virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; From 8a8d12277bec034a6f46aaa00cfaa2ba60b933be Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 6 Feb 2018 23:05:57 +0100 Subject: [PATCH 050/187] working on weapon attachment replication and ability avatar --- .../AbilityFramework/AFAbilityComponent.cpp | 18 +-- .../AbilityFramework/AFAbilityComponent.h | 10 +- .../Abilities/GAAbilityBase.cpp | 3 - .../Abilities/GAAbilityBase.h | 11 +- .../AMAbilityManagerComponent.cpp | 26 +++- .../AMAbilityManagerComponent.h | 10 +- Source/ActionRPGGame/ARPlayerController.cpp | 1 + .../Weapons/ARWeaponAbilityBase.cpp | 9 +- .../Weapons/ARWeaponAbilityBase.h | 3 +- Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 41 +++++- Source/ActionRPGGame/Weapons/ARWeaponBase.h | 15 +- .../Weapons/ARWeaponManagerComponent.cpp | 137 ++++++++++++------ .../Weapons/ARWeaponManagerComponent.h | 116 ++++++++++++++- 13 files changed, 310 insertions(+), 90 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index a3c5340..5df2282 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -585,7 +585,7 @@ void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InA //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = nullptr; FGameplayTag AbilityTag = Ability->AbilityTag; - InArraySerializerC.RemoveAbilityFromAction(AbilityTag, FGameplayTag()); + InArraySerializerC.RemoveAbilityFromAction(AbilityTag); InArraySerializerC.AbilitiesInputs.Remove(AbilityTag); } } @@ -672,7 +672,7 @@ void FGASAbilityContainer::RemoveAbility(const FGameplayTag& AbilityIn) if (Index == INDEX_NONE) return; MarkItemDirty(AbilitiesItems[Index]); - RemoveAbilityFromAction(AbilityIn, FGameplayTag()); + RemoveAbilityFromAction(AbilityIn); AbilitiesItems.RemoveAt(Index); MarkArrayDirty(); } @@ -687,15 +687,15 @@ FGameplayTag FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& In return Ability; } -void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag) { - TArray OutActions; + /*TArray OutActions; AbilityToAction.RemoveAndCopyValue(InAbilityTag, OutActions); for(const FGameplayTag& Action : OutActions) { ActionToAbility.Remove(Action); - } + }*/ //AbilitiesInputs.Remove(InAbilityTag); } @@ -857,7 +857,7 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c { if (AbilityContainer.IsAbilityBoundToAction(Tag).IsValid()) { - RemoveAbilityFromAction(InAbilityTag, Tag); + RemoveAbilityFromAction(InAbilityTag, FGameplayTag()); } } @@ -898,7 +898,7 @@ FGameplayTag UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InA } void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { - AbilityContainer.RemoveAbilityFromAction(InAbilityTag, InInputTag); + AbilityContainer.RemoveAbilityFromAction(InAbilityTag); } void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) { @@ -981,7 +981,7 @@ void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, { for (const FGameplayTag& Input : InInputTag) { - AbilityContainer.RemoveAbilityFromAction(InAbilityTag, Input); + AbilityContainer.RemoveAbilityFromAction(AlreadyBound); } } } @@ -989,7 +989,7 @@ void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, { if (AlreadyBound.IsValid()) { - NativeRemoveAbility(AlreadyBound); + AbilityContainer.RemoveAbilityFromAction(AlreadyBound); } if (UAssetManager* Manager = UAssetManager::GetIfValid()) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 4f650af..9a96084 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -156,6 +156,8 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer //abilityTag, Ability Ptr TMap AbilitiesInputs; + TMap TagToAbility; + void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, AActor* InAvatar); @@ -163,7 +165,7 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InInputTag); - void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag); UGAAbilityBase* GetAbility(FGameplayTag TagIn); @@ -688,7 +690,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void AddOnAbilityReadyDelegate(const FGameplayTag& InAbilityTag, FAFOnAbilityReady& InDelegate) { - OnAbilityReadyMap.Add(InAbilityTag, InDelegate); + if(InDelegate.IsBound()) + OnAbilityReadyMap.Add(InAbilityTag, InDelegate); } void NotifyOnAbilityReady(const FGameplayTag& InAbilityTag) @@ -704,7 +707,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void AddOnAbilityInputReadyDelegate(const FGameplayTag& InAbilityTag, const FAFOnAbilityReady& InDelegate) { - OnAbilityInputReadyMap.Add(InAbilityTag, InDelegate); + if(InDelegate.IsBound()) + OnAbilityInputReadyMap.Add(InAbilityTag, InDelegate); } void NotifyOnAbilityInputReady(const FGameplayTag& InAbilityTag) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index d1a13f6..da94213 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -209,7 +209,6 @@ void UGAAbilityBase::InitAbility() TickFunction.SetTickFunctionEnable(true); OnAbilityInited(); } - void UGAAbilityBase::OnAttributeSetReplicated() { UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); @@ -675,12 +674,10 @@ void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty //possibly can be infered upon replication. //does other players need info about this ? DOREPLIFETIME(UGAAbilityBase, POwner); - DOREPLIFETIME(UGAAbilityBase, Character); DOREPLIFETIME(UGAAbilityBase, PCOwner); DOREPLIFETIME(UGAAbilityBase, AICOwner); //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. - DOREPLIFETIME(UGAAbilityBase, AvatarActor) } int32 UGAAbilityBase::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 8711b5f..776d515 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -164,10 +164,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask */ /* */ - UPROPERTY(VisibleAnywhere, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") APawn* POwner; - UPROPERTY(VisibleAnywhere, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") - ACharacter* Character; UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") APlayerController* PCOwner; UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") @@ -181,9 +179,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask It will need some common interfaces for getting data out. */ - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") class AActor* AvatarActor; - + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") UCameraComponent* OwnerCamera; @@ -307,6 +305,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); void InitAbility(); +public: UFUNCTION() void OnAttributeSetReplicated(); //called on both server and client after InitAbility(); @@ -639,4 +638,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintCallable, DisplayName = "Get Avatar", Category = "AbilityFramework|Abilities|Helpers") AActor* BP_GetAvatar(); + + virtual void OnAvatarReady() {}; }; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 927f0a2..0deb51e 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -101,16 +101,20 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit return; TArray IAbilityInput; - if(bBindInput) + //if(bBindInput) IAbilityInput = GetInputTag(InGroup, InSlot); - FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReady, InAbilityTag, - IAbilityInput, InGroup, InSlot); + FAFOnAbilityReady del; + if (IsClient()) + { + del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, + IAbilityInput, InGroup, InSlot); + AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + } - AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); AbilityComp->NativeAddAbilityFromTag(InAbilityTag, InAvatar, IAbilityInput);// , /*Input*/ ShootInput); } -void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, +void UAMAbilityManagerComponent::OnAbilityReadyInternal(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) { APlayerController* MyPC = Cast(GetOwner()); @@ -132,6 +136,7 @@ void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArra InAbilityTag, InAbilityInput, InGroup, InSlot); AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); + ExecuteAbilityReadyEvent(InAbilityTag); } else { @@ -141,6 +146,7 @@ void UAMAbilityManagerComponent::OnAbilityReady(FGameplayTag InAbilityTag, TArra AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); ExecuteAbilityReadyEvent(InAbilityTag); } + OnAbilityReady(InAbilityTag, InAbilityInput, InGroup, InSlot); } void UAMAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput, @@ -160,7 +166,7 @@ void UAMAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, SetAbility(InGroup, InSlot, Ability); SetAbilityTag(InGroup, InSlot, InAbilityTag); SetInputTag(InGroup, InSlot, InAbilityInput); - ExecuteAbilityReadyEvent(InAbilityTag); + //ExecuteAbilityReadyEvent(InAbilityTag); } void UAMAbilityManagerComponent::NextGroup() @@ -337,4 +343,10 @@ bool UAMAbilityManagerComponent::IsClient() const return true; } return false; -} \ No newline at end of file +} + +void UAMAbilityManagerComponent::BindOnAbilityReadDelegate(FGameplayTag InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) +{ + +} diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index b4fec7f..f793841 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -125,10 +125,15 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent void BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); +protected: + virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) {}; +private: UFUNCTION() - void OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput, + void OnAbilityReadyInternal(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); +public: UFUNCTION() void OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); @@ -180,7 +185,8 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent } protected: class UAFAbilityComponent* GetAbilityComponent(); - + void BindOnAbilityReadDelegate(FGameplayTag InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot); bool IsServerOrStandalone() const; bool IsClientOrStandalone() const; bool IsClient() const; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index ca0d04b..44e36c5 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -57,6 +57,7 @@ void AARPlayerController::SetPawn(APawn* InPawn) InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); } + WeaponManager->POwner = InPawn; //UIAbilityManagerComponent->BindInputs(); } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp index 3d9a7e5..22b8d27 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -1,9 +1,16 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARWeaponAbilityBase.h" -#include "ARWeaponAvatar.h" +#include "ARWeaponBase.h" void UARWeaponAbilityBase::OnAbilityInited() { +} + +void UARWeaponAbilityBase::OnAvatarReady() +{ + //AARWeaponBase* Weapon = Cast(AvatarActor); + //Weapon->SetPawn(POwner); + //Weapon->Equip(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h index 998717c..7f49860 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -17,7 +17,8 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase public: UPROPERTY(EditAnywhere, Category = "Configuration") - TSubclassOf WeaponAvatar; + TSubclassOf WeaponAvatar; virtual void OnAbilityInited() override; + virtual void OnAvatarReady() override; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp index 53c7f8c..77fc517 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp @@ -11,7 +11,8 @@ AARWeaponBase::AARWeaponBase() { // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. PrimaryActorTick.bCanEverTick = true; - + bReplicates = true; + SetReplicates(true); } // Called when the game starts or when spawned @@ -51,7 +52,8 @@ void AARWeaponBase::Equip() if (!Character) return; - AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); + AttachToActor(Character, FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); + //AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); } void AARWeaponBase::UnEquip() { @@ -61,6 +63,26 @@ void AARWeaponBase::UnEquip() DetachFromActor(FDetachmentTransformRules::KeepWorldTransform); } + +void AARWeaponBase::Holster(const FName& Socket) +{ + if (!POwner) + return; + + AARCharacter* Character = Cast(POwner); + if (!Character) + return; + //AttachToActor(Character, FAttachmentTransformRules::SnapToTargetNotIncludingScale, Socket); + AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, Socket); +} +void AARWeaponBase::Multicast_Equip_Implementation() +{ + Equip(); +} +void AARWeaponBase::Multicast_Holster_Implementation(const FName& Socket) +{ + Holster(Socket); +} void AARWeaponBase::OnWeaponAbilityReady(EAMGroup Group) { if (!POwner) @@ -72,5 +94,18 @@ void AARWeaponBase::OnWeaponAbilityReady(EAMGroup Group) if (!WeaponManagerComponent) return; - WeaponManagerComponent->OnWeaponAbilityReady(WeaponAbility, Group); + WeaponManagerComponent->OnWeaponAbilityReady(WeaponAbility, this, Group); +} + +void AARWeaponBase::OnRep_AttachmentReplication() +{ + Super::OnRep_AttachmentReplication(); + if (!POwner) + return; + + AARCharacter* Character = Cast(POwner); + if (!Character) + return; + //AttachToActor(Character, FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); + AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, GetAttachmentReplication().AttachSocket); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Weapons/ARWeaponBase.h index f58f286..eb965d3 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.h @@ -37,13 +37,26 @@ class ACTIONRPGGAME_API AARWeaponBase : public AActor , class UAMAbilityManagerComponent* WeaponManager); virtual void Equip(); virtual void UnEquip(); + virtual void Holster(const FName& Socket); + UFUNCTION(NetMulticast, Reliable) + void Multicast_Equip(); + void Multicast_Equip_Implementation(); + + UFUNCTION(NetMulticast, Reliable) + void Multicast_Holster(const FName& Socket); + void Multicast_Holster_Implementation(const FName& Socket); UFUNCTION() virtual void OnWeaponAbilityReady(EAMGroup Group); - + inline void SetPawn(APawn* InPawn) + { + POwner = InPawn; + } const inline FGameplayTag& GetWeaponAbility() const { return WeaponAbility; } + + virtual void OnRep_AttachmentReplication() override; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 5b198ca..9688418 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -7,6 +7,32 @@ #include "ARWeaponBase.h" #include "Engine/World.h" +void FARWeaponItem::PreReplicatedRemove(const struct FARWeaponContainer& InArraySerializer) +{ + +} +void FARWeaponItem::PostReplicatedAdd(const struct FARWeaponContainer& InArraySerializer) +{ + Weapon->OnAddToWeaponManager(Group + , EAMSlot::Slot001 + , InArraySerializer.WeaponManager->POwner + , InArraySerializer.WeaponManager); +} +void FARWeaponItem::PostReplicatedChange(const struct FARWeaponContainer& InArraySerializer) +{ + +} +void FARWeaponContainer::Initialize(class UARWeaponManagerComponent* InWeaponManager) +{ + WeaponManager = InWeaponManager; +} +void FARWeaponContainer::AddWeapon(const FARWeaponItem& InWeapon) +{ + MarkItemDirty(const_cast(InWeapon)); + Weapons.Add(InWeapon); + MarkArrayDirty(); +} + // Sets default values for this component's properties UARWeaponManagerComponent::UARWeaponManagerComponent() { @@ -20,6 +46,7 @@ UARWeaponManagerComponent::UARWeaponManagerComponent() // Called when the game starts void UARWeaponManagerComponent::BeginPlay() { + EquippedWeapons.Initialize(this); Super::BeginPlay(); APlayerController* MyPC = Cast(GetOwner()); @@ -34,6 +61,7 @@ void UARWeaponManagerComponent::BeginPlay() if (!AbilityComp) return; + //POwner = MyPC->GetPawn(); } @@ -63,23 +91,6 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (IsClient()) { ServerAddWeaponToManager(Group, Slot, Idx); - if (Group == EAMGroup::Group001) - { - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); - FAFOnAbilityReady ReadyDel = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::ClientOnWeaponAbilityReady, - WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), Group); - - AbilityComp->AddOnAbilityReadyDelegate(WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), ReadyDel); - - TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); - //if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, - WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), WeaponInput); - - AbilityComp->SetAbilityToAction(WeaponClasses[Idx].GetDefaultObject()->GetWeaponAbility(), WeaponInput, ReadyDelegate); - } - } } else { @@ -88,30 +99,24 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) return; - APawn* POwner = MyPC->GetPawn(); + //APawn* POwner = MyPC->GetPawn(); + IAFAbilityInterface* ABInt = Cast(POwner); if (!ABInt) return; - UWorld* World = GetWorld(); - FActorSpawnParameters SpawnParams; - AARWeaponBase* Weapon = World->SpawnActor(WeaponClasses[Idx], SpawnParams); - Weapon->OnAddToWeaponManager(Group, Slot, POwner, this); - AbilityToWeapon.Add(Weapon->GetWeaponAbility(), Weapon); - if (Group == EAMGroup::Group001) + AARWeaponBase* Weapon = GetWorld()->SpawnActor(WeaponClasses[Idx], SpawnParams); + Weapon->SetPawn(POwner); + FARWeaponAttachment* Config = WeaponAttachment.FindByPredicate([&](const FARWeaponAttachment& Item) { - CurrentWeapon = Weapon; - CurrentWeapon->Equip(); - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); - TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); - - { - AbilityComp->SetAbilityToAction(Weapon->GetWeaponAbility(), WeaponInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(Weapon->GetWeaponAbility()); - } - } - Weapons.Add(Weapon); + return Item == Group; + }); + if (Config) + Weapon->Multicast_Holster(Config->SocketName); + + EquippedWeapons.AddWeapon(FARWeaponItem(Weapon, Group)); + } } @@ -255,33 +260,69 @@ void UARWeaponManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifeti { Super::GetLifetimeReplicatedProps(OutLifetimeProps); - DOREPLIFETIME(UARWeaponManagerComponent, CurrentWeapon); + DOREPLIFETIME(UARWeaponManagerComponent, EquippedWeapons); } -void UARWeaponManagerComponent::OnRep_CurrentWeapon() -{ - if (CurrentWeapon) - { - int sd = 0; - } -} -void UARWeaponManagerComponent::OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, EAMGroup InGroup) +void UARWeaponManagerComponent::OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, AARWeaponBase* InWeapon, EAMGroup InGroup) { UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); if (!AbilityComponent) return; UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(WeaponAbility)); + /*AARWeaponBase* Weapon = AbilityToWeapon.FindRef(WeaponAbility);;*/ + Ability->AvatarActor = InWeapon; + SetAbility(InGroup, EAMSlot::Slot001, Ability); SetAbilityTag(InGroup, EAMSlot::Slot001, WeaponAbility); + + //if (IsClient()) + //{ + // Server_HolsterWeapon(InWeapon, InGroup); + //} + //else + //{ + // FARWeaponAttachment* Config = WeaponAttachment.FindByPredicate([&](const FARWeaponAttachment& Item) + // { + // return Item == InGroup; + // }); + // if (Config) + // { + // InWeapon->Multicast_Holster(Config->SocketName); + // } + //} } -void UARWeaponManagerComponent::ClientOnWeaponAbilityReady(FGameplayTag WeaponAbility, EAMGroup InGroup) +bool UARWeaponManagerComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) { - UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); + bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); + + return WroteSomething; +} +void UARWeaponManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag + , const TArray& InAbilityInput + , EAMGroup InGroup, EAMSlot InSlot) +{ + /*UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); if (!AbilityComponent) return; - UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(WeaponAbility)); + UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(InAbilityTag)); SetAbility(InGroup, EAMSlot::Slot001, Ability); - SetAbilityTag(InGroup, EAMSlot::Slot001, WeaponAbility); + SetAbilityTag(InGroup, EAMSlot::Slot001, InAbilityTag);*/ +} + +void UARWeaponManagerComponent::Server_HolsterWeapon_Implementation(AARWeaponBase* InWeapon, EAMGroup InGroup) +{ + FARWeaponAttachment* Config = WeaponAttachment.FindByPredicate([&](const FARWeaponAttachment& Item) + { + return Item == InGroup; + }); + if (Config) + { + InWeapon->Multicast_Holster(Config->SocketName); + } +} +bool UARWeaponManagerComponent::Server_HolsterWeapon_Validate(AARWeaponBase* InWeapon, EAMGroup InGroup) +{ + return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 7bde2b8..9a974ed 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -12,6 +12,93 @@ DECLARE_DELEGATE_OneParam(FAROnWeaponReady, class UARWeaponAbilityBase*); +USTRUCT() +struct FARWeaponItem : public FFastArraySerializerItem +{ + GENERATED_BODY() + UPROPERTY() + class AARWeaponBase* Weapon; + UPROPERTY() + EAMGroup Group; + + FARWeaponItem() + : Weapon(nullptr) + , Group(EAMGroup::MAX) + {} + + FARWeaponItem(AARWeaponBase* InWeapon, EAMGroup InGroup) + : Weapon(InWeapon) + , Group(InGroup) + {} + +public: + void PreReplicatedRemove(const struct FARWeaponContainer& InArraySerializer); + void PostReplicatedAdd(const struct FARWeaponContainer& InArraySerializer); + void PostReplicatedChange(const struct FARWeaponContainer& InArraySerializer); + + bool operator==(const FARWeaponItem& Other) const + { + return Weapon == Other.Weapon; + } +}; + +USTRUCT() +struct FARWeaponContainer : public FFastArraySerializer +{ + GENERATED_BODY() + + friend struct FARWeaponItem; +public: + UPROPERTY() + TArray Weapons; +protected: + UPROPERTY() + class UARWeaponManagerComponent* WeaponManager; + +public: + void Initialize(class UARWeaponManagerComponent* InWeaponManager); + void AddWeapon(const FARWeaponItem& InWeapon); + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(Weapons, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FARWeaponContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + +USTRUCT(BlueprintType) +struct FARWeaponAttachment +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + EAMGroup Group; + + UPROPERTY(EditAnywhere) + FName SocketName; + + + bool operator==(int32 InGroup) const + { + return Group == AMIntToEnum(InGroup); + } + + bool operator==(const FARWeaponAttachment& Other) const + { + return Group == Other.Group; + } + bool operator==(EAMGroup InGroup) const + { + return Group == InGroup; + } +}; /* Add On Character. */ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComponent @@ -21,18 +108,26 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> WeaponClasses; + UPROPERTY(EditAnywhere, Category = "Attachment Config") + TArray WeaponAttachment; + + //currently equipped weapons UPROPERTY() TArray Weapons; //currently active weapons. - UPROPERTY(BlueprintReadOnly, ReplicatedUsing=OnRep_CurrentWeapon, Category = "Weapon Manager") + UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") class AARWeaponBase* CurrentWeapon; - UFUNCTION() - void OnRep_CurrentWeapon(); TMap AbilityToWeapon; + + UPROPERTY(Replicated) + FARWeaponContainer EquippedWeapons; + public: + UPROPERTY() + class APawn* POwner; // Sets default values for this component's properties UARWeaponManagerComponent(); @@ -67,12 +162,13 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UFUNCTION() void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); - void OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, EAMGroup InGroup); - - UFUNCTION() - void ClientOnWeaponAbilityReady(FGameplayTag WeaponAbility, EAMGroup InGroup); + void OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, AARWeaponBase* InWeapon, EAMGroup InGroup); + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; protected: + virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) override; + virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; @@ -80,4 +176,10 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp FGameplayTag FindNextValid(); FGameplayTag FindPreviousValid(); + + UFUNCTION(Server, Reliable, WithValidation) + void Server_HolsterWeapon(AARWeaponBase* InWeapon, EAMGroup InGroup); + void Server_HolsterWeapon_Implementation(AARWeaponBase* InWeapon, EAMGroup InGroup); + bool Server_HolsterWeapon_Validate(AARWeaponBase* InWeapon, EAMGroup InGroup); + }; From 71f1dc80be34254c635eeea8781b611f5f820517 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 8 Feb 2018 00:27:48 +0100 Subject: [PATCH 051/187] changed weapon attachment --- .../AbilityFramework/AFAbilityComponent.cpp | 50 +++----- .../AbilityFramework/AFAbilityComponent.h | 19 +-- Source/ActionRPGGame/ARCharacter.cpp | 40 ++++++ Source/ActionRPGGame/ARCharacter.h | 39 ++++++ Source/ActionRPGGame/ARPlayerController.cpp | 5 +- Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 7 ++ Source/ActionRPGGame/Weapons/ARItemWeapon.h | 24 ++++ .../Weapons/ARWeaponAbilityBase.cpp | 1 - .../Weapons/ARWeaponAbilityBase.h | 3 - .../ActionRPGGame/Weapons/ARWeaponAvatar.cpp | 27 ---- Source/ActionRPGGame/Weapons/ARWeaponAvatar.h | 28 ----- Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 111 ---------------- Source/ActionRPGGame/Weapons/ARWeaponBase.h | 62 --------- .../Weapons/ARWeaponManagerComponent.cpp | 118 +++--------------- .../Weapons/ARWeaponManagerComponent.h | 93 +------------- .../Weapons/ARWeaponPawnManagerComponent.cpp | 117 +++++++++++++++++ .../Weapons/ARWeaponPawnManagerComponent.h | 85 +++++++++++++ 17 files changed, 369 insertions(+), 460 deletions(-) create mode 100644 Source/ActionRPGGame/Weapons/ARItemWeapon.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARItemWeapon.h delete mode 100644 Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp delete mode 100644 Source/ActionRPGGame/Weapons/ARWeaponAvatar.h delete mode 100644 Source/ActionRPGGame/Weapons/ARWeaponBase.cpp delete mode 100644 Source/ActionRPGGame/Weapons/ARWeaponBase.h create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 5df2282..f5b9701 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -699,25 +699,27 @@ void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbility //AbilitiesInputs.Remove(InAbilityTag); } -void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag) { - if (ActionToAbility.Contains(InInputTag)) + for (const FGameplayTag& InputTag : InInputTag) { - FGameplayTag AbilityTag = ActionToAbility.FindRef(InInputTag); - UE_LOG(AbilityFramework, Log, TEXT("FGASAbilityContainer: Input %s is already abount to Ability %s"), - *InInputTag.ToString(), - *AbilityTag.ToString() - ); - - //return; - } + if (ActionToAbility.Contains(InputTag)) + { + FGameplayTag AbilityTag = ActionToAbility.FindRef(InputTag); + UE_LOG(AbilityFramework, Log, TEXT("FGASAbilityContainer: Input %s is already abount to Ability %s"), + *InputTag.ToString(), + *AbilityTag.ToString() + ); - FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InInputTag); - AbilityTag = InAbilityTag; + //return; + } - TArray& ActionTag = AbilityToAction.FindOrAdd(InAbilityTag); - ActionTag.Add(InInputTag); + FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InputTag); + AbilityTag = InAbilityTag; + TArray& ActionTag = AbilityToAction.FindOrAdd(InputTag); + ActionTag.Add(InputTag); + } if (!AbilitiesComp.IsValid()) return; if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) @@ -861,22 +863,9 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c } } - for (const FGameplayTag& Tag : InInputTag) - { - SetAbilityToAction(InAbilityTag, Tag, InputDelegate); - } -} -void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, - const FAFOnAbilityReady& InputDelegate) -{ - //check if there is input under tag - //clear it - //then bind. - - AbilityContainer.SetAbilityToAction(InAbilityTag, InInputTag); ENetRole role = GetOwnerRole(); - + if (GetOwner()->GetNetMode() == ENetMode::NM_Client && role == ENetRole::ROLE_AutonomousProxy) { @@ -887,6 +876,7 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c ServerSetAbilityToAction(InAbilityTag, InInputTag); } } + FGameplayTag UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag) { for (const FGameplayTag& Tag : InInputTag) @@ -900,14 +890,14 @@ void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityT { AbilityContainer.RemoveAbilityFromAction(InAbilityTag); } -void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const TArray& InInputTag) { if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) { SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); } } -bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const TArray& InInputTag) { return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 9a96084..21e7eb2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -163,7 +163,7 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer AActor* InAvatar); void RemoveAbility(const FGameplayTag& AbilityIn); - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InInputTag); void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag); @@ -806,16 +806,15 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, //need to be called on both client and server. //Change InInputTag To Array, clear previous binds on the same tag. void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag, const FAFOnAbilityReady& InputDelegate); FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); - +protected: UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); - void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); - bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); - + void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const TArray& InInputTag); +public: /* Called when ability action has been binded on server. */ UFUNCTION(Client, Reliable) void ClientNotifyAbilityInputReady(FGameplayTag AbilityTag); @@ -826,22 +825,24 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void BP_InputPressed(FGameplayTag ActionName); void NativeInputPressed(FGameplayTag ActionName); +protected: UFUNCTION(Server, Reliable, WithValidation) void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - +public: UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") void BP_InputReleased(FGameplayTag ActionName); void NativeInputReleased(FGameplayTag ActionName); +protected: UFUNCTION(Server, Reliable, WithValidation) void ServerNativeInputReleased(FGameplayTag ActionName); virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); - +public: /* Finds ability using asset registry and then gives it to component. Only valid on server. diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index d14b567..1b9966c 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -10,11 +10,16 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" +#include "Weapons/ARWeaponPawnManagerComponent.h" #include "ARPlayerController.h" ////////////////////////////////////////////////////////////////////////// // AARCharacter +const FName WeaponSocket::HolsteredRightWeapon = TEXT("spine_RightWeaponSocket"); +const FName WeaponSocket::HolsteredLeftWeapon = TEXT("spine_LeftWeaponSocket"); +const FName WeaponSocket::EquipedMainWeapon = TEXT("hand_rSocket"); + AARCharacter::AARCharacter() { // Set size for collision capsule @@ -50,10 +55,45 @@ AARCharacter::AARCharacter() FollowCamera->TransformUpdated.AddUObject(this, &AARCharacter::OnCameraTransformUpdate); + Weapons = CreateDefaultSubobject(TEXT("Weapons")); + + HolsteredRightWeapon = CreateDefaultSubobject(TEXT("HolsteredRightWeapon")); + //HolsteredRightWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform); + HolsteredRightWeapon->SetupAttachment(GetMesh(), WeaponSocket::HolsteredRightWeapon); + + + HolsteredLeftWeapon = CreateDefaultSubobject(TEXT("HolsteredLeftWeapon")); + //HolsteredLeftWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); + HolsteredLeftWeapon->SetupAttachment(GetMesh(), WeaponSocket::HolsteredLeftWeapon); + + + HolsteredBackDownWeapon = CreateDefaultSubobject(TEXT("HolsteredBackDownWeapon")); + //HolsteredBackDownWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); + HolsteredBackDownWeapon->SetupAttachment(GetMesh()); + + + HolsteredSideLeftWeapon = CreateDefaultSubobject(TEXT("HolsteredSideLeftWeapon")); + //HolsteredSideLeftWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); + HolsteredSideLeftWeapon->SetupAttachment(GetMesh()); + + + EquipedMainWeapon = CreateDefaultSubobject(TEXT("EquipedMainWeapon")); + //EquipedMainWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); + EquipedMainWeapon->SetupAttachment(GetMesh(), WeaponSocket::EquipedMainWeapon); + + + // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) } +void AARCharacter::BeginPlay() +{ + Super::BeginPlay(); + + Weapons->SetPOwner(this); +} + ////////////////////////////////////////////////////////////////////////// // Input diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index b5bf071..6b1ec44 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -19,7 +19,13 @@ struct FARCameraTransform UPROPERTY(BlueprintReadOnly) FVector Location; }; +struct WeaponSocket +{ + static const FName HolsteredRightWeapon; + static const FName HolsteredLeftWeapon; + static const FName EquipedMainWeapon; +}; UCLASS(config=Game) class AARCharacter : public ACharacter, public IAFAbilityInterface { @@ -36,9 +42,25 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFAbilityComponent* Abilities; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class UARWeaponPawnManagerComponent* Weapons; UPROPERTY(EditAnywhere, Category = "Default Abilities") TArray AbilitiesToGive; + + //Weapons + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* HolsteredRightWeapon; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* HolsteredLeftWeapon; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* HolsteredBackDownWeapon; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* HolsteredSideLeftWeapon; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* EquipedMainWeapon; + public: UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") FARCameraTransform CameraTransform; @@ -46,6 +68,8 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface public: AARCharacter(); + virtual void BeginPlay() override; + /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) float BaseTurnRate; @@ -113,5 +137,20 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface void Multicast_CameraTransform_Implementation(FARCameraTransform InCameraTransform); void OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport); + + inline UARWeaponPawnManagerComponent* GetWeapons() + { + return Weapons; + } + + inline USkeletalMeshComponent* GetHolsteredRightWeapon() + { + return HolsteredRightWeapon; + } + + inline USkeletalMeshComponent* GetEquipedMainWeapon() + { + return EquipedMainWeapon; + } }; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 44e36c5..5f9de16 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -90,6 +90,7 @@ void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGamepl return; UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - - AbilityComp->SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); + TArray Inputs; + Inputs.Add(InInputTag); + AbilityComp->SetAbilityToAction(InAbilityTag, Inputs, FAFOnAbilityReady()); } diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp new file mode 100644 index 0000000..64da854 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemWeapon.h" + + + + diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h new file mode 100644 index 0000000..ff29eaa --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "ARItemWeapon.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType) +class ACTIONRPGGAME_API UARItemWeapon : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Ability") + FGameplayTag Ability; + UPROPERTY(EditAnywhere, Category = "Visual") + TSoftObjectPtr WeaponMesh; + + +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp index 22b8d27..ed0b52a 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -1,7 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARWeaponAbilityBase.h" -#include "ARWeaponBase.h" void UARWeaponAbilityBase::OnAbilityInited() diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h index 7f49860..935c5b1 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -16,9 +16,6 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase GENERATED_BODY() public: - UPROPERTY(EditAnywhere, Category = "Configuration") - TSubclassOf WeaponAvatar; - virtual void OnAbilityInited() override; virtual void OnAvatarReady() override; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp deleted file mode 100644 index 2a3870c..0000000 --- a/Source/ActionRPGGame/Weapons/ARWeaponAvatar.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponAvatar.h" - - -// Sets default values -AARWeaponAvatar::AARWeaponAvatar() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void AARWeaponAvatar::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AARWeaponAvatar::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAvatar.h b/Source/ActionRPGGame/Weapons/ARWeaponAvatar.h deleted file mode 100644 index 2d403db..0000000 --- a/Source/ActionRPGGame/Weapons/ARWeaponAvatar.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "ARWeaponAvatar.generated.h" - -UCLASS() -class ACTIONRPGGAME_API AARWeaponAvatar : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - AARWeaponAvatar(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp deleted file mode 100644 index 77fc517..0000000 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp +++ /dev/null @@ -1,111 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponBase.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.h" -#include "AMAbilityManagerComponent.h" -#include "ARWeaponManagerComponent.h" -#include "../ARCharacter.h" -// Sets default values -AARWeaponBase::AARWeaponBase() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - bReplicates = true; - SetReplicates(true); -} - -// Called when the game starts or when spawned -void AARWeaponBase::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AARWeaponBase::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} -void AARWeaponBase::OnAddToWeaponManager(EAMGroup Group, EAMSlot Slot - , class APawn* InPOwner - , class UAMAbilityManagerComponent* WeaponManager) -{ - UARWeaponManagerComponent* WManager = Cast(WeaponManager); - WeaponManagerComponent = WManager; - - if (!WManager) - return; - - POwner = InPOwner; - FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &AARWeaponBase::OnWeaponAbilityReady, Group); - WManager->AddOnAbilityReadyEvent(WeaponAbility, Delegate); - WManager->NativeEquipAbility(WeaponAbility, Group, Slot, this, false); -} -void AARWeaponBase::Equip() -{ - if (!POwner) - return; - - AARCharacter* Character = Cast(POwner); - if (!Character) - return; - - AttachToActor(Character, FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); - //AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); -} -void AARWeaponBase::UnEquip() -{ - AARCharacter* Character = Cast(POwner); - if (!Character) - return; - - DetachFromActor(FDetachmentTransformRules::KeepWorldTransform); -} - -void AARWeaponBase::Holster(const FName& Socket) -{ - if (!POwner) - return; - - AARCharacter* Character = Cast(POwner); - if (!Character) - return; - //AttachToActor(Character, FAttachmentTransformRules::SnapToTargetNotIncludingScale, Socket); - AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, Socket); -} -void AARWeaponBase::Multicast_Equip_Implementation() -{ - Equip(); -} -void AARWeaponBase::Multicast_Holster_Implementation(const FName& Socket) -{ - Holster(Socket); -} -void AARWeaponBase::OnWeaponAbilityReady(EAMGroup Group) -{ - if (!POwner) - return; - - AARCharacter* Character = Cast(POwner); - if (!Character) - return; - if (!WeaponManagerComponent) - return; - - WeaponManagerComponent->OnWeaponAbilityReady(WeaponAbility, this, Group); -} - -void AARWeaponBase::OnRep_AttachmentReplication() -{ - Super::OnRep_AttachmentReplication(); - if (!POwner) - return; - - AARCharacter* Character = Cast(POwner); - if (!Character) - return; - //AttachToActor(Character, FAttachmentTransformRules::SnapToTargetNotIncludingScale, SocketName); - AttachToComponent(Character->GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale, GetAttachmentReplication().AttachSocket); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Weapons/ARWeaponBase.h deleted file mode 100644 index eb965d3..0000000 --- a/Source/ActionRPGGame/Weapons/ARWeaponBase.h +++ /dev/null @@ -1,62 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "GameplayTags.h" -#include "AMTypes.h" -#include "ARWeaponBase.generated.h" - -UCLASS() -class ACTIONRPGGAME_API AARWeaponBase : public AActor -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere) - FGameplayTag WeaponAbility; - UPROPERTY(EditAnywhere) - FName SocketName; - UPROPERTY() - APawn* POwner; - UPROPERTY() - UARWeaponManagerComponent* WeaponManagerComponent; -public: - // Sets default values for this actor's properties - AARWeaponBase(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - virtual void OnAddToWeaponManager(EAMGroup Group, EAMSlot Slot - , class APawn* InPOwner - , class UAMAbilityManagerComponent* WeaponManager); - virtual void Equip(); - virtual void UnEquip(); - virtual void Holster(const FName& Socket); - UFUNCTION(NetMulticast, Reliable) - void Multicast_Equip(); - void Multicast_Equip_Implementation(); - - UFUNCTION(NetMulticast, Reliable) - void Multicast_Holster(const FName& Socket); - void Multicast_Holster_Implementation(const FName& Socket); - - UFUNCTION() - virtual void OnWeaponAbilityReady(EAMGroup Group); - - inline void SetPawn(APawn* InPawn) - { - POwner = InPawn; - } - const inline FGameplayTag& GetWeaponAbility() const - { - return WeaponAbility; - } - - virtual void OnRep_AttachmentReplication() override; -}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 9688418..f24e054 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -4,35 +4,9 @@ #include "AFAbilityInterface.h" #include "AFAbilityComponent.h" #include "ARWeaponAbilityBase.h" -#include "ARWeaponBase.h" +#include "ARItemWeapon.h" #include "Engine/World.h" -void FARWeaponItem::PreReplicatedRemove(const struct FARWeaponContainer& InArraySerializer) -{ - -} -void FARWeaponItem::PostReplicatedAdd(const struct FARWeaponContainer& InArraySerializer) -{ - Weapon->OnAddToWeaponManager(Group - , EAMSlot::Slot001 - , InArraySerializer.WeaponManager->POwner - , InArraySerializer.WeaponManager); -} -void FARWeaponItem::PostReplicatedChange(const struct FARWeaponContainer& InArraySerializer) -{ - -} -void FARWeaponContainer::Initialize(class UARWeaponManagerComponent* InWeaponManager) -{ - WeaponManager = InWeaponManager; -} -void FARWeaponContainer::AddWeapon(const FARWeaponItem& InWeapon) -{ - MarkItemDirty(const_cast(InWeapon)); - Weapons.Add(InWeapon); - MarkArrayDirty(); -} - // Sets default values for this component's properties UARWeaponManagerComponent::UARWeaponManagerComponent() { @@ -46,7 +20,6 @@ UARWeaponManagerComponent::UARWeaponManagerComponent() // Called when the game starts void UARWeaponManagerComponent::BeginPlay() { - EquippedWeapons.Initialize(this); Super::BeginPlay(); APlayerController* MyPC = Cast(GetOwner()); @@ -77,7 +50,7 @@ UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() return GetAbility(ActiveGroup, EAMSlot::Slot001); } -void UARWeaponManagerComponent::AddToWeaponInventory(TSubclassOf InWeapon) +void UARWeaponManagerComponent::AddToWeaponInventory(TSubclassOf InWeapon) { WeaponClasses.Add(InWeapon); } @@ -88,35 +61,26 @@ void UARWeaponManagerComponent::BP_AddWeaponToManager(EAMGroup Group, EAMSlot Sl } void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) { + AARCharacter* Character = Cast(POwner); + if (Character) + { + Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()->WeaponMesh); + } if (IsClient()) { ServerAddWeaponToManager(Group, Slot, Idx); } else { - if (WeaponClasses.Num() < 0) - return; APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) return; - //APawn* POwner = MyPC->GetPawn(); IAFAbilityInterface* ABInt = Cast(POwner); if (!ABInt) return; - FActorSpawnParameters SpawnParams; - AARWeaponBase* Weapon = GetWorld()->SpawnActor(WeaponClasses[Idx], SpawnParams); - Weapon->SetPawn(POwner); - FARWeaponAttachment* Config = WeaponAttachment.FindByPredicate([&](const FARWeaponAttachment& Item) - { - return Item == Group; - }); - if (Config) - Weapon->Multicast_Holster(Config->SocketName); - - EquippedWeapons.AddWeapon(FARWeaponItem(Weapon, Group)); - + Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()->WeaponMesh); } } @@ -198,6 +162,11 @@ void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTa return; UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponTag)); + AARCharacter* Character = Cast(POwner); + if (Character) + { + Character->GetWeapons()->Equip(ActiveGroup, WeaponClasses[0].GetDefaultObject()->WeaponMesh); + } if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, @@ -209,10 +178,6 @@ void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTa { AbilityComp->SetAbilityToAction(NextWeaponTag, WeaponInput, FAFOnAbilityReady()); ExecuteAbilityReadyEvent(NextWeaponTag); - AARWeaponBase* PreviousWeapon = AbilityToWeapon.FindRef(PreviousWeaponTag); - PreviousWeapon->UnEquip(); - CurrentWeapon = AbilityToWeapon.FindRef(NextWeaponTag); - CurrentWeapon->Equip(); } } FGameplayTag UARWeaponManagerComponent::FindNextValid() @@ -256,42 +221,13 @@ FGameplayTag UARWeaponManagerComponent::FindPreviousValid() return WeaponAbilityTag; } -void UARWeaponManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - - DOREPLIFETIME(UARWeaponManagerComponent, EquippedWeapons); -} - -void UARWeaponManagerComponent::OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, AARWeaponBase* InWeapon, EAMGroup InGroup) -{ - UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); - if (!AbilityComponent) - return; - - UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(WeaponAbility)); - /*AARWeaponBase* Weapon = AbilityToWeapon.FindRef(WeaponAbility);;*/ - Ability->AvatarActor = InWeapon; - - SetAbility(InGroup, EAMSlot::Slot001, Ability); - SetAbilityTag(InGroup, EAMSlot::Slot001, WeaponAbility); +//void UARWeaponManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +//{ +// Super::GetLifetimeReplicatedProps(OutLifetimeProps); +// +// DOREPLIFETIME(UARWeaponManagerComponent, EquippedWeapons); +//} - //if (IsClient()) - //{ - // Server_HolsterWeapon(InWeapon, InGroup); - //} - //else - //{ - // FARWeaponAttachment* Config = WeaponAttachment.FindByPredicate([&](const FARWeaponAttachment& Item) - // { - // return Item == InGroup; - // }); - // if (Config) - // { - // InWeapon->Multicast_Holster(Config->SocketName); - // } - //} -} bool UARWeaponManagerComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) { bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); @@ -310,19 +246,3 @@ void UARWeaponManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag SetAbility(InGroup, EAMSlot::Slot001, Ability); SetAbilityTag(InGroup, EAMSlot::Slot001, InAbilityTag);*/ } - -void UARWeaponManagerComponent::Server_HolsterWeapon_Implementation(AARWeaponBase* InWeapon, EAMGroup InGroup) -{ - FARWeaponAttachment* Config = WeaponAttachment.FindByPredicate([&](const FARWeaponAttachment& Item) - { - return Item == InGroup; - }); - if (Config) - { - InWeapon->Multicast_Holster(Config->SocketName); - } -} -bool UARWeaponManagerComponent::Server_HolsterWeapon_Validate(AARWeaponBase* InWeapon, EAMGroup InGroup) -{ - return true; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 9a974ed..791dced 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -11,68 +11,6 @@ DECLARE_DELEGATE_OneParam(FAROnWeaponReady, class UARWeaponAbilityBase*); - -USTRUCT() -struct FARWeaponItem : public FFastArraySerializerItem -{ - GENERATED_BODY() - UPROPERTY() - class AARWeaponBase* Weapon; - UPROPERTY() - EAMGroup Group; - - FARWeaponItem() - : Weapon(nullptr) - , Group(EAMGroup::MAX) - {} - - FARWeaponItem(AARWeaponBase* InWeapon, EAMGroup InGroup) - : Weapon(InWeapon) - , Group(InGroup) - {} - -public: - void PreReplicatedRemove(const struct FARWeaponContainer& InArraySerializer); - void PostReplicatedAdd(const struct FARWeaponContainer& InArraySerializer); - void PostReplicatedChange(const struct FARWeaponContainer& InArraySerializer); - - bool operator==(const FARWeaponItem& Other) const - { - return Weapon == Other.Weapon; - } -}; - -USTRUCT() -struct FARWeaponContainer : public FFastArraySerializer -{ - GENERATED_BODY() - - friend struct FARWeaponItem; -public: - UPROPERTY() - TArray Weapons; -protected: - UPROPERTY() - class UARWeaponManagerComponent* WeaponManager; - -public: - void Initialize(class UARWeaponManagerComponent* InWeaponManager); - void AddWeapon(const FARWeaponItem& InWeapon); - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(Weapons, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FARWeaponContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; - USTRUCT(BlueprintType) struct FARWeaponAttachment { @@ -106,25 +44,12 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp GENERATED_BODY() protected: UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") - TArray> WeaponClasses; + TArray> WeaponClasses; UPROPERTY(EditAnywhere, Category = "Attachment Config") - TArray WeaponAttachment; - - - //currently equipped weapons - UPROPERTY() - TArray Weapons; - - //currently active weapons. - UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") - class AARWeaponBase* CurrentWeapon; - - TMap AbilityToWeapon; - - UPROPERTY(Replicated) - FARWeaponContainer EquippedWeapons; - + FName EquipSocketName; + UPROPERTY(EditAnywhere, Category = "Attachment Config") + TArray WeaponAttachment; public: UPROPERTY() class APawn* POwner; @@ -142,7 +67,7 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UGAAbilityBase* GetCurrentWeapon(); UFUNCTION(BlueprintCallable, Category = "Weapon Manager") - void AddToWeaponInventory(TSubclassOf InWeapon); + void AddToWeaponInventory(TSubclassOf InWeapon); UFUNCTION(BlueprintCallable, meta=(DisplayName="Add Weapon To Manager"), Category = "Weapon Manager") void BP_AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); @@ -162,8 +87,6 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UFUNCTION() void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); - void OnWeaponAbilityReady(const FGameplayTag& WeaponAbility, AARWeaponBase* InWeapon, EAMGroup InGroup); - bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; protected: virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, @@ -176,10 +99,4 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp FGameplayTag FindNextValid(); FGameplayTag FindPreviousValid(); - - UFUNCTION(Server, Reliable, WithValidation) - void Server_HolsterWeapon(AARWeaponBase* InWeapon, EAMGroup InGroup); - void Server_HolsterWeapon_Implementation(AARWeaponBase* InWeapon, EAMGroup InGroup); - bool Server_HolsterWeapon_Validate(AARWeaponBase* InWeapon, EAMGroup InGroup); - }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp new file mode 100644 index 0000000..6801e2d --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp @@ -0,0 +1,117 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponPawnManagerComponent.h" + +#include "../ARCharacter.h" + +// Sets default values for this component's properties +UARWeaponPawnManagerComponent::UARWeaponPawnManagerComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + WeaponHelper.Add(&Group001HolsteredAttachment); + WeaponHelper.Add(&Group002HolsteredAttachment); + WeaponHelper.Add(&Group003HolsteredAttachment); + WeaponHelper.Add(&Group004HolsteredAttachment); + // ... +} + + +// Called when the game starts +void UARWeaponPawnManagerComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UARWeaponPawnManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +void UARWeaponPawnManagerComponent::SetWeapon(TSoftObjectPtr InWeapon, USkeletalMeshComponent* Component) +{ + if (POwner) + { + if (AARCharacter* Character = Cast(POwner)) + { + Component->SetSkeletalMesh(InWeapon.Get()); + } + } +} + +void UARWeaponPawnManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + + DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group001HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group002HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group003HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group004HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, MainHandWeapon, COND_SkipOwner); +} + +void UARWeaponPawnManagerComponent::Equip(EAMGroup Group, TSoftObjectPtr InWeapon) +{ + MainHandWeapon.WeaponMesh = InWeapon; + MainHandWeapon.RepCounter++; + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(InWeapon, Character->GetEquipedMainWeapon()); + } +} + +void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, TSoftObjectPtr InWeapon) +{ + WeaponHelper[AMEnumToInt(Group)]->WeaponMesh = InWeapon; + WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(InWeapon, Character->GetHolsteredRightWeapon()); + } +} + +void UARWeaponPawnManagerComponent::OnRep_Group001HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group001HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + } +} +void UARWeaponPawnManagerComponent::OnRep_Group002HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group002HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + } +} +void UARWeaponPawnManagerComponent::OnRep_Group003HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group003HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + } +} +void UARWeaponPawnManagerComponent::OnRep_Group004HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group004HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + } +} + +void UARWeaponPawnManagerComponent::OnRep_MainHandWeapon() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(MainHandWeapon.WeaponMesh, Character->GetHolsteredRightWeapon()); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h new file mode 100644 index 0000000..3fe8827 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h @@ -0,0 +1,85 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + +#include "AMTypes.h" + +#include "ARWeaponPawnManagerComponent.generated.h" + +USTRUCT() +struct FARWeapon +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Attachment Test") + TSoftObjectPtr WeaponMesh; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + FName SocketName; + + UPROPERTY(EditAnywhere, Category = "Attachment Test") + uint8 RepCounter; +}; + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY(ReplicatedUsing = OnRep_Group001HolsteredAttachment) + FARWeapon Group001HolsteredAttachment; + UPROPERTY(ReplicatedUsing = OnRep_Group002HolsteredAttachment) + FARWeapon Group002HolsteredAttachment; + UPROPERTY(ReplicatedUsing = OnRep_Group003HolsteredAttachment) + FARWeapon Group003HolsteredAttachment; + UPROPERTY(ReplicatedUsing = OnRep_Group004HolsteredAttachment) + FARWeapon Group004HolsteredAttachment; + UPROPERTY(ReplicatedUsing = OnRep_MainHandWeapon) + FARWeapon MainHandWeapon; + + UPROPERTY() + class APawn* POwner; + + TMap GroupToComponent; + + TArray WeaponHelper; + +public: + // Sets default values for this component's properties + UARWeaponPawnManagerComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + void Equip(EAMGroup Group, TSoftObjectPtr InWeapon); + void Holster(EAMGroup Group, TSoftObjectPtr InWeapon); + inline void SetPOwner(APawn* InPawn) + { + POwner = InPawn; + } + +protected: + void SetWeapon(TSoftObjectPtr InWeapon, USkeletalMeshComponent* Component); + UFUNCTION() + void OnRep_Group001HolsteredAttachment(); + UFUNCTION() + void OnRep_Group002HolsteredAttachment(); + UFUNCTION() + void OnRep_Group003HolsteredAttachment(); + UFUNCTION() + void OnRep_Group004HolsteredAttachment(); + + UFUNCTION() + void OnRep_MainHandWeapon(); +}; From cefb236fe4783d00bfb656bcac0a1bc899b622d2 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Feb 2018 02:14:25 +0100 Subject: [PATCH 052/187] more weapon attachment work --- Config/DefaultGameplayTags.ini | 3 + Config/DefaultInput.ini | 1 + .../AbilityFramework/AFAbilityComponent.cpp | 4 + .../AbilityFramework/AFAbilityComponent.h | 5 +- .../AMAbilityManagerComponent.cpp | 2 +- .../AMAbilityManagerComponent.h | 2 +- Source/ActionRPGGame/ARCharacter.cpp | 44 ++++- Source/ActionRPGGame/ARCharacter.h | 46 ++++- Source/ActionRPGGame/ARPlayerController.cpp | 26 ++- Source/ActionRPGGame/ARPlayerController.h | 6 + .../Attributes/ARAbilityAttributes.cpp | 7 + .../Attributes/ARAbilityAttributes.h | 6 +- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 15 +- Source/ActionRPGGame/Weapons/ARWeaponBase.cpp | 29 +++ Source/ActionRPGGame/Weapons/ARWeaponBase.h | 33 ++++ .../Weapons/ARWeaponManagerComponent.cpp | 182 +++++++++++++++--- .../Weapons/ARWeaponManagerComponent.h | 32 ++- .../Weapons/ARWeaponPawnManagerComponent.cpp | 90 ++++++--- .../Weapons/ARWeaponPawnManagerComponent.h | 23 ++- 19 files changed, 465 insertions(+), 91 deletions(-) create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponBase.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponBase.h diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 16ddb24..e739edd 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -7,6 +7,8 @@ NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") ++GameplayTagList=(Tag="Ability.Input.GolsterWeapon",DevComment="") ++GameplayTagList=(Tag="Ability.Input.HolsterWeapon",DevComment="") +GameplayTagList=(Tag="Ability.Input.Jump",DevComment="") +GameplayTagList=(Tag="Ability.Input.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.Input.PreviousWeapon",DevComment="") @@ -37,6 +39,7 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") ++GameplayTagList=(Tag="Input.UI.Holster",DevComment="") +GameplayTagList=(Tag="Input.UI.WeaponNext",DevComment="") +GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 0638191..4334455 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -48,6 +48,7 @@ DefaultViewportMouseLockMode=LockOnCapture +ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="Input.UI.WeaponPrevious",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +ActionMappings=(ActionName="InputInventory",Key=I,bShift=False,bCtrl=False,bAlt=False,bCmd=False) ++ActionMappings=(ActionName="Input.UI.Holster",Key=O,bShift=False,bCtrl=False,bAlt=False,bCmd=False) +AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) +AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) +AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index f5b9701..c05c200 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -1036,6 +1036,10 @@ bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(FGameplayTag InAbil void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar) { + if (AbilityContainer.AbilityExists(InAbilityTag)) + { + return; + } if (GetOwnerRole() < ENetRole::ROLE_Authority) { return; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 21e7eb2..bc7c20e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -173,7 +173,10 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer void HandleInputReleased(FGameplayTag ActionName); void TriggerAbylityByTag(FGameplayTag InTag); - + bool AbilityExists(const FGameplayTag& AbilityTag) const + { + return AbilitiesInputs.Contains(AbilityTag); + } bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 0deb51e..fcd8ad0 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -105,7 +105,7 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit IAbilityInput = GetInputTag(InGroup, InSlot); FAFOnAbilityReady del; - if (IsClient()) + //if (IsClient()) { del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, IAbilityInput, InGroup, InSlot); diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index f793841..3292301 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -92,7 +92,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent TArray> AbilityTagsSet; TArray>> AbilitySet; - + TArray> ValidGroups; TMap AbilityReadyEvents; DECLARE_DELEGATE_TwoParams(FGroupConfirmDelegate, int32, bool) diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 1b9966c..25a4062 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -10,6 +10,8 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" +#include "Weapons/ARWeaponBase.h" + #include "Weapons/ARWeaponPawnManagerComponent.h" #include "ARPlayerController.h" @@ -57,29 +59,29 @@ AARCharacter::AARCharacter() Weapons = CreateDefaultSubobject(TEXT("Weapons")); - HolsteredRightWeapon = CreateDefaultSubobject(TEXT("HolsteredRightWeapon")); + WeaponHolsteredRight = CreateDefaultSubobject(TEXT("WeaponHolsteredRight")); //HolsteredRightWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform); - HolsteredRightWeapon->SetupAttachment(GetMesh(), WeaponSocket::HolsteredRightWeapon); + WeaponHolsteredRight->SetupAttachment(GetMesh(), WeaponSocket::HolsteredRightWeapon); - HolsteredLeftWeapon = CreateDefaultSubobject(TEXT("HolsteredLeftWeapon")); + WeaponHolsteredLeft = CreateDefaultSubobject(TEXT("WeaponHolsteredLeft")); //HolsteredLeftWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); - HolsteredLeftWeapon->SetupAttachment(GetMesh(), WeaponSocket::HolsteredLeftWeapon); + WeaponHolsteredLeft->SetupAttachment(GetMesh(), WeaponSocket::HolsteredLeftWeapon); - HolsteredBackDownWeapon = CreateDefaultSubobject(TEXT("HolsteredBackDownWeapon")); + HolsteredBackDown = CreateDefaultSubobject(TEXT("HolsteredBackDown")); //HolsteredBackDownWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); - HolsteredBackDownWeapon->SetupAttachment(GetMesh()); + HolsteredBackDown->SetupAttachment(GetMesh()); - HolsteredSideLeftWeapon = CreateDefaultSubobject(TEXT("HolsteredSideLeftWeapon")); + WeaponHolsteredSideLeft = CreateDefaultSubobject(TEXT("WeaponHolsteredSideLeft")); //HolsteredSideLeftWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); - HolsteredSideLeftWeapon->SetupAttachment(GetMesh()); + WeaponHolsteredSideLeft->SetupAttachment(GetMesh()); - EquipedMainWeapon = CreateDefaultSubobject(TEXT("EquipedMainWeapon")); + WeaponEquipedMain = CreateDefaultSubobject(TEXT("WeaponEquipedMain")); //EquipedMainWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); - EquipedMainWeapon->SetupAttachment(GetMesh(), WeaponSocket::EquipedMainWeapon); + WeaponEquipedMain->SetupAttachment(GetMesh(), WeaponSocket::EquipedMainWeapon); @@ -229,4 +231,26 @@ void AARCharacter::OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EU CameraTransform.ForwardVector = FollowCamera->GetForwardVector(); CameraTransform.Location = FollowCamera->GetComponentLocation(); //Multicast_CameraTransform(CamTransform); +} + +class AARWeaponBase* AARCharacter::GetMainWeapon() const +{ + return GetMainWeapon(); +} + +USkeletalMeshComponent* AARCharacter::GetMainWeaponMesh() const +{ + if (!GetEquipedMainWeapon()->GetChildActor()) + return nullptr; + + return GetMainWeapon()->GetMesh(); +} + +FVector AARCharacter::GetMainWeaponSocket(const FName& Socket) const +{ + USkeletalMeshComponent* Component = GetMainWeaponMesh(); + if (!Component) + return GetMesh()->GetSocketLocation(TEXT("headSocket")); + + return Component->GetSocketLocation(Socket); } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 6b1ec44..5ff09c8 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "GameFramework/Character.h" +#include "Components/ChildActorComponent.h" #include "GameplayTags.h" #include "AFAbilityComponent.h" #include "AFAbilityInterface.h" @@ -50,16 +51,16 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface //Weapons UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) - USkeletalMeshComponent* HolsteredRightWeapon; + UChildActorComponent* WeaponHolsteredRight; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) - USkeletalMeshComponent* HolsteredLeftWeapon; + UChildActorComponent* WeaponHolsteredLeft; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) - USkeletalMeshComponent* HolsteredBackDownWeapon; + UChildActorComponent* HolsteredBackDown; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) - USkeletalMeshComponent* HolsteredSideLeftWeapon; + UChildActorComponent* WeaponHolsteredSideLeft; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) - USkeletalMeshComponent* EquipedMainWeapon; + UChildActorComponent* WeaponEquipedMain; public: UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") @@ -143,14 +144,41 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface return Weapons; } - inline USkeletalMeshComponent* GetHolsteredRightWeapon() + inline UChildActorComponent* GetHolsteredRightWeapon() { - return HolsteredRightWeapon; + return WeaponHolsteredRight; + } + inline UChildActorComponent* GetHolsteredLeftWeapon() + { + return WeaponHolsteredLeft; + } + inline UChildActorComponent* GetHolsteredBackDownWeapon() + { + return HolsteredBackDown; + } + inline UChildActorComponent* GetHolsteredSideLeftWeapon() + { + return WeaponHolsteredSideLeft; } - inline USkeletalMeshComponent* GetEquipedMainWeapon() + inline UChildActorComponent* GetEquipedMainWeapon() const { - return EquipedMainWeapon; + return WeaponEquipedMain; } + + template + T* GetMainWeapon() const + { + return Cast(GetEquipedMainWeapon()->GetChildActor()); + } + + UFUNCTION(BlueprintPure, Category = "Character | Weapons") + class AARWeaponBase* GetMainWeapon() const; + + UFUNCTION(BlueprintPure, Category = "Character | Weapons") + USkeletalMeshComponent* GetMainWeaponMesh() const; + + UFUNCTION(BlueprintPure, Category = "Character | Weapons") + FVector GetMainWeaponSocket(const FName& Socket) const; }; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 5f9de16..751068d 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -20,6 +20,7 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); AbilityManager->ComponentTags.Add(TEXT("AbilityManager")); + bInputBount = false; } void AARPlayerController::SetPawn(APawn* InPawn) @@ -37,10 +38,18 @@ void AARPlayerController::SetPawn(APawn* InPawn) if (!AbilityComp) return; - AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); - AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); - AbilityManager->BindInputs(InputComponent, AbilityComp); - WeaponManager->BindInputs(InputComponent, AbilityComp); + if (!bInputBount) + { + AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); + AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); + AbilityComp->BindAbilityToAction(InputComponent, InputHolsterWeapon); + InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); + InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); + + AbilityManager->BindInputs(InputComponent, AbilityComp); + WeaponManager->BindInputs(InputComponent, AbilityComp); + bInputBount = true; + } //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); @@ -54,8 +63,13 @@ void AARPlayerController::SetPawn(APawn* InPawn) PrevWeap.Add(InputPreviousWeapon); AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); - InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); - InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); + FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytHolstersWeapon, InputHolsterWeapon); + AbilityComp->AddOnAbilityReadyDelegate(AbilitytHolstersWeapon, del3); + TArray HolsterInput; + HolsterInput.Add(InputHolsterWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytHolstersWeapon, nullptr, HolsterInput); + + } WeaponManager->POwner = InPawn; //UIAbilityManagerComponent->BindInputs(); diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 9fe3efb..413a8fd 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -33,6 +33,12 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag AbilitytPreviousWeapon; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag InputHolsterWeapon; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag AbilitytHolstersWeapon; + + bool bInputBount; public: AARPlayerController(const FObjectInitializer& ObjectInitializer); virtual void SetPawn(APawn* InPawn) override; diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp index 18272af..41a0521 100644 --- a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp @@ -1,3 +1,10 @@ #include "ARAbilityAttributes.h" +void UARAbilityAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + DOREPLIFETIME_CONDITION(UARAbilityAttributes, CastTime, COND_OwnerOnly); + DOREPLIFETIME_CONDITION(UARAbilityAttributes, Cooldown, COND_OwnerOnly); + DOREPLIFETIME_CONDITION(UARAbilityAttributes, BaseDamage, COND_OwnerOnly); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h index e2703f7..6973f04 100644 --- a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h +++ b/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h @@ -14,11 +14,11 @@ class ACTIONRPGGAME_API UARAbilityAttributes : public UGAAttributesBase { GENERATED_BODY() public: - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase CastTime; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase Cooldown; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase BaseDamage; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index ff29eaa..63c6f60 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -17,8 +17,17 @@ class ACTIONRPGGAME_API UARItemWeapon : public UObject public: UPROPERTY(EditAnywhere, Category = "Ability") FGameplayTag Ability; - UPROPERTY(EditAnywhere, Category = "Visual") - TSoftObjectPtr WeaponMesh; - + UPROPERTY(EditAnywhere, Category = "Visual") + TSoftClassPtr Weapon; + + UPROPERTY(EditAnywhere, Category = "Transforms") + FVector HolsteredPosition; + UPROPERTY(EditAnywhere, Category = "Transforms") + FRotator HolsteredRotation; + + UPROPERTY(EditAnywhere, Category = "Transforms") + FVector EquipedPosition; + UPROPERTY(EditAnywhere, Category = "Transforms") + FRotator EquipedRotation; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp new file mode 100644 index 0000000..a2efacb --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponBase.h" + +#include "Components/SkeletalMeshComponent.h" +// Sets default values +AARWeaponBase::AARWeaponBase() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + + Mesh = CreateDefaultSubobject(TEXT("Mesh")); + SetRootComponent(Mesh); +} + +// Called when the game starts or when spawned +void AARWeaponBase::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AARWeaponBase::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Weapons/ARWeaponBase.h new file mode 100644 index 0000000..d6d4e29 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponBase.h @@ -0,0 +1,33 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "ARWeaponBase.generated.h" + +UCLASS() +class ACTIONRPGGAME_API AARWeaponBase : public AActor +{ + GENERATED_BODY() +private: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class USkeletalMeshComponent* Mesh; +public: + // Sets default values for this actor's properties + AARWeaponBase(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + class USkeletalMeshComponent* GetMesh() + { + return Mesh; + } +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index f24e054..9c65f79 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -5,6 +5,7 @@ #include "AFAbilityComponent.h" #include "ARWeaponAbilityBase.h" #include "ARItemWeapon.h" +#include "../ARCharacter.h" #include "Engine/World.h" // Sets default values for this component's properties @@ -64,8 +65,12 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, AARCharacter* Character = Cast(POwner); if (Character) { - Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()->WeaponMesh); + Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()); + ActiveGroup = EAMGroup::Group005; } + NativeEquipAbility(WeaponClasses[Idx].GetDefaultObject()->Ability, + Group, EAMSlot::Slot001, POwner); + if (IsClient()) { ServerAddWeaponToManager(Group, Slot, Idx); @@ -80,7 +85,8 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (!ABInt) return; - Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()->WeaponMesh); + Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()); + ActiveGroup = EAMGroup::Group005; } } @@ -96,58 +102,188 @@ bool UARWeaponManagerComponent::ServerAddWeaponToManager_Validate(EAMGroup Group void UARWeaponManagerComponent::NextWeapon() { FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - NextGroup(); + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex++; + if (CurrentIndex > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } + + if (ActiveGroup < AMIntToEnum(Groups.Num())) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + } + FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { NextWeaponAbility = FindNextValid(); } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNextWeapon(AMEnumToInt(ActiveGroup)); + } + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); } void UARWeaponManagerComponent::PreviousWeapon() { FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - PreviousGroup(); + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex--; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (CurrentIndex < 0) + { + ActiveGroup = AMIntToEnum(Groups.Num() - 1); + } FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { NextWeaponAbility = FindPreviousValid(); } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerPreviousWeapon(static_cast(ActiveGroup)); + } + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); } +void UARWeaponManagerComponent::HolsterWeapon() +{ + ActiveGroup = EAMGroup::Group005; + if (AARCharacter* Character = Cast(POwner)) + { + Character->GetWeapons()->HolsterActive(ActiveGroup); + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerHolsterWeapon(static_cast(ActiveGroup)); + } +} -void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags) +void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponIndex) { - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex++; + if (CurrentIndex > MAX_WEAPONS) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } - //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); + if (ActiveGroup < AMIntToEnum(0)) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = EAMGroup::Group001; + } + } + + FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + if (!NextWeaponAbility.IsValid()) + { + NextWeaponAbility = FindNextValid(); + } + if (WeaponIndex == AMEnumToInt(ActiveGroup)) + { + ClientNextWeapon(AMEnumToInt(ActiveGroup), true); + } + else + { + ClientNextWeapon(AMEnumToInt(ActiveGroup), false); + } + + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +} +bool UARWeaponManagerComponent::ServerNextWeapon_Validate(int32 WeaponIndex) +{ + return true; } -void UARWeaponManagerComponent::OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) +void UARWeaponManagerComponent::ClientNextWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess) { if (bPredictionSuccess) return; +} - //something gone wrong.. we need to change weapon to correct one. - //we probabaly already changed. So just get current group. - FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - - //and then get correct one from server. - FGameplayTag NextWeaponAbility = GetAbilityTag(ValidGroup, EAMSlot::Slot001); - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +void UARWeaponManagerComponent::ServerPreviousWeapon_Implementation(int32 WeaponIndex) +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex--; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (CurrentIndex < 0) + { + ActiveGroup = AMIntToEnum(MAX_WEAPONS - 1); + } + FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + if (!NextWeaponAbility.IsValid()) + { + NextWeaponAbility = FindPreviousValid(); + } + //so Server index is different. Client might tried to cheat + //or sometrhing. We will override it. + //situation where client can chage multiple weapons within second + //should not have place, as there is animation and/or internal cooldown on weapon change. + //since it will be done trough ability. + if (ActiveGroup != AMIntToEnum(WeaponIndex)) + { + ClientNextGroup(AMEnumToInt(ActiveGroup), false); + } + else + { + ClientNextGroup(AMEnumToInt(ActiveGroup), true); + } +} +bool UARWeaponManagerComponent::ServerPreviousWeapon_Validate(int32 WeaponIndex) +{ + return true; } -void UARWeaponManagerComponent::OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) +void UARWeaponManagerComponent::ClientPreviousWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess) { if (bPredictionSuccess) return; +} - //something gone wrong.. we need to change weapon to correct one. - //we probabaly already changed. So just get current group. - FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); +void UARWeaponManagerComponent::ServerHolsterWeapon_Implementation(int32 WeaponIndex) +{ + ActiveGroup = EAMGroup::Group005; + if (AARCharacter* Character = Cast(POwner)) + { + Character->GetWeapons()->HolsterActive(ActiveGroup); + } +} +bool UARWeaponManagerComponent::ServerHolsterWeapon_Validate(int32 WeaponIndex) +{ + return true; +} - //and then get correct one from server. - FGameplayTag NextWeaponAbility = GetAbilityTag(ValidGroup, EAMSlot::Slot001); - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); +void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags) +{ + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + + //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); } void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag) @@ -165,7 +301,7 @@ void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTa AARCharacter* Character = Cast(POwner); if (Character) { - Character->GetWeapons()->Equip(ActiveGroup, WeaponClasses[0].GetDefaultObject()->WeaponMesh); + Character->GetWeapons()->Equip(ActiveGroup, WeaponClasses[0].GetDefaultObject()); } if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 791dced..25c8ef7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -43,6 +43,7 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp { GENERATED_BODY() protected: + static constexpr int32 MAX_WEAPONS = 4; //maximum weapon + empty hands UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> WeaponClasses; @@ -84,19 +85,44 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UFUNCTION(BlueprintCallable) void PreviousWeapon(); + UFUNCTION(BlueprintCallable) + void HolsterWeapon(); + +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerNextWeapon(int32 WeaponIndex); + void ServerNextWeapon_Implementation(int32 WeaponIndex); + bool ServerNextWeapon_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientNextWeapon(int32 WeaponIndex, bool bPredictionSuccess); + void ClientNextWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerPreviousWeapon(int32 WeaponIndex); + void ServerPreviousWeapon_Implementation(int32 WeaponIndex); + bool ServerPreviousWeapon_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientPreviousWeapon(int32 WeaponIndex, bool bPredictionSuccess); + void ClientPreviousWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerHolsterWeapon(int32 WeaponIndex); + void ServerHolsterWeapon_Implementation(int32 WeaponIndex); + bool ServerHolsterWeapon_Validate(int32 WeaponIndex); + + UFUNCTION() void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); +public: bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; protected: virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) override; - virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; - virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; - void EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag); FGameplayTag FindNextValid(); FGameplayTag FindPreviousValid(); + }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp index 6801e2d..0896886 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp @@ -1,7 +1,8 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARWeaponPawnManagerComponent.h" - +#include "Engine/AssetManager.h" +#include "ARItemWeapon.h" #include "../ARCharacter.h" // Sets default values for this component's properties @@ -25,7 +26,13 @@ void UARWeaponPawnManagerComponent::BeginPlay() Super::BeginPlay(); // ... - + if (AARCharacter* Character = Cast(GetOwner())) + { + GroupToComponent.Add(EAMGroup::Group001, Character->GetHolsteredRightWeapon()); + GroupToComponent.Add(EAMGroup::Group002, Character->GetHolsteredLeftWeapon()); + GroupToComponent.Add(EAMGroup::Group003, Character->GetHolsteredBackDownWeapon()); + GroupToComponent.Add(EAMGroup::Group004, Character->GetHolsteredSideLeftWeapon()); + } } @@ -33,19 +40,13 @@ void UARWeaponPawnManagerComponent::BeginPlay() void UARWeaponPawnManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) { Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - // ... } -void UARWeaponPawnManagerComponent::SetWeapon(TSoftObjectPtr InWeapon, USkeletalMeshComponent* Component) +void UARWeaponPawnManagerComponent::SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component) { - if (POwner) - { - if (AARCharacter* Character = Cast(POwner)) - { - Component->SetSkeletalMesh(InWeapon.Get()); - } - } + FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponPawnManagerComponent::AsynWeaponLoaded, Component, InWeapon); + UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); } void UARWeaponPawnManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const @@ -59,59 +60,98 @@ void UARWeaponPawnManagerComponent::GetLifetimeReplicatedProps(TArray< class FLi DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, MainHandWeapon, COND_SkipOwner); } -void UARWeaponPawnManagerComponent::Equip(EAMGroup Group, TSoftObjectPtr InWeapon) +void UARWeaponPawnManagerComponent::Equip(EAMGroup Group, class UARItemWeapon* InWeapon) { - MainHandWeapon.WeaponMesh = InWeapon; + MainHandWeapon.Weapon = InWeapon->Weapon; + MainHandWeapon.Position = InWeapon->EquipedPosition; + MainHandWeapon.Rotation = InWeapon->EquipedRotation; + MainHandWeapon.Group = Group; MainHandWeapon.RepCounter++; + WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); + WeaponHelper[AMEnumToInt(Group)]->RepCounter++; if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(InWeapon, Character->GetEquipedMainWeapon()); + SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + GroupToComponent[Group]->SetChildActorClass(nullptr); } } -void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, TSoftObjectPtr InWeapon) +void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) { - WeaponHelper[AMEnumToInt(Group)]->WeaponMesh = InWeapon; + WeaponHelper[AMEnumToInt(Group)]->Weapon = InWeapon->Weapon; + WeaponHelper[AMEnumToInt(Group)]->Position = InWeapon->HolsteredPosition; + WeaponHelper[AMEnumToInt(Group)]->Rotation = InWeapon->HolsteredRotation; + WeaponHelper[AMEnumToInt(Group)]->Group = Group; WeaponHelper[AMEnumToInt(Group)]->RepCounter++; if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(InWeapon, Character->GetHolsteredRightWeapon()); + //Character->GetHolsteredRightWeapon()->SetSkeletalMesh(nullptr); + SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); } } - -void UARWeaponPawnManagerComponent::OnRep_Group001HolsteredAttachment() +void UARWeaponPawnManagerComponent::HolsterActive(EAMGroup Group) { + WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Weapon = MainHandWeapon.Weapon; + WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Group = MainHandWeapon.Group; + WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->RepCounter++; + + MainHandWeapon.Weapon.Reset(); + MainHandWeapon.RepCounter++; + if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(Group001HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + SetWeapon(*WeaponHelper[AMEnumToInt(MainHandWeapon.Group)], GroupToComponent[MainHandWeapon.Group]); } } +void UARWeaponPawnManagerComponent::OnRep_Group001HolsteredAttachment() +{ + ///if (Group001HolsteredAttachment.WeaponMesh.IsPending()) + ///{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group001HolsteredAttachment, Character->GetHolsteredRightWeapon()); + } + ///} +} void UARWeaponPawnManagerComponent::OnRep_Group002HolsteredAttachment() { if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(Group002HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + SetWeapon(Group002HolsteredAttachment, Character->GetHolsteredLeftWeapon()); } } void UARWeaponPawnManagerComponent::OnRep_Group003HolsteredAttachment() { if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(Group003HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + SetWeapon(Group003HolsteredAttachment, Character->GetHolsteredRightWeapon()); } } void UARWeaponPawnManagerComponent::OnRep_Group004HolsteredAttachment() { if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(Group004HolsteredAttachment.WeaponMesh, Character->GetHolsteredRightWeapon()); + SetWeapon(Group004HolsteredAttachment, Character->GetHolsteredRightWeapon()); } } -void UARWeaponPawnManagerComponent::OnRep_MainHandWeapon() +void UARWeaponPawnManagerComponent::OnRep_MainHandWeapon(FARWeapon OldWeapon) { if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(MainHandWeapon.WeaponMesh, Character->GetHolsteredRightWeapon()); + SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + GroupToComponent[MainHandWeapon.Group]->SetChildActorClass(nullptr); } +} + +void UARWeaponPawnManagerComponent::AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon) +{ + Component->SetChildActorClass(InWeapon.Weapon.Get()); + + Component->SetRelativeLocation(FVector(0,0,0)); + Component->SetRelativeRotation(FRotator(0,0,0)); + + Component->SetRelativeLocation(InWeapon.Position); + Component->SetRelativeRotation(InWeapon.Rotation); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h index 3fe8827..25408e7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h @@ -18,10 +18,17 @@ struct FARWeapon GENERATED_BODY() public: UPROPERTY(EditAnywhere, Category = "Attachment Test") - TSoftObjectPtr WeaponMesh; + TSoftClassPtr Weapon; UPROPERTY(EditAnywhere, Category = "Attachment Test") FName SocketName; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + FVector Position; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + FRotator Rotation; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + EAMGroup Group; + UPROPERTY(EditAnywhere, Category = "Attachment Test") uint8 RepCounter; }; @@ -45,7 +52,7 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent UPROPERTY() class APawn* POwner; - TMap GroupToComponent; + TMap GroupToComponent; TArray WeaponHelper; @@ -62,15 +69,16 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - void Equip(EAMGroup Group, TSoftObjectPtr InWeapon); - void Holster(EAMGroup Group, TSoftObjectPtr InWeapon); + void Equip(EAMGroup Group, class UARItemWeapon* InWeapon); + void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); + void HolsterActive(EAMGroup Group); inline void SetPOwner(APawn* InPawn) { POwner = InPawn; } protected: - void SetWeapon(TSoftObjectPtr InWeapon, USkeletalMeshComponent* Component); + void SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component); UFUNCTION() void OnRep_Group001HolsteredAttachment(); UFUNCTION() @@ -81,5 +89,8 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent void OnRep_Group004HolsteredAttachment(); UFUNCTION() - void OnRep_MainHandWeapon(); + void OnRep_MainHandWeapon(FARWeapon OldWeapon); + + UFUNCTION() + void AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon); }; From 0aaa89c90c59a47ddea18e0c5fffde4393de4f9d Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Feb 2018 19:15:40 +0100 Subject: [PATCH 053/187] fixes for weapon swapping --- .../Weapons/ARWeaponManagerComponent.cpp | 69 +++++++++---------- .../Weapons/ARWeaponManagerComponent.h | 5 +- .../Weapons/ARWeaponPawnManagerComponent.cpp | 55 ++++++++++++++- .../Weapons/ARWeaponPawnManagerComponent.h | 1 + 4 files changed, 89 insertions(+), 41 deletions(-) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 9c65f79..cc0bc1e 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -22,7 +22,7 @@ UARWeaponManagerComponent::UARWeaponManagerComponent() void UARWeaponManagerComponent::BeginPlay() { Super::BeginPlay(); - + EquipedWeapons.SetNum(MAX_WEAPONS+1); APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) return; @@ -66,6 +66,7 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (Character) { Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()); + EquipedWeapons[AMEnumToInt(Group)] = WeaponClasses[Idx].GetDefaultObject(); ActiveGroup = EAMGroup::Group005; } NativeEquipAbility(WeaponClasses[Idx].GetDefaultObject()->Ability, @@ -86,6 +87,7 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, return; Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()); + EquipedWeapons[AMEnumToInt(Group)] = WeaponClasses[Idx].GetDefaultObject(); ActiveGroup = EAMGroup::Group005; } @@ -101,6 +103,7 @@ bool UARWeaponManagerComponent::ServerAddWeaponToManager_Validate(EAMGroup Group void UARWeaponManagerComponent::NextWeapon() { + EAMGroup OldGroup = ActiveGroup; FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); ENetMode NetMode = GetOwner()->GetNetMode(); if (NetMode == ENetMode::NM_Client @@ -108,7 +111,7 @@ void UARWeaponManagerComponent::NextWeapon() { int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex++; - if (CurrentIndex > Groups.Num()) + if (CurrentIndex > MAX_WEAPONS) { ActiveGroup = EAMGroup::Group001; } @@ -117,13 +120,6 @@ void UARWeaponManagerComponent::NextWeapon() ActiveGroup = AMIntToEnum(CurrentIndex); } - if (ActiveGroup < AMIntToEnum(Groups.Num())) - { - } - else - { - ActiveGroup = EAMGroup::Group001; - } } FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); @@ -136,10 +132,11 @@ void UARWeaponManagerComponent::NextWeapon() ServerNextWeapon(AMEnumToInt(ActiveGroup)); } - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility, OldGroup); } void UARWeaponManagerComponent::PreviousWeapon() { + EAMGroup OldGroup = ActiveGroup; FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex--; @@ -158,7 +155,7 @@ void UARWeaponManagerComponent::PreviousWeapon() ServerPreviousWeapon(static_cast(ActiveGroup)); } - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility, OldGroup); } void UARWeaponManagerComponent::HolsterWeapon() @@ -176,30 +173,20 @@ void UARWeaponManagerComponent::HolsterWeapon() void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponIndex) { + EAMGroup OldGroup = ActiveGroup; FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - int32 CurrentIndex = AMEnumToInt(ActiveGroup); + + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + if(WeaponIndex > CurrentIndex) CurrentIndex++; - if (CurrentIndex > MAX_WEAPONS) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - if (ActiveGroup < AMIntToEnum(0)) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = EAMGroup::Group001; - } + if (CurrentIndex > MAX_WEAPONS) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); } FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); @@ -216,7 +203,7 @@ void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponInde ClientNextWeapon(AMEnumToInt(ActiveGroup), false); } - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility); + EquipWeapon(CurrentWeaponAbility, NextWeaponAbility, OldGroup); } bool UARWeaponManagerComponent::ServerNextWeapon_Validate(int32 WeaponIndex) { @@ -231,12 +218,18 @@ void UARWeaponManagerComponent::ClientNextWeapon_Implementation(int32 WeaponInde void UARWeaponManagerComponent::ServerPreviousWeapon_Implementation(int32 WeaponIndex) { int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex--; - ActiveGroup = AMIntToEnum(CurrentIndex); + if(CurrentIndex > WeaponIndex) + CurrentIndex--; + if (CurrentIndex < 0) { ActiveGroup = AMIntToEnum(MAX_WEAPONS - 1); } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } + FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { @@ -286,7 +279,7 @@ void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); } -void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag) +void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag, EAMGroup OldGroup) { if (!NextWeaponTag.IsValid()) { @@ -301,7 +294,9 @@ void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTa AARCharacter* Character = Cast(POwner); if (Character) { - Character->GetWeapons()->Equip(ActiveGroup, WeaponClasses[0].GetDefaultObject()); + Character->GetWeapons()->EquipInactive(ActiveGroup, EquipedWeapons[AMEnumToInt(ActiveGroup)] + , OldGroup + , EquipedWeapons[AMEnumToInt(OldGroup)]); } if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 25c8ef7..9fbecdb 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -47,6 +47,9 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> WeaponClasses; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") + TArray EquipedWeapons; + UPROPERTY(EditAnywhere, Category = "Attachment Config") FName EquipSocketName; UPROPERTY(EditAnywhere, Category = "Attachment Config") @@ -120,7 +123,7 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) override; - void EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag); + void EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag, EAMGroup OldGroup); FGameplayTag FindNextValid(); FGameplayTag FindPreviousValid(); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp index 0896886..f91dc07 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp @@ -45,8 +45,20 @@ void UARWeaponPawnManagerComponent::TickComponent(float DeltaTime, ELevelTick Ti void UARWeaponPawnManagerComponent::SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component) { - FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponPawnManagerComponent::AsynWeaponLoaded, Component, InWeapon); - UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); + if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) + { + Component->SetChildActorClass(InWeapon.Weapon.Get()); + Component->SetRelativeLocation(FVector(0, 0, 0)); + Component->SetRelativeRotation(FRotator(0, 0, 0)); + + Component->SetRelativeLocation(InWeapon.Position); + Component->SetRelativeRotation(InWeapon.Rotation); + } + else + { + FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponPawnManagerComponent::AsynWeaponLoaded, Component, InWeapon); + UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); + } } void UARWeaponPawnManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const @@ -75,7 +87,43 @@ void UARWeaponPawnManagerComponent::Equip(EAMGroup Group, class UARItemWeapon* I GroupToComponent[Group]->SetChildActorClass(nullptr); } } +void UARWeaponPawnManagerComponent::EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon) +{ + if (InOldWeapon) + { + WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; + WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; + WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; + WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; + //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); + SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); + } + + MainHandWeapon.Weapon = WeaponHelper[AMEnumToInt(Group)]->Weapon; + MainHandWeapon.Position = InWeapon->EquipedPosition; + MainHandWeapon.Rotation = InWeapon->EquipedRotation; + MainHandWeapon.Group = Group; + MainHandWeapon.RepCounter++; + + WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); + WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + if(!InOldWeapon) + { + WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); + WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + } + if (AARCharacter* Character = Cast(POwner)) + { + + SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + //GroupToComponent[Group]->SetChildActorClass(nullptr); + } +} void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) { WeaponHelper[AMEnumToInt(Group)]->Weapon = InWeapon->Weapon; @@ -140,8 +188,9 @@ void UARWeaponPawnManagerComponent::OnRep_MainHandWeapon(FARWeapon OldWeapon) { if (AARCharacter* Character = Cast(POwner)) { + //SetWeapon(OldWeapon, GroupToComponent[OldWeapon.Group]); SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - GroupToComponent[MainHandWeapon.Group]->SetChildActorClass(nullptr); + //GroupToComponent[MainHandWeapon.Group]->SetChildActorClass(nullptr); } } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h index 25408e7..12e51f2 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h @@ -70,6 +70,7 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent void Equip(EAMGroup Group, class UARItemWeapon* InWeapon); + void EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon); void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); void HolsterActive(EAMGroup Group); inline void SetPOwner(APawn* InPawn) From aa97c83c0538896e9332142a56e505ae79248852 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sun, 11 Feb 2018 20:16:59 +0100 Subject: [PATCH 054/187] started refactoring of AbilityFramework to remove dead code and minimize publicly exposed state interaction --- ActionRPGGame.uproject | 328 +++++++++--------- .../AbilityFramework/AFAbilityComponent.cpp | 100 +++--- .../AbilityFramework/AFAbilityComponent.h | 13 +- .../Source/AbilityFramework/AFCueManager.cpp | 25 +- .../Source/AbilityFramework/AFCueManager.h | 11 +- .../Abilities/GAAbilityBase.cpp | 12 +- .../Abilities/GAAbilityBase.h | 2 +- .../Attributes/GAAttributeBase.cpp | 4 +- .../AFAttributeStongerOverride.cpp | 2 +- .../AFAtributeDurationAdd.cpp | 2 +- .../AFAttributeDurationOverride.cpp | 2 +- .../AFPeriodApplicationAdd.cpp | 4 +- .../AFPeriodApplicationExtend.cpp | 4 +- .../AFPeriodApplicationInfiniteAdd.cpp | 2 +- .../AFPeriodApplicationOverride.cpp | 4 +- .../Effects/GABlueprintLibrary.cpp | 52 ++- .../AbilityFramework/Effects/GAEffectCue.cpp | 11 - .../AbilityFramework/Effects/GAGameEffect.cpp | 159 ++++----- .../AbilityFramework/Effects/GAGameEffect.h | 116 +++++-- .../Source/AbilityFramework/GAGlobalTypes.cpp | 10 + .../Source/AbilityFramework/GAGlobalTypes.h | 32 +- .../AbilityManager/AbilityManager.Build.cs | 3 + Source/ActionRPGGame/ARCharacter.cpp | 14 +- .../Weapons/ARWeaponManagerComponent.cpp | 18 +- .../Weapons/ARWeaponPawnManagerComponent.cpp | 4 +- 25 files changed, 504 insertions(+), 430 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index afefb76..6dd6e58 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -3,164 +3,172 @@ "EngineAssociation": "{A36EBF10-476D-8159-343E-8FA796F9AC8F}", "Category": "", "Description": "", - "Modules": [ - { - "Name": "ActionRPGGame", - "Type": "Runtime", - "LoadingPhase": "Default", - "AdditionalDependencies": [ - "AbilityFramework", - "AbilityFrameworkDebugger", - "AbilityManager", - "Engine", - "AIModule", - "UMG", - "CoreUObject" - ] - }, - { - "Name": "ActionRPGGameEditor", - "Type": "Editor", - "LoadingPhase": "Default", - "AdditionalDependencies": [ - "AbilityFramework", - "AbilityFrameworkEditor", - "AbilityFrameworkDebugger", - "AbilityManager", - "Engine", - "AIModule", - "UMG", - "CoreUObject" - ] - } - ], - "Plugins" : [ - { - "Name": "ActorSequence", - "Enabled": true - }, - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "AbilityFrameworkDebugger", - "Enabled": true - }, - { - "Name": "AbilityManager", - "Enabled": true - }, - { - "Name": "ActorSequenceEditor", - "Enabled": true - }, - { - "Name": "ImagePlate", - "Enabled": true - }, - { - "Name": "PerformanceMonitor", - "Enabled": true - }, - { - "Name": "OnlineSubsystemAmazon", - "Enabled": true - }, - { - "Name": "OnlineFramework", - "Enabled": true - }, - { - "Name": "SteamVR", - "Enabled": false - }, - { - "Name": "OculusVR", - "Enabled": false - }, - { - "Name": "Niagara", - "Enabled": true - }, - { - "Name": "SoundUtilities", - "Enabled": true - }, - { - "Name": "SoundVisualizations", - "Enabled": true - }, - { - "Name": "BlueprintStats", - "Enabled": true - }, - { - "Name": "LocationServicesBPLibrary", - "Enabled": false - }, - { - "Name": "WindowsDeviceProfileSelector", - "Enabled": true - }, - { - "Name": "AndroidDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "IOSDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "AndroidMedia", - "Enabled": false - }, - { - "Name": "MobileLauncherProfileWizard", - "Enabled": false - }, - { - "Name": "MobilePatchingUtils", - "Enabled": false - }, - { - "Name": "AndroidMoviePlayer", - "Enabled": false - }, - { - "Name": "AppleMoviePlayer", - "Enabled": false - }, - { - "Name": "GoogleCloudMessaging", - "Enabled": false - }, - { - "Name": "OnlineSubsystemIOS", - "Enabled": false, - "SupportedTargetPlatforms": [ - "IOS", - "TVOS" - ] - }, - { - "Name": "OnlineSubsystemGooglePlay", - "Enabled": false, - "SupportedTargetPlatforms": [ - "Android" - ] - }, - { - "Name": "ApexDestruction", - "Enabled": true - }, - { - "Name": "AndroidPermission", - "Enabled": false - } - ], - "TargetPlatforms": [ - "LinuxNoEditor", - "WindowsNoEditor" - ] + "Modules": [ + { + "Name": "ActionRPGGame", + "Type": "Runtime", + "LoadingPhase": "Default", + "AdditionalDependencies": [ + "AbilityFramework", + "AbilityFrameworkDebugger", + "AbilityManager", + "Engine", + "AIModule", + "UMG", + "CoreUObject" + ] + }, + { + "Name": "ActionRPGGameEditor", + "Type": "Editor", + "LoadingPhase": "Default", + "AdditionalDependencies": [ + "AbilityFramework", + "AbilityFrameworkEditor", + "AbilityFrameworkDebugger", + "AbilityManager", + "Engine", + "AIModule", + "UMG", + "CoreUObject" + ] + } + ], + "Plugins": [ + { + "Name": "ActorSequence", + "Enabled": true + }, + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "AbilityFrameworkDebugger", + "Enabled": true + }, + { + "Name": "AbilityManager", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false + }, + { + "Name": "Niagara", + "Enabled": true + }, + { + "Name": "SoundUtilities", + "Enabled": true + }, + { + "Name": "SoundVisualizations", + "Enabled": true + }, + { + "Name": "BlueprintStats", + "Enabled": true + }, + { + "Name": "LocationServicesBPLibrary", + "Enabled": false + }, + { + "Name": "WindowsDeviceProfileSelector", + "Enabled": true + }, + { + "Name": "AndroidDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "IOSDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "AndroidMedia", + "Enabled": false + }, + { + "Name": "MobileLauncherProfileWizard", + "Enabled": false + }, + { + "Name": "MobilePatchingUtils", + "Enabled": false + }, + { + "Name": "AndroidMoviePlayer", + "Enabled": false + }, + { + "Name": "AppleMoviePlayer", + "Enabled": false + }, + { + "Name": "GoogleCloudMessaging", + "Enabled": false + }, + { + "Name": "OnlineSubsystemIOS", + "Enabled": false, + "SupportedTargetPlatforms": [ + "IOS", + "TVOS" + ] + }, + { + "Name": "OnlineSubsystemGooglePlay", + "Enabled": false, + "SupportedTargetPlatforms": [ + "Android" + ] + }, + { + "Name": "ApexDestruction", + "Enabled": true + }, + { + "Name": "AndroidPermission", + "Enabled": false + }, + { + "Name": "AppleARKit", + "Enabled": false + }, + { + "Name": "GLTFImporter", + "Enabled": true + } + ], + "TargetPlatforms": [ + "LinuxNoEditor", + "WindowsNoEditor" + ] } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index c05c200..9b19a70 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -181,6 +181,8 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); + FAFCueHandle CueHandle = FAFCueHandle::GenerateHandle(); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams; @@ -188,14 +190,14 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn CueParams.Causer = InContext.Causer; CueParams.HitResult = InContext.HitResult; CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.Period; - CueParams.Duration = InProperty.Duration; + CueParams.Period = InProperty.GetPeriod(); + CueParams.Duration = InProperty.GetDuration(); //if (mode == ENetMode::NM_Standalone // || role >= ENetRole::ROLE_Authority) { //AsyncTask(ENamedThreads::GameThread, [=]() //{ - MulticastApplyEffectCue(CueParams); + MulticastApplyEffectCue(CueParams, CueHandle); //}); } } @@ -223,10 +225,11 @@ FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn Handle = InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); if (!PropertyByHandle.Contains(Handle)) PropertyByHandle.Add(Handle, &InProperty); - + + EffectToCue.Add(Handle, CueHandle); OnEffectAppliedToTarget.Broadcast(Handle); - if(InProperty.Duration == 0 - && InProperty.Period == 0) + if(InProperty.GetDuration() == 0 + && InProperty.GetPeriod() == 0) { OnEffectRemoved.Broadcast(Handle); } @@ -280,8 +283,13 @@ void UAFAbilityComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectPrope //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? Effect.OnExecuted(); - MulticastExecuteEffectCue(HandleIn); - InProperty.Execution->ExecuteEffect(HandleIn, Mod, HandleIn.GetContextRef(), InProperty, Modifier); + ExecuteEffectEvent(InProperty.GetSpec()->OnPeriodEvent); + + FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + if (CueHandle) + MulticastExecuteEffectCue(HandleIn, *CueHandle); + + InProperty.EffectExecution(HandleIn, Mod, HandleIn.GetContextRef(), Modifier); PostExecuteEffect(); } void UAFAbilityComponent::PostExecuteEffect() @@ -295,11 +303,11 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper HandleIn.GetEffectPtr()->OnExpired(); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); - + ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); if (mode == ENetMode::NM_DedicatedServer || mode == ENetMode::NM_ListenServer) { - ClientExpireEffect(InProperty.PredictionHandle); + ClientExpireEffect(InProperty.GetPredictionHandle()); } if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) @@ -309,24 +317,16 @@ void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProper CueParams.Causer = InContext.Causer; CueParams.HitResult = InContext.HitResult; CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.Period; - CueParams.Duration = InProperty.Duration; + CueParams.Period = InProperty.GetPeriod(); + CueParams.Duration = InProperty.GetDuration(); - //if (mode == ENetMode::NM_Standalone - // || role >= ENetRole::ROLE_Authority) - { - MulticastRemoveEffectCue(CueParams); - } - } -// if (role < ENetRole::ROLE_Authority -// || mode == ENetMode::NM_Standalone) - { - FAFEffectRepInfo* RepInfo = GameEffectContainer.GetReplicationInfo(HandleIn); - if (RepInfo) + FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + if(CueHandle) { - RepInfo->OnExpired(); + MulticastRemoveEffectCue(CueParams, *CueHandle); } } + TArray handles = GameEffectContainer.RemoveEffect(InProperty); for (const FGAEffectHandle& Handle : handles) { @@ -342,28 +342,24 @@ void UAFAbilityComponent::ClientExpireEffect_Implementation(FAFPredictionHandle void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle) { - { - FAFEffectRepInfo* RepInfo = GameEffectContainer.GetReplicationInfo(InHandle); - if (RepInfo && - (RepInfo->Type == ERepInfoType::LocallyPredicted - || RepInfo->Type == ERepInfoType::Server)) - { - RepInfo->OnExpired(); - } - } - if (GetOwnerRole() == ENetRole::ROLE_Authority - || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + //if (GetOwnerRole() == ENetRole::ROLE_Authority + // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) { InternalRemoveEffect(InProperty, InContext); } + ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); FGAEffectCueParams CueParams; CueParams.Instigator = InContext.Instigator; CueParams.Causer = InContext.Causer; CueParams.HitResult = InContext.HitResult; CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.Period; - CueParams.Duration = InProperty.Duration; - MulticastRemoveEffectCue(CueParams); + CueParams.Period = InProperty.GetPeriod(); + CueParams.Duration = InProperty.GetDuration(); + FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); + if (CueHandle) + { + MulticastRemoveEffectCue(CueParams, *CueHandle); + } } void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) @@ -378,8 +374,8 @@ void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProper CueParams.Causer = InContext.Causer; CueParams.HitResult = InContext.HitResult; CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.Period; - CueParams.Duration = InProperty.Duration; + CueParams.Period = InProperty.GetPeriod(); + CueParams.Duration = InProperty.GetDuration(); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); if (mode == ENetMode::NM_Standalone @@ -397,12 +393,12 @@ void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProper } -void UAFAbilityComponent::MulticastApplyEffectCue_Implementation( FGAEffectCueParams CueParams) +void UAFAbilityComponent::MulticastApplyEffectCue_Implementation( FGAEffectCueParams CueParams, FAFCueHandle InHandle) { ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); if(mode == ENetMode::NM_Standalone - || mode != ENetMode::NM_DedicatedServer) + || role != ENetRole::ROLE_Authority) { FString prefix = ""; if (mode == ENetMode::NM_Client) @@ -420,23 +416,29 @@ void UAFAbilityComponent::MulticastApplyEffectCue_Implementation( FGAEffectCuePa *CueParams.Instigator->GetName() ); - UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams); + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); } } -void UAFAbilityComponent::MulticastExecuteEffectCue_Implementation(FGAEffectHandle EffectHandle) +void UAFAbilityComponent::MulticastExecuteEffectCue_Implementation(FGAEffectHandle EffectHandle, FAFCueHandle InHandle) { - // ActiveCues.ExecuteCue(EffectHandle); + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleExecuteCue(InHandle); + } } -void UAFAbilityComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams) +void UAFAbilityComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) { ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); - //if (mode == ENetMode::NM_Standalone - // || role != ENetRole::ROLE_Authority) + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) { - UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams); + UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams, InHandle); } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index bc7c20e..ee53e6c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -339,6 +339,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, //Maps effect handles to Properties from which effect was created. //usefull when all we have is handle or PredictionHandle. TMap PropertyByHandle; + + TMap EffectToCue; FAFEffectRepInfoDelegate OnEffectRepInfoApplied; FAFEffectRepInfoDelegate OnEffectRepInfoRemoved; @@ -484,14 +486,15 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, */ UFUNCTION(NetMulticast, Unreliable) - void MulticastApplyEffectCue(FGAEffectCueParams CueParams); - virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams); + void MulticastApplyEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); UFUNCTION(NetMulticast, Unreliable) - void MulticastExecuteEffectCue(FGAEffectHandle EffectHandle); + void MulticastExecuteEffectCue(FGAEffectHandle EffectHandle, FAFCueHandle InHandle); + void MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); UFUNCTION(NetMulticast, Unreliable) - void MulticastRemoveEffectCue(FGAEffectCueParams CueParams); + void MulticastRemoveEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); UFUNCTION(NetMulticast, Unreliable) void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); @@ -678,6 +681,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, OnEffectEvent.Remove(InEventTag); } + /*UFUNCTION(NetMulticast, Reliable) + MulticastExecuteEffect()*/ TMap OnEffectApplyToSelf; TMap OnEffectApplyToTarget; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp index 316df5a..c988060 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp @@ -77,7 +77,7 @@ void UAFCueManager::HandleOnPIEEnd(bool InVal) } } - + ActiveCues.Empty(); InstancedCues.Empty(); UsedCues.Empty(); } @@ -140,7 +140,7 @@ void UAFCueManager::HandlePostLoadMap(UWorld* InWorld) void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams) + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) { if (!CurrentWorld) CurrentWorld = CueParams.Instigator->GetWorld(); @@ -152,7 +152,7 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, { AGAEffectCue* actor = nullptr; - + ENetRole mode = CueParams.Instigator->GetRemoteRole(); TUniquePtr>& Cues = InstancedCues.FindOrAdd(CueTag); if (Cues.IsValid()) { @@ -170,6 +170,7 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, } if (actor) { + ActiveCues.Add(InHandle, actor); actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.GetActor(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); } return;//don't try to load asset, we already have pooled instance. @@ -187,7 +188,7 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, FPrimaryAssetTypeInfo Info; if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams, InHandle); Manager->LoadPrimaryAsset(PrimaryAssetId, TArray(), @@ -196,10 +197,20 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, } } } +void UAFCueManager::HandleExecuteCue(FAFCueHandle InHandle) +{ + AGAEffectCue** Cue = ActiveCues.Find(InHandle); + if (Cue) + { + AGAEffectCue* cue = *Cue; + cue->NativeOnExecuted(); + } +} void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag , FPrimaryAssetId InPrimaryAssetId - , FGAEffectCueParams CueParams) + , FGAEffectCueParams CueParams + , FAFCueHandle InHandle) { if (UAssetManager* Manager = UAssetManager::GetIfValid()) { @@ -283,6 +294,7 @@ void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag if (actor) { + ActiveCues.Add(InHandle, actor); actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); } @@ -295,7 +307,7 @@ void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag } void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams) + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) { if (!CurrentWorld) CurrentWorld = CueParams.Instigator->GetWorld(); @@ -321,6 +333,7 @@ void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, if (actor) { + ActiveCues.Remove(InHandle); Cues->Enqueue(actor); actor->NativeOnRemoved(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h index aed97c7..86bb9c7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h @@ -27,6 +27,9 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject //store per instigator ? Causer ? //stores used cues. TMap>>> UsedCues; + + TMap ActiveCues; + public: void Initialize(); #if WITH_EDITOR @@ -38,11 +41,13 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject public: static UAFCueManager* Get(); void HandleCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams); + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); + void HandleExecuteCue(FAFCueHandle InHandle); void HandleRemoveCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams); + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); protected: void OnFinishedLoad(FGameplayTag InCueTag , FPrimaryAssetId InPrimaryAssetId - , FGAEffectCueParams CueParams); + , FGAEffectCueParams CueParams + , FAFCueHandle InHandle); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index da94213..6d2bc3f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -159,11 +159,12 @@ void UGAAbilityBase::TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbi void UGAAbilityBase::InitAbility() { //still want to initialize, as Spec is used in multiple places. - ActivationEffect.InitializeIfNotInitialized(); - CooldownEffect.InitializeIfNotInitialized(); - AttributeCost.InitializeIfNotInitialized(); - AbilityAttributeCost.InitializeIfNotInitialized(); DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)); + ActivationEffect.InitializeIfNotInitialized(DefaultContext); + CooldownEffect.InitializeIfNotInitialized(DefaultContext); + AttributeCost.InitializeIfNotInitialized(DefaultContext); + AbilityAttributeCost.InitializeIfNotInitialized(DefaultContext); + if (AbilityComponent) { World = AbilityComponent->GetWorld(); @@ -607,7 +608,7 @@ bool UGAAbilityBase::IsOnCooldown() bool UGAAbilityBase::IsActivating() { bool bAbilityActivating = false; - bool bHaveEffect = AbilityComponent->IsEffectActive(ActivationEffect.Handle); + bool bHaveEffect = AbilityComponent->IsEffectActive(ActivationEffect.GetHandle(this)); bool bInActivatingState = AbilityState == EAFAbilityState::Activating; UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); bAbilityActivating = bHaveEffect || bInActivatingState; @@ -676,6 +677,7 @@ void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty DOREPLIFETIME(UGAAbilityBase, POwner); DOREPLIFETIME(UGAAbilityBase, PCOwner); DOREPLIFETIME(UGAAbilityBase, AICOwner); + DOREPLIFETIME(UGAAbilityBase, AvatarActor); //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 776d515..7da25e6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -179,7 +179,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask It will need some common interfaces for getting data out. */ - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") class AActor* AvatarActor; UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp index 7142125..c263ee9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -189,8 +189,8 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& ExtensionClass.GetDefaultObject()->OnPreAttributeModify(CurrentValue); } float returnValue = -1; - bool isPeriod = InProperty.Period > 0; - bool IsDuration = InProperty.Duration > 0; + bool isPeriod = InProperty.GetPeriod() > 0; + bool IsDuration = InProperty.GetDuration() > 0; if ( !isPeriod & IsDuration) { FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp index 2e1ca83..aa16de6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp @@ -14,7 +14,7 @@ bool UAFAttributeStongerOverride::CanApply(FGAEffect* EffectIn, FGAEffectPropert const FGAEffectHandle& InHandle) { bool bCanApply = true; - FGAAttribute Attribute = InProperty.Spec->AtributeModifier.Attribute; + FGAAttribute Attribute = InProperty.GetSpec()->AtributeModifier.Attribute; FAFAttributeBase* AttributePtr = EffectIn->Context.TargetInterface->GetAttribute(Attribute); if (AttributePtr) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp index 2743ce4..9aa1689 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -17,7 +17,7 @@ bool UAFAtributeDurationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.Duration, false); + InProperty.GetDuration(), false); InContainer->AddEffect(InProperty, InHandle); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp index 1da6d76..3e8e5a6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -32,7 +32,7 @@ bool UAFAttributeDurationOverride::ApplyEffect(const FGAEffectHandle& InHandle, FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.Duration, false); + InProperty.GetDuration(), false); InContainer->AddEffect(InProperty, InHandle); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp index a820ad7..68fcced 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -15,13 +15,13 @@ bool UAFPeriodApplicationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struc FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.Duration, false); + InProperty.GetDuration(), false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.Period, true); + InProperty.GetPeriod(), true); InContainer->AddEffect(InProperty, InHandle); //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index 034d4c6..721992d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -32,13 +32,13 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.Duration, false); + InProperty.GetDuration(), false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.Period, true); + InProperty.GetPeriod(), true); InContainer->AddEffect(InProperty, InHandle); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp index 567f2cd..80f932a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -15,7 +15,7 @@ bool UAFPeriodApplicationInfiniteAdd::ApplyEffect(const FGAEffectHandle& InHandl FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.Period, true); + InProperty.GetPeriod(), true); InContainer->AddEffect(InProperty, InHandle, true); //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp index 5afd83d..18e18f9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -24,13 +24,13 @@ bool UAFPeriodApplicationOverride::ApplyEffect(const FGAEffectHandle& InHandle, FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.Duration, false); + InProperty.GetDuration(), false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.Period, true); + InProperty.GetPeriod(), true); InContainer->AddEffect(InProperty, InHandle); //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 284edee..f24b567 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -47,8 +47,8 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); return FGAEffectHandle(); } - - InEffect.InitializeIfNotInitialized(); + FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + InEffect.InitializeIfNotInitialized(Context); if (!InEffect.IsInitialized()) { @@ -56,22 +56,8 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, return FGAEffectHandle(); } - FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - //FAFQueueApplyEffect QueuedEffect; - //QueuedEffect.Effect = &InEffect; - //QueuedEffect.Target = Target; - //QueuedEffect.Causer = Causer; - //QueuedEffect.Instigator = Instigator; - //QueuedEffect.HitIn = HitIn; - //QueuedEffect.Modifier = Modifier; - // - //Context.InstigatorComp->QueuedEffects.Enqueue(QueuedEffect); - //return FGAEffectHandle(); - /*if (!Context.IsValid()) - { - return FGAEffectHandle(); - }*/ + UAFAbilityComponent* Target2 = Context.TargetComp.Get(); if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) { @@ -82,13 +68,11 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, return FGAEffectHandle(); } UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); - InEffect.Duration = InEffect.GetSpec()->Duration.GetFloatValue(Context); - InEffect.Period = InEffect.GetSpec()->Period.GetFloatValue(Context); FGAEffect* effect = nullptr; - if (InEffect.Duration <= 0 && InEffect.Period <= 0) + if (InEffect.GetDuration() <= 0 && InEffect.GetPeriod() <= 0) { - if (!InEffect.Handle.IsValid()) + if (!InEffect.IsHandleValid(Target)) { effect = new FGAEffect(InEffect.GetSpec(), Context); AddTagsToEffect(effect); @@ -97,7 +81,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, } else { - effect = InEffect.Handle.GetEffectPtr().Get(); + effect = InEffect.GetHandle(Target).GetEffectPtr().Get(); } } else @@ -116,7 +100,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, } } FGAEffectHandle Handle = Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); - if (InEffect.Duration > 0 || InEffect.Period > 0) + if (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0) { InEffect.AddHandle(Context.Target.Get(), Handle); } @@ -133,8 +117,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); return FGAEffectHandle(); } - - InEffect->InitializeIfNotInitialized(); + FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + + InEffect->InitializeIfNotInitialized(Context); if (!InEffect->IsInitialized()) { @@ -142,7 +127,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, return FGAEffectHandle(); } - FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + /*if (!Context.IsValid()) { @@ -158,13 +143,11 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, return FGAEffectHandle(); } UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); - InEffect->Duration = InEffect->GetSpec()->Duration.GetFloatValue(Context); - InEffect->Period = InEffect->GetSpec()->Period.GetFloatValue(Context); FGAEffect* effect = nullptr; - if (InEffect->Duration <= 0 && InEffect->Period <= 0) + if (InEffect->GetDuration() <= 0 && InEffect->GetPeriod() <= 0) { - if (!InEffect->Handle.IsValid()) + if (!InEffect->IsHandleValid(Target)) { effect = new FGAEffect(InEffect->GetSpec(), Context); AddTagsToEffect(effect); @@ -173,7 +156,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, } else { - effect = InEffect->Handle.GetEffectPtr().Get(); + effect = InEffect->GetHandle(Target).GetEffectPtr().Get(); } } else @@ -192,7 +175,12 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, } } - return Context.InstigatorComp->ApplyEffectToTarget(effect, *InEffect, Context, Modifier); + FGAEffectHandle Handle = Context.InstigatorComp->ApplyEffectToTarget(effect, *InEffect, Context, Modifier); + if (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0) + { + InEffect->AddHandle(Context.Target.Get(), Handle); + } + return Handle; } FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit(FGAEffectProperty& InEffect, const FHitResult& Target, class APawn* Instigator, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp index e742625..0564782 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp @@ -140,12 +140,6 @@ void AGAEffectCue::Tick( float DeltaTime ) void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, const FHitResult& HitInfo, const FGAEffectCueParams& CueParams) { - if (CueParams.Period > 0) - { - FTimerDelegate del = FTimerDelegate::CreateUObject(this, &AGAEffectCue::NativeOnExecuted); - FTimerManager& Timer = GetWorld()->GetTimerManager(); - Timer.SetTimer(PeriodTimer, del, CueParams.Period, true); - } BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); if (!SequencePlayer) { @@ -159,11 +153,6 @@ void AGAEffectCue::NativeOnExecuted() } void AGAEffectCue::NativeOnRemoved() { - FTimerManager& Timer = GetWorld()->GetTimerManager(); - Timer.ClearTimer(PeriodTimer); - SequencePlayer->JumpToPosition(0); - SequencePlayer->Stop(); - OnRemoved(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index c417bd2..e52f539 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -26,12 +26,46 @@ void FGAEffectProperty::Initialize() Execution = GetSpec()->ExecutionType.GetDefaultObject(); } } -void FGAEffectProperty::InitializeIfNotInitialized() +void FGAEffectProperty::InitializeIfNotInitialized(const FGAEffectContext& InContext) { if (!IsInitialized()) { Initialize(); } + if (Spec) + { + Duration = GetSpec()->Duration.GetFloatValue(InContext); + Period = GetSpec()->Period.GetFloatValue(InContext); + } +} +bool FGAEffectProperty::CanApply(FGAEffect* EffectIn + , struct FGAEffectContainer* InContainer + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + return ApplicationRequirement->CanApply(EffectIn, *this, InContainer, InContext, InHandle); +} +bool FGAEffectProperty::ApplyEffect(const FGAEffectHandle& InHandle + , struct FGAEffect* EffectIn + , struct FGAEffectContainer* InContainer + , const FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + return Application->ApplyEffect(InHandle, EffectIn, *this, InContainer, InContext, Modifier); +} +void FGAEffectProperty::ExecuteEffect(const FGAEffectHandle& InHandle + , const FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + Application->ExecuteEffect(InHandle, *this, InContext, Modifier); +} + +void FGAEffectProperty::EffectExecution(const FGAEffectHandle& HandleIn + , FGAEffectMod& ModIn + , FGAEffectContext& Context + , const FAFFunctionModifier& Modifier) +{ + Execution->ExecuteEffect(HandleIn, ModIn, Context, *this, Modifier); } FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, @@ -44,66 +78,10 @@ FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, floa { }; -void FAFEffectRepInfo::Init() -{ - FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - ENetRole role = OwningComoponent->GetOwnerRole(); - ENetMode mode = OwningComoponent->GetOwner()->GetNetMode(); - - FTimerDelegate PeriodDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnPeriod); - Timer.SetTimer(PeriodHandle, PeriodDuration, - PeriodTime, true); -} -void FAFEffectRepInfo::OnExpired() -{ - UE_LOG(AbilityFramework, Log, TEXT("Client FAFEffectRepInfo. OnExpired")); - OwningComoponent->ExecuteEffectEvent(GetSpec()->OnExpiredEvent); - - FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnExpired ")); - EffectInfoLog += Spec.GetDefaultObject()->EffectTag.ToString(); // GetEffectTag().ToString(); - AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); - FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - Timer.ClearTimer(ExpiredHandle); - Timer.ClearTimer(PeriodHandle); - //OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); - - OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); - OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); - OwningComoponent->RemoveEffectEvent(GetSpec()->OnRemovedEvent); -} -void FAFEffectRepInfo::OnPeriod() -{ - OwningComoponent->ExecuteEffectEvent(GetSpec()->OnPeriodEvent); -} -void FAFEffectRepInfo::OnRemoved() -{ - FString EffectInfoLog(TEXT("FAFEffectRepInfo::OnRemoved ")); - EffectInfoLog += GetEffectTag().ToString(); - AddLogDebugInfo(EffectInfoLog, OwningComoponent->GetWorld()); - FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - Timer.ClearTimer(ExpiredHandle); - Timer.ClearTimer(PeriodHandle); - OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); - - OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); - OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); - OwningComoponent->RemoveEffectEvent(GetSpec()->OnRemovedEvent); -} void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) { InArraySerializer.EffectInfos.Remove(Handle); - //InArraySerializer.OwningComponent->OnEffectRepInfoRemoved.Broadcast(this); - FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - Timer.ClearTimer(ExpiredHandle); - Timer.ClearTimer(PeriodHandle); - OwningComoponent->ExecuteEffectEvent(GetSpec()->OnRemovedEvent); - - OwningComoponent->RemoveEffectEvent(GetSpec()->OnExpiredEvent); - OwningComoponent->RemoveEffectEvent(GetSpec()->OnPeriodEvent); - OwningComoponent->RemoveEffectEvent(GetSpec()->OnRemovedEvent); - - OwningComoponent->OnEffectRemoved.Broadcast(Handle); } void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) { @@ -126,20 +104,6 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); Type = ERepInfoType::RemotePredicted; - //OwningComoponent->ExecuteEffectEvent(OnAppliedEvent); - - FTimerManager& Timer = OwningComoponent->GetWorld()->GetTimerManager(); - AppliedTime = OwningComoponent->GetWorld()->GetTimeSeconds(); - FTimerDelegate delDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnExpired); - Timer.SetTimer(ExpiredHandle, delDuration, - Duration, false); - - FTimerDelegate PeriodDuration = FTimerDelegate::CreateRaw(this, &FAFEffectRepInfo::OnPeriod); - Timer.SetTimer(PeriodHandle, PeriodDuration, - PeriodTime, true); - Handle.EffectPtr = MakeShareable(new FGAEffect(Spec.GetDefaultObject(), Context)); - OwningComoponent->OnEffectAppliedToTarget.Broadcast(Handle); - } void FAFEffectRepInfo::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) { @@ -394,8 +358,8 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr , const FAFFunctionModifier& Modifier) { FGAEffectHandle Handle; - bool bHasDuration = InProperty.Duration > 0; - bool bHasPeriod = InProperty.Period > 0; + bool bHasDuration = InProperty.GetDuration() > 0; + bool bHasPeriod = InProperty.GetPeriod() > 0; ENetRole role = OwningComponent->GetOwnerRole(); ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); @@ -403,17 +367,17 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr { Handle = FGAEffectHandle::GenerateHandle(EffectIn); } - if (InProperty.ApplicationRequirement->CanApply(EffectIn, InProperty, this, InContext, Handle)) + if (InProperty.CanApply(EffectIn, this, InContext, Handle)) { if(!bHasDuration && !bHasPeriod) //instatnt effect. { - if (InProperty.Handle.IsValid()) + if (InProperty.IsHandleValid(InContext.Target.Get())) { - if (InProperty.Application->ApplyEffect(InProperty.Handle, - EffectIn, InProperty, this, InContext)) + Handle = InProperty.GetHandle(InContext.Target.Get()); + if (InProperty.ApplyEffect(Handle, + EffectIn, this, InContext)) { - Handle = InProperty.Handle; - InProperty.Application->ExecuteEffect(InProperty.Handle, InProperty, InContext, Modifier); + InProperty.ExecuteEffect(Handle, InContext, Modifier); // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); } } @@ -421,23 +385,21 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr { Handle = FGAEffectHandle::GenerateHandle(EffectIn); EffectIn->Handle = Handle; - InProperty.Handle = Handle; - if (InProperty.Application->ApplyEffect(Handle, - EffectIn, InProperty, this, InContext)) + if (InProperty.ApplyEffect(Handle, + EffectIn, this, InContext)) { - InProperty.Application->ExecuteEffect(Handle, InProperty, InContext, Modifier); + InProperty.ExecuteEffect(Handle, InContext, Modifier); // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); } } - } else { EffectIn->Handle = Handle; - if (InProperty.Application->ApplyEffect(Handle, - EffectIn, InProperty, this, InContext)) + if (InProperty.ApplyEffect(Handle, + EffectIn, this, InContext)) { - InProperty.Application->ExecuteEffect(Handle, InProperty, InContext, Modifier); + InProperty.ExecuteEffect(Handle, InContext, Modifier); //generate it only on client, and apply prediction key from client. //if server replicates with valid key, then nothing happens. //if not we try to rewind effect application. @@ -452,15 +414,15 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr } - HandleByPrediction.Add(InProperty.PredictionHandle, Handle); - PredictionByHandle.Add(Handle, InProperty.PredictionHandle); + HandleByPrediction.Add(InProperty.GetPredictionHandle(), Handle); + PredictionByHandle.Add(Handle, InProperty.GetPredictionHandle()); EffectIn->OnApplied(); - if (InProperty.Spec->IfHaveTagEffect.RequiredTag.IsValid() - && InContext.TargetComp->HasTag(InProperty.Spec->IfHaveTagEffect.RequiredTag)) + if (InProperty.GetSpec()->IfHaveTagEffect.RequiredTag.IsValid() + && InContext.TargetComp->HasTag(InProperty.GetSpec()->IfHaveTagEffect.RequiredTag)) { - for (TSubclassOf& Effect : InProperty.Spec->IfHaveTagEffect.Effects) + for (TSubclassOf& Effect : InProperty.GetSpec()->IfHaveTagEffect.Effects) { FGAEffectProperty prop(Effect); UGABlueprintLibrary::ApplyEffect(prop, InContext.Target.Get(), InContext.Instigator.Get(), InContext.Causer.Get(), InContext.HitResult); @@ -480,7 +442,7 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c //add replication handle (and send it to server ?) const UWorld* World = OwningComponent->GetWorld(); - FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.Period, InProperty.Duration, 0, OwningComponent); + FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.GetPeriod(), InProperty.GetDuration(), 0, OwningComponent); if(bIsServer) { RepInfo->Type = ERepInfoType::Server; @@ -492,14 +454,13 @@ void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, c RepInfo->Spec = InProperty.GetClass(); RepInfo->Context = InHandle.GetContext(); RepInfo->Handle = InHandle; - RepInfo->PredictionHandle = InProperty.PredictionHandle; - RepInfo->Init(); + RepInfo->PredictionHandle = InProperty.GetPredictionHandle(); MarkItemDirty(*RepInfo); ActiveEffectInfos.Add(*RepInfo); MarkArrayDirty(); //predictevily add effect info ? - PredictedEffectInfos.Add(InProperty.PredictionHandle, RepInfo); + PredictedEffectInfos.Add(InProperty.GetPredictionHandle(), RepInfo); EffectInfos.Add(InHandle, RepInfo); } @@ -523,7 +484,7 @@ TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectPrope , const FGAEffectContext& InContext) { TSet Handles; - UGAGameEffectSpec* Spec = InProperty.Spec; + UGAGameEffectSpec* Spec = InProperty.GetSpec(); EGAEffectAggregation Aggregation = Spec->EffectAggregation; UClass* EffectClass = Spec->GetClass(); @@ -696,7 +657,7 @@ void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) { - UGAGameEffectSpec* Spec = InProperty.Spec; + UGAGameEffectSpec* Spec = InProperty.GetSpec(); EGAEffectAggregation Aggregation = Spec->EffectAggregation; //TSet* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); @@ -753,7 +714,7 @@ void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num) { - UGAGameEffectSpec* Spec = HandleIn.Spec; + UGAGameEffectSpec* Spec = HandleIn.GetSpec(); EGAEffectAggregation Aggregation = Spec->EffectAggregation; FObjectKey key(HandleIn.GetClass()); TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 9f82703..5c25281 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -326,7 +326,7 @@ USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectProperty { GENERATED_BODY() -public: +protected: UPROPERTY(EditAnywhere, Category = "Effect") FGAEffectClass SpecClass; @@ -340,7 +340,7 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty class UGAGameEffectSpec* Spec; UPROPERTY() FAFPredictionHandle PredictionHandle; - +protected: UPROPERTY() float Duration; UPROPERTY() @@ -352,7 +352,6 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty so we don't create new object every time instant effect is created as potentially there can be quite a lot of allocations. */ - FGAEffectHandle Handle; /* Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. @@ -362,6 +361,7 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty TMap Handles; TMap HandleToTarget; TMap Contexts; + TMap EffectCues; public: FGAEffectProperty() : ApplicationRequirement(nullptr), @@ -386,15 +386,42 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } UGAGameEffectSpec* GetSpec() const { return Spec; } + bool CanApply(FGAEffect* EffectIn + , struct FGAEffectContainer* InContainer + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle); + + bool ApplyEffect(const FGAEffectHandle& InHandle + , struct FGAEffect* EffectIn + , struct FGAEffectContainer* InContainer + , const FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + void ExecuteEffect(const FGAEffectHandle& InHandle + , const FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + void EffectExecution(const FGAEffectHandle& HandleIn + , FGAEffectMod& ModIn + , FGAEffectContext& Context + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + //intentionally non const. - FGAEffectHandle& GetHandleRef() { return Handle; } - void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; + //FGAEffectHandle& GetHandleRef() { return Handle; } + //void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} void Initialize(); - void InitializeIfNotInitialized(); - + void InitializeIfNotInitialized(const FGAEffectContext& InContext); + inline float GetPeriod() const + { + return Period; + } + inline float GetDuration() const + { + return Duration; + } void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) { FObjectKey key(Target); @@ -402,35 +429,60 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty HandleToTarget.Add(InHandle, Target); } - void RemoveHandle(const FGAEffectHandle& InHandle) - { - UObject* Target = nullptr; - HandleToTarget.RemoveAndCopyValue(InHandle, Target); - if(Target) - { - FObjectKey key(Target); - Handles.Remove(key); - Contexts.Remove(InHandle); - } - } - - FGAEffectHandle FindTargetEffect(UObject* Target) + FGAEffectHandle GetHandle(UObject* From) { - FObjectKey key(Target); + FObjectKey key(From); if (FGAEffectHandle* handle = Handles.Find(key)) return *handle; return FGAEffectHandle(); } - - FGAEffectHandle FindTargetEffect(UObject* Target) const + FGAEffectHandle GetHandle(UObject* From) const { - FObjectKey key(Target); + FObjectKey key(From); if (const FGAEffectHandle* handle = Handles.Find(key)) return *handle; return FGAEffectHandle(); } + + inline FAFPredictionHandle GetPredictionHandle() const + { + return PredictionHandle; + } + + bool IsHandleValid(UObject* For) + { + FObjectKey Key(For); + FGAEffectHandle* Handle = Handles.Find(Key); + if (Handle) + { + return Handle->IsValid(); + } + return false; + } + bool IsHandleValid(UObject* For) const + { + FObjectKey Key(For); + const FGAEffectHandle* Handle = Handles.Find(Key); + if (Handle) + { + return Handle->IsValid(); + } + return false; + } + void RemoveHandle(const FGAEffectHandle& InHandle) + { + UObject* Target = nullptr; + HandleToTarget.RemoveAndCopyValue(InHandle, Target); + if(Target) + { + FObjectKey key(Target); + Handles.Remove(key); + Contexts.Remove(InHandle); + } + } + void SetPredictionHandle(const FAFPredictionHandle& InHandle) { PredictionHandle = InHandle; @@ -454,10 +506,10 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { return ApplicationRequirement && Application && Execution && Spec; } - const bool IsValidHandle() const + /*const bool IsValidHandle() const { return Handle.IsValid(); - } + }*/ const bool operator==(const FGAEffectProperty& Other) const { return SpecClass == Other.SpecClass; @@ -469,7 +521,7 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty void operator=(const FGAEffectProperty& Other) { SpecClass = Other.SpecClass; - Handle = Other.Handle; + //Handle = Other.Handle; } void operator=(const TSubclassOf& Other) { @@ -673,9 +725,6 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem UPROPERTY(NotReplicated) float LastPeriodTime; - - FTimerHandle ExpiredHandle; - FTimerHandle PeriodHandle; class UAFAbilityComponent* OwningComoponent; UGAGameEffectSpec* GetSpec() const @@ -683,13 +732,6 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem return Spec.GetDefaultObject(); } - //UPROPERTY() - // FGAEffectContext Context; - - void Init(); - void OnExpired(); - void OnPeriod(); - void OnRemoved(); void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index bdd6957..1388364 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -332,4 +332,14 @@ bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) const bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) const { return AllTags.HasAllExact(TagsIn); +} + +FAFCueHandle FAFCueHandle::GenerateHandle() +{ + static uint32 HandleIndex = 0; + HandleIndex++; + + FAFCueHandle NewHandle(HandleIndex); + + return NewHandle; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 8264e31..490b720 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -395,7 +395,6 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle // }; //}; - USTRUCT() struct FAFPredictionHandle { @@ -829,4 +828,33 @@ struct ABILITYFRAMEWORK_API FGAEffectCueParams Causer(CauserIn) {}; //bool NetSerialize(FArchive& Ar, class UPackageMap* Map, bool& bOutSuccess); -}; \ No newline at end of file +}; + +USTRUCT() +struct FAFCueHandle +{ + GENERATED_BODY(); +private: + UPROPERTY() + uint32 Handle; + + FAFCueHandle(uint32 InHandle) + : Handle(InHandle) + {} +public: + FAFCueHandle() + : Handle(0) + {} + + static FAFCueHandle GenerateHandle(); + + bool operator==(const FAFCueHandle Other) const + { + return Handle == Other.Handle; + } + + friend uint32 GetTypeHash(const FAFCueHandle& InHandle) + { + return InHandle.Handle; + } +}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs index b57046b..9729348 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs +++ b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs @@ -19,6 +19,9 @@ public AbilityManager(ReadOnlyTargetRules Target) : base(Target) PrivateIncludePaths.AddRange( new string[] { "AbilityManager/Private", + "AbilityManager/Abilities", + "AbilityManager/Attributes", + "AbilityManager/Effects", // ... add other private include paths required here ... } ); diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 25a4062..5b6877c 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -218,7 +218,7 @@ void AARCharacter::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > { Super::GetLifetimeReplicatedProps(OutLifetimeProps); - DOREPLIFETIME(AARCharacter, CameraTransform); + DOREPLIFETIME_CONDITION(AARCharacter, CameraTransform, COND_SkipOwner); } void AARCharacter::Multicast_CameraTransform_Implementation(FARCameraTransform InCameraTransform) @@ -227,10 +227,14 @@ void AARCharacter::Multicast_CameraTransform_Implementation(FARCameraTransform I } void AARCharacter::OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport) { - FARCameraTransform CamTransform; - CameraTransform.ForwardVector = FollowCamera->GetForwardVector(); - CameraTransform.Location = FollowCamera->GetComponentLocation(); - //Multicast_CameraTransform(CamTransform); + if (GetNetMode() == ENetMode::NM_Standalone + || Role == ENetRole::ROLE_Authority + || Role == ENetRole::ROLE_AutonomousProxy) + { + CameraTransform.ForwardVector = FollowCamera->GetForwardVector(); + CameraTransform.Location = FollowCamera->GetComponentLocation(); + } + //Multicast_CameraTransform(CameraTransform); } class AARWeaponBase* AARCharacter::GetMainWeapon() const diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index cc0bc1e..4780cc5 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -319,11 +319,18 @@ FGameplayTag UARWeaponManagerComponent::FindNextValid() while (!WeaponAbilityTag.IsValid()) { Idx++; - if (Idx > Groups.Num() - 1) + if (Idx > MAX_WEAPONS - 1) { Idx = 0; } WeaponAbilityTag = GetAbilityTag(AMIntToEnum(Idx), EAMSlot::Slot001); + + //no weapon at first index, just assume there is nothing equipped. + if ((Idx == 0) && !WeaponAbilityTag.IsValid()) + { + SelectGroup(EAMGroup::Group005); + break; + } } if (WeaponAbilityTag.IsValid()) { @@ -341,7 +348,14 @@ FGameplayTag UARWeaponManagerComponent::FindPreviousValid() Idx--; if (Idx < 0) { - Idx = 0; + Idx = MAX_WEAPONS - 1; + } + + //again no ability for weapon. + if ((Idx == (MAX_WEAPONS - 1) ) && !WeaponAbilityTag.IsValid()) + { + SelectGroup(EAMGroup::Group005); + break; } WeaponAbilityTag = GetAbilityTag(AMIntToEnum(Idx), EAMSlot::Slot001); } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp index f91dc07..b7902d5 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp @@ -92,8 +92,8 @@ void UARWeaponPawnManagerComponent::EquipInactive(EAMGroup Group, UARItemWeapon* if (InOldWeapon) { WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; - WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; - WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; + //WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; + //WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); From 231022fca076d6cf5633c56baccf4d544c52eb82 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 13 Feb 2018 00:27:09 +0100 Subject: [PATCH 055/187] first part of refactor, Splitted effects into seprate component and started reworking publicly accessible interface, the plan is that write part will be minimal and mostly unmutable readers will be publicly exposed --- .../AbilityFramework/AFAbilityComponent.cpp | 375 +--- .../AbilityFramework/AFAbilityComponent.h | 257 +-- .../AbilityFramework/AFAbilityInterface.cpp | 16 +- .../AbilityFramework/AFAbilityInterface.h | 20 +- .../{GAGlobals.cpp => AFAbilityTypes.cpp} | 3 +- .../Source/AbilityFramework/AFAbilityTypes.h | 24 + .../AbilityFramework/AFEffectsComponent.cpp | 412 +++++ .../AbilityFramework/AFEffectsComponent.h | 198 ++ .../Abilities/GAAbilityBase.cpp | 75 +- .../Abilities/GAAbilityBase.h | 6 +- .../Abilities/GAAbilitySet.cpp | 8 - .../AbilityFramework/Abilities/GAAbilitySet.h | 21 - .../Tasks/GAAbilityTask_PlayMontage.cpp | 12 +- .../Tasks/GAAbilityTask_PlayMontage.h | 10 +- .../AnimNotify/AFAbilityNotifyState.cpp | 6 +- .../AnimNotify/AFAbilityNotifyState.h | 4 +- .../AnimNotify/AFAnimNotify.cpp | 2 +- .../AnimNotify/AFAnimNotify.h | 6 +- .../Effects/AFEffectCustomApplication.cpp | 2 +- .../AFAtributeDurationAdd.cpp | 4 +- .../AFAttributeDurationOverride.cpp | 18 +- .../AFPeriodApplicationAdd.cpp | 6 +- .../AFPeriodApplicationExtend.cpp | 8 +- .../AFPeriodApplicationInfiniteAdd.cpp | 4 +- .../AFPeriodApplicationOverride.cpp | 6 +- .../Effects/EffectTasks/AFEffectTask.h | 11 +- .../AFEffectTask_AttributeChange.cpp | 14 +- .../AFEffectTask_AttributeChange.h | 4 +- .../EffectTasks/AFEffectTask_EffectEvent.cpp | 10 +- .../EffectTasks/AFEffectTask_EffectEvent.h | 4 +- .../Effects/GABlueprintLibrary.cpp | 16 +- .../Effects/GAEffectExtension.cpp | 66 +- .../Effects/GAEffectExtension.h | 32 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 17 +- .../AbilityFramework/Effects/GAGameEffect.h | 7 +- .../Source/AbilityFramework/GAGlobalTypes.cpp | 29 +- .../Source/AbilityFramework/GAGlobalTypes.h | 13 +- .../Source/AbilityFramework/GAGlobals.h | 88 - .../Tests/GAAttributesTest.cpp | 13 - .../AbilityFramework/Tests/GAAttributesTest.h | 49 - .../Tests/GAAttributesTests.cpp | 1647 ----------------- .../Tests/GACharacterAttributeTest.cpp | 71 - .../Tests/GACharacterAttributeTest.h | 41 - .../Tests/GACustomCalculationTest.cpp | 22 - .../Tests/GACustomCalculationTest.h | 19 - .../Tests/GASpellExecutionTest.cpp | 15 - .../Tests/GASpellExecutionTest.h | 15 - .../Tests/GAffectSpecTestOne.cpp | 8 - .../Tests/GAffectSpecTestOne.h | 20 - .../AbilityFrameworkDebugger/AFDCharacter.cpp | 34 - .../AbilityFrameworkDebugger/AFDCharacter.h | 31 - .../AFDCharacterAttributes.cpp | 7 - .../AFDCharacterAttributes.h | 27 - .../AbilityFrameworkDebugger/AFDDummyPawn.cpp | 84 - .../AbilityFrameworkDebugger/AFDDummyPawn.h | 65 - .../AbilityFrameworkDebugger/AFDGameMode.cpp | 7 - .../AbilityFrameworkDebugger/AFDGameMode.h | 20 - .../AbilityFrameworkDebugger/SAFDEffects.cpp | 25 +- .../AbilityFrameworkDebugger/SAFDEffects.h | 8 +- Source/ActionRPGGame/AI/ARAICharacter.cpp | 27 +- Source/ActionRPGGame/AI/ARAICharacter.h | 13 +- Source/ActionRPGGame/ARCharacter.cpp | 34 +- Source/ActionRPGGame/ARCharacter.h | 17 +- 63 files changed, 927 insertions(+), 3206 deletions(-) rename Plugins/AbilityFramework/Source/AbilityFramework/{GAGlobals.cpp => AFAbilityTypes.cpp} (64%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 9b19a70..becc3ca 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -9,8 +9,6 @@ #include "Engine/ActorChannel.h" #include "Animation/AnimInstance.h" #include "Animation/AnimMontage.h" -#include "GAGlobals.h" -#include "Abilities/GAAbilitySet.h" #include "Attributes/GAAttributesBase.h" #include "AFAbilityInterface.h" #include "Effects/GAEffectExecution.h" @@ -23,8 +21,8 @@ #include "Effects/GABlueprintLibrary.h" #include "Async.h" #include "AFAbilityComponent.h" - - +#include "AFEffectsComponent.h" +#include "AFAbilityInterface.h" DEFINE_STAT(STAT_ApplyEffect); DEFINE_STAT(STAT_ModifyAttribute); @@ -124,10 +122,7 @@ void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickTyp DefaultAttributes->Tick(DeltaTime); } } -void UAFAbilityComponent::Update() -{ -} void UAFAbilityComponent::BeginPlay() { Super::BeginPlay(); @@ -144,319 +139,10 @@ void UAFAbilityComponent::DestroyComponent(bool bPromoteChildren) } -FGAEffectHandle UAFAbilityComponent::ApplyEffectToSelf(FGAEffect* EffectIn - ,FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier) -{ - const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; - FAFEventData Data; - - for (const FGameplayTag& Tag : AppliedEventTags) - { - if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) - { - Event->Broadcast(Data); - } - } - if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) - { - Delegate->ExecuteIfBound(); - } - - FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); - GameEffectContainer.MarkArrayDirty(); - OnEffectAppliedToSelf.Broadcast(Handle); - return Handle; -} - - -FGAEffectHandle UAFAbilityComponent::ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier) -{ - if(FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) - { - Delegate->ExecuteIfBound(); - } - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - - FAFCueHandle CueHandle = FAFCueHandle::GenerateHandle(); - - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams; - CueParams.Instigator = InContext.Instigator; - CueParams.Causer = InContext.Causer; - CueParams.HitResult = InContext.HitResult; - CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.GetPeriod(); - CueParams.Duration = InProperty.GetDuration(); - //if (mode == ENetMode::NM_Standalone - // || role >= ENetRole::ROLE_Authority) - { - //AsyncTask(ENamedThreads::GameThread, [=]() - //{ - MulticastApplyEffectCue(CueParams, CueHandle); - //}); - } - } - FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - } - else if (mode == ENetMode::NM_DedicatedServer) - { - prefix = FString::Printf(TEXT("DedicatedServer: ")); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), - *prefix, - *GetOwner()->GetName(), - *InContext.Instigator->GetName() - ); - //here, we should start attribute change prediction - //either change attribute or apply effect which will do so - - //execute cue from effect regardless if we have target object or not. - if (InContext.TargetComp.IsValid()) - { - FGAEffectHandle Handle; - Handle = InContext.TargetComp->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); - if (!PropertyByHandle.Contains(Handle)) - PropertyByHandle.Add(Handle, &InProperty); - - EffectToCue.Add(Handle, CueHandle); - OnEffectAppliedToTarget.Broadcast(Handle); - if(InProperty.GetDuration() == 0 - && InProperty.GetPeriod() == 0) - { - OnEffectRemoved.Broadcast(Handle); - } - return Handle; - } - return FGAEffectHandle(); -} - void UAFAbilityComponent::OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) { -} -void UAFAbilityComponent::ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty - ,FAFFunctionModifier Modifier, FGAEffectContext InContex) -{ - /* - this patth will give effects chance to do any replicated events, like applying cues. - WE do not make any replication at the ApplyEffect because some effect might want to apply cues - on periods on expiration etc, and all those will go trouch ExecuteEffect path. - */ - const FGameplayTagContainer& RequiredTags = InProperty.GetSpec()->RequiredTags; - if (RequiredTags.Num() > 0) - { - if (!HasAll(RequiredTags)) - { - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *HandleIn.GetEffectSpec()->GetName(), *RequiredTags.ToString()); - return; - } - } - - //apply execution events: - const FGameplayTagContainer& ExecuteEventTags = InProperty.GetSpec()->ExecuteEventTags; - FAFEventData Data; - for (const FGameplayTag& Tag : ExecuteEventTags) - { - if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) - { - Event->Broadcast(Data); - } - } - - //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); - FGAEffect& Effect = HandleIn.GetEffectRef(); - FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() - , InProperty.GetSpec() - , InContex - , HandleIn); - - //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? - - Effect.OnExecuted(); - ExecuteEffectEvent(InProperty.GetSpec()->OnPeriodEvent); - - FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); - if (CueHandle) - MulticastExecuteEffectCue(HandleIn, *CueHandle); - - InProperty.EffectExecution(HandleIn, Mod, HandleIn.GetContextRef(), Modifier); - PostExecuteEffect(); -} -void UAFAbilityComponent::PostExecuteEffect() -{ - -} -void UAFAbilityComponent::ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty, - FGAEffectContext InContext) -{ - //call effect internal delegate: - HandleIn.GetEffectPtr()->OnExpired(); - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); - if (mode == ENetMode::NM_DedicatedServer - || mode == ENetMode::NM_ListenServer) - { - ClientExpireEffect(InProperty.GetPredictionHandle()); - } - - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams; - CueParams.Instigator = InContext.Instigator; - CueParams.Causer = InContext.Causer; - CueParams.HitResult = InContext.HitResult; - CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.GetPeriod(); - CueParams.Duration = InProperty.GetDuration(); - - FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); - if(CueHandle) - { - MulticastRemoveEffectCue(CueParams, *CueHandle); - } - } - - TArray handles = GameEffectContainer.RemoveEffect(InProperty); - for (const FGAEffectHandle& Handle : handles) - { - OnEffectExpired.Broadcast(Handle); - } -} - -void UAFAbilityComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) -{ - -} - -void UAFAbilityComponent::RemoveEffect(const FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, const FGAEffectHandle& InHandle) -{ - //if (GetOwnerRole() == ENetRole::ROLE_Authority - // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) - { - InternalRemoveEffect(InProperty, InContext); - } - ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); - FGAEffectCueParams CueParams; - CueParams.Instigator = InContext.Instigator; - CueParams.Causer = InContext.Causer; - CueParams.HitResult = InContext.HitResult; - CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.GetPeriod(); - CueParams.Duration = InProperty.GetDuration(); - FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); - if (CueHandle) - { - MulticastRemoveEffectCue(CueParams, *CueHandle); - } -} -void UAFAbilityComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, - const FGAEffectContext& InContext) -{ - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); - - //MulticastRemoveEffectCue(HandleIn); - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams; - CueParams.Instigator = InContext.Instigator; - CueParams.Causer = InContext.Causer; - CueParams.HitResult = InContext.HitResult; - CueParams.CueTags = InProperty.GetSpec()->Cues.CueTags; - CueParams.Period = InProperty.GetPeriod(); - CueParams.Duration = InProperty.GetDuration(); - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role >= ENetRole::ROLE_Authority) - { - //MulticastRemoveEffectCue(CueParams); - } - } - - TArray handles = GameEffectContainer.RemoveEffect(InProperty); - for(const FGAEffectHandle& Handle : handles) - { - OnEffectRemoved.Broadcast(Handle); - } -} - - -void UAFAbilityComponent::MulticastApplyEffectCue_Implementation( FGAEffectCueParams CueParams, FAFCueHandle InHandle) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if(mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - int32 client = GPlayInEditorID - 1; - if (client == 2) - { - float dupa = 0; - } - prefix = FString::Printf(TEXT("Client %d: "), client); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : MulticastApplyEffectCue Owner: %s, Instigator: %s" ), - *prefix, - *GetOwner()->GetName(), - *CueParams.Instigator->GetName() - ); - - UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); - } -} - -void UAFAbilityComponent::MulticastExecuteEffectCue_Implementation(FGAEffectHandle EffectHandle, FAFCueHandle InHandle) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - UAFCueManager::Get()->HandleExecuteCue(InHandle); - } -} - -void UAFAbilityComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams, InHandle); - } -} - -void UAFAbilityComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) -{ - -} -void UAFAbilityComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) -{ - -} -void UAFAbilityComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) -{ - -} -void UAFAbilityComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) -{ - } void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const @@ -466,13 +152,10 @@ void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProp //to allow prediction for UI. DOREPLIFETIME(UAFAbilityComponent, DefaultAttributes); DOREPLIFETIME(UAFAbilityComponent, RepAttributes); - DOREPLIFETIME(UAFAbilityComponent, GameEffectContainer); DOREPLIFETIME(UAFAbilityComponent, ActiveCues); - DOREPLIFETIME(UAFAbilityComponent, AbilityContainer); - //DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); + DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); DOREPLIFETIME_CONDITION(UAFAbilityComponent, RepMontage, COND_SkipOwner); - //DOREPLIFETIME(UAFAbilityComponent, RepMontage); } void UAFAbilityComponent::OnRep_ActiveEffects() { @@ -519,61 +202,14 @@ void UAFAbilityComponent::GetSubobjectsWithStableNamesForNetworking(TArrayIsBound()) - { - Delegate->Broadcast(InEventData); - } - } -} void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const { - TagContainer = AppliedTags.AllTags; -} -bool UAFAbilityComponent::HasMatchingGameplayTag(FGameplayTag TagToCheck) const -{ - return AppliedTags.HasTag(TagToCheck); -} - -bool UAFAbilityComponent::HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const -{ - return AppliedTags.HasAll(TagContainer); -} - -bool UAFAbilityComponent::HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const -{ - return AppliedTags.HasAny(TagContainer); -} - -bool UAFAbilityComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) -{ - bool bDenyApplication = false; - if (InTags.Num() > 0) + if (IAFAbilityInterface* ABInterface = Cast(GetOwner())) { - bDenyApplication = HasAll(InTags); + TagContainer = ABInterface->NativeGetEffectsComponent()->AppliedTags.AllTags; } - return bDenyApplication; } -bool UAFAbilityComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) -{ - bool bAllowApplication = true; - if (InTags.Num() > 0) - { - bAllowApplication = HasAll(InTags); - } - return bAllowApplication; -} const bool FGASAbilityItem::operator==(const FGameplayTag& AbilityTag) const { return Ability->AbilityTag == AbilityTag; @@ -796,7 +432,6 @@ void UAFAbilityComponent::InitializeComponent() DefaultAttributes->InitializeAttributes(this); DefaultAttributes->InitializeAttributesFromTable(); } - GameEffectContainer.OwningComponent = this; ActiveCues.OwningComp = this; //ActiveCues.OwningComponent = this; AppliedTags.AddTagContainer(DefaultTags); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index ee53e6c..7ee3629 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -5,20 +5,19 @@ #include "GameplayTask.h" #include "GameplayTasksComponent.h" #include "GameplayTags.h" -#include "GAGlobals.h" +#include "AFAbilityTypes.h" + #include "Attributes/GAAttributeBase.h" #include "Attributes/GAAttributesBase.h" #include "Effects/GAEffectCueGlobals.h" #include "Effects/GAGameEffect.h" #include "GAGlobalTypes.h" -//#include "Messaging.h" + #include "GameplayTagAssetInterface.h" -#include "AFAbilityInterface.h" #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" -#include "AFAssetManager.h" #include "AFAbilityComponent.generated.h" @@ -31,7 +30,7 @@ DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttr DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); -DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate , FAFEventData); + DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectRepInfoDelegate, FAFEffectRepInfo*); @@ -40,7 +39,7 @@ DECLARE_DELEGATE(FAFOnAbilityReady); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); DECLARE_DELEGATE(FAFGenericAttributeDelegate); -DECLARE_DELEGATE(FAFEffectEvent); + //UAFAssetManager* GetAssetManager() //{ // return Cast(UAssetManager::GetIfValid()); @@ -92,7 +91,7 @@ struct FGAContextSetup {}; }; DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); -DECLARE_DELEGATE_ThreeParams(FAFMontageGenericDelegate, const FAFAbilityNotifyData&, const FGameplayTag&, const FName&); +DECLARE_DELEGATE_TwoParams(FAFMontageGenericDelegate, const FGameplayTag&, const FName&); /* TODO:: Implement fast serialization for structs. */ /* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ /**/ @@ -316,57 +315,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, FGAOnAttributeModifed OnAttributeModifed; UPROPERTY(BlueprintAssignable, Category = "Game Attributes") FGAOnAttributeModifed OnTargetAttributeModifed; - /* Effect/Attribute System Delegates */ - //UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectAppliedToTarget; - - //UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectAppliedToSelf; - - //UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectExecuted; - - //UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectExpired; - //UPROPERTY(BlueprintAssignable, Category = "Effect") - FGAGenericEffectDelegate OnEffectRemoved; - - /* NEW EFFECT SYSTEM */ - UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) - FGAEffectContainer GameEffectContainer; - - //Maps effect handles to Properties from which effect was created. - //usefull when all we have is handle or PredictionHandle. - TMap PropertyByHandle; - TMap EffectToCue; - - FAFEffectRepInfoDelegate OnEffectRepInfoApplied; - FAFEffectRepInfoDelegate OnEffectRepInfoRemoved; - /* - Default effects applied when character spawns. - Can contain things like attribute regen, racial bonuses - racial debuffs etc. - */ - UPROPERTY(EditAnywhere, Category = "Effects") - TArray> DefaultEffects; - - TMap EffectEvents; TMap AttributeChanged; - const FGAGenericEffectDelegate& GetOnEffectApppliedToTarget() const - { - return OnEffectAppliedToTarget; - } - const FGAGenericEffectDelegate& GetOnEffectRemoved() const - { - return OnEffectRemoved; - } - - void RegisterToEffectEvents(void* Object, TFunction InFunction); - void BroadcastAttributeChange(const FGAAttribute& InAttribute, const FAFAttributeChangedData& InData); @@ -408,109 +361,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; /* UActorComponent Interface - End **/ -public: - ///////////////////////////////////////////////// - //////////// EFFECTS HANDLING - - void Update(); - - /* - * @call Order: - * Previous Function: UAFAbilityComponent::ApplyEffectToTarget - * Next Function: FGAEffectContainer::ApplyEffect - * Apply target to Me. Try to apply effect to container and launch Events in: - * TMap OnEffectEvent - event is called before application; - * TMap OnEffectApplyToSelf - event is called before application; - * - * @param EffectIn* - Effect to apply - * @param InProperty - cached effect information - * @param InContext - Context about effect application. Target, instigator, causer. - * @param Modifier - optional modifier which can be applied to effect. - * @return Handle to Effect; - */ - FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - /* - * @call Order: - * Previous Function: UGABlueprintLibrary::ApplyEffect - * Next Function: UAFAbilityComponent::ApplyEffectToSelf - * Apply effect to target provided inside Context. - * Try launch events: - * TMap OnEffectApplyToTarget - event is called before application - * - * @param EffectIn* - Effect to apply - * @param InProperty - cached effect information - * @param InContext - Context about effect application. Target, instigator, causer. - * @param Modifier - optional modifier which can be applied to effect. - * @return Handle to Effect; - */ - FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - - void ApplyEffectToTarget(TSubclassOf InSpecClass, - const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); - - /* Have to to copy handle around, because timer delegates do not support references. */ - void ExecuteEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty - ,FAFFunctionModifier Modifier, FGAEffectContext InContext); - virtual void PostExecuteEffect(); - /* ExpireEffect is used to remove existing effect naturally when their time expires. */ - void ExpireEffect(FGAEffectHandle HandleIn, FGAEffectProperty InProperty, - FGAEffectContext InContext); - - UFUNCTION(Client, Reliable) - void ClientExpireEffect(FAFPredictionHandle PredictionHandle); - void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); - - /* RemoveEffect is used to remove effect by force. */ - void RemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); - void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); - - const TSet& GetAllEffectsHandles() const - { - return GameEffectContainer.GetAllEffectHandles(); - } - const TArray& GetAllEffectsInfo() const - { - return GameEffectContainer.GetAllEffectsInfo(); - } - /* - Need prediction for spawning effects on client, - and then on updateing them predicitvely on all other clients. - */ - /* - - */ - UFUNCTION(NetMulticast, Unreliable) - void MulticastApplyEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastExecuteEffectCue(FGAEffectHandle EffectHandle, FAFCueHandle InHandle); - void MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastRemoveEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); - - //////////// EFFECTS HANDLING - ///////////////////////////////////////////////// - public: ///////////////////////////////////////////////// //////////// ATTRIBUTES HANDLING @@ -538,9 +388,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, Attribute replication. */ void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); - - FAFEventDelegate& GetTagEvent(FGameplayTag TagIn); - void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); //Helper functions: public: /* @@ -554,69 +401,10 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UFUNCTION(BlueprintCallable, Category = GameplayTags) virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; - /** - * Check if the asset has a gameplay tag that matches against the specified tag (expands to include parents of asset tags) - * - * @param TagToCheck Tag to check for a match - * - * @return True if the asset has a gameplay tag that matches, false if not - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual bool HasMatchingGameplayTag(FGameplayTag TagToCheck) const override; - - /** - * Check if the asset has gameplay tags that matches against all of the specified tags (expands to include parents of asset tags) - * - * @param TagContainer Tag container to check for a match - * - * @return True if the asset has matches all of the gameplay tags, will be true if container is empty - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual bool HasAllMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; - - /** - * Check if the asset has gameplay tags that matches against any of the specified tags (expands to include parents of asset tags) - * - * @param TagContainer Tag container to check for a match - * - * @return True if the asset has matches any of the gameplay tags, will be false if container is empty - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual bool HasAnyMatchingGameplayTags(const FGameplayTagContainer& TagContainer) const override; /* IGameplayTagAssetInterface End */ - bool DenyEffectApplication(const FGameplayTagContainer& InTags); - bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); - /* - Effect Container Wrapp Start - */ - /* - */ - inline bool IsEffectActive(const FGAEffectHandle& HandleIn) { return GameEffectContainer.IsEffectActive(HandleIn); }; - /* - Effect Container Wrapp End - */ - - /* Counted Tag Container Wrapper Start */ - inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; - inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; - inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; - inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; - inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } - inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; - inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; - inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; - inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; - inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; - inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } - /* Counted Tag Container Wrapper Start */ - - /* Active Effects Wrapper Start */ - inline int32 GetEffectsNum() const { return GameEffectContainer.GetEffectsNum(); }; - /* Active Effects Wrapper End */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; @@ -650,42 +438,13 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") class UGAAbilityBase* ExecutingAbility; - TMap OnEffectEvent; - void AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) - { - if (!InEventTag.IsValid()) - return; - if (!OnEffectEvent.Contains(InEventTag)) - { - UE_LOG(AbilityFramework, Log, TEXT("AddEffectEvent: %s"), *InEventTag.ToString()); - OnEffectEvent.Add(InEventTag, InEvent); - } - } - void ExecuteEffectEvent(const FGameplayTag& InEventTag) - { - if (!InEventTag.IsValid()) - return; - FSimpleDelegate* Delegate = OnEffectEvent.Find(InEventTag); - if (Delegate) - { - UE_LOG(AbilityFramework, Log, TEXT("ExecuteEffectEvent: %s"), *InEventTag.ToString()); - Delegate->ExecuteIfBound(); - } - } - void RemoveEffectEvent(const FGameplayTag& InEventTag) - { - if (!InEventTag.IsValid()) - return; - UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); - OnEffectEvent.Remove(InEventTag); - } /*UFUNCTION(NetMulticast, Reliable) MulticastExecuteEffect()*/ - TMap OnEffectApplyToSelf; + - TMap OnEffectApplyToTarget; + /* True if player is currently casting/channeling/activating(?) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp index 677c6d4..3a128d8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp @@ -2,9 +2,23 @@ #include "AbilityFramework.h" #include "AFAbilityInterface.h" - +#include "AFAbilityComponent.h" +#include "AFEffectsComponent.h" +#include "AFAttributeComponent.h" UAFAbilityInterface::UAFAbilityInterface(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { } +//class UGAAttributesBase* IAFAbilityInterface::GetAttributes() +//{ +// return nullptr;// GetAbilityComp()->DefaultAttributes; +//} + +FGAEffectHandle IAFAbilityInterface::ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, InProperty, InContext, Modifier); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h index 9be3384..2774341 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h @@ -3,7 +3,7 @@ #include "Effects/GAGameEffect.h" #include "Attributes/GAAttributeGlobals.h" #include "GAGlobalTypes.h" -//#include "Messaging.h" +#include "AFAbilityComponent.h" #include "AFAbilityInterface.generated.h" @@ -21,11 +21,15 @@ class IAFAbilityInterface public: virtual FVector GetSocketLocation(FName SocketNameIn){ return FVector::ZeroVector; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UGAAttributesBase* GetAttributes() = 0; + virtual class UAFAbilityComponent* GetAbilityComp() = 0; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UAFAbilityComponent* GetAbilityComp() { return nullptr; }; + virtual class UAFEffectsComponent* GetEffectsComponent() = 0; + + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const = 0; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; @@ -37,8 +41,6 @@ class IAFAbilityInterface virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) { return FGAEffectHandle(); }; virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) {}; //override to allow gathering tags from causer //those tags will be merged into effect owned tags. @@ -46,6 +48,14 @@ class IAFAbilityInterface virtual FAFPredictionHandle GetPredictionHandle() { return FAFPredictionHandle(); } + + FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual class UGAAttributesBase* GetAttributes() { return GetAbilityComp()->DefaultAttributes; }; + template T* GetAttributesTyped() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp similarity index 64% rename from Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp rename to Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp index c7e7b6d..1df88dc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp @@ -1,5 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "GAGlobals.h" +#include "AFAbilityComponent.h" +#include "AFAbilityTypes.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h new file mode 100644 index 0000000..fff88cb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "AFAbilityTypes.generated.h" +/** + * + */ +USTRUCT() +struct FAFAb +{ + GENERATED_BODY() +}; + +struct FAFAbilityItem +{ + +}; + +struct FAFAbilityContainer +{ + +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp new file mode 100644 index 0000000..2b4a4aa --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -0,0 +1,412 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectsComponent.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + +#include "AFAbilityInterface.h" +#include "Effects/GAEffectExecution.h" +#include "Effects/GAGameEffect.h" +#include "Effects/GAEffectExtension.h" +#include "Effects/GAEffectCue.h" +#include "AFCueManager.h" +#include "Effects/GABlueprintLibrary.h" + +// Sets default values for this component's properties +UAFEffectsComponent::UAFEffectsComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UAFEffectsComponent::BeginPlay() +{ + Super::BeginPlay(); + GameEffectContainer.OwningComponent = this; + // ... + +} +void UAFEffectsComponent::InitializeComponent() +{ + Super::InitializeComponent(); + + GameEffectContainer.OwningComponent = this; +} + +// Called every frame +void UAFEffectsComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; + FAFEventData Data; + + for (const FGameplayTag& Tag : AppliedEventTags) + { + if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + { + Event->Broadcast(Data); + } + } + if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) + { + Delegate->ExecuteIfBound(); + } + + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); + GameEffectContainer.MarkArrayDirty(); + return Handle; +} + +FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier) +{ + if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) + { + Delegate->ExecuteIfBound(); + } + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + + FAFCueHandle CueHandle = FAFCueHandle::GenerateHandle(); + + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams(InContext, InProperty); + MulticastApplyEffectCue(CueParams, CueHandle); + } + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + } + else if (mode == ENetMode::NM_DedicatedServer) + { + prefix = FString::Printf(TEXT("DedicatedServer: ")); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), + *prefix, + *GetOwner()->GetName(), + *InContext.Instigator->GetName() + ); + //here, we should start attribute change prediction + //either change attribute or apply effect which will do so + + //execute cue from effect regardless if we have target object or not. + if (InContext.TargetComp.IsValid()) + { + FGAEffectHandle Handle; + Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + if (!PropertyByHandle.Contains(Handle)) + PropertyByHandle.Add(Handle, &InProperty); + + EffectToCue.Add(Handle, CueHandle); + + return Handle; + } + return FGAEffectHandle(); +} + + +/* Have to to copy handle around, because timer delegates do not support references. */ +void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn + , FGAEffectProperty InProperty + , FAFFunctionModifier Modifier + , FGAEffectContext InContext) +{ + /* + this patth will give effects chance to do any replicated events, like applying cues. + WE do not make any replication at the ApplyEffect because some effect might want to apply cues + on periods on expiration etc, and all those will go trouch ExecuteEffect path. + */ + const FGameplayTagContainer& RequiredTags = InProperty.GetSpec()->RequiredTags; + if (RequiredTags.Num() > 0) + { + if (!HasAll(RequiredTags)) + { + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *HandleIn.GetEffectSpec()->GetName(), *RequiredTags.ToString()); + return; + } + } + + //apply execution events: + const FGameplayTagContainer& ExecuteEventTags = InProperty.GetSpec()->ExecuteEventTags; + FAFEventData Data; + for (const FGameplayTag& Tag : ExecuteEventTags) + { + if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + { + Event->Broadcast(Data); + } + } + + //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); + FGAEffect& Effect = HandleIn.GetEffectRef(); + FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() + , InProperty.GetSpec() + , InContext + , HandleIn); + + //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? + + Effect.OnExecuted(); + ExecuteEffectEvent(InProperty.GetSpec()->OnPeriodEvent); + + FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + if (CueHandle) + MulticastExecuteEffectCue(*CueHandle); + + InProperty.EffectExecution(HandleIn, Mod, HandleIn.GetContextRef(), Modifier); + PostExecuteEffect(); +} + +void UAFEffectsComponent::PostExecuteEffect() +{ + +} +/* ExpireEffect is used to remove existing effect naturally when their time expires. */ +void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn + , FGAEffectProperty InProperty + , FGAEffectContext InContext) +{ + //call effect internal delegate: + HandleIn.GetEffectPtr()->OnExpired(); + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); + if (mode == ENetMode::NM_DedicatedServer + || mode == ENetMode::NM_ListenServer) + { + ClientExpireEffect(InProperty.GetPredictionHandle()); + } + + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams(InContext, InProperty); + + FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + if (CueHandle) + { + MulticastRemoveEffectCue(CueParams, *CueHandle); + } + } + + TArray handles = GameEffectContainer.RemoveEffect(InProperty); +} + +void UAFEffectsComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) +{ + +} + +void UAFEffectsComponent::RemoveEffect(const FGAEffectProperty& InProperty + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + +} +void UAFEffectsComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) +{ + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); + + //MulticastRemoveEffectCue(HandleIn); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams(InContext, InProperty); + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role >= ENetRole::ROLE_Authority) + { + //MulticastRemoveEffectCue(CueParams); + } + } + + TArray handles = GameEffectContainer.RemoveEffect(InProperty); +} + +const TSet& UAFEffectsComponent::GetAllEffectsHandles() const +{ + return GameEffectContainer.GetAllEffectHandles(); +} + +void UAFEffectsComponent::AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) +{ + if (!InEventTag.IsValid()) + return; + if (!OnEffectEvent.Contains(InEventTag)) + { + UE_LOG(AbilityFramework, Log, TEXT("AddEffectEvent: %s"), *InEventTag.ToString()); + OnEffectEvent.Add(InEventTag, InEvent); + } +} +void UAFEffectsComponent::ExecuteEffectEvent(const FGameplayTag& InEventTag) +{ + if (!InEventTag.IsValid()) + return; + FSimpleDelegate* Delegate = OnEffectEvent.Find(InEventTag); + if (Delegate) + { + UE_LOG(AbilityFramework, Log, TEXT("ExecuteEffectEvent: %s"), *InEventTag.ToString()); + Delegate->ExecuteIfBound(); + } +} +void UAFEffectsComponent::RemoveEffectEvent(const FGameplayTag& InEventTag) +{ + if (!InEventTag.IsValid()) + return; + UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); + OnEffectEvent.Remove(InEventTag); +} +FAFEventDelegate& UAFEffectsComponent::GetTagEvent(FGameplayTag TagIn) +{ + FAFEventDelegate& Delegate = EffectEvents.FindChecked(TagIn); + return Delegate; +} + +void UAFEffectsComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + FAFEventDelegate* Delegate = EffectEvents.Find(TagIn); + if (Delegate) + { + if (Delegate->IsBound()) + { + Delegate->Broadcast(InEventData); + } + } +} + +bool UAFEffectsComponent::IsEffectActive(const FGAEffectHandle& InHandle) const +{ + return GameEffectContainer.IsEffectActive(InHandle); +} + +bool UAFEffectsComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) +{ + bool bDenyApplication = false; + if (InTags.Num() > 0) + { + bDenyApplication = HasAll(InTags); + } + return bDenyApplication; +} + +bool UAFEffectsComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) +{ + bool bAllowApplication = true; + if (InTags.Num() > 0) + { + bAllowApplication = HasAll(InTags); + } + return bAllowApplication; +} + +/* +Need prediction for spawning effects on client, +and then on updateing them predicitvely on all other clients. +*/ +/* + +*/ +void UAFEffectsComponent::MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + FString prefix = ""; + if (mode == ENetMode::NM_Client) + { + int32 client = GPlayInEditorID - 1; + if (client == 2) + { + float dupa = 0; + } + prefix = FString::Printf(TEXT("Client %d: "), client); + } + UE_LOG(AbilityFramework, Log, TEXT("%s : MulticastApplyEffectCue Owner: %s, Instigator: %s"), + *prefix, + *GetOwner()->GetName(), + *CueParams.Instigator->GetName() + ); + + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); + } +} +void UAFEffectsComponent::MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleExecuteCue(InHandle); + } +} + +void UAFEffectsComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams, InHandle); + } +} + +void UAFEffectsComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} + +void UAFEffectsComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) +{ + +} + +void UAFEffectsComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) +{ + +} + +void UAFEffectsComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} + + +/*Network Functions - BEGIN */ + +void UAFEffectsComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + + DOREPLIFETIME(UAFEffectsComponent, GameEffectContainer); +} + +void UAFEffectsComponent::OnRep_GameEffectContainer() +{ + +} + +/*Network Functions - END */ \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h new file mode 100644 index 0000000..8b4c870 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -0,0 +1,198 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "GameplayTags.h" +#include "GameplayTagAssetInterface.h" + +#include "Attributes/GAAttributeBase.h" +#include "Attributes/GAAttributesBase.h" +#include "Effects/GAEffectCueGlobals.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" + +#include "AFEffectsComponent.generated.h" + +DECLARE_DELEGATE(FAFEffectEvent); +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent +{ + GENERATED_BODY() +public: + friend class UGAAbilityBase; + friend class IAFAbilityInterface; + friend class UAFAbilityComponent; + friend class UAFEffectTask_EffectEvent; + +private: + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DefaultTags; + + UPROPERTY() + FGACountedTagContainer AppliedTags; + + UPROPERTY() + FGACountedTagContainer ImmunityTags; + + UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) + FGAEffectContainer GameEffectContainer; + + TMap OnEffectApplyToTarget; + TMap OnEffectApplyToSelf; + TMap EffectEvents; + + TMap PropertyByHandle; + TMap EffectToCue; + +TMap OnEffectEvent; + +public: + // Sets default values for this component's properties + UAFEffectsComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + + /** UActorComponent Interface - Begin */ + virtual void InitializeComponent() override; + /* UActorComponent Interface - End **/ + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + +protected: + + /* + * @call Order: + * Previous Function: UAFAbilityComponent::ApplyEffectToTarget + * Next Function: FGAEffectContainer::ApplyEffect + * Apply target to Me. Try to apply effect to container and launch Events in: + * TMap OnEffectEvent - event is called before application; + * TMap OnEffectApplyToSelf - event is called before application; + * + * @param EffectIn* - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect; + */ + FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + /* + * @call Order: + * Previous Function: UGABlueprintLibrary::ApplyEffect + * Next Function: UAFAbilityComponent::ApplyEffectToSelf + * Apply effect to target provided inside Context. + * Try launch events: + * TMap OnEffectApplyToTarget - event is called before application + * + * @param EffectIn* - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect; + */ + FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn + , FGAEffectProperty& InProperty + , FGAEffectContext& InContext + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + +public: + /* Have to to copy handle around, because timer delegates do not support references. */ + void ExecuteEffect(FGAEffectHandle HandleIn + , FGAEffectProperty InProperty + , FAFFunctionModifier Modifier + , FGAEffectContext InContext); + + virtual void PostExecuteEffect(); + /* ExpireEffect is used to remove existing effect naturally when their time expires. */ +public: + void ExpireEffect(FGAEffectHandle HandleIn + , FGAEffectProperty InProperty + , FGAEffectContext InContext); +protected: + UFUNCTION(Client, Reliable) + void ClientExpireEffect(FAFPredictionHandle PredictionHandle); + void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); + + /* RemoveEffect is used to remove effect by force. */ + void RemoveEffect(const FGAEffectProperty& InProperty + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle); + void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); + + const TSet& GetAllEffectsHandles() const; + + void AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent); + void ExecuteEffectEvent(const FGameplayTag& InEventTag); + void RemoveEffectEvent(const FGameplayTag& InEventTag); + bool IsEffectActive(const FGAEffectHandle& InHandle) const; + + FAFEventDelegate& GetTagEvent(FGameplayTag TagIn); + void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); +public: + bool DenyEffectApplication(const FGameplayTagContainer& InTags); + bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); +protected: + /* + + */ + UFUNCTION(NetMulticast, Unreliable) + void MulticastApplyEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExecuteEffectCue(FAFCueHandle InHandle); + void MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastRemoveEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + void MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + void MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); + void MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); + void MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + void MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); +public: + /* Counted Tag Container Wrapper Start */ + inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; + inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; + inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; + inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; + inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } + inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; + inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; + inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; + inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; + inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; + inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } + /* Counted Tag Container Wrapper Start */ + + + /*Network Functions - BEGIN */ +protected: + UFUNCTION() + void OnRep_GameEffectContainer(); + + /*Network Functions - END */ +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 6d2bc3f..facb55e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -7,6 +7,7 @@ #include "../GAGlobalTypes.h" #include "../Effects/GAEffectGlobalTypes.h" #include "../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "GameplayTagContainer.h" #include "Net/UnrealNetwork.h" @@ -307,7 +308,7 @@ void UGAAbilityBase::FinishAbility() OnAbilityFinished(); NativeFinishAbility(); AbilityState = EAFAbilityState::Waiting; - AbilityComponent->AppliedTags.RemoveTagContainer(ActivationAddedTags); + GetEffectsComponent()->AppliedTags.RemoveTagContainer(ActivationAddedTags); } void UGAAbilityBase::NativeFinishAbility() { @@ -317,7 +318,7 @@ void UGAAbilityBase::NativeFinishAbility() OnConfirmDelegate.RemoveAll(this); if (!ActivationEffectHandle.IsValid()) { - AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); ActivationEffectHandle.Reset(); } //remove effect. @@ -336,9 +337,9 @@ void UGAAbilityBase::NativeCancelActivation() AbilityComponent->ExecutingAbility = nullptr; OnConfirmDelegate.Clear(); OnConfirmDelegate.RemoveAll(this); - if (AbilityComponent) + if (GetEffectsComponent()) { - AbilityComponent->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); AbilityState = EAFAbilityState::Waiting; ActivationEffectHandle.Reset(); } @@ -369,7 +370,7 @@ bool UGAAbilityBase::ApplyCooldownEffect() FAFFunctionModifier Modifier; FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); - AbilityComponent->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); + GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, this, POwner, this, Modifier); @@ -415,7 +416,7 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) ActivationEffectHandle.Reset(); FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); - AbilityComponent->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); FAFFunctionModifier Modifier; ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(ActivationEffect, @@ -428,7 +429,7 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) if (PeriodCheck > 0) { FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); - AbilityComponent->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); } @@ -453,12 +454,12 @@ bool UGAAbilityBase::CanUseAbility() //now Lets check tags if (CanUse) { - if (AbilityComponent->HasAll(ActivationRequiredTags)) + if (GetEffectsComponent()->HasAll(ActivationRequiredTags)) { CanUse = true; } //blocking takes precedence. - if (AbilityComponent->HasAny(ActivationBlockedTags)) + if (GetEffectsComponent()->HasAny(ActivationBlockedTags)) { CanUse = false; } @@ -532,6 +533,25 @@ UAFAbilityComponent* UGAAbilityBase::GetAbilityComp() } return nullptr; } + +UAFEffectsComponent* UGAAbilityBase::GetEffectsComponent() +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->GetEffectsComponent(); + } + return nullptr; +} +UAFEffectsComponent* UGAAbilityBase::NativeGetEffectsComponent() const +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->NativeGetEffectsComponent(); + } + return nullptr; +} float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const { return NativeGetAttributeValue(AttributeIn); @@ -544,15 +564,6 @@ float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const { return Attributes->GetCurrentAttributeValue(AttributeIn); } -FGAEffectHandle UGAAbilityBase::ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) -{ - return AbilityComponent->ApplyEffectToTarget(EffectIn, InProperty, InContext); -}; -void UGAAbilityBase::RemoveTagContainer(const FGameplayTagContainer& TagsIn) -{ - AbilityComponent->RemoveTagContainer(TagsIn); -}; bool UGAAbilityBase::ApplyAttributeCost() { @@ -598,7 +609,7 @@ bool UGAAbilityBase::CheckAbilityAttributeCost() bool UGAAbilityBase::IsOnCooldown() { bool bOnCooldown = false; - bOnCooldown = AbilityComponent->IsEffectActive(CooldownEffectHandle); + bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle); if (bOnCooldown) { OnNotifyOnCooldown.Broadcast(); @@ -608,7 +619,7 @@ bool UGAAbilityBase::IsOnCooldown() bool UGAAbilityBase::IsActivating() { bool bAbilityActivating = false; - bool bHaveEffect = AbilityComponent->IsEffectActive(ActivationEffect.GetHandle(this)); + bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffect.GetHandle(this)); bool bInActivatingState = AbilityState == EAFAbilityState::Activating; UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); bAbilityActivating = bHaveEffect || bInActivatingState; @@ -720,7 +731,7 @@ bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) bool bHaveTag = false; if (IAFAbilityInterface* Interface = Cast(Target)) { - if (UAFAbilityComponent* Comp = Interface->GetAbilityComp()) + if (UAFEffectsComponent* Comp = GetEffectsComponent()) { if (Comp->HasTag(Tag)) { @@ -735,7 +746,7 @@ bool UGAAbilityBase::HaveAnyGameplayTag(AActor* Target, const FGameplayTagContai bool bHaveTag = false; if (IAFAbilityInterface* Interface = Cast(Target)) { - if (UAFAbilityComponent* Comp = Interface->GetAbilityComp()) + if (UAFEffectsComponent* Comp = GetEffectsComponent()) { if (Comp->HasAny(Tag)) { @@ -811,23 +822,23 @@ bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float R //Helpers float UGAAbilityBase::GetActivationRemainingTime() const { - return AbilityComponent->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); } float UGAAbilityBase::GetActivationRemainingTimeNormalized() const { - return AbilityComponent->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); } float UGAAbilityBase::GetActivationCurrentTime() const { - return AbilityComponent->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); } float UGAAbilityBase::GetActivationCurrentTimeNormalized() const { - return AbilityComponent->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); } float UGAAbilityBase::GetActivationEndTime() const { - return AbilityComponent->GameEffectContainer.GetEndTime(ActivationEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle); } float UGAAbilityBase::BP_GetActivationRemainingTime() { @@ -853,23 +864,23 @@ float UGAAbilityBase::BP_GetActivationEndTime() float UGAAbilityBase::GetCooldownRemainingTime() const { - return AbilityComponent->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); } float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const { - return AbilityComponent->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); } float UGAAbilityBase::GetCooldownCurrentTime() const { - return AbilityComponent->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); } float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const { - return AbilityComponent->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); } float UGAAbilityBase::GetCooldownEndTime() const { - return AbilityComponent->GameEffectContainer.GetEndTime(CooldownEffectHandle); + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle); } float UGAAbilityBase::BP_GetCooldownRemainingTime() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 7da25e6..6a96cdb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -1,5 +1,4 @@ #pragma once -#include "GAGlobals.h" #include "../GAGlobalTypes.h" #include "../Effects/GAGameEffect.h" #include "GameplayTasksComponent.h" @@ -496,6 +495,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask /** IAFAbilityInterface Begin */ virtual class UGAAttributesBase* GetAttributes() override; virtual class UAFAbilityComponent* GetAbilityComp() override; + virtual class UAFEffectsComponent* GetEffectsComponent() override; + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; @@ -503,9 +504,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty) override { Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); }; - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; virtual FAFPredictionHandle GetPredictionHandle() override; /* IAFAbilityInterface End **/ UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp deleted file mode 100644 index fa676e4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../AbilityFramework.h" -#include "GAAbilitySet.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h deleted file mode 100644 index 68c8637..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilitySet.h +++ /dev/null @@ -1,21 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Object.h" -#include "../GAGlobals.h" -#include "GAAbilitySet.generated.h" - -/** - * - */ -UCLASS(Blueprintable) -class ABILITYFRAMEWORK_API UGAAbilitySet : public UObject -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Config") - FGameplayTag AbilityTag; - UPROPERTY(EditAnywhere, Category = "Config") - FGASAbilitySetContainer AbilitySet; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp index aae1e99..afdbd32 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp @@ -36,15 +36,15 @@ void UGAAbilityTask_PlayMontage::Activate() } } -void UGAAbilityTask_PlayMontage::BroadcastStartNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName) +void UGAAbilityTask_PlayMontage::BroadcastStartNotifyState(const FGameplayTag& InTag, const FName& InName) { - NotifyBegin.Broadcast(DataIn, InTag, InName); + NotifyBegin.Broadcast(InTag, InName); } -void UGAAbilityTask_PlayMontage::BroadcastEndNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName) +void UGAAbilityTask_PlayMontage::BroadcastEndNotifyState(const FGameplayTag& InTag, const FName& InName) { - NotifyTick.Broadcast(DataIn, InTag, InName); + NotifyTick.Broadcast(InTag, InName); } -void UGAAbilityTask_PlayMontage::BroadcastTickNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName) +void UGAAbilityTask_PlayMontage::BroadcastTickNotifyState(const FGameplayTag& InTag, const FName& InName) { - NotifyEnd.Broadcast(DataIn, InTag, InName); + NotifyEnd.Broadcast(InTag, InName); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h index e7aeb21..2a2b708 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h @@ -3,10 +3,10 @@ #pragma once #include "GAAbilityTask.h" -#include "GAGlobals.h" +#include "AFAbilityTypes.h" #include "GAAbilityTask_PlayMontage.generated.h" -DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FGASGenericMontageDelegate, FAFAbilityNotifyData, Data, FGameplayTag, Tag, FName, NotifyName); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGASGenericMontageDelegate, FGameplayTag, Tag, FName, NotifyName); /** * @@ -39,7 +39,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_PlayMontage : public UGAAbilityTask virtual void Activate() override; - void BroadcastStartNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName); - void BroadcastEndNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName); - void BroadcastTickNotifyState(const FAFAbilityNotifyData& DataIn, const FGameplayTag& InTag, const FName& InName); + void BroadcastStartNotifyState(const FGameplayTag& InTag, const FName& InName); + void BroadcastEndNotifyState(const FGameplayTag& InTag, const FName& InName); + void BroadcastTickNotifyState(const FGameplayTag& InTag, const FName& InName); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp index 67dc98d..10e8534 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp @@ -14,20 +14,20 @@ void UAFAbilityNotifyState::NotifyBegin(class USkeletalMeshComponent * MeshComp, if (IAbilities) { CachedAbilitiesComp = IAbilities->GetAbilityComp(); - CachedAbilitiesComp->OnAbilityNotifyBegin.ExecuteIfBound(Data, Tag, Name); + CachedAbilitiesComp->OnAbilityNotifyBegin.ExecuteIfBound(Tag, Name); } } void UAFAbilityNotifyState::NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) { if (CachedAbilitiesComp) { - CachedAbilitiesComp->OnAbilityNotifyTick.ExecuteIfBound(Data, Tag, Name); + CachedAbilitiesComp->OnAbilityNotifyTick.ExecuteIfBound(Tag, Name); } } void UAFAbilityNotifyState::NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) { if (CachedAbilitiesComp) { - CachedAbilitiesComp->OnAbilityNotifyEnd.ExecuteIfBound(Data, Tag, Name); + CachedAbilitiesComp->OnAbilityNotifyEnd.ExecuteIfBound(Tag, Name); } } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h index 5dd37a5..d2a949a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h @@ -3,7 +3,7 @@ #pragma once #include "Animation/AnimNotifies/AnimNotifyState.h" -#include "GAGlobals.h" +#include "GameplayTags.h" #include "AFAbilityNotifyState.generated.h" /** @@ -14,8 +14,6 @@ class ABILITYFRAMEWORK_API UAFAbilityNotifyState : public UAnimNotifyState { GENERATED_BODY() protected: - UPROPERTY(EditAnywhere, Category = "Data") - FAFAbilityNotifyData Data; UPROPERTY(EditAnywhere) FGameplayTag Tag; UPROPERTY(EditAnywhere) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp index 7282ecc..26e0f2d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp @@ -15,5 +15,5 @@ void UAFAnimNotify::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* return; UAFAbilityComponent* Comp = IAbilities->GetAbilityComp(); - Comp->OnAbilityNotifyBegin.ExecuteIfBound(Data, Tag, Name); + Comp->OnAbilityNotifyBegin.ExecuteIfBound(Tag, Name); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h index dbc5ecd..b6e0390 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h @@ -3,7 +3,7 @@ #pragma once #include "Animation/AnimNotifies/AnimNotify.h" -#include "GAGlobals.h" +#include "GameplayTags.h" #include "AFAnimNotify.generated.h" /** @@ -15,9 +15,7 @@ class ABILITYFRAMEWORK_API UAFAnimNotify : public UAnimNotify GENERATED_BODY() virtual void Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) override; - - UPROPERTY(EditAnywhere) - FAFAbilityNotifyData Data; + UPROPERTY(EditAnywhere) FGameplayTag Tag; UPROPERTY(EditAnywhere) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp index c6d124e..934cf99 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp @@ -20,5 +20,5 @@ void UAFEffectCustomApplication::ExecuteEffect(const FGAEffectHandle& InHandle, const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier) { - InHandle.GetContext().TargetComp->ExecuteEffect(InHandle, InProperty, Modifier, InContext); + InHandle.GetContext().GetTargetEffectsComponent()->ExecuteEffect(InHandle, InProperty, Modifier, InContext); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp index 9aa1689..0969d5c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "AFAtributeDurationAdd.h" @@ -15,7 +15,7 @@ bool UAFAtributeDurationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct { FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.GetDuration(), false); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp index 3e8e5a6..311ad07 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "AFAttributeDurationOverride.h" @@ -13,28 +13,14 @@ bool UAFAttributeDurationOverride::ApplyEffect(const FGAEffectHandle& InHandle, const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier) { - //TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); - //for (const FGAEffectHandle& handle : handles) - //{ - // InContainer->RemoveEffect(InProperty); - //} - ////if (!InHandle.GetWithPeriod()) - //{ - // handles = InContainer->GetHandlesByAttribute(InHandle); - // for (const FGAEffectHandle& handle : handles) - // { - // InContainer->RemoveEffect(InProperty); - // } - //} InContainer->RemoveEffect(InProperty); FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.GetDuration(), false); InContainer->AddEffect(InProperty, InHandle); - //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp index 68fcced..e186577 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "AFPeriodApplicationAdd.h" @@ -13,13 +13,13 @@ bool UAFPeriodApplicationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struc { FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.GetDuration(), false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.GetPeriod(), true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index 721992d..5778b24 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "AFPeriodApplicationExtend.h" @@ -22,7 +22,7 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st float NewDuration = RemainingTime + Effect.GetDurationTime(); DurationTimer.ClearTimer(handle.GetEffectPtr()->DurationTimerHandle); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(handle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(handle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(handle.GetEffectPtr()->DurationTimerHandle, delDuration, NewDuration, false); } @@ -30,13 +30,13 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st { FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.GetDuration(), false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.GetPeriod(), true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp index 80f932a..9ce7e3f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "AFPeriodApplicationInfiniteAdd.h" @@ -13,7 +13,7 @@ bool UAFPeriodApplicationInfiniteAdd::ApplyEffect(const FGAEffectHandle& InHandl { FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.GetPeriod(), true); InContainer->AddEffect(InProperty, InHandle, true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp index 18e18f9..e27d5fe 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -2,7 +2,7 @@ #include "AbilityFramework.h" #include "../GAGameEffect.h" -#include "../../AFAbilityComponent.h" +#include "AFEffectsComponent.h" #include "AFPeriodApplicationOverride.h" @@ -22,13 +22,13 @@ bool UAFPeriodApplicationOverride::ApplyEffect(const FGAEffectHandle& InHandle, FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExpireEffect, InHandle, InProperty, InContext); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, InProperty.GetDuration(), false); FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().TargetComp.Get(), &UAFAbilityComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, InProperty.GetPeriod(), true); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index b2c66f7..a63c2e2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -19,7 +19,8 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask UPROPERTY() class UGAEffectExtension* Effect; UPROPERTY() - class UAFAbilityComponent* AbilityComponent; + class UAFEffectsComponent* EffectsComponent; + public: template static T* NewEffectTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) @@ -32,10 +33,10 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask { return Cast(CachedTask); }*/ - MyObj->Effect = ThisAbility; - MyObj->AbilityComponent = ThisAbility->OwningComponent; - MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); - MyObj->InstanceName = InstanceName; + //MyObj->Effect = ThisAbility; + //MyObj->EffectsComponent = ThisAbility->OwningComponent; + //MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); + //MyObj->InstanceName = InstanceName; //ThisAbility->AddAbilityTask(InTaskName, MyObj); return MyObj; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp index 48a75eb..7a428eb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp @@ -25,10 +25,10 @@ UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeCha void UAFEffectTask_AttributeChange::Activate() { - UAFAbilityComponent* ASC = GetTargetASC(); + UAFEffectsComponent* ASC = GetTargetASC(); if (ASC) { - MyHandle = ASC->AttributeChanged.FindOrAdd(Attribute).AddUObject(this, &UAFEffectTask_AttributeChange::AttributeChangedCallback); + // MyHandle = ASC->AttributeChanged.FindOrAdd(Attribute).AddUObject(this, &UAFEffectTask_AttributeChange::AttributeChangedCallback); } Super::Activate(); @@ -53,28 +53,28 @@ void UAFEffectTask_AttributeChange::SetExternalTarget(AActor* Actor) if (IAFAbilityInterface* interface = Cast(Actor)) { UseExternalTarget = true; - OptionalExternalTarget = interface->GetAbilityComp(); + OptionalExternalTarget = interface->GetEffectsComponent(); } } } -UAFAbilityComponent* UAFEffectTask_AttributeChange::GetTargetASC() +UAFEffectsComponent* UAFEffectTask_AttributeChange::GetTargetASC() { if (UseExternalTarget) { return OptionalExternalTarget; } - return AbilityComponent; + return EffectsComponent; } void UAFEffectTask_AttributeChange::OnDestroy(bool AbilityEnding) { - UAFAbilityComponent* ASC = GetTargetASC(); + UAFEffectsComponent* ASC = GetTargetASC(); if (ASC && MyHandle.IsValid()) { - ASC->AttributeChanged.FindOrAdd(Attribute).Remove(MyHandle); + // ASC->AttributeChanged.FindOrAdd(Attribute).Remove(MyHandle); } Super::OnDestroy(AbilityEnding); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h index 4302a7f..fc5b661 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h @@ -28,7 +28,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask void SetExternalTarget(AActor* Actor); - class UAFAbilityComponent* GetTargetASC(); + class UAFEffectsComponent* GetTargetASC(); virtual void Activate() override; @@ -39,7 +39,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask FGAAttribute Attribute; UPROPERTY() - UAFAbilityComponent* OptionalExternalTarget; + UAFEffectsComponent* OptionalExternalTarget; bool UseExternalTarget; bool OnlyTriggerOnce; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp index 5695c16..b6b1802 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -25,7 +25,7 @@ UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UObject* void UAFEffectTask_EffectEvent::Activate() { - UAFAbilityComponent* ASC = GetTargetASC(); + UAFEffectsComponent* ASC = GetTargetASC(); if (ASC) { MyHandle = ASC->EffectEvents.FindOrAdd(Tag).AddUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); @@ -54,25 +54,25 @@ void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) if (IAFAbilityInterface* interface = Cast(Actor)) { UseExternalTarget = true; - OptionalExternalTarget = interface->GetAbilityComp(); + OptionalExternalTarget = interface->GetEffectsComponent(); } } } -UAFAbilityComponent* UAFEffectTask_EffectEvent::GetTargetASC() +UAFEffectsComponent* UAFEffectTask_EffectEvent::GetTargetASC() { if (UseExternalTarget) { return OptionalExternalTarget; } - return AbilityComponent; + return EffectsComponent; } void UAFEffectTask_EffectEvent::OnDestroy(bool AbilityEnding) { - UAFAbilityComponent* ASC = GetTargetASC(); + UAFEffectsComponent* ASC = GetTargetASC(); if (ASC && MyHandle.IsValid()) { ASC->EffectEvents.FindOrAdd(Tag).Remove(MyHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h index f1074c7..c123a25 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -27,7 +27,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask void SetExternalTarget(AActor* Actor); - class UAFAbilityComponent* GetTargetASC(); + class UAFEffectsComponent* GetTargetASC(); virtual void Activate() override; @@ -38,7 +38,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask FGameplayTag Tag; UPROPERTY() - UAFAbilityComponent* OptionalExternalTarget; + UAFEffectsComponent* OptionalExternalTarget; bool UseExternalTarget; bool OnlyTriggerOnce; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index f24b567..245ce03 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -58,7 +58,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, - UAFAbilityComponent* Target2 = Context.TargetComp.Get(); + UAFEffectsComponent* Target2 = Context.GetTargetEffectsComponent(); if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) { return FGAEffectHandle(); @@ -99,7 +99,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, effect->PredictionHandle = Ability->GetPredictionHandle(); } } - FGAEffectHandle Handle = Context.InstigatorComp->ApplyEffectToTarget(effect, InEffect, Context, Modifier); + IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + + FGAEffectHandle Handle = InstigatorInterface->ApplyEffectToTarget(effect, InEffect, Context, Modifier); if (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0) { InEffect.AddHandle(Context.Target.Get(), Handle); @@ -133,7 +135,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, { return FGAEffectHandle(); }*/ - UAFAbilityComponent* Target2 = Context.TargetComp.Get(); + UAFEffectsComponent* Target2 = Context.GetTargetEffectsComponent(); if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) { return FGAEffectHandle(); @@ -174,8 +176,8 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, effect->PredictionHandle = Ability->GetPredictionHandle(); } } - - FGAEffectHandle Handle = Context.InstigatorComp->ApplyEffectToTarget(effect, *InEffect, Context, Modifier); + IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + FGAEffectHandle Handle = InstigatorInterface->ApplyEffectToTarget(effect, *InEffect, Context, Modifier); if (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0) { InEffect->AddHandle(Context.Target.Get(), Handle); @@ -312,6 +314,6 @@ void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag Eve if (!TargetComp) return; - FAFEventData EventData; - TargetComp->NativeTriggerTagEvent(EventTag, EventData); + //FAFEventData EventData; + //TargetComp->NativeTriggerTagEvent(EventTag, EventData); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp index 325f09d..0f1b6cc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp @@ -33,39 +33,39 @@ void UGAEffectExtension::NativeOnEffectRemoved() OnEffectRemoved(); } /** GameplayTaskOwnerInterface - Begin */ -void UGAEffectExtension::OnGameplayTaskInitialized(UGameplayTask& Task) -{ - //if (UGAAbilityTask* task = Cast(&Task)) - //{ - // task->Ability = this; - //} -} -UGameplayTasksComponent* UGAEffectExtension::GetGameplayTasksComponent(const UGameplayTask& Task) const -{ - return OwningComponent; -} -/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ -void UGAEffectExtension::OnGameplayTaskActivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Add(&Task); - //AbilityComponent->OnGameplayTaskActivated(Task); -} -/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ -void UGAEffectExtension::OnGameplayTaskDeactivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Remove(&Task); - //AbilityComponent->OnGameplayTaskDeactivated(Task); -} -AActor* UGAEffectExtension::GetGameplayTaskOwner(const UGameplayTask* Task) const -{ - return OwningComponent->GetOwner(); -} -AActor* UGAEffectExtension::GetGameplayTaskAvatar(const UGameplayTask* Task) const -{ - return Avatar; -} +//void UGAEffectExtension::OnGameplayTaskInitialized(UGameplayTask& Task) +//{ +// //if (UGAAbilityTask* task = Cast(&Task)) +// //{ +// // task->Ability = this; +// //} +//} +//UGameplayTasksComponent* UGAEffectExtension::GetGameplayTasksComponent(const UGameplayTask& Task) const +//{ +// return OwningComponent; +//} +///** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ +//void UGAEffectExtension::OnGameplayTaskActivated(UGameplayTask& Task) +//{ +// UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); +// ActiveTasks.Add(&Task); +// //AbilityComponent->OnGameplayTaskActivated(Task); +//} +///** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ +//void UGAEffectExtension::OnGameplayTaskDeactivated(UGameplayTask& Task) +//{ +// UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); +// ActiveTasks.Remove(&Task); +// //AbilityComponent->OnGameplayTaskDeactivated(Task); +//} +//AActor* UGAEffectExtension::GetGameplayTaskOwner(const UGameplayTask* Task) const +//{ +// return OwningComponent->GetOwner(); +//} +//AActor* UGAEffectExtension::GetGameplayTaskAvatar(const UGameplayTask* Task) const +//{ +// return Avatar; +//} /** GameplayTaskOwnerInterface - end */ UWorld* UGAEffectExtension::GetWorld() const diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h index 344cb03..f185909 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h @@ -19,14 +19,14 @@ Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). */ UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplayTaskOwnerInterface +class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject //, public IGameplayTaskOwnerInterface { GENERATED_BODY() public: UPROPERTY(BlueprintReadOnly, Category = "Context") FGAEffectContext Context; UPROPERTY() - class UAFAbilityComponent* OwningComponent; + class UAFEffectsComponent* OwningComponent; UPROPERTY() class AActor* Avatar; @@ -61,25 +61,25 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplay void NativeOnEffectRemoved(); /** GameplayTaskOwnerInterface - Begin */ - virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; - /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ - /** Get owner of a task or default one when task is null */ - virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; + //virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; + ///** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ + ///** Get owner of a task or default one when task is null */ + //virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; - /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ - virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; + ///** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ + //virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; - /** Get default priority for running a task */ - virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; + ///** Get default priority for running a task */ + //virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; - /** Notify called after GameplayTask finishes initialization (not active yet) */ - virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; + ///** Notify called after GameplayTask finishes initialization (not active yet) */ + //virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; - /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ - virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + ///** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ + //virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ - virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; + ///** Notify called after GameplayTask changes state from Active (finishing or pausing) */ + //virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; /** GameplayTaskOwnerInterface - end */ virtual UWorld* GetWorld() const override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index e52f539..e50cf1d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -69,7 +69,7 @@ void FGAEffectProperty::EffectExecution(const FGAEffectHandle& HandleIn } FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, - class UAFAbilityComponent* InComponent) + class UAFEffectsComponent* InComponent) : AppliedTime(AppliedTimeIn), PeriodTime(PeriodTimeIn), Duration(DurationIn), @@ -101,7 +101,6 @@ void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArra OwningComoponent = InArraySerializer.OwningComponent; AppliedTime = OwningComoponent->GetWorld()->GetTimeSeconds(); InArraySerializer.EffectInfos.Add(Handle, this); - InArraySerializer.OwningComponent->OnEffectRepInfoApplied.Broadcast(this); Type = ERepInfoType::RemotePredicted; } @@ -144,7 +143,7 @@ FGAEffect::FGAEffect(class UGAGameEffectSpec* GameEffectIn, if (GameEffect->Extension) { Extension = NewObject(Context.Target.Get(), GameEffect->Extension); - Extension->OwningComponent = Context.TargetComp.Get(); + Extension->OwningComponent = Context.GetTargetEffectsComponent(); } if (ContextIn.TargetComp.IsValid()) { @@ -420,7 +419,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr EffectIn->OnApplied(); if (InProperty.GetSpec()->IfHaveTagEffect.RequiredTag.IsValid() - && InContext.TargetComp->HasTag(InProperty.GetSpec()->IfHaveTagEffect.RequiredTag)) + && InContext.GetTargetEffectsComponent()->HasTag(InProperty.GetSpec()->IfHaveTagEffect.RequiredTag)) { for (TSubclassOf& Effect : InProperty.GetSpec()->IfHaveTagEffect.Effects) { @@ -540,7 +539,7 @@ void FGAEffectContainer::AddEffectByClass(const FGAEffectHandle& HandleIn) EGAEffectAggregation Aggregation = Spec->EffectAggregation; UClass* EffectClass = Spec->GetClass(); TSet Handles; - UAFAbilityComponent* Target = HandleIn.GetContextRef().TargetComp.Get(); + UAFEffectsComponent* Target = HandleIn.GetContextRef().GetTargetEffectsComponent(); switch (Aggregation) { case EGAEffectAggregation::AggregateByInstigator: @@ -775,6 +774,14 @@ bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) } return false; } +bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) const +{ + if (ActiveEffectHandles.Contains(HandleIn)) + { + return true; + } + return false; +} bool FGAEffectContainer::ContainsEffectOfClass(const FGAEffectProperty& InProperty) { FObjectKey key(InProperty.GetClass()); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 5c25281..85ab32e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -725,7 +725,7 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem UPROPERTY(NotReplicated) float LastPeriodTime; - class UAFAbilityComponent* OwningComoponent; + class UAFEffectsComponent* OwningComoponent; UGAGameEffectSpec* GetSpec() const { @@ -788,7 +788,7 @@ struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem } FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, - class UAFAbilityComponent* InComponent); + class UAFEffectsComponent* InComponent); }; USTRUCT() @@ -875,7 +875,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TArray TargetInstancedEffects; UPROPERTY(NotReplicated) - class UAFAbilityComponent* OwningComponent; + class UAFEffectsComponent* OwningComponent; public: //FGAEffectContainer(); /* @@ -925,6 +925,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer void ApplyEffectsFromMods() {}; void DoesQualify() {}; bool IsEffectActive(const FGAEffectHandle& HandleIn); + bool IsEffectActive(const FGAEffectHandle& HandleIn) const; bool ContainsEffectOfClass(const FGAEffectProperty& InProperty); bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index 1388364..b7d6425 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -218,6 +218,26 @@ class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() const return nullptr; } +class UAFEffectsComponent* FGAEffectContext::GetTargetEffectsComponent() +{ + IAFAbilityInterface* AttrInt = Cast(Target.Get()); + if (AttrInt) + { + return AttrInt->GetEffectsComponent(); + } + return nullptr; +} + +class UAFEffectsComponent* FGAEffectContext::GetTargetEffectsComponent() const +{ + IAFAbilityInterface* AttrInt = Cast(Target.Get()); + if (AttrInt) + { + return AttrInt->GetEffectsComponent(); + } + return nullptr; +} + FGAEffectContext::~FGAEffectContext() { Target.Reset(); @@ -342,4 +362,11 @@ FAFCueHandle FAFCueHandle::GenerateHandle() FAFCueHandle NewHandle(HandleIndex); return NewHandle; -} \ No newline at end of file +} + +FGAEffectCueParams::FGAEffectCueParams(const FGAEffectContext& InContext, const struct FGAEffectProperty& InProperty) + : HitResult(InContext.HitResult) + , Instigator(InContext.Instigator) + , Causer(InContext.Causer) + , CueTags(InProperty.GetSpec()->Cues.CueTags) +{}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 490b720..f413aa1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -282,6 +282,8 @@ struct ABILITYFRAMEWORK_API FGAEffectContext class UGAAttributesBase* GetInstigatorAttributes() const; class UGAAttributesBase* GetCauserAttributes() const; + class UAFEffectsComponent* GetTargetEffectsComponent(); + class UAFEffectsComponent* GetTargetEffectsComponent() const; FGAEffectContext() {} @@ -808,18 +810,10 @@ struct ABILITYFRAMEWORK_API FGAEffectCueParams /** The physical actor that actually did the damage, can be a weapon or projectile */ UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") TWeakObjectPtr Causer; - /* Which ability spawned (if applicable) */ - UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") - TWeakObjectPtr Ability; - - /* Tick interval for periodic effects */ - UPROPERTY(BlueprintReadOnly, Category = "GameplayCue") - float Period; - UPROPERTY(BlueprintReadOnly, Category = "GameplayCue") - float Duration; UPROPERTY(BlueprintReadOnly) FGameplayTagContainer CueTags; + FGAEffectCueParams() {}; FGAEffectCueParams(const FHitResult& InHitResult, AActor* InstigatorIn, UObject* CauserIn) @@ -827,6 +821,7 @@ struct ABILITYFRAMEWORK_API FGAEffectCueParams Instigator(InstigatorIn), Causer(CauserIn) {}; + FGAEffectCueParams(const FGAEffectContext& InContext, const struct FGAEffectProperty& InProperty); //bool NetSerialize(FArchive& Ar, class UPackageMap* Map, bool& bOutSuccess); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h deleted file mode 100644 index b011d8d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobals.h +++ /dev/null @@ -1,88 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once -#include "Engine/NetSerialization.h" -#include "GameplayTags.h" -#include "GAGlobals.generated.h" -/** - * - */ -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASAbilitySetItem -{ - GENERATED_USTRUCT_BODY() -public: - /* Index in this array coresponds directly FGASActiveAbility::ActiveAbilities Index*/ - UPROPERTY(EditAnywhere) - TSubclassOf AbilityClass; - - UPROPERTY(EditAnywhere) - FGameplayTag Binding; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASAbilitySetContainer -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Abilities; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFAbilityNotifyData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere) - float TEMP; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASAbilityHit : public FFastArraySerializerItem -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - FHitResult Hit; - - FGASAbilityHit() - {} - - FGASAbilityHit(const FHitResult& HitIn) - : Hit(HitIn) - {}; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASAbilityHitArray : public FFastArraySerializer -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - TArray Hits; - - inline void AddHit(const FHitResult& HitIn) - { - Hits.Add(FGASAbilityHit(HitIn)); - } - - inline void Empty() - { - Hits.Empty(); - } - - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(Hits, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FGASAbilityHitArray > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp deleted file mode 100644 index adcb2e0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAAttributesTest.h" - - - - -void UGAAttributesTest::InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) -{ - - Super::InitializeAttributes(InOwningAttributeComp); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h deleted file mode 100644 index 4553dc4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTest.h +++ /dev/null @@ -1,49 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "../Attributes/GAAttributesBase.h" -#include "GAAttributesTest.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAttributesTest : public UGAAttributesBase -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase Health; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase Energy; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase Stamina; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase Magic; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase Inteligence; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase MagicDamageBonus; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase MagicDamageMultiplayer; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase Armor; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase MagicDefensePercentage; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase MagicDefenseFlat; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase MagicalBonus; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase PhysicalBonus; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Base Attributes") - FAFAttributeBase MagicResistance; -public: - virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) override; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp deleted file mode 100644 index 7ab732b..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAAttributesTests.cpp +++ /dev/null @@ -1,1647 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "AutomationTest.h" -#include "GameplayTagsModule.h" -#include "../GAGlobalTypes.h" -#include "../Attributes/GAAttributeBase.h" -#include "../Effects/GAGameEffect.h" -#include "../AFAbilityComponent.h" -#include "../Attributes/GAAttributesBase.h" -#include "../Effects/GAEffectExecution.h" -#include "../Effects/GABlueprintLibrary.h" -#include "GAAttributesTest.h" -#include "GASpellExecutionTest.h" -#include "GACharacterAttributeTest.h" -#include "GACustomCalculationTest.h" -#include "GAffectSpecTestOne.h" -#include "../Effects/ApplicationRequirement/AFAttributeStongerOverride.h" -#include "../Effects/CustomApplications/AFAttributeDurationOverride.h" -#include "../Effects/CustomApplications/AFPeriodApplicationOverride.h" -#include "../Effects/CustomApplications/AFAtributeDurationAdd.h" -#include "../Effects/CustomApplications/AFPeriodApplicationAdd.h" -#include "../Effects/CustomApplications/AFAttributeDurationInfinite.h" -#include "../Effects/CustomApplications/AFPeriodApplicationExtend.h" - -#if WITH_EDITOR - -static UDataTable* CreateGameplayDataTable() -{ - FString CSV(TEXT(",Tag,CategoryText,")); - CSV.Append(TEXT("\r\n0,Damage")); - CSV.Append(TEXT("\r\n1,Damage.Basic")); - CSV.Append(TEXT("\r\n2,Damage.Type1")); - CSV.Append(TEXT("\r\n3,Damage.Type2")); - CSV.Append(TEXT("\r\n4,Damage.Reduce")); - CSV.Append(TEXT("\r\n5,Damage.Buffable")); - CSV.Append(TEXT("\r\n6,Damage.Buff")); - CSV.Append(TEXT("\r\n7,Damage.Physical")); - CSV.Append(TEXT("\r\n8,Damage.Fire")); - CSV.Append(TEXT("\r\n9,Damage.Buffed.FireBuff")); - CSV.Append(TEXT("\r\n10,Damage.Mitigated.Armor")); - CSV.Append(TEXT("\r\n11,Lifesteal")); - CSV.Append(TEXT("\r\n12,Shield")); - CSV.Append(TEXT("\r\n13,Buff")); - CSV.Append(TEXT("\r\n14,Immune")); - CSV.Append(TEXT("\r\n15,FireDamage")); - CSV.Append(TEXT("\r\n16,ShieldAbsorb")); - CSV.Append(TEXT("\r\n17,Stackable")); - CSV.Append(TEXT("\r\n18,Stack")); - CSV.Append(TEXT("\r\n19,Stack.CappedNumber")); - CSV.Append(TEXT("\r\n20,Stack.DiminishingReturns")); - CSV.Append(TEXT("\r\n21,Protect.Damage")); - CSV.Append(TEXT("\r\n22,SpellDmg.Buff")); - CSV.Append(TEXT("\r\n23,GameplayCue.Burning")); - CSV.Append(TEXT("\r\n24,Damage.Fire")); - CSV.Append(TEXT("\r\n25,Damage.Ice")); - CSV.Append(TEXT("\r\n26,Damage.Acid")); - CSV.Append(TEXT("\r\n27,Damage.Earth")); - CSV.Append(TEXT("\r\n28,Damage.Electricity")); - CSV.Append(TEXT("\r\n29,Damage.Darkness")); - CSV.Append(TEXT("\r\n30,Damage.Necrotic")); - CSV.Append(TEXT("\r\n31,Damage.Radiant")); - CSV.Append(TEXT("\r\n32,Damage.Water")); - - auto DataTable = NewObject(GetTransientPackage(), FName(TEXT("TempDataTable"))); - DataTable->RowStruct = FGameplayTagTableRow::StaticStruct(); - DataTable->CreateTableFromCSVString(CSV); - - FGameplayTagTableRow * Row = (FGameplayTagTableRow*)DataTable->RowMap["0"]; - if (Row) - { - check(Row->Tag == TEXT("Damage")); - } - return DataTable; -}; - -struct FTagsInput -{ - FGameplayTagContainer OwnedTags; - FGameplayTagContainer EffectTags; - FGameplayTagContainer AttributeTags; - FGameplayTagContainer DenyTags; - FGameplayTagContainer AppliedImmunityTags; - FGameplayTagContainer ApplyTags; - FGameplayTagContainer RequiredTags; - FGameplayTagContainer OngoingRequiredTags; -}; -#define CONSTRUCT_CLASS(Class, Name) Class* Name = NewObject(GetTransientPackage(), FName(TEXT(#Name))) -class GameEffectsTestSuite -{ - UWorld* World; - FAutomationTestBase* Test; - - AGACharacterAttributeTest* SourceActor; - UAFAbilityComponent* SourceComponent; - - AGACharacterAttributeTest* DestActor; - UAFAbilityComponent* DestComponent; - - AGACharacterAttributeTest* TargetOne; - UAFAbilityComponent* TargetCompOne; - - AGACharacterAttributeTest* TargetTwo; - UAFAbilityComponent* TargetCompTwo; - -public: - GameEffectsTestSuite(UWorld* WorldIn, FAutomationTestBase* TestIn) - : World(WorldIn), - Test(TestIn) - { - SourceActor = World->SpawnActor(); - SourceComponent = SourceActor->Attributes; - SourceComponent->DefaultAttributes = NewObject(SourceActor->Attributes); - SourceComponent->GetAttributes()->Health.SetBaseValue(100); - SourceComponent->GetAttributes()->Energy.SetBaseValue(100); - SourceComponent->GetAttributes()->Stamina.SetBaseValue(100); - SourceComponent->GetAttributes()->Health.SetMaxValue(500); - SourceComponent->GetAttributes()->Energy.SetMaxValue(500); - SourceComponent->GetAttributes()->Stamina.SetMaxValue(500); - /*SourceComponent->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; - SourceComponent->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; - SourceComponent->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add; -*/ - SourceComponent->GetAttributes()->MagicalBonus.SetMaxValue(500); - SourceComponent->GetAttributes()->PhysicalBonus.SetMaxValue(500); - SourceComponent->GetAttributes()->MagicResistance.SetMaxValue(500); - - //SourceComponent->GetAttributes()->MagicalBonus.Stacking = EAFAttributeStacking::Override; - //SourceComponent->GetAttributes()->PhysicalBonus.Stacking = EAFAttributeStacking::Add; - //SourceComponent->GetAttributes()->MagicResistance.Stacking = EAFAttributeStacking::Override; - - SourceComponent->GetAttributes()->Health.InitializeAttribute(SourceComponent, TEXT("Health")); - SourceComponent->GetAttributes()->Energy.InitializeAttribute(SourceComponent, TEXT("Energy")); - SourceComponent->GetAttributes()->Stamina.InitializeAttribute(SourceComponent, TEXT("Stamina")); - - SourceComponent->GetAttributes()->MagicalBonus.InitializeAttribute(SourceComponent, TEXT("MagicalBonus")); - SourceComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(SourceComponent, TEXT("PhysicalBonus")); - SourceComponent->GetAttributes()->MagicResistance.InitializeAttribute(SourceComponent, TEXT("MagicResistance")); - SourceComponent->DefaultAttributes->InitializeAttributes(SourceComponent); - - DestActor = World->SpawnActor(); - DestComponent = DestActor->Attributes; - DestComponent->DefaultAttributes = NewObject(DestActor->Attributes); - DestComponent->GetAttributes()->Health.SetBaseValue(100); - DestComponent->GetAttributes()->Energy.SetBaseValue(100); - DestComponent->GetAttributes()->Stamina.SetBaseValue(100); - DestComponent->GetAttributes()->Health.SetMaxValue(500); - DestComponent->GetAttributes()->Energy.SetMaxValue(500); - DestComponent->GetAttributes()->Stamina.SetMaxValue(500); - /*DestComponent->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; - DestComponent->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; - DestComponent->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add;*/ - DestComponent->GetAttributes()->MagicalBonus.SetMaxValue(500); - DestComponent->GetAttributes()->PhysicalBonus.SetMaxValue(500); - DestComponent->GetAttributes()->MagicResistance.SetMaxValue(500); - - DestComponent->GetAttributes()->Health.InitializeAttribute(DestComponent, TEXT("Health")); - DestComponent->GetAttributes()->Energy.InitializeAttribute(DestComponent, TEXT("Energy")); - DestComponent->GetAttributes()->Stamina.InitializeAttribute(DestComponent, TEXT("Stamina")); - - DestComponent->GetAttributes()->MagicalBonus.InitializeAttribute(DestComponent, TEXT("MagicalBonus")); - DestComponent->GetAttributes()->PhysicalBonus.InitializeAttribute(DestComponent, TEXT("PhysicalBonus")); - DestComponent->GetAttributes()->MagicResistance.InitializeAttribute(DestComponent, TEXT("MagicResistance")); - DestComponent->DefaultAttributes->InitializeAttributes(DestComponent); - - TargetOne = World->SpawnActor(); - TargetCompOne = TargetOne->Attributes; - TargetCompOne->DefaultAttributes = NewObject(TargetOne->Attributes); - TargetCompOne->GetAttributes()->Health.SetBaseValue(100); - TargetCompOne->GetAttributes()->Energy.SetBaseValue(100); - TargetCompOne->GetAttributes()->Stamina.SetBaseValue(100); - TargetCompOne->GetAttributes()->Health.SetMaxValue(500); - TargetCompOne->GetAttributes()->Energy.SetMaxValue(500); - TargetCompOne->GetAttributes()->Stamina.SetMaxValue(500); - //TargetCompOne->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; - //TargetCompOne->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; - //TargetCompOne->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add; - TargetCompOne->GetAttributes()->MagicalBonus.SetMaxValue(500); - TargetCompOne->GetAttributes()->PhysicalBonus.SetMaxValue(500); - TargetCompOne->GetAttributes()->MagicResistance.SetMaxValue(500); - - TargetCompOne->GetAttributes()->Health.InitializeAttribute(TargetCompOne, TEXT("Health")); - TargetCompOne->GetAttributes()->Energy.InitializeAttribute(TargetCompOne, TEXT("Energy")); - TargetCompOne->GetAttributes()->Stamina.InitializeAttribute(TargetCompOne, TEXT("Stamina")); - - TargetCompOne->GetAttributes()->MagicalBonus.InitializeAttribute(TargetCompOne, TEXT("MagicalBonus")); - TargetCompOne->GetAttributes()->PhysicalBonus.InitializeAttribute(TargetCompOne, TEXT("PhysicalBonus")); - TargetCompOne->GetAttributes()->MagicResistance.InitializeAttribute(TargetCompOne, TEXT("MagicResistance")); - TargetCompOne->DefaultAttributes->InitializeAttributes(TargetCompOne); - - - TargetTwo = World->SpawnActor(); - TargetCompTwo = TargetTwo->Attributes; - TargetCompTwo->DefaultAttributes = NewObject(TargetTwo->Attributes); - TargetCompTwo->GetAttributes()->Health.SetBaseValue(100); - TargetCompTwo->GetAttributes()->Energy.SetBaseValue(100); - TargetCompTwo->GetAttributes()->Stamina.SetBaseValue(100); - TargetCompTwo->GetAttributes()->Health.SetMaxValue(500); - TargetCompTwo->GetAttributes()->Energy.SetMaxValue(500); - TargetCompTwo->GetAttributes()->Stamina.SetMaxValue(500); - //TargetCompTwo->GetAttributes()->Health.Stacking = EAFAttributeStacking::StrongerOverride; - //TargetCompTwo->GetAttributes()->Energy.Stacking = EAFAttributeStacking::Override; - //TargetCompTwo->GetAttributes()->Stamina.Stacking = EAFAttributeStacking::Add; - TargetCompTwo->GetAttributes()->MagicalBonus.SetMaxValue(500); - TargetCompTwo->GetAttributes()->PhysicalBonus.SetMaxValue(500); - TargetCompTwo->GetAttributes()->MagicResistance.SetMaxValue(500); - - TargetCompTwo->GetAttributes()->Health.InitializeAttribute(TargetCompTwo, TEXT("Health")); - TargetCompTwo->GetAttributes()->Energy.InitializeAttribute(TargetCompTwo, TEXT("Energy")); - TargetCompTwo->GetAttributes()->Stamina.InitializeAttribute(TargetCompTwo, TEXT("Stamina")); - - TargetCompTwo->GetAttributes()->MagicalBonus.InitializeAttribute(TargetCompTwo, TEXT("MagicalBonus")); - TargetCompTwo->GetAttributes()->PhysicalBonus.InitializeAttribute(TargetCompTwo, TEXT("PhysicalBonus")); - TargetCompTwo->GetAttributes()->MagicResistance.InitializeAttribute(TargetCompTwo, TEXT("MagicResistance")); - TargetCompTwo->DefaultAttributes->InitializeAttributes(TargetCompTwo); - - //DestActor->BeginPlay(); - //SourceActor->BeginPlay(); - } - - ~GameEffectsTestSuite() - { - // run after each test - - // destroy the actors - if (SourceActor) - { - World->EditorDestroyActor(SourceActor, false); - } - if (DestActor) - { - World->EditorDestroyActor(DestActor, false); - } - } - void TickWorld(float Time) - { - const float step = 0.01f; - while (Time > 0.f) - { - World->Tick(ELevelTick::LEVELTICK_All, FMath::Min(Time, step)); - Time -= step; - - // This is terrible but required for subticking like this. - // we could always cache the real GFrameCounter at the start of our tests and restore it when finished. - GFrameCounter++; - } - } - FGameplayTag RequestTag(const FName& TagIn) - { - return UGameplayTagsManager::Get().RequestGameplayTag(TagIn); - } - - FGameplayTagContainer CreateTags(const TArray& TagsIn) - { - FGameplayTagContainer OutTags; - TArray Tags; - for (const FName& Tag : TagsIn) - { - FGameplayTag ReqTeg = UGameplayTagsManager::Get().RequestGameplayTag(Tag); - if (ReqTeg.IsValid()) - { - Tags.Add(ReqTeg); - } - } - OutTags = FGameplayTagContainer::CreateFromArray(Tags); - //OutTags.FillParentTags(); - return OutTags; - } - - void TestEqual(const FString& TestText, float Actual, float Expected) - { - Test->TestEqual(FString::Printf(TEXT("%s: %f (actual) != %f (expected)"), *TestText, Actual, Expected), Actual, Expected); - } - void TestEqual(const FString& TestText, int32 Actual, int32 Expected) - { - Test->TestEqual(FString::Printf(TEXT("%s: %f (actual) != %f (expected)"), *TestText, Actual, Expected), Actual, Expected); - } - void TestEqualTags(const FString& TestText, FName Actual, FName Expected) - { - Test->TestEqual(FString::Printf(TEXT("%s: %s (actual) != %s (expected)"), *TestText, *Actual.ToString(), *Expected.ToString()), Actual, Expected); - } - void TestEqualTags(const FString& TestText, FGameplayTag Actual, FGameplayTag Expected) - { - Test->TestEqual(FString::Printf(TEXT("%s: %s (actual) != %s (expected)"), *TestText, *Actual.ToString(), *Expected.ToString()), Actual, Expected); - } - FGAAttributeModifier CreateAttributeModifer(const TArray& OwnedTags, float ModValue, - EGAAttributeMod ModType, const FName& Attribute) - { - FGAAttributeModifier AttributeModifier; - AttributeModifier.Attribute = FGAAttribute(Attribute); - AttributeModifier.AttributeMod = ModType; - AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; - AttributeModifier.Magnitude.DirectModifier.Value = ModValue; - - return AttributeModifier; - } - - FGAEffectProperty CreateEffectSpec(const TArray& OwnedTags, float ModValue, - EGAAttributeMod ModType, const FName& Attribute, TSubclassOf CDO) - { - TSubclassOf c = CDO; - FGAEffectProperty Spec; - //UGAGameEffectSpec* Effect = NewObject(GetTransientPackage()); - Spec = c; - //Spec = Effect; - UGAGameEffectSpec* cds = Spec.GetClass().GetDefaultObject(); - cds->ExecutionType = UGASpellExecutionTest::StaticClass(); - cds->ApplicationRequirement = UAFEffectApplicationRequirement::StaticClass(); - cds->Application = UAFEffectCustomApplication::StaticClass(); - FGAAttributeModifier AttributeModifier; - AttributeModifier.Attribute = FGAAttribute(Attribute); - AttributeModifier.AttributeMod = ModType; - AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; - AttributeModifier.Magnitude.DirectModifier.Value = ModValue; - cds->OwnedTags = CreateTags(OwnedTags); - cds->AtributeModifier = AttributeModifier; - FGAMagnitude DurationMag; - DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; - DurationMag.DirectModifier.Value = 0; - cds->Duration = DurationMag; - FGAMagnitude PeriodMag; - PeriodMag.CalculationType = EGAMagnitudeCalculation::Direct; - PeriodMag.DirectModifier.Value = 0; - cds->Period = PeriodMag; - return Spec; - } - FGAEffectProperty CreateEffectDurationSpec(const TArray& OwnedTags, float ModValue, - EGAAttributeMod ModType, const FName& Attribute, EGAEffectStacking Stacking, - const TArray& AttributeTags = TArray(), - const TArray& ApplyTags = TArray(), - const FTagsInput& TagsIn = FTagsInput(), - TSubclassOf ApplReq = UAFEffectApplicationRequirement::StaticClass(), - TSubclassOf Appl = UAFEffectCustomApplication::StaticClass(), - TSubclassOf CDO = UGAGameEffectSpec::StaticClass() - ) - { - const float Duration = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - FGAEffectProperty Spec; - Spec = CDO; - UGAGameEffectSpec* cdo = Spec.GetClass().GetDefaultObject(); - - //UClass* clas = DuplicateObject(UGAGameEffectSpec::StaticClass()); - //Spec.Spec = - cdo->ExecutionType = UGAEffectExecution::StaticClass(); - cdo->ApplicationRequirement = ApplReq; - cdo->Application = Appl; - cdo->OwnedTags = CreateTags(OwnedTags); - cdo->bExecuteOnApplication = true; - if (AttributeTags.Num() > 0) - cdo->AttributeTags = CreateTags(AttributeTags); - if (ApplyTags.Num() > 0) - cdo->ApplyTags = CreateTags(ApplyTags); - - cdo->RequiredTags = TagsIn.RequiredTags; - cdo->DenyTags = TagsIn.DenyTags; - cdo->ExecutionRequiredTags = TagsIn.OngoingRequiredTags; - - FGAAttributeModifier AttributeModifier; - AttributeModifier.Attribute = FGAAttribute(Attribute); - AttributeModifier.AttributeMod = ModType; - AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; - AttributeModifier.Magnitude.DirectModifier.Value = ModValue; - cdo->AtributeModifier = AttributeModifier; - FGAMagnitude DurationMag; - DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; - DurationMag.DirectModifier.Value = Duration; - cdo->Duration = DurationMag; - FGAMagnitude PeriodMag; - PeriodMag.CalculationType = EGAMagnitudeCalculation::Direct; - PeriodMag.DirectModifier.Value = 0; - cdo->Period = PeriodMag; - return Spec; - } - - FGAEffectProperty CreateEffectPeriodicSpec(const TArray& OwnedTags, float ModValue, - EGAAttributeMod ModType, const FName& Attribute, EGAEffectStacking Stacking, - const TArray& AttributeTags = TArray(), - const TArray& ApplyTags = TArray(), - const FTagsInput& TagsIn = FTagsInput(), - TSubclassOf CDO = UGAGameEffectSpec::StaticClass(), - TSubclassOf Appl = UAFEffectCustomApplication::StaticClass(), - bool InExecuteOnApplication = false - ) - { - const float Duration = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - FGAEffectProperty Spec; - Spec = CDO; - UGAGameEffectSpec* cdo = Spec.GetClass().GetDefaultObject(); - - cdo->ExecutionType = UGAEffectExecution::StaticClass(); - cdo->ApplicationRequirement = UAFAttributeStongerOverride::StaticClass(); - cdo->Application = Appl; - - cdo->OwnedTags = CreateTags(OwnedTags); - if (AttributeTags.Num() > 0) - cdo->AttributeTags = CreateTags(AttributeTags); - if (ApplyTags.Num() > 0) - cdo->ApplyTags = CreateTags(ApplyTags); - - cdo->RequiredTags = TagsIn.RequiredTags; - cdo->DenyTags = TagsIn.DenyTags; - cdo->ExecutionRequiredTags = TagsIn.OngoingRequiredTags; - cdo->bExecuteOnApplication = InExecuteOnApplication; - FGAAttributeModifier AttributeModifier; - AttributeModifier.Attribute = FGAAttribute(Attribute); - AttributeModifier.AttributeMod = ModType; - AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; - AttributeModifier.Magnitude.DirectModifier.Value = ModValue; - cdo->AtributeModifier = AttributeModifier; - FGAMagnitude DurationMag; - DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; - DurationMag.DirectModifier.Value = Duration; - cdo->Duration = DurationMag; - FGAMagnitude PeriodMag; - PeriodMag.CalculationType = EGAMagnitudeCalculation::Direct; - PeriodMag.DirectModifier.Value = PeriodSecs; - cdo->Period = PeriodMag; - return Spec; - } - - FGAEffectProperty CreateEffectInfiniteSpec(const TArray& OwnedTags, float ModValue, - EGAAttributeMod ModType, const FName& Attribute, EGAEffectStacking Stacking, - const TArray& AttributeTags = TArray(), - const TArray& ApplyTags = TArray(), - const FTagsInput& TagsIn = FTagsInput(), - TSubclassOf CDO = UGAGameEffectSpec::StaticClass(), - TSubclassOf ApplReq = UAFEffectApplicationRequirement::StaticClass(), - TSubclassOf Appl = UAFEffectCustomApplication::StaticClass() - ) - { - const float Duration = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - FGAEffectProperty Spec; - Spec = CDO; - UGAGameEffectSpec* cdo = Spec.GetClass().GetDefaultObject(); - - //UClass* clas = DuplicateObject(UGAGameEffectSpec::StaticClass()); - //Spec.Spec = - cdo->ApplicationRequirement = ApplReq; - cdo->Application = Appl; - cdo->ExecutionType = UGAEffectExecution::StaticClass(); - cdo->OwnedTags = CreateTags(OwnedTags); - cdo->bExecuteOnApplication = true; - if (AttributeTags.Num() > 0) - cdo->AttributeTags = CreateTags(AttributeTags); - if (ApplyTags.Num() > 0) - cdo->ApplyTags = CreateTags(ApplyTags); - - cdo->RequiredTags = TagsIn.RequiredTags; - cdo->DenyTags = TagsIn.DenyTags; - cdo->ExecutionRequiredTags = TagsIn.OngoingRequiredTags; - - FGAAttributeModifier AttributeModifier; - AttributeModifier.Attribute = FGAAttribute(Attribute); - AttributeModifier.AttributeMod = ModType; - AttributeModifier.Magnitude.CalculationType = EGAMagnitudeCalculation::Direct; - AttributeModifier.Magnitude.DirectModifier.Value = ModValue; - cdo->AtributeModifier = AttributeModifier; - FGAMagnitude DurationMag; - DurationMag.CalculationType = EGAMagnitudeCalculation::Direct; - DurationMag.DirectModifier.Value = Duration; - cdo->Duration = DurationMag; - - return Spec; - } - - void ApplyEffectModifiers() - { - - } - void Test_CompareTagContainers() - { - TArray OwnedTags1; - OwnedTags1.Add(TEXT("Damage.Ice")); - OwnedTags1.Add(TEXT("Damage.Spell")); - FGameplayTagContainer A = CreateTags(OwnedTags1); - - TArray OwnedTags2; - OwnedTags2.Add(TEXT("Damage")); - FGameplayTagContainer B = CreateTags(OwnedTags2); - - TArray OwnedTags3; - OwnedTags3.Add(TEXT("Damage.Spell")); - FGameplayTagContainer C = CreateTags(OwnedTags3); - - TArray OwnedTags4; - OwnedTags4.Add(TEXT("Damage.Ice")); - OwnedTags4.Add(TEXT("Damage.Spell")); - OwnedTags4.Add(TEXT("Ability.Fireball")); - - FGameplayTagContainer Ability = CreateTags(OwnedTags4); - - bool A_Ability = A.HasAll(Ability); //false - bool B_Ability = B.HasAll(Ability); //false - bool C_Ability = C.HasAll(Ability); //false - - Test->TestFalse("A_ABility: ", A_Ability); - Test->TestFalse("B_ABility: ", B_Ability); - Test->TestFalse("C_ABility: ", C_Ability); - - bool Ability_A = Ability.HasAll(A); //true - bool Ability_B = Ability.HasAll(B); //true - bool Ability_C = Ability.HasAll(C); //true - Test->TestTrue("Ability_A: ", Ability_A); - Test->TestTrue("Ability_B: ", Ability_B); - Test->TestTrue("Ability_C: ", Ability_C); - } - - void Test_InstantEffectApplication() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - FGAEffectProperty Effect = CreateEffectSpec(OwnedTags, 10, - EGAAttributeMod::Subtract, "Health", UGAGameEffectSpec::StaticClass()); - - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Post: ", PostVal, 90.0f); - } - //Damage.Fire - //Damage.Basic - //Damage.Buffed.FireBuff - //Damage.Acid - //Buff - //Immune - //Item - //Item.Rune - //Spell - //Stackable - //Attribute.Health - //Condition.Burning - void Test_PeriodicDamageEffect() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - AttributeTags.Add(TEXT("Buff")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Buff")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 5, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - ++NumApplications; - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Post: ", PostVal, 100.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - - ++NumApplications; - - // check that health has been reduced - - } - TickWorld(PeriodSecs); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 55.0f); - } - - void Test_DurationBuffEffect() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 5, - EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass()); - - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - - ++NumApplications; - - // check that health has been reduced - - } - TickWorld(PeriodSecs); - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Post: ", PostVal, 55.0f); - } - - void Test_AtttributeStatckingOverride() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Energy"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), - UAFAttributeDurationOverride::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - - - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Energy")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Energy")); - TestEqual("Source Health PPost: ", PostVal, 150.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, - EGAAttributeMod::Add, TEXT("Energy"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), - UAFAttributeDurationOverride::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Energy")); - TestEqual("Source Health Post2: ", PostVal2, 130.0f); - } - - // check that health has been reduced - - } - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Energy")); - TestEqual("Source Health Finished: ", FinishedVal, 100.0f); - } - - void Test_AtttributeStatckingStrongerOverride() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), - UAFAttributeDurationOverride::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 150.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, - EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), - UAFAttributeDurationOverride::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - //for (int32 i = 0; i < NumPeriods; ++i) - //{ - // // advance time by one period - // TickWorld(PeriodSecs); - //} - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 100.0f); - } - - void Test_AtttributeStatckingStrongerOverrideReversed() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 30, - EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), - UAFAttributeDurationOverride::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 130.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFAttributeStongerOverride::StaticClass(), - UAFAttributeDurationOverride::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 100.0f); - } - - void Test_AtttributeStatckingeAdd() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), - UAFAtributeDurationAdd::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PPost: ", PostVal, 150.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, - EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), - UAFAtributeDurationAdd::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Post2: ", PostVal2, 180.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PreFinished: ", PreFinishedVal, 130.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Finished: ", FinishedVal, 100.0f); - } - void Test_AtttributeStatckingeAddSameProp() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), - UAFAtributeDurationAdd::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PPost: ", PostVal, 150.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Post2: ", PostVal2, 200.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PreFinished: ", PreFinishedVal, 150.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Finished: ", FinishedVal, 100.0f); - } - - void Test_AtttributeStatckingeAddSamePropDifferentTargets() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectDurationSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UAFEffectApplicationRequirement::StaticClass(), - UAFAtributeDurationAdd::StaticClass(), - UGAGameEffectSpec::StaticClass() - ); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PPost: ", PostVal, 150.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, TargetOne, SourceActor, SourceActor, FuncMod); - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = TargetCompOne->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("TargetCompOne Stamina PreFinished: ", PreFinishedVal, 150.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Finished: ", FinishedVal, 100.0f); - - float TargetOneFinish = TargetCompOne->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("TargetCompOne Stamina PreFinished: ", TargetOneFinish, 100.0f); - } - - void Test_AtttributeStatckingeAddInfinite() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectInfiniteSpec(OwnedTags, 50, - EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFEffectApplicationRequirement::StaticClass(), - UAFAttributeDurationInfinite::StaticClass() - ); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PPost: ", PostVal, 150.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - //if (i == 5) - //{ - // FGAEffectProperty EffectWeaker = CreateEffectDurationSpec(OwnedTags, 30, - // EGAAttributeMod::Add, TEXT("Stamina"), EGAEffectStacking::Override, - // AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass()); - // UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - // float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - // TestEqual("Source Stamina Post2: ", PostVal2, 180.0f); - //} - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina PreFinished: ", PreFinishedVal, 150.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Finished: ", FinishedVal, 150.0f); - FGAEffectContext Context = UGABlueprintLibrary::MakeContext(DestActor, SourceActor, DestActor, SourceActor, FHitResult(ForceInit)); - //DestComponent->RemoveEffect(Effect, Context); - float PostRemovedVal = DestComponent->GetAttributeValue(FGAAttribute("Stamina")); - TestEqual("Source Stamina Finished: ", PostRemovedVal, 100.0f); - } - - void Test_EffectStatckingOverride() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 5, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost2: ", PostVal2, 70.0f); - FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 32.0f); - } - - void Test_EffectStatckingOverrideSameClass() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 5, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost2: ", PostVal2, 70.0f); - FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Override, - AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 32.0f); - } - - void Test_EffectStatckingAdd() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationAdd::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost2: ", PostVal2, 88.0f); - FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, - AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), - UAFPeriodApplicationAdd::StaticClass()); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 74.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 62.0f); - } - - void Test_EffectStatckingAddSameHandle() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationAdd::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost2: ", PostVal2, 88.0f); - /*FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, - AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), - UAFPeriodApplicationAdd::StaticClass());*/ - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 74.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 62.0f); - } - - void Test_EffectStatckingAddSameHandleDifferentTargets() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationAdd::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - //TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("DestComponent Health PPost2: ", PostVal2, 88.0f); - - /*FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Add, - AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), - UAFPeriodApplicationAdd::StaticClass());*/ - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, TargetOne, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - UE_LOG(AbilityFramework, Log, TEXT("Val: %d"), i * 2); - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("DestComponent Health PreFinishedVal: ", PreFinishedVal, 80.0f);; - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = TargetCompOne->GetAttributeValue(FGAAttribute("Health")); - TestEqual("TargetCompOne Health Finished: ", FinishedVal, 82.0f); - } - - - void Test_EffectStatckingDurationDifferentEffects() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 1, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost2: ", PostVal2, 94.0f); - FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, - AttributeTags, ApplyTags, TagsIn, UGAffectSpecTestOne::StaticClass(), - UAFPeriodApplicationOverride::StaticClass()); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 84.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 72.0f); - } - - void Test_EffectStatckingDurationSameEffects() - { - TArray OwnedTags; - OwnedTags.Add("Ability.Fireball"); - TArray AttributeTags; - AttributeTags.Add(TEXT("Damage.Fire")); - - TArray ApplyTags; - ApplyTags.Add(TEXT("Damage.Fire")); - ApplyTags.Add(TEXT("Ability.Fireball")); - - FTagsInput TagsIn; - - FGAEffectProperty Effect = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationExtend::StaticClass()); - - int32 NumApplications = 0; - float PreVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Pre: ", PreVal, 100.0f); - FAFFunctionModifier FuncMod; - UGABlueprintLibrary::ApplyGameEffectToActor(Effect, DestActor, SourceActor, SourceActor, FuncMod); - - TickWorld(SMALL_NUMBER); - //++NumApplications; - float PostVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost: ", PostVal, 100.0f); - const int32 NumPeriods = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - TickWorld(PeriodSecs * .1f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - if (i == 5) - { - float PostVal2 = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PPost2: ", PostVal2, 88.0f); - FGAEffectProperty EffectWeaker = CreateEffectPeriodicSpec(OwnedTags, 2, - EGAAttributeMod::Subtract, TEXT("Health"), EGAEffectStacking::Duration, - AttributeTags, ApplyTags, TagsIn, UGAGameEffectSpec::StaticClass(), - UAFPeriodApplicationExtend::StaticClass()); - UGABlueprintLibrary::ApplyGameEffectToActor(EffectWeaker, DestActor, SourceActor, SourceActor, FuncMod); - //TestEqual("Source Health Post2: ", PostVal2, 150.0f); - } - - // check that health has been reduced - - } - float PreFinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health PreFinishedVal: ", PreFinishedVal, 80.0f); - for (int32 i = 0; i < NumPeriods; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - } - TickWorld(PeriodSecs * 0.1f); - float FinishedVal = DestComponent->GetAttributeValue(FGAAttribute("Health")); - TestEqual("Source Health Finished: ", FinishedVal, 60.0f); - } - - void Test_StrongerOverrideNonStackingHealthBonus() - { - const float Duration = 10; - const float PeriodSecs = 1.0f; - const float DamagePerPeriod = 5.f; - for (int32 i = 0; i < 9; ++i) - { - // advance time by one period - TickWorld(PeriodSecs); - //++NumApplications;; - } - - // advance time by one extra period - TickWorld(PeriodSecs); - } - -}; -#define ADD_TEST(Name) \ - TestFunctions.Add(&GameEffectsTestSuite::Name); \ - TestFunctionNames.Add(TEXT(#Name)) - - - -class FGAAttributesTests : public FAutomationTestBase -{ -public: - typedef void (GameEffectsTestSuite::*TestFunc)(); - TArray TestFunctions; - TArray TestFunctionNames; - - FGAAttributesTests(const FString& InName) - : FAutomationTestBase(InName, false) - { - ADD_TEST(Test_CompareTagContainers); - ADD_TEST(Test_InstantEffectApplication); - ADD_TEST(Test_PeriodicDamageEffect); - ADD_TEST(Test_AtttributeStatckingOverride); - ADD_TEST(Test_AtttributeStatckingStrongerOverride); - ADD_TEST(Test_AtttributeStatckingStrongerOverrideReversed); - ADD_TEST(Test_AtttributeStatckingeAdd); - ADD_TEST(Test_AtttributeStatckingeAddSameProp); - ADD_TEST(Test_AtttributeStatckingeAddSamePropDifferentTargets); - ADD_TEST(Test_AtttributeStatckingeAddInfinite); - ADD_TEST(Test_EffectStatckingOverride); - ADD_TEST(Test_EffectStatckingOverrideSameClass); - ADD_TEST(Test_EffectStatckingAdd); - ADD_TEST(Test_EffectStatckingAddSameHandle); - ADD_TEST(Test_EffectStatckingAddSameHandleDifferentTargets); - ADD_TEST(Test_EffectStatckingDurationDifferentEffects); - ADD_TEST(Test_EffectStatckingDurationSameEffects); - ADD_TEST(Test_StrongerOverrideNonStackingHealthBonus); - }; - virtual uint32 GetTestFlags() const override - { - //EAutomationTestFlags::Type::EditorContext | - return (EAutomationTestFlags::Type::EngineFilter); - }//EAutomationTestFlags::EditorContext | EAutomationTestFlags::SmokeFilter; } - virtual bool IsStressTest() const { return false; } - virtual uint32 GetRequiredDeviceNum() const override { return 1; } - - virtual FString GetBeautifiedTestName() const override { return TEXT("GameAttributes.Attributes"); } - virtual void GetTests(TArray& OutBeautifiedNames, TArray & OutTestCommands) const override - { - for (const FString& TestFunctionName : TestFunctionNames) - { - OutBeautifiedNames.Add(TestFunctionName); - OutTestCommands.Add(TestFunctionName); - } - } - bool RunTest(const FString& Parameters) - { - TestFunc TestFunction = nullptr; - for (int32 i = 0; i < TestFunctionNames.Num(); ++i) - { - if (TestFunctionNames[i] == Parameters) - { - TestFunction = TestFunctions[i]; - break; - } - } - if (TestFunction == nullptr) - { - return false; - } - //UDataTable* TagTable = CreateGameplayDataTable(); - - //IGameplayTagsModule::Get().GetGameplayTagsManager().PopulateTreeFromDataTable(TagTable); - IGameplayTagsModule& GameplayTagsModule = IGameplayTagsModule::Get(); - TArray TagsList; - - FString ItemTags = "/Game/Data/GameplayTags/DamageStatusTags.DamageStatusTags"; - TagsList.Add(ItemTags); - - UGameplayTagsManager::Get().DestroyGameplayTagTree(); - //UGameplayTagsManager::Get().LoadGameplayTagTables(); - UGameplayTagsManager::Get().ConstructGameplayTagTree(); - - UWorld *World = UWorld::CreateWorld(EWorldType::Game, false); - FWorldContext &WorldContext = GEngine->CreateNewWorldContext(EWorldType::Game); - WorldContext.SetCurrentWorld(World); - - FURL URL; - World->InitializeActorsForPlay(URL); - World->BeginPlay(); - - // run the matching test - uint64 InitialFrameCounter = GFrameCounter; - { - GameEffectsTestSuite Tester(World, this); - (Tester.*TestFunction)(); - } - GFrameCounter = InitialFrameCounter; - - GEngine->DestroyWorldContext(World); - World->DestroyWorld(false); - return true; - } -}; - -namespace AbilityFrameworkTests -{ - FGAAttributesTests FGAAttributesTestsAutomationTestInstance(TEXT("FGAAttributesTests")); -} - -#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp deleted file mode 100644 index 882246c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.cpp +++ /dev/null @@ -1,71 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../AFAbilityComponent.h" -#include "GACharacterAttributeTest.h" - - -// Sets default values -AGACharacterAttributeTest::AGACharacterAttributeTest() -{ - // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - Attributes = CreateDefaultSubobject(TEXT("Attributes")); -} - -// Called when the game starts or when spawned -void AGACharacterAttributeTest::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AGACharacterAttributeTest::Tick( float DeltaTime ) -{ - Super::Tick( DeltaTime ); - -} - -// Called to bind functionality to input -void AGACharacterAttributeTest::SetupPlayerInputComponent(class UInputComponent* InInputComponent) -{ - Super::SetupPlayerInputComponent(InputComponent); - -} - -class UGAAttributesBase* AGACharacterAttributeTest::GetAttributes() -{ - return Attributes->DefaultAttributes; -} -class UAFAbilityComponent* AGACharacterAttributeTest::GetAbilityComp() -{ - return Attributes; -} -void AGACharacterAttributeTest::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - FGAEffectProperty& InProperty) -{ - GetAttributes()->ModifyAttribute(ModIn, HandleIn, InProperty); -} - -FAFAttributeBase* AGACharacterAttributeTest::GetAttribute(FGAAttribute AttributeIn) -{ - return GetAttributes()->GetAttribute(AttributeIn); -} -void AGACharacterAttributeTest::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) -{ - GetAttribute(AttributeIn)->RemoveBonus(HandleIn, InMod); -} -FGAEffectHandle AGACharacterAttributeTest::ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) -{ - return GetAbilityComp()->ApplyEffectToTarget(EffectIn, InProperty, InContext); -}; -void AGACharacterAttributeTest::RemoveTagContainer(const FGameplayTagContainer& TagsIn) -{ - GetAbilityComp()->RemoveTagContainer(TagsIn); -} -float AGACharacterAttributeTest::NativeGetAttributeValue(const FGAAttribute AttributeIn) const -{ - return 0; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h deleted file mode 100644 index a772172..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACharacterAttributeTest.h +++ /dev/null @@ -1,41 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GameFramework/Character.h" -#include "../AFAbilityInterface.h" -#include "GACharacterAttributeTest.generated.h" - -UCLASS() -class ABILITYFRAMEWORK_API AGACharacterAttributeTest : public ACharacter, public IAFAbilityInterface -{ - GENERATED_BODY() -public: - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Attributes") - class UAFAbilityComponent* Attributes; -public: - // Sets default values for this character's properties - AGACharacterAttributeTest(); - - // Called when the game starts or when spawned - virtual void BeginPlay() override; - - // Called every frame - virtual void Tick( float DeltaSeconds ) override; - - // Called to bind functionality to input - virtual void SetupPlayerInputComponent(class UInputComponent* InInputComponent) override; - - - virtual class UGAAttributesBase* GetAttributes() override; - virtual class UAFAbilityComponent* GetAbilityComp() override; - virtual float GetAttributeValue(FGAAttribute AttributeIn) const override { return 0; }; - virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// override { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; - - virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn);// override { return DefaultAttributes->GetAttribute(AttributeIn); }; - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty, FGAEffectContext& InContext) override;// { return ApplyEffectToTarget(EffectIn, HandleIn); }; - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; - virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const;// override { return 0; }; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp deleted file mode 100644 index e0c66ba..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAAttributesTest.h" -#include "GACustomCalculationTest.h" - - - - -float UGACustomCalculationTest::NativeCalculateMagnitude(const FGAEffectHandle& HandleIn) -{ - UGAAttributesTest* InstAttr = Cast(HandleIn.GetContext().GetInstigatorAttributes()); - UGAAttributesTest* TargetAttr = Cast(HandleIn.GetContext().GetTargetAttributes()); - if (InstAttr && TargetAttr) - { - FGAIndividualMods ModsOut; - /*float MagicBonus = InstAttr->MagicalBonus.GetFinalValueByTags(HandleIn.GetOwnedTags(), ModsOut); - float MagicResistance = TargetAttr->MagicResistance.GetFinalValueByTags(HandleIn.GetOwnedTags(), ModsOut); - return MagicBonus - MagicResistance;*/ - } - return 0; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h deleted file mode 100644 index 3e212b2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GACustomCalculationTest.h +++ /dev/null @@ -1,19 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "../Effects/GACustomCalculation.h" -#include "GACustomCalculationTest.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGACustomCalculationTest : public UGACustomCalculation -{ - GENERATED_BODY() - -public: - virtual float NativeCalculateMagnitude(const FGAEffectHandle& HandleIn) override; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp deleted file mode 100644 index 408549d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.cpp +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GameplayTagContainer.h" -#include "../AFAbilityComponent.h" -#include "../Attributes/GAAttributesBase.h" -#include "GASpellExecutionTest.h" - -#include "Effects/GAGameEffect.h" - -UGASpellExecutionTest::UGASpellExecutionTest(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h deleted file mode 100644 index 04efdee..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GASpellExecutionTest.h +++ /dev/null @@ -1,15 +0,0 @@ -#pragma once -#include "../Effects/GAEffectExecution.h" -#include "../Effects/GAGameEffect.h" -#include "GASpellExecutionTest.generated.h" - -/* - -*/ -UCLASS(BlueprintType, Blueprintable) -class UGASpellExecutionTest : public UGAEffectExecution -{ - GENERATED_BODY() -public: - UGASpellExecutionTest(const FObjectInitializer& ObjectInitializer); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp deleted file mode 100644 index 2f65d91..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAffectSpecTestOne.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h b/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h deleted file mode 100644 index afa2a74..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Tests/GAffectSpecTestOne.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/GAGameEffect.h" -#include "GAffectSpecTestOne.generated.h" - -/** - * - */ -UCLASS(NotBlueprintType, NotBlueprintable) -class ABILITYFRAMEWORK_API UGAffectSpecTestOne : public UGAGameEffectSpec -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp deleted file mode 100644 index a249885..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.cpp +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDCharacter.h" - - -// Sets default values -AAFDCharacter::AAFDCharacter() -{ - // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void AAFDCharacter::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AAFDCharacter::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - -// Called to bind functionality to input -void AAFDCharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) -{ - Super::SetupPlayerInputComponent(PlayerInputComponent); - -} - diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h deleted file mode 100644 index dcfddd9..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacter.h +++ /dev/null @@ -1,31 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Character.h" -#include "AFDCharacter.generated.h" - -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API AAFDCharacter : public ACharacter -{ - GENERATED_BODY() - -public: - // Sets default values for this character's properties - AAFDCharacter(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - // Called to bind functionality to input - virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; - - - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp deleted file mode 100644 index 5c645c8..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDCharacterAttributes.h" - - - - diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h deleted file mode 100644 index ce37f0c..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDCharacterAttributes.h +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Attributes/GAAttributesBase.h" -#include "AFDCharacterAttributes.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API UAFDCharacterAttributes : public UGAAttributesBase -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Base") - FAFAttributeBase Health; - UPROPERTY(EditAnywhere, Category = "Base") - FAFAttributeBase Energy; - UPROPERTY(EditAnywhere, Category = "Base") - FAFAttributeBase Stamina; - - UPROPERTY(EditAnywhere, Category = "Base") - FAFAttributeBase Armor; - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp deleted file mode 100644 index e3c67df..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.cpp +++ /dev/null @@ -1,84 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDDummyPawn.h" -#include "Attributes/GAAttributesBase.h" - -// Sets default values -AAFDDummyPawn::AAFDDummyPawn(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - // Set this pawn to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - - Arrow = ObjectInitializer.CreateDefaultSubobject(this, TEXT("Arrow")); - Collision = ObjectInitializer.CreateDefaultSubobject(this, TEXT("Collision")); - Abilities = ObjectInitializer.CreateDefaultSubobject(this, TEXT("Abilities")); - - SetRootComponent(Arrow); - Collision->AttachToComponent(RootComponent, FAttachmentTransformRules::KeepRelativeTransform); -} - -// Called when the game starts or when spawned -void AAFDDummyPawn::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void AAFDDummyPawn::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - -// Called to bind functionality to input -void AAFDDummyPawn::SetupPlayerInputComponent(UInputComponent* PlayerInputComponent) -{ - Super::SetupPlayerInputComponent(PlayerInputComponent); - -} -/* AFAbilityInterface Implementation START */ -class UGAAttributesBase* AAFDDummyPawn::GetAttributes() -{ - return Abilities->GetAttributes(); -} - -class UAFAbilityComponent* AAFDDummyPawn::GetAbilityComp() -{ - return Abilities; -} - -float AAFDDummyPawn::GetAttributeValue(FGAAttribute AttributeIn) const -{ - return Abilities->GetAttributeValue(AttributeIn); -} -void AAFDDummyPawn::ModifyAttribute(FGAEffectMod& ModIn - , const FGAEffectHandle& HandleIn - , struct FGAEffectProperty& InProperty) -{ - GetAttributes()->ModifyAttribute(ModIn, HandleIn, InProperty); -} - -FAFAttributeBase* AAFDDummyPawn::GetAttribute(FGAAttribute AttributeIn) -{ - return Abilities->GetAttribute(AttributeIn); -}; - -void AAFDDummyPawn::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) -{ - Abilities->RemoveBonus(AttributeIn, HandleIn, InMod); -}; - -float AAFDDummyPawn::NativeGetAttributeValue(const FGAAttribute AttributeIn) const -{ - return Abilities->NativeGetAttributeValue(AttributeIn); -}; - -FGAEffectHandle AAFDDummyPawn::ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext) -{ - return Abilities->ApplyEffectToTarget(EffectIn, InProperty, InContext); -}; -/* AFAbilityInterface Implementation END */ \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h deleted file mode 100644 index 498923a..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDDummyPawn.h +++ /dev/null @@ -1,65 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Pawn.h" -#include "Components/ArrowComponent.h" -#include "Components/CapsuleComponent.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.h" -#include "AFDDummyPawn.generated.h" - -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API AAFDDummyPawn : public APawn, public IAFAbilityInterface -{ - GENERATED_BODY() -protected: - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components") - UArrowComponent* Arrow; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components") - UCapsuleComponent* Collision; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components") - UAFAbilityComponent* Abilities; -public: - // Sets default values for this pawn's properties - AAFDDummyPawn(const FObjectInitializer& ObjectInitializer); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - // Called to bind functionality to input - virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; - - /* AFAbilityInterface Implementation START */ - virtual FVector GetSocketLocation(FName SocketNameIn) override { return FVector::ZeroVector; }; - - virtual class UGAAttributesBase* GetAttributes() override; - - virtual class UAFAbilityComponent* GetAbilityComp() override; - - virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; - - virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) override; - - virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; - - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; - - virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; - - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext) override; - - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override {}; - /* AFAbilityInterface Implementation END */ -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp deleted file mode 100644 index e64ba5c..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDGameMode.h" - - - - diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h deleted file mode 100644 index e93d3fe..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDGameMode.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/GameModeBase.h" -#include "AFDGameMode.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API AAFDGameMode : public AGameModeBase -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp index 50a1ca6..53bd36c 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp @@ -9,10 +9,6 @@ void SAFDEffects::Construct(const FArguments& InArgs) AFInterface = InArgs._AbilityInterface; AbilityComponent = AFInterface->GetAbilityComp(); - OnEffectAppliedHandle = AbilityComponent->OnEffectAppliedToTarget.AddSP(this, &SAFDEffects::OnEffectApplied); - OnEffectRemovedHandle = AbilityComponent->OnEffectRemoved.AddSP(this, &SAFDEffects::OnEffectRemoved); - OnEffectExpiredHandle = AbilityComponent->OnEffectExpired.AddSP(this, &SAFDEffects::OnEffectRemoved); - InitializeEffects(); ChildSlot [ @@ -31,9 +27,7 @@ void SAFDEffects::Construct(const FArguments& InArgs) END_SLATE_FUNCTION_BUILD_OPTIMIZATION SAFDEffects::~SAFDEffects() { - AbilityComponent->OnEffectAppliedToTarget.Remove(OnEffectAppliedHandle); - AbilityComponent->OnEffectRemoved.Remove(OnEffectRemovedHandle); - AbilityComponent->OnEffectExpired.Remove(OnEffectExpiredHandle); + } void SAFDEffects::InitializeEffects() @@ -41,17 +35,6 @@ void SAFDEffects::InitializeEffects() if (!AbilityComponent.IsValid()) return; - for(const FAFEffectRepInfo& RepInfo : AbilityComponent->GetAllEffectsInfo()) - { - TSharedPtr Row = MakeShareable(new FAFDEffectRow); - Row->Handle = RepInfo.Handle; - Row->RepInfo = const_cast(&RepInfo); - Row->AbilityComponent = AbilityComponent; - Row->EffectClassName = RepInfo.Handle.GetEffectSpec()->GetName(); - Row->TimeRemaining = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetTimeRemaining)); - Row->PeriodTime = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetPeriodTime)); - Effects.Add(Row); - } //ListView->RebuildList(); } @@ -89,12 +72,6 @@ TSharedRef SAFDEffects::GenerateListRow(TSharedPtr Eff void SAFDEffects::OnEffectApplied(FGAEffectHandle InHandle) { TSharedPtr Row = MakeShareable(new FAFDEffectRow); - Row->Handle = InHandle; - Row->RepInfo = AbilityComponent->GameEffectContainer.GetReplicationInfo(InHandle); - Row->AbilityComponent = AbilityComponent; - Row->EffectClassName = InHandle.GetEffectSpec()->GetName(); - Row->TimeRemaining = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetTimeRemaining)); - Row->PeriodTime = TAttribute::Create(TAttribute::FGetter::CreateSP(Row.Get(), &FAFDEffectRow::GetPeriodTime)); UE_LOG(LogTemp, Warning, TEXT("SAFDEffects::OnEffectAppliede")); Effects.Add(Row); diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h index 9ebe342..9144215 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h @@ -21,14 +21,14 @@ struct FAFDEffectRow : public TSharedFromThis FText GetTimeRemaining() const { - //return FText::AsNumber(0); - return FText::AsNumber(AbilityComponent->GameEffectContainer.GetRemainingTime(Handle)); + return FText::AsNumber(0); + //return FText::AsNumber(AbilityComponent->GameEffectContainer.GetRemainingTime(Handle)); } FText GetPeriodTime() const { - //return FText::AsNumber(0); - return FText::AsNumber(RepInfo->GetPeriodTime(static_cast(FPlatformTime::Seconds()))); + return FText::AsNumber(0); + //return FText::AsNumber(RepInfo->GetPeriodTime(static_cast(FPlatformTime::Seconds()))); } const bool operator==(const FAFDEffectRow& Other) const diff --git a/Source/ActionRPGGame/AI/ARAICharacter.cpp b/Source/ActionRPGGame/AI/ARAICharacter.cpp index 3825c9a..0c6de26 100644 --- a/Source/ActionRPGGame/AI/ARAICharacter.cpp +++ b/Source/ActionRPGGame/AI/ARAICharacter.cpp @@ -9,6 +9,7 @@ AARAICharacter::AARAICharacter() // Set this character to call Tick() every frame. You can turn this off to improve performance if you don't need it. PrimaryActorTick.bCanEverTick = true; Abilities = CreateDefaultSubobject(TEXT("Abilities")); + EffectsComponent = CreateDefaultSubobject(TEXT("EffectsComponent")); } // Called when the game starts or when spawned @@ -33,17 +34,18 @@ void AARAICharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputCompo } /* IAFAbilityInterface- BEGIN */ - -class UGAAttributesBase* AARAICharacter::GetAttributes() -{ - return GetAbilityComp()->DefaultAttributes; -} - class UAFAbilityComponent* AARAICharacter::GetAbilityComp() { return Abilities; }; - +class UAFEffectsComponent* AARAICharacter::GetEffectsComponent() +{ + return EffectsComponent; +} +class UAFEffectsComponent* AARAICharacter::NativeGetEffectsComponent() const +{ + return EffectsComponent; +} float AARAICharacter::GetAttributeValue(FGAAttribute AttributeIn) const { return Abilities->GetAttributeValue(AttributeIn); @@ -69,15 +71,4 @@ float AARAICharacter::NativeGetAttributeValue(const FGAAttribute AttributeIn) co { return Abilities->NativeGetAttributeValue(AttributeIn); } - -FGAEffectHandle AARAICharacter::ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) -{ - return Abilities->ApplyEffectToTarget(EffectIn, InProperty, InContext); -} - -void AARAICharacter::RemoveTagContainer(const FGameplayTagContainer& TagsIn) -{ - Abilities->RemoveTagContainer(TagsIn); -} /* IAFAbilityInterface- END */ \ No newline at end of file diff --git a/Source/ActionRPGGame/AI/ARAICharacter.h b/Source/ActionRPGGame/AI/ARAICharacter.h index 00b0c07..bf5e5c8 100644 --- a/Source/ActionRPGGame/AI/ARAICharacter.h +++ b/Source/ActionRPGGame/AI/ARAICharacter.h @@ -6,6 +6,8 @@ #include "GameFramework/Character.h" #include "GameplayTags.h" #include "AFAbilityComponent.h" +#include "AFEffectsComponent.h" + #include "AFAbilityInterface.h" #include "ARAICharacter.generated.h" @@ -17,6 +19,8 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt protected: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFAbilityComponent* Abilities; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class UAFEffectsComponent* EffectsComponent; public: // Sets default values for this character's properties AARAICharacter(); @@ -35,10 +39,12 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt /* IAFAbilityInterface- BEGIN */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UGAAttributesBase* GetAttributes() override; + virtual class UAFAbilityComponent* GetAbilityComp() override; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UAFAbilityComponent* GetAbilityComp() override; + virtual class UAFEffectsComponent* GetEffectsComponent() override; + + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; @@ -50,9 +56,6 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; /* IAFAbilityInterface- END */ }; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 5b6877c..9898586 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -54,7 +54,10 @@ AARCharacter::AARCharacter() FollowCamera->bUsePawnControlRotation = false; // Camera does not rotate relative to arm Abilities = CreateDefaultSubobject(TEXT("Abilities")); - + Abilities->SetIsReplicated(true); + EffectsComponent = CreateDefaultSubobject(TEXT("EffectsComponent")); + EffectsComponent->SetIsReplicated(true); + FollowCamera->TransformUpdated.AddUObject(this, &AARCharacter::OnCameraTransformUpdate); Weapons = CreateDefaultSubobject(TEXT("Weapons")); @@ -166,16 +169,19 @@ void AARCharacter::MoveRight(float Value) } /* IAFAbilityInterface- BEGIN */ -class UGAAttributesBase* AARCharacter::GetAttributes() -{ - return GetAbilityComp()->DefaultAttributes; -} - class UAFAbilityComponent* AARCharacter::GetAbilityComp() { return Abilities; }; +class UAFEffectsComponent* AARCharacter::GetEffectsComponent() +{ + return EffectsComponent; +} +class UAFEffectsComponent* AARCharacter::NativeGetEffectsComponent() const +{ + return EffectsComponent; +} float AARCharacter::GetAttributeValue(FGAAttribute AttributeIn) const { return Abilities->GetAttributeValue(AttributeIn); @@ -201,17 +207,6 @@ float AARCharacter::NativeGetAttributeValue(const FGAAttribute AttributeIn) cons { return Abilities->NativeGetAttributeValue(AttributeIn); } - -FGAEffectHandle AARCharacter::ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) -{ - return Abilities->ApplyEffectToTarget(EffectIn, InProperty, InContext); -} - -void AARCharacter::RemoveTagContainer(const FGameplayTagContainer& TagsIn) -{ - Abilities->RemoveTagContainer(TagsIn); -} /* IAFAbilityInterface- END */ void AARCharacter::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const @@ -221,10 +216,6 @@ void AARCharacter::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > DOREPLIFETIME_CONDITION(AARCharacter, CameraTransform, COND_SkipOwner); } -void AARCharacter::Multicast_CameraTransform_Implementation(FARCameraTransform InCameraTransform) -{ - CameraTransform = InCameraTransform; -} void AARCharacter::OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport) { if (GetNetMode() == ENetMode::NM_Standalone @@ -234,7 +225,6 @@ void AARCharacter::OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EU CameraTransform.ForwardVector = FollowCamera->GetForwardVector(); CameraTransform.Location = FollowCamera->GetComponentLocation(); } - //Multicast_CameraTransform(CameraTransform); } class AARWeaponBase* AARCharacter::GetMainWeapon() const diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 5ff09c8..5cad90e 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -6,6 +6,7 @@ #include "GameFramework/Character.h" #include "Components/ChildActorComponent.h" #include "GameplayTags.h" +#include "AFEffectsComponent.h" #include "AFAbilityComponent.h" #include "AFAbilityInterface.h" #include "ARCharacter.generated.h" @@ -42,6 +43,8 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFAbilityComponent* Abilities; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + class UAFEffectsComponent* EffectsComponent; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UARWeaponPawnManagerComponent* Weapons; @@ -111,11 +114,12 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface FORCEINLINE class UCameraComponent* GetFollowCamera() const { return FollowCamera; } /* IAFAbilityInterface- BEGIN */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UGAAttributesBase* GetAttributes() override; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") virtual class UAFAbilityComponent* GetAbilityComp() override; + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UAFEffectsComponent* GetEffectsComponent() override; + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; @@ -126,17 +130,8 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; - - virtual FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn, - FGAEffectProperty& InProperty, FGAEffectContext& InContext) override; - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) override; - /* IAFAbilityInterface- END */ - UFUNCTION(NetMulticast, Unreliable) - void Multicast_CameraTransform(FARCameraTransform InCameraTransform); - void Multicast_CameraTransform_Implementation(FARCameraTransform InCameraTransform); - void OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport); inline UARWeaponPawnManagerComponent* GetWeapons() From 8f6b67fa318a838499b76e72cee33ee6fa451179 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 14 Feb 2018 00:06:14 +0100 Subject: [PATCH 056/187] removing more redunant code from effects system --- .../AbilityFramework/AFAbilityComponent.h | 2 - .../AbilityFramework/AFEffectsComponent.cpp | 12 + .../Abilities/GAAbilityBase.cpp | 2 +- .../Effects/GABlueprintLibrary.cpp | 18 +- .../Effects/GABlueprintLibrary.h | 2 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 231 +++++---------- .../AbilityFramework/Effects/GAGameEffect.h | 263 ++++++------------ .../Source/AbilityFramework/GAGlobalTypes.cpp | 4 +- .../Source/AbilityFramework/GAGlobalTypes.h | 2 - .../AbilityFrameworkDebugger/SAFDEffects.h | 1 - 10 files changed, 176 insertions(+), 361 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 7ee3629..094ac1f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -33,8 +33,6 @@ DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); -DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectRepInfoDelegate, FAFEffectRepInfo*); - DECLARE_DELEGATE(FAFOnAbilityReady); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); DECLARE_DELEGATE(FAFGenericAttributeDelegate); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 2b4a4aa..c801048 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -221,7 +221,19 @@ void UAFEffectsComponent::RemoveEffect(const FGAEffectProperty& InProperty , const FGAEffectContext& InContext , const FGAEffectHandle& InHandle) { + //if (GetOwnerRole() == ENetRole::ROLE_Authority + // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + { + InternalRemoveEffect(InProperty, InContext); + } + ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); + FGAEffectCueParams CueParams(InContext, InProperty); + FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); + if (CueHandle) + { + MulticastRemoveEffectCue(CueParams, *CueHandle); + } } void UAFEffectsComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index facb55e..37725d1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -639,7 +639,7 @@ float UGAAbilityBase::GetCurrentActivationTime() { if (ActivationEffectHandle.IsValid()) { - return ActivationEffectHandle.GetEffectPtr()->GetCurrentActivationTime(); + return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); } return 0; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 245ce03..ba7010a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -74,10 +74,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, { if (!InEffect.IsHandleValid(Target)) { - effect = new FGAEffect(InEffect.GetSpec(), Context); + effect = new FGAEffect(InEffect.GetClass(), Context); AddTagsToEffect(effect); effect->Context = Context; - effect->GameEffect = InEffect.GetSpec(); } else { @@ -86,10 +85,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, } else { - effect = new FGAEffect(InEffect.GetSpec(), Context); + effect = new FGAEffect(InEffect.GetClass(), Context); AddTagsToEffect(effect); effect->Context = Context; - effect->GameEffect = InEffect.GetSpec(); } if (Ability) { @@ -151,10 +149,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, { if (!InEffect->IsHandleValid(Target)) { - effect = new FGAEffect(InEffect->GetSpec(), Context); + effect = new FGAEffect(InEffect->GetClass(), Context); AddTagsToEffect(effect); effect->Context = Context; - effect->GameEffect = InEffect->GetSpec(); } else { @@ -163,10 +160,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, } else { - effect = new FGAEffect(InEffect->GetSpec(), Context); + effect = new FGAEffect(InEffect->GetClass(), Context); AddTagsToEffect(effect); effect->Context = Context; - effect->GameEffect = InEffect->GetSpec(); } if (Ability) { @@ -206,7 +202,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject(FGAEffectProperty& InEf FHitResult Hit(ForceInit); return ApplyEffect(InEffect, Target, Instigator, Causer, Hit, Modifier); } -FGAEffectHandle UGABlueprintLibrary::MakeEffect(UGAGameEffectSpec* SpecIn, +FGAEffectHandle UGABlueprintLibrary::MakeEffect(TSubclassOf SpecIn, FGAEffectHandle HandleIn, class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn) { @@ -284,8 +280,8 @@ void UGABlueprintLibrary::AddTagsToEffect(FGAEffect* EffectIn) { if (EffectIn) { - EffectIn->OwnedTags.AppendTags(EffectIn->GameEffect->OwnedTags); - EffectIn->ApplyTags.AppendTags(EffectIn->GameEffect->ApplyTags); + EffectIn->OwnedTags.AppendTags(EffectIn->GetEffect()->OwnedTags); + EffectIn->ApplyTags.AppendTags(EffectIn->GetEffect()->ApplyTags); } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h index 95752cb..ff13138 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h @@ -58,7 +58,7 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar /* Create Effect but does not apply it. */ - static FGAEffectHandle MakeEffect(UGAGameEffectSpec* SpecIn, + static FGAEffectHandle MakeEffect(TSubclassOf SpecIn, FGAEffectHandle HandleIn, class UObject* Target, class APawn* Instigator, UObject* Causer, const FHitResult& HitIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index e50cf1d..5027436 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -1,14 +1,15 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" +#include "AbilityFramework.h" #include "GameplayTagContainer.h" -#include "../AFAbilityComponent.h" -#include "../Attributes/GAAttributesBase.h" -#include "../AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "Attributes/GAAttributesBase.h" +#include "AFAbilityInterface.h" #include "GAEffectExecution.h" #include "GAEffectExtension.h" -#include "../GAGlobalTypes.h" +#include "GAGlobalTypes.h" + #include "AFEffectApplicationRequirement.h" #include "AFEffectCustomApplication.h" #include "GAGameEffect.h" @@ -68,43 +69,18 @@ void FGAEffectProperty::EffectExecution(const FGAEffectHandle& HandleIn Execution->ExecuteEffect(HandleIn, ModIn, Context, *this, Modifier); } -FAFEffectRepInfo::FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, - class UAFEffectsComponent* InComponent) - : AppliedTime(AppliedTimeIn), - PeriodTime(PeriodTimeIn), - Duration(DurationIn), - ReplicationTime(ReplicationTimeIn), - OwningComoponent(InComponent) +void FGAEffect::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) { -}; - -void FAFEffectRepInfo::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) -{ - InArraySerializer.EffectInfos.Remove(Handle); } -void FAFEffectRepInfo::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) +void FGAEffect::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) { - if (PredictionHandle.IsValid() && InArraySerializer.PredictedEffectInfos.Contains(PredictionHandle)) - { - //remove predicted effect and move on. - FGAEffectContainer& cont = const_cast(InArraySerializer); - auto RemovePredicate = [&](const FAFEffectRepInfo& EmitterHandle) { return EmitterHandle.Handle == Handle; }; - //cont.ActiveEffectInfos.Remove(*this); - cont.ActiveEffectInfos.RemoveAll(RemovePredicate); - return; - } - else - { - //remove predicted effect. - } - OwningComoponent = InArraySerializer.OwningComponent; - AppliedTime = OwningComoponent->GetWorld()->GetTimeSeconds(); - InArraySerializer.EffectInfos.Add(Handle, this); - Type = ERepInfoType::RemotePredicted; - + AppliedTime = InArraySerializer.OwningComponent->GetWorld()->TimeSeconds; + LastTickTime = InArraySerializer.OwningComponent->GetWorld()->TimeSeconds; + Handle = FGAEffectHandle::GenerateHandle(this); + const_cast(InArraySerializer).ApplyFromPrediction(Handle, PredictionHandle); } -void FAFEffectRepInfo::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) +void FGAEffect::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) { } @@ -134,31 +110,6 @@ float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) return 0; } -FGAEffect::FGAEffect(class UGAGameEffectSpec* GameEffectIn, - const FGAEffectContext& ContextIn) - : GameEffect(GameEffectIn), - Context(ContextIn) -{ - OwnedTags = GameEffectIn->OwnedTags; - if (GameEffect->Extension) - { - Extension = NewObject(Context.Target.Get(), GameEffect->Extension); - Extension->OwningComponent = Context.GetTargetEffectsComponent(); - } - if (ContextIn.TargetComp.IsValid()) - { - TargetWorld = ContextIn.TargetComp->GetWorld(); - AppliedTime = TargetWorld->TimeSeconds; - LastTickTime = TargetWorld->TimeSeconds; - } - else if (ContextIn.InstigatorComp.IsValid()) - { - TargetWorld = ContextIn.InstigatorComp->GetWorld(); - AppliedTime = TargetWorld->TimeSeconds; - LastTickTime = TargetWorld->TimeSeconds; - } - IsActive = false; -} float FAFStatics::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn , const FGAEffectContext& InContext @@ -227,12 +178,36 @@ FGAEffectMod FAFStatics::GetAttributeModifier(FGAAttributeModifier& ModInfoIn } return ModOut; } +FGAEffect::FGAEffect(TSubclassOf GameEffectIn, + const FGAEffectContext& ContextIn) + : GameEffectClass(GameEffectIn), + Context(ContextIn) +{ + OwnedTags = GetEffect()->OwnedTags; + if (GetEffect()->Extension) + { + Extension = NewObject(Context.Target.Get(), GetEffect()->Extension); + Extension->OwningComponent = Context.GetTargetEffectsComponent(); + } + if (ContextIn.TargetComp.IsValid()) + { + TargetWorld = ContextIn.TargetComp->GetWorld(); + AppliedTime = TargetWorld->TimeSeconds; + LastTickTime = TargetWorld->TimeSeconds; + } + else if (ContextIn.InstigatorComp.IsValid()) + { + TargetWorld = ContextIn.InstigatorComp->GetWorld(); + AppliedTime = TargetWorld->TimeSeconds; + LastTickTime = TargetWorld->TimeSeconds; + } +} + FGAEffect::~FGAEffect() { - if (Extension.IsValid()) + if (Extension) { Extension->MarkPendingKill(); - Extension.Reset(); } } void FGAEffect::SetContext(const FGAEffectContext& ContextIn) @@ -242,55 +217,41 @@ void FGAEffect::SetContext(const FGAEffectContext& ContextIn) void FGAEffect::OnApplied() { - IsActive = true; AppliedTime = TargetWorld->TimeSeconds; - if (Extension.IsValid()) + if (Extension) { Extension->NativeOnEffectApplied(); } -} -void FGAEffect::OnDuration() -{ - } void FGAEffect::OnExecuted() { - OnEffectPeriod.Broadcast(Handle); - if (Extension.IsValid()) + if (Extension) { Extension->NativeOnEffectExecuted(); } } void FGAEffect::OnExpired() { - OnEffectExpired.Broadcast(Handle); - IsActive = false; - if (Extension.IsValid()) + if (Extension) { Extension->NativeOnEffectExpired(); } } void FGAEffect::OnRemoved() { - OnEffectRemoved.Broadcast(Handle); - IsActive = false; - if (Extension.IsValid()) + if (Extension) { Extension->NativeOnEffectRemoved(); } } -void FGAEffect::DurationExpired() -{ - -} float FGAEffect::GetDurationTime() const { - return GetFloatFromAttributeMagnitude(GameEffect->Duration); + return GetFloatFromAttributeMagnitude(GetEffect()->Duration); } float FGAEffect::GetPeriodTime() const { - return GetFloatFromAttributeMagnitude(GameEffect->Period); + return GetFloatFromAttributeMagnitude(GetEffect()->Period); } float FGAEffect::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const { @@ -318,24 +279,13 @@ float FGAEffect::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) return 0; } -float FGAEffect::GetCurrentActivationTime() -{ - float CurrentTime = TargetWorld->TimeSeconds; - return CurrentTime - AppliedTime; -} -float FGAEffect::GetCurrentActivationTime() const +float FGAEffect::GetCurrentDuration() const { float CurrentTime = TargetWorld->TimeSeconds; return CurrentTime - AppliedTime; } -float FGAEffect::GetCurrentTickTime() -{ - float CurrentTime = TargetWorld->TimeSeconds; - return CurrentTime - LastTickTime; -} - void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams) { /*if (!EffectCue) @@ -405,18 +355,24 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr //we probabaly don't need to unwind attribute changes, since next replication from //server will overridem them anyway. - ApplyReplicationInfo(Handle, InProperty); bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::EffectApplied %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Handle.GetEffectSpec()->GetName() ); } } } - - HandleByPrediction.Add(InProperty.GetPredictionHandle(), Handle); - PredictionByHandle.Add(Handle, InProperty.GetPredictionHandle()); + if (bHasDuration || bHasPeriod) + { + EffectIn->PredictionHandle = InProperty.GetPredictionHandle(); + EffectIn->AppliedTime = OwningComponent->GetWorld()->TimeSeconds; + EffectIn->LastTickTime = OwningComponent->GetWorld()->TimeSeconds; + MarkItemDirty(*EffectIn); + ActiveEffectInfos.Add(*EffectIn); + MarkArrayDirty(); - EffectIn->OnApplied(); + HandleByPrediction.Add(InProperty.GetPredictionHandle(), Handle); + PredictionByHandle.Add(Handle, InProperty.GetPredictionHandle()); + } if (InProperty.GetSpec()->IfHaveTagEffect.RequiredTag.IsValid() && InContext.GetTargetEffectsComponent()->HasTag(InProperty.GetSpec()->IfHaveTagEffect.RequiredTag)) @@ -431,37 +387,6 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr return Handle; } -void FGAEffectContainer::ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) -{ - ENetMode mode = OwningComponent->GetNetMode(); - ENetRole role = OwningComponent->GetOwnerRole(); - - bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; - UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::ApplyReplicationInfo"), bIsServer ? TEXT("Server") : TEXT("Client")); - - //add replication handle (and send it to server ?) - const UWorld* World = OwningComponent->GetWorld(); - FAFEffectRepInfo* RepInfo = new FAFEffectRepInfo(World->GetTimeSeconds(), InProperty.GetPeriod(), InProperty.GetDuration(), 0, OwningComponent); - if(bIsServer) - { - RepInfo->Type = ERepInfoType::Server; - } - else - { - RepInfo->Type = ERepInfoType::LocallyPredicted; - } - RepInfo->Spec = InProperty.GetClass(); - RepInfo->Context = InHandle.GetContext(); - RepInfo->Handle = InHandle; - RepInfo->PredictionHandle = InProperty.GetPredictionHandle(); - MarkItemDirty(*RepInfo); - ActiveEffectInfos.Add(*RepInfo); - MarkArrayDirty(); - //predictevily add effect info ? - - PredictedEffectInfos.Add(InProperty.GetPredictionHandle(), RepInfo); - EffectInfos.Add(InHandle, RepInfo); -} EGAEffectAggregation FGAEffectContainer::GetEffectAggregation(const FGAEffectHandle& HandleIn) const { @@ -594,7 +519,8 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn const_cast(InProperty).RemoveHandle(HandleIn); - ActiveEffectHandles.Remove(HandleIn); + + InfiniteEffects.Remove(HandleIn); TArray* handles = EffectByClass.Find(FObjectKey(InProperty.GetClass())); if (handles && handles->Num() > 0) @@ -605,18 +531,18 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn EffectByClass.Remove(FObjectKey(InProperty.GetClass())); } } - FAFEffectRepInfo* Out = nullptr; - EffectInfos.RemoveAndCopyValue(HandleIn, Out); + FGAEffectHandle* Out = ActiveEffectHandles.Find(HandleIn); if (Out) { - FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); - EffectInfoLog += Out->GetEffectTag().ToString(); - AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); - MarkItemDirty(*Out); - ActiveEffectInfos.Remove(*Out); + //FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); + //EffectInfoLog += Out->GetEffectTag().ToString(); + //AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); + FGAEffect* Effect = Out->GetEffectPtr().Get(); + MarkItemDirty(*Effect); + ActiveEffectInfos.Remove(Out->GetEffect()); MarkArrayDirty(); - delete Out; } + ActiveEffectHandles.Remove(HandleIn); FAFPredictionHandle* PredHandle = PredictionByHandle.Find(HandleIn); if(PredHandle) { @@ -644,7 +570,6 @@ void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn } if (Effect.IsValid()) { - Effect->OnEffectRemoved.Broadcast(Effect->Handle); Target->RemoveTagContainer(Effect->ApplyTags); FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); DurationTimer.ClearTimer(Effect->DurationTimerHandle); @@ -703,7 +628,6 @@ void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn RemoveEffectProtected(HandleIn, InProperty); if (Effect.IsValid()) { - Effect->OnEffectRemoved.Broadcast(Effect->Handle); Target->RemoveTagContainer(Effect->ApplyTags); FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); DurationTimer.ClearTimer(Effect->DurationTimerHandle); @@ -717,7 +641,6 @@ TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty EGAEffectAggregation Aggregation = Spec->EffectAggregation; FObjectKey key(HandleIn.GetClass()); TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); - FAFEffectRepInfo* Out = nullptr; if (!handles) return TArray(); @@ -756,16 +679,6 @@ TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty return copy; } -//FGAEffectContainer::FGAEffectContainer() -//{ -//} - -void FGAEffectContainer::ApplyEffectInstance(class UGAEffectExtension* EffectIn) -{ - -} - - bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) { if (ActiveEffectHandles.Contains(HandleIn)) @@ -791,10 +704,12 @@ bool FGAEffectContainer::ContainsEffectOfClass(const FGAEffectProperty& InProper } return false; } -//TSharedPtr FGAEffectContainer::GetEffectByHandle(const FGAEffectHandle& HandleIn) -//{ -// return ActiveEffects.FindRef(HandleIn); -//} + +void FGAEffectContainer::ApplyFromPrediction(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle) +{ + +} + UWorld* FGAEffectContainer::GetWorld() const { if (OwningComponent) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 85ab32e..deae199 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -550,48 +550,58 @@ struct FAFStatics Final effect which then is used to apply custom calculations and attribute changes. */ DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectMulicastDelegate, const FGAEffectHandle&); - -struct ABILITYFRAMEWORK_API FGAEffect : public TSharedFromThis +UENUM() +enum class ERepInfoType : uint8 +{ + LocallyPredicted, + RemotePredicted, + Server +}; +USTRUCT() +struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, public TSharedFromThis { + + GENERATED_BODY() /* Cached pointer to original effect spec. */ - TWeakObjectPtr Extension; + UPROPERTY(NotReplicated) + class UGAEffectExtension* Extension; + UWorld* TargetWorld; /* Calculated mods ready to be applied. These are perlimenarly calculcated mods, which can be furhter modified by Calculation object. */ - - - /* Contains all tags gathered on the way to application ? */ - - bool IsActive; public: - //pointer ? Acces trough handle ? - class UGAGameEffectSpec* GameEffect; - FGAEffectContext Context; + + //Spec from which this effect originated. + UPROPERTY() + TSubclassOf GameEffectClass; + UPROPERTY() + FAFPredictionHandle PredictionHandle; + UPROPERTY() + FGAEffectContext Context; + FGameplayTagContainer OwnedTags; FGameplayTagContainer ApplyTags; FGameplayTagContainer RequiredTags; FGAEffectHandle Handle; - FAFPredictionHandle PredictionHandle; mutable FTimerHandle PeriodTimerHandle; mutable FTimerHandle DurationTimerHandle; - FGAEffectMod AttributeMod; + //FGAEffectMod AttributeMod; //because I'm fancy like that and like to make spearate public for fields and functions. public: - //Simple delegates to make sure they are bound only to one object. - FAFEffectMulicastDelegate OnEffectPeriod; - FAFEffectMulicastDelegate OnEffectExpired; - FAFEffectMulicastDelegate OnEffectRemoved; - float AppliedTime; float LastTickTime; public: + void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); + void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); + void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); + void SetContext(const FGAEffectContext& ContextIn); class UAFAbilityComponent* GetInstigatorComp() { return Context.InstigatorComp.Get(); } @@ -599,37 +609,48 @@ struct ABILITYFRAMEWORK_API FGAEffect : public TSharedFromThis inline void AddOwnedTags(const FGameplayTagContainer& TagsIn) { OwnedTags.AppendTags(TagsIn); } inline void AddApplyTags(const FGameplayTagContainer& TagsIn) { ApplyTags.AppendTags(TagsIn); } void OnApplied(); - void OnDuration(); void OnExpired(); void OnRemoved(); void OnExecuted(); - void DurationExpired(); float GetDurationTime() const; float GetPeriodTime() const; - float GetCurrentActivationTime(); - float GetCurrentActivationTime() const; - float GetCurrentTickTime(); + float GetCurrentDuration() const; float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const; + + UGAGameEffectSpec* GetEffect() + { + return GameEffectClass.GetDefaultObject(); + } + UGAGameEffectSpec* GetEffect() const + { + return GameEffectClass.GetDefaultObject(); + } bool IsValid() const { - return GameEffect != nullptr; + return GameEffectClass != nullptr; } FString ToString() { - if (GameEffect) + if (GameEffectClass) { - return GameEffect->GetName(); + return GameEffectClass->GetName(); } return FString(); } FGAEffect() - : GameEffect(nullptr) + : GameEffectClass(nullptr) {} - FGAEffect(class UGAGameEffectSpec* GameEffectIn, + FGAEffect(TSubclassOf GameEffectIn, const FGAEffectContext& ContextIn); ~FGAEffect(); + + + bool operator==(const FGAEffect& Other) const + { + return Handle == Other.Handle; + } }; /* @@ -682,115 +703,6 @@ struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer TArray Effects; }; -/* - Simplified and minimal version of game effect replicated back to clients. -*/ -UENUM() -enum class ERepInfoType : uint8 -{ - LocallyPredicted, - RemotePredicted, - Server -}; -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFEffectRepInfo : public FFastArraySerializerItem -{ - GENERATED_USTRUCT_BODY() - -public: - UPROPERTY() - ERepInfoType Type; - - UPROPERTY() - TSubclassOf Spec; - - UPROPERTY() - FGAEffectContext Context; - - //Handle to effect, which is using this info. - UPROPERTY() - FGAEffectHandle Handle; - - UPROPERTY() - FAFPredictionHandle PredictionHandle; - - UPROPERTY(NotReplicated) - float AppliedTime; - UPROPERTY() - float PeriodTime; - UPROPERTY() - float Duration; - UPROPERTY() - float ReplicationTime; - UPROPERTY(NotReplicated) - float LastPeriodTime; - - class UAFEffectsComponent* OwningComoponent; - - UGAGameEffectSpec* GetSpec() const - { - return Spec.GetDefaultObject(); - } - - - void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); - void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); - void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); - - FGameplayTag GetEffectTag() - { - return GetSpec()->EffectTag; - } - - float GetPeriodTime(float InWorldTime) - { - if (InWorldTime > (LastPeriodTime + PeriodTime)) - LastPeriodTime = InWorldTime; - return InWorldTime - LastPeriodTime; - } - - float GetRemainingTime(float InWorldTime) const - { - return Duration - (InWorldTime - AppliedTime); - } - float GetRemainingTimeNormalized(float InWorldTime) const - { - float Time = Duration - (InWorldTime - AppliedTime); - //1,0 ? - float Normalized = FMath::GetMappedRangeValueClamped(FVector2D(Duration, 0), FVector2D(1, 0), Time); - return Normalized; - } - /* Get Current effect ime clamped to max duration */ - float GetCurrentTime(float InWorldTime) const - { - return FMath::Clamp(InWorldTime - AppliedTime, 0, Duration); - } - float GetCurrentTimeNormalized(float InWorldTime) const - { - float Time = FMath::Clamp(InWorldTime - AppliedTime, 0, Duration); - float Normalized = FMath::GetMappedRangeValueClamped(FVector2D(0, Duration), FVector2D(0, 1), Time); - return Normalized; - } - float GetEndTime() const - { - return AppliedTime + Duration; - } - FAFEffectRepInfo() - {}; - - const bool operator==(const FAFEffectRepInfo& Other) const - { - return Handle == Other.Handle; - } - friend uint32 GetTypeHash(const FAFEffectRepInfo& InHandle) - { - return GetTypeHash(InHandle.Handle); - } - - FAFEffectRepInfo(float AppliedTimeIn, float PeriodTimeIn, float DurationIn, float ReplicationTimeIn, - class UAFEffectsComponent* InComponent); -}; - USTRUCT() struct ABILITYFRAMEWORK_API FGAGameCue { @@ -819,12 +731,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer GENERATED_USTRUCT_BODY() public: UPROPERTY() - TArray ActiveEffectInfos; - //IDK might be actually easier to map Handles to active effects on clients - //as Handle should be synced between client and server. - //that's why handle should only be created on server (and by that, effects). - //change to SharedPtr ? - mutable TMap EffectInfos; + TArray ActiveEffectInfos; UPROPERTY() TMap HandleByPrediction; @@ -833,7 +740,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TMap PredictionByHandle; - TMap PredictedEffectInfos; + TMap PredictedEffectInfos; TMap> EffectByAttribute; @@ -870,14 +777,10 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TMap> TargetEffectByClass; - /* Keeps effects instanced per target actor. */ - UPROPERTY(NotReplicated) - TArray TargetInstancedEffects; - UPROPERTY(NotReplicated) class UAFEffectsComponent* OwningComponent; public: - //FGAEffectContainer(); + /* * @call Order: * Previous Function: UAFAbilityComponent::ApplyEffectToSelf @@ -898,7 +801,6 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer , const FGAEffectContext& InContext , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - void ApplyReplicationInfo(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ TArray RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ @@ -920,17 +822,19 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer void RemoveEffectProtected(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); void RemoveInstigatorEffect(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); void RemoveTargetEffect(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); - void ApplyEffectInstance(class UGAEffectExtension* EffectIn); //modifiers void ApplyEffectsFromMods() {}; void DoesQualify() {}; bool IsEffectActive(const FGAEffectHandle& HandleIn); bool IsEffectActive(const FGAEffectHandle& HandleIn) const; bool ContainsEffectOfClass(const FGAEffectProperty& InProperty); + + void ApplyFromPrediction(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle); + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { //return FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); - return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); + return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); } const TSet& GetAllEffectHandles() const @@ -938,55 +842,48 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer return ActiveEffectHandles; } - const TArray& GetAllEffectsInfo() const - { - return ActiveEffectInfos; - } - UWorld* GetWorld() const; - - FAFEffectRepInfo* GetReplicationInfo(const FGAEffectHandle& InHandle) - { - return EffectInfos.FindRef(InHandle); - } ///Helpers float GetRemainingTime(const FGAEffectHandle& InHandle) const { - FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); - if (!Info) - return 0; - //lets assume value is always valid... - return Info->GetRemainingTime(GetWorld()->GetTimeSeconds()); + if (InHandle.GetEffectPtr().IsValid()) + { + float Duration = InHandle.GetEffectPtr()->GetDurationTime(); + return FMath::Clamp(Duration - InHandle.GetEffectPtr()->GetCurrentDuration(), 0, Duration); + } + return 0; } float GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const { - FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); - if (!Info) - return 0; - return Info->GetRemainingTimeNormalized(GetWorld()->GetTimeSeconds()); + if (InHandle.GetEffectPtr().IsValid()) + { + float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); + float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); + return FMath::Clamp(CurrentDuration * 1 / MaxDuration, 0, 1); + } + return 0; } /* Get Current effect ime clamped to max duration */ float GetCurrentTime(const FGAEffectHandle& InHandle) const { - FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); - if (!Info) - return 0; - return Info->GetCurrentTime(GetWorld()->GetTimeSeconds()); + if(InHandle.GetEffectPtr().IsValid()) + return InHandle.GetEffectPtr()->GetCurrentDuration(); + return 0; } float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const { - FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); - if (!Info) - return 0; - return Info->GetCurrentTimeNormalized(GetWorld()->GetTimeSeconds()); + if (InHandle.GetEffectPtr().IsValid()) + { + float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); + float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); + return CurrentDuration * 1 / MaxDuration; + } + return 0; } float GetEndTime(const FGAEffectHandle& InHandle) const { - FAFEffectRepInfo* Info = EffectInfos.FindRef(InHandle); - if (!Info) - return 0; - return Info->GetEndTime(); + return 0; } }; template<> diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index b7d6425..9ca40b5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -48,8 +48,8 @@ FGAEffectHandle::~FGAEffectHandle() FGAEffectContext& FGAEffectHandle::GetContextRef() { return EffectPtr->Context; } FGAEffectContext& FGAEffectHandle::GetContextRef() const { return EffectPtr->Context; } -UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() { return EffectPtr->GameEffect; } -UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() const { return EffectPtr->GameEffect; } +UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() { return EffectPtr->GetEffect(); } +UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() const { return EffectPtr->GetEffect(); } uint32 FGAEffectHandle::GetHandle() const { return Handle; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index f413aa1..54f182e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -306,8 +306,6 @@ USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectHandle { GENERATED_BODY() -public: - friend struct FAFEffectRepInfo; protected: //just to be safe we don't run out of numbers.. UPROPERTY() diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h index 9144215..6d17270 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h @@ -14,7 +14,6 @@ struct FAFDEffectRow : public TSharedFromThis { FString EffectClassName; FGAEffectHandle Handle; - FAFEffectRepInfo* RepInfo; TAttribute TimeRemaining; TAttribute PeriodTime; TWeakObjectPtr AbilityComponent; From 2a6ac7745680f34443a781c9a3f952334a3df713 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 15 Feb 2018 23:12:21 +0100 Subject: [PATCH 057/187] changed handle to contain raw pointer instead of shared, because it caused cyclic depedency on replication --- .../AbilityFramework/AFEffectsComponent.cpp | 2 +- .../Abilities/GAAbilityBase.cpp | 1 + .../AFPeriodApplicationExtend.cpp | 4 +- .../Effects/GABlueprintLibrary.cpp | 4 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 60 +++++++++++++++--- .../AbilityFramework/Effects/GAGameEffect.h | 63 ++++++------------- .../Source/AbilityFramework/GAGlobalTypes.cpp | 16 ++--- .../Source/AbilityFramework/GAGlobalTypes.h | 15 ++--- 8 files changed, 95 insertions(+), 70 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index c801048..f7fbc18 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -159,7 +159,7 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); - FGAEffect& Effect = HandleIn.GetEffectRef(); + FGAEffect& Effect = HandleIn.GetEffect(); FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() , InProperty.GetSpec() , InContext diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 37725d1..f5165b3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -390,6 +390,7 @@ void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) { //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); OnCooldownEnd(InHandle); + ActiveCooldownHandle.Reset(); } void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index 5778b24..b96a754 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -15,8 +15,8 @@ bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, st TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); for (const FGAEffectHandle& handle : handles) { - FGAEffect& ExtEffect = handle.GetEffectRef(); - FGAEffect& Effect = InHandle.GetEffectRef(); + FGAEffect& ExtEffect = handle.GetEffect(); + FGAEffect& Effect = InHandle.GetEffect(); FTimerManager& DurationTimer = handle.GetContext().TargetComp->GetWorld()->GetTimerManager(); float RemainingTime = DurationTimer.GetTimerRemaining(handle.GetEffectPtr()->DurationTimerHandle); float NewDuration = RemainingTime + Effect.GetDurationTime(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index ba7010a..5b3245f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -80,7 +80,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, } else { - effect = InEffect.GetHandle(Target).GetEffectPtr().Get(); + effect = InEffect.GetHandle(Target).GetEffectPtr(); } } else @@ -155,7 +155,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, } else { - effect = InEffect->GetHandle(Target).GetEffectPtr().Get(); + effect = InEffect->GetHandle(Target).GetEffectPtr(); } } else diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 5027436..ea1664a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -77,7 +77,9 @@ void FGAEffect::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerial { AppliedTime = InArraySerializer.OwningComponent->GetWorld()->TimeSeconds; LastTickTime = InArraySerializer.OwningComponent->GetWorld()->TimeSeconds; + Extension = nullptr; Handle = FGAEffectHandle::GenerateHandle(this); + const_cast(InArraySerializer).ApplyFromPrediction(Handle, PredictionHandle); } void FGAEffect::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) @@ -184,6 +186,7 @@ FGAEffect::FGAEffect(TSubclassOf GameEffectIn, Context(ContextIn) { OwnedTags = GetEffect()->OwnedTags; + Extension = nullptr; if (GetEffect()->Extension) { Extension = NewObject(Context.Target.Get(), GetEffect()->Extension); @@ -537,7 +540,7 @@ void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn //FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); //EffectInfoLog += Out->GetEffectTag().ToString(); //AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); - FGAEffect* Effect = Out->GetEffectPtr().Get(); + FGAEffect* Effect = Out->GetEffectPtr(); MarkItemDirty(*Effect); ActiveEffectInfos.Remove(Out->GetEffect()); MarkArrayDirty(); @@ -559,7 +562,7 @@ void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn TMap>* InstigatorEffect = InstigatorEffectByClass.Find(Instigator); TSet* HandlesToRemove = InstigatorEffect->Find(EffectClass); IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; - TSharedPtr Effect = HandleIn.GetEffectPtr(); + FGAEffect* Effect = HandleIn.GetEffectPtr(); if (HandlesToRemove) { HandlesToRemove->Remove(HandleIn); @@ -568,7 +571,7 @@ void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn InstigatorEffect->Remove(EffectClass); } } - if (Effect.IsValid()) + if (Effect) { Target->RemoveTagContainer(Effect->ApplyTags); FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); @@ -587,7 +590,7 @@ void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, c if (!ActiveEffectHandles.Contains(InHandle)) { - UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *InHandle.GetEffectRef().ToString()); + UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *InHandle.GetEffect().ToString()); return; } switch (Aggregation) @@ -614,7 +617,7 @@ void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn TSet* Handles = TargetEffectByClass.Find(EffectClass); IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; - TSharedPtr Effect = HandleIn.GetEffectPtr(); + FGAEffect* Effect = HandleIn.GetEffectPtr(); if (Handles) { @@ -626,7 +629,7 @@ void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn } RemoveEffectProtected(HandleIn, InProperty); - if (Effect.IsValid()) + if (Effect) { Target->RemoveTagContainer(Effect->ApplyTags); FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); @@ -655,7 +658,7 @@ TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty { if (!ActiveEffectHandles.Contains(OutHandle)) { - UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffectRef().ToString()); + UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffect().ToString()); continue; } switch (Aggregation) @@ -724,4 +727,47 @@ UGAGameEffectSpec::UGAGameEffectSpec() ExecutionType = UGAEffectExecution::StaticClass(); ApplicationRequirement = UAFEffectApplicationRequirement::StaticClass(); Application = UAFEffectCustomApplication::StaticClass(); +} + +float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) const +{ + if (InHandle.IsValid()) + { + float Duration = InHandle.GetEffectPtr()->GetDurationTime(); + return FMath::Clamp(Duration - InHandle.GetEffectPtr()->GetCurrentDuration(), 0, Duration); + } + return 0; +} +float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const +{ + if (InHandle.IsValid()) + { + float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); + float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); + + float CurrentTime = ((CurrentDuration / MaxDuration) - 1) * (-1); + + return CurrentTime;// FMath::Clamp(CurrentTime, 1, 0); + } + return 0; +} +float FGAEffectContainer::GetCurrentTime(const FGAEffectHandle& InHandle) const +{ + if (InHandle.IsValid()) + return InHandle.GetEffectPtr()->GetCurrentDuration(); + return 0; +} +float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const +{ + if (InHandle.IsValid()) + { + float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); + float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); + return CurrentDuration * 1 / MaxDuration; + } + return 0; +} +float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const +{ + return 0; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index deae199..d4a9a3f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -2,7 +2,6 @@ //#include "GAGlobalTypes.h" #include "GAEffectGlobalTypes.h" #include "GameplayTagContainer.h" -//#include "NetSerialization.h" #include "GAGameEffect.generated.h" DECLARE_STATS_GROUP(TEXT("GameEffect"), STATGROUP_GameEffect, STATCAT_Advanced); @@ -558,7 +557,7 @@ enum class ERepInfoType : uint8 Server }; USTRUCT() -struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, public TSharedFromThis +struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, TSharedFromThis { GENERATED_BODY() @@ -626,6 +625,15 @@ struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, publi { return GameEffectClass.GetDefaultObject(); } + FGAEffectContext& GetContext() + { + return Context; + } + const FGAEffectContext& GetContext() const + { + return Context; + } + bool IsValid() const { return GameEffectClass != nullptr; @@ -724,15 +732,16 @@ struct ABILITYFRAMEWORK_API FGameCueContainer void AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams); }; - USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer { - GENERATED_USTRUCT_BODY() + GENERATED_BODY() public: UPROPERTY() TArray ActiveEffectInfos; + TMap> HandleToEffect; + UPROPERTY() TMap HandleByPrediction; @@ -845,46 +854,14 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer UWorld* GetWorld() const; ///Helpers - float GetRemainingTime(const FGAEffectHandle& InHandle) const - { - if (InHandle.GetEffectPtr().IsValid()) - { - float Duration = InHandle.GetEffectPtr()->GetDurationTime(); - return FMath::Clamp(Duration - InHandle.GetEffectPtr()->GetCurrentDuration(), 0, Duration); - } - return 0; - } - float GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const - { - if (InHandle.GetEffectPtr().IsValid()) - { - float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); - float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); - return FMath::Clamp(CurrentDuration * 1 / MaxDuration, 0, 1); - } - return 0; - } + float GetRemainingTime(const FGAEffectHandle& InHandle) const; + float GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const; /* Get Current effect ime clamped to max duration */ - float GetCurrentTime(const FGAEffectHandle& InHandle) const - { - if(InHandle.GetEffectPtr().IsValid()) - return InHandle.GetEffectPtr()->GetCurrentDuration(); - return 0; - } - float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const - { - if (InHandle.GetEffectPtr().IsValid()) - { - float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); - float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); - return CurrentDuration * 1 / MaxDuration; - } - return 0; - } - float GetEndTime(const FGAEffectHandle& InHandle) const - { - return 0; - } + float GetCurrentTime(const FGAEffectHandle& InHandle) const; + float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const; + float GetEndTime(const FGAEffectHandle& InHandle) const; + + TSharedPtr GetEffect(const FGAEffectHandle& InHandle) { return HandleToEffect[InHandle]; } }; template<> struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index 9ca40b5..ce2ca49 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -53,14 +53,14 @@ UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() const { return EffectPtr->Ge uint32 FGAEffectHandle::GetHandle() const { return Handle; } -FGAEffect FGAEffectHandle::GetEffect() { return *EffectPtr.Get(); } -FGAEffect FGAEffectHandle::GetEffect() const { return *EffectPtr.Get(); } +FGAEffect& FGAEffectHandle::GetEffect() { return *EffectPtr; } +FGAEffect& FGAEffectHandle::GetEffect() const { return *EffectPtr; } -FGAEffect& FGAEffectHandle::GetEffectRef() { return EffectPtr.ToSharedRef().Get(); } -FGAEffect& FGAEffectHandle::GetEffectRef() const { return EffectPtr.ToSharedRef().Get(); }; +//FGAEffect& FGAEffectHandle::GetEffectRef() { return *EffectPtr; } +//FGAEffect& FGAEffectHandle::GetEffectRef() const { return *EffectPtr; }; -TSharedPtr FGAEffectHandle::GetEffectPtr() { return EffectPtr; }; -TSharedPtr FGAEffectHandle::GetEffectPtr() const { return EffectPtr; }; +FGAEffect* FGAEffectHandle::GetEffectPtr() { return EffectPtr; }; +FGAEffect* FGAEffectHandle::GetEffectPtr() const { return EffectPtr; }; void FGAEffectHandle::SetContext(const FGAEffectContext& ContextIn) { EffectPtr->SetContext(ContextIn); } void FGAEffectHandle::SetContext(const FGAEffectContext& ContextIn) const { EffectPtr->SetContext(ContextIn); } @@ -121,7 +121,7 @@ EGAAttributeMod FGAEffectHandle::GetAttributeMod() const bool FGAEffectHandle::IsValid() const { - return (Handle != INDEX_NONE) && EffectPtr.IsValid();// && EffectPtr->Context.IsValid(); + return (Handle != INDEX_NONE) && EffectPtr != nullptr;// && EffectPtr->Context.IsValid(); } //void FGAEffectHandle::operator=(const FGAEffectHandle& Other) //{ @@ -131,7 +131,7 @@ bool FGAEffectHandle::IsValid() const void FGAEffectHandle::Reset() { Handle = INDEX_NONE; - EffectPtr.Reset(); + EffectPtr = nullptr; } FAFPredictionHandle FAFPredictionHandle::GenerateClientHandle(UAFAbilityComponent* InComponent) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 54f182e..5edc9ec 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -311,7 +311,7 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle UPROPERTY() uint32 Handle; //Fname Guid ? - TSharedPtr EffectPtr; + FGAEffect* EffectPtr; public: FGAEffectContext& GetContextRef(); @@ -322,14 +322,14 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle uint32 GetHandle() const; - FGAEffect GetEffect(); - FGAEffect GetEffect() const; + FGAEffect& GetEffect(); + FGAEffect& GetEffect() const; - FGAEffect& GetEffectRef(); - FGAEffect& GetEffectRef() const; + //FGAEffect& GetEffectRef(); + //FGAEffect& GetEffectRef() const; - TSharedPtr GetEffectPtr(); - TSharedPtr GetEffectPtr() const; + FGAEffect* GetEffectPtr(); + FGAEffect* GetEffectPtr() const; void SetContext(const FGAEffectContext& ContextIn); void SetContext(const FGAEffectContext& ContextIn) const; @@ -379,6 +379,7 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle FGAEffectHandle() : Handle(INDEX_NONE) + , EffectPtr(nullptr) {} FGAEffectHandle(uint32 HandleIn, FGAEffect* EffectIn); From 3c1fddea18540fa617f4fc1a9a052f80bb3e8bd8 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 20 Feb 2018 22:24:59 +0100 Subject: [PATCH 058/187] refactoring of effects system --- .../AbilityFramework/AFAbilityComponent.cpp | 6 +- .../AbilityFramework/AFAbilityComponent.h | 2 +- .../AbilityFramework/AFAbilityInterface.cpp | 9 +- .../AbilityFramework/AFAbilityInterface.h | 7 +- .../AbilityFramework/AFEffectsComponent.cpp | 118 ++- .../AbilityFramework/AFEffectsComponent.h | 42 +- .../Abilities/GAAbilityBase.cpp | 73 +- .../Abilities/GAAbilityBase.h | 39 +- .../Attributes/GAAttributeBase.cpp | 20 +- .../Attributes/GAAttributeBase.h | 1 - .../GAAttributesBlueprintFunctionLibrary.cpp | 16 +- .../GAAttributesBlueprintFunctionLibrary.h | 12 +- .../Effects/AFEffectApplicationRequirement.h | 9 +- .../Effects/AFEffectCustomApplication.cpp | 20 +- .../Effects/AFEffectCustomApplication.h | 17 +- .../AFAttributeStongerOverride.cpp | 17 +- .../AFAttributeStongerOverride.h | 9 +- .../AFEffectAlreadyApplied.cpp | 11 +- .../AFEffectAlreadyApplied.h | 9 +- .../AFAtributeDurationAdd.cpp | 20 +- .../AFAtributeDurationAdd.h | 10 +- .../AFAttributeDurationInfinite.cpp | 12 +- .../AFAttributeDurationInfinite.h | 10 +- .../AFAttributeDurationOverride.cpp | 21 +- .../AFAttributeDurationOverride.h | 10 +- .../AFPeriodApplicationAdd.cpp | 30 +- .../AFPeriodApplicationAdd.h | 19 +- .../AFPeriodApplicationExtend.cpp | 51 +- .../AFPeriodApplicationExtend.h | 18 +- .../AFPeriodApplicationInfiniteAdd.cpp | 21 +- .../AFPeriodApplicationInfiniteAdd.h | 18 +- .../AFPeriodApplicationOverride.cpp | 36 +- .../AFPeriodApplicationOverride.h | 19 +- .../AFPeriodicApplInfiniteOverride.h | 10 +- .../Effects/GABlueprintLibrary.cpp | 423 +++++---- .../Effects/GABlueprintLibrary.h | 98 ++- .../Effects/GACustomCalculation.h | 2 +- .../Effects/GAEffectExecution.cpp | 6 +- .../Effects/GAEffectExecution.h | 2 +- .../Effects/GAEffectGlobalTypes.cpp | 8 +- .../Effects/GAEffectGlobalTypes.h | 4 +- .../AbilityFramework/Effects/GAGameEffect.cpp | 828 +++++++++--------- .../AbilityFramework/Effects/GAGameEffect.h | 737 ++++++++++++---- .../Source/AbilityFramework/GAGlobalTypes.cpp | 135 ++- .../Source/AbilityFramework/GAGlobalTypes.h | 103 +-- .../AbilityFrameworkEditor.cpp | 10 +- .../EffectEditor/GAEffectBlueprintFactory.cpp | 2 +- .../GAEffectClassStructWidget.cpp | 2 +- .../GAEffectDetails.cpp | 2 +- Source/ActionRPGGame/ARCharacter.cpp | 12 +- 50 files changed, 1783 insertions(+), 1333 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index becc3ca..ac99f37 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -91,9 +91,13 @@ void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHa { //OnAttributePreModifed.Broadcast(ModIn, 0); //Add log. + if (!DefaultAttributes) + { + return; + } float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); FAFAttributeChangedData Data; - FGAEffectContext& Context = HandleIn.GetContextRef(); + FGAEffectContext& Context = InProperty.GetContext(HandleIn).GetRef(); Data.Mod = ModIn; Data.Target = Context.Target; Data.Location = Context.HitResult.Location; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 094ac1f..f48dfd9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -413,7 +413,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, const FGAEffectContext& InContext); FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; - void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; private: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp index 3a128d8..134412e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp @@ -15,10 +15,11 @@ UAFAbilityInterface::UAFAbilityInterface(const FObjectInitializer& ObjectInitial // return nullptr;// GetAbilityComp()->DefaultAttributes; //} -FGAEffectHandle IAFAbilityInterface::ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext +FGAEffectHandle IAFAbilityInterface::ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { - return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, InProperty, InContext, Modifier); + return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, InHandle, Params, Modifier); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h index 2774341..f5ede8f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h @@ -49,9 +49,10 @@ class IAFAbilityInterface virtual FAFPredictionHandle GetPredictionHandle() { return FAFPredictionHandle(); } - FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext + FGAEffectHandle ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); virtual class UGAAttributesBase* GetAttributes() { return GetAbilityComp()->DefaultAttributes; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index f7fbc18..46f1859 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -48,12 +48,15 @@ void UAFEffectsComponent::TickComponent(float DeltaTime, ELevelTick TickType, FA // ... } -FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext +FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { + FGAEffectProperty& InProperty = Params.GetProperty(); const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; + FAFEventData Data; for (const FGameplayTag& Tag : AppliedEventTags) @@ -68,16 +71,19 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf(FGAEffect* EffectIn Delegate->ExecuteIfBound(); } - FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InProperty, InContext, Modifier); + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InHandle, Params, Modifier); GameEffectContainer.MarkArrayDirty(); return Handle; } -FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext +FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { + FGAEffectProperty& InProperty = Params.GetProperty(); + FGAEffectContext& InContext = Params.GetContext(); if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) { Delegate->ExecuteIfBound(); @@ -92,28 +98,11 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget(FGAEffect* EffectIn FGAEffectCueParams CueParams(InContext, InProperty); MulticastApplyEffectCue(CueParams, CueHandle); } - FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - } - else if (mode == ENetMode::NM_DedicatedServer) - { - prefix = FString::Printf(TEXT("DedicatedServer: ")); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : ApplyEffectToTarget Owner: %s, Instigator: %s"), - *prefix, - *GetOwner()->GetName(), - *InContext.Instigator->GetName() - ); - //here, we should start attribute change prediction - //either change attribute or apply effect which will do so - - //execute cue from effect regardless if we have target object or not. + if (InContext.TargetComp.IsValid()) { FGAEffectHandle Handle; - Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InProperty, InContext, Modifier); + Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InHandle, Params, Modifier); if (!PropertyByHandle.Contains(Handle)) PropertyByHandle.Add(Handle, &InProperty); @@ -127,27 +116,29 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget(FGAEffect* EffectIn /* Have to to copy handle around, because timer delegates do not support references. */ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn - , FGAEffectProperty InProperty - , FAFFunctionModifier Modifier - , FGAEffectContext InContext) + , FAFEffectParams Params + , FAFFunctionModifier Modifier) { + FGAEffectContext& Context = Params.Context.GetRef(); + FGAEffectProperty& Property = Params.Property.GetRef(); + FAFEffectSpec& EffectSpec = Params.GetSpec(); /* this patth will give effects chance to do any replicated events, like applying cues. WE do not make any replication at the ApplyEffect because some effect might want to apply cues on periods on expiration etc, and all those will go trouch ExecuteEffect path. */ - const FGameplayTagContainer& RequiredTags = InProperty.GetSpec()->RequiredTags; + const FGameplayTagContainer& RequiredTags = Property.GetSpec()->RequiredTags; if (RequiredTags.Num() > 0) { if (!HasAll(RequiredTags)) { - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *HandleIn.GetEffectSpec()->GetName(), *RequiredTags.ToString()); + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *Property.GetSpec()->GetName(), *RequiredTags.ToString()); return; } } //apply execution events: - const FGameplayTagContainer& ExecuteEventTags = InProperty.GetSpec()->ExecuteEventTags; + const FGameplayTagContainer& ExecuteEventTags = Property.GetSpec()->ExecuteEventTags; FAFEventData Data; for (const FGameplayTag& Tag : ExecuteEventTags) { @@ -158,23 +149,23 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn } //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *HandleIn.GetEffectSpec()->GetName()); - FGAEffect& Effect = HandleIn.GetEffect(); - FGAEffectMod Mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() - , InProperty.GetSpec() - , InContext + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *Property.GetSpec()->GetName()); + + FGAEffectMod Mod = FAFStatics::GetAttributeModifier(Property.GetAttributeModifier() + , Property.GetSpec() + , Context , HandleIn); //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? - Effect.OnExecuted(); - ExecuteEffectEvent(InProperty.GetSpec()->OnPeriodEvent); + EffectSpec.OnExecuted(); + ExecuteEffectEvent(Property.GetSpec()->OnPeriodEvent); FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); if (CueHandle) MulticastExecuteEffectCue(*CueHandle); - InProperty.EffectExecution(HandleIn, Mod, HandleIn.GetContextRef(), Modifier); + Property.EffectExecution(HandleIn, Mod, Params, Modifier); PostExecuteEffect(); } @@ -184,11 +175,14 @@ void UAFEffectsComponent::PostExecuteEffect() } /* ExpireEffect is used to remove existing effect naturally when their time expires. */ void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn - , FGAEffectProperty InProperty - , FGAEffectContext InContext) + , FAFEffectParams Params) { //call effect internal delegate: - HandleIn.GetEffectPtr()->OnExpired(); + FGAEffectProperty& InProperty = Params.GetProperty(); + FGAEffectContext& InContext = Params.GetContext(); + FAFEffectSpec& EffectSpec = Params.GetSpec(); + FGAEffect* Effect = GameEffectContainer.GetEffect(HandleIn); + EffectSpec.OnExpired(); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); @@ -209,7 +203,7 @@ void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn } } - TArray handles = GameEffectContainer.RemoveEffect(InProperty); + TArray handles = GameEffectContainer.RemoveEffect(Params.Property); } void UAFEffectsComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) @@ -217,7 +211,7 @@ void UAFEffectsComponent::ClientExpireEffect_Implementation(FAFPredictionHandle } -void UAFEffectsComponent::RemoveEffect(const FGAEffectProperty& InProperty +void UAFEffectsComponent::RemoveEffect(const FAFPropertytHandle& InProperty , const FGAEffectContext& InContext , const FGAEffectHandle& InHandle) { @@ -227,7 +221,7 @@ void UAFEffectsComponent::RemoveEffect(const FGAEffectProperty& InProperty InternalRemoveEffect(InProperty, InContext); } ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); - FGAEffectCueParams CueParams(InContext, InProperty); + FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); if (CueHandle) @@ -235,14 +229,14 @@ void UAFEffectsComponent::RemoveEffect(const FGAEffectProperty& InProperty MulticastRemoveEffectCue(CueParams, *CueHandle); } } -void UAFEffectsComponent::InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext) +void UAFEffectsComponent::InternalRemoveEffect(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext) { UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); //MulticastRemoveEffectCue(HandleIn); if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) { - FGAEffectCueParams CueParams(InContext, InProperty); + FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); if (mode == ENetMode::NM_Standalone @@ -255,11 +249,6 @@ void UAFEffectsComponent::InternalRemoveEffect(const FGAEffectProperty& InProper TArray handles = GameEffectContainer.RemoveEffect(InProperty); } -const TSet& UAFEffectsComponent::GetAllEffectsHandles() const -{ - return GameEffectContainer.GetAllEffectHandles(); -} - void UAFEffectsComponent::AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) { if (!InEventTag.IsValid()) @@ -331,6 +320,11 @@ bool UAFEffectsComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InT return bAllowApplication; } +FGAEffect* UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) +{ + return *GameEffectContainer.ActiveEffects.Find(InHandle); +} + /* Need prediction for spawning effects on client, and then on updateing them predicitvely on all other clients. @@ -345,22 +339,6 @@ void UAFEffectsComponent::MulticastApplyEffectCue_Implementation(FGAEffectCuePar if (mode == ENetMode::NM_Standalone || role != ENetRole::ROLE_Authority) { - FString prefix = ""; - if (mode == ENetMode::NM_Client) - { - int32 client = GPlayInEditorID - 1; - if (client == 2) - { - float dupa = 0; - } - prefix = FString::Printf(TEXT("Client %d: "), client); - } - UE_LOG(AbilityFramework, Log, TEXT("%s : MulticastApplyEffectCue Owner: %s, Instigator: %s"), - *prefix, - *GetOwner()->GetName(), - *CueParams.Instigator->GetName() - ); - UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); } } @@ -414,6 +392,8 @@ void UAFEffectsComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProp Super::GetLifetimeReplicatedProps(OutLifetimeProps); DOREPLIFETIME(UAFEffectsComponent, GameEffectContainer); + DOREPLIFETIME(UAFEffectsComponent, AppliedTags); + DOREPLIFETIME(UAFEffectsComponent, ImmunityTags); } void UAFEffectsComponent::OnRep_GameEffectContainer() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index 8b4c870..8577da5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -22,7 +22,7 @@ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent { GENERATED_BODY() -public: +private: friend class UGAAbilityBase; friend class IAFAbilityInterface; friend class UAFAbilityComponent; @@ -32,10 +32,10 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer DefaultTags; - UPROPERTY() + UPROPERTY(Replicated) FGACountedTagContainer AppliedTags; - UPROPERTY() + UPROPERTY(Replicated) FGACountedTagContainer ImmunityTags; UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) @@ -48,7 +48,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent TMap PropertyByHandle; TMap EffectToCue; -TMap OnEffectEvent; + TMap OnEffectEvent; public: // Sets default values for this component's properties @@ -82,9 +82,10 @@ TMap OnEffectEvent; * @param Modifier - optional modifier which can be applied to effect. * @return Handle to Effect; */ - FGAEffectHandle ApplyEffectToSelf(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext + FGAEffectHandle ApplyEffectToSelf( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); /* @@ -101,37 +102,35 @@ TMap OnEffectEvent; * @param Modifier - optional modifier which can be applied to effect. * @return Handle to Effect; */ - FGAEffectHandle ApplyEffectToTarget(FGAEffect* EffectIn - , FGAEffectProperty& InProperty - , FGAEffectContext& InContext + FGAEffectHandle ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); public: /* Have to to copy handle around, because timer delegates do not support references. */ void ExecuteEffect(FGAEffectHandle HandleIn - , FGAEffectProperty InProperty - , FAFFunctionModifier Modifier - , FGAEffectContext InContext); + , FAFEffectParams Params + , FAFFunctionModifier Modifier); virtual void PostExecuteEffect(); /* ExpireEffect is used to remove existing effect naturally when their time expires. */ public: void ExpireEffect(FGAEffectHandle HandleIn - , FGAEffectProperty InProperty - , FGAEffectContext InContext); + , FAFEffectParams Params); + protected: UFUNCTION(Client, Reliable) void ClientExpireEffect(FAFPredictionHandle PredictionHandle); void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); /* RemoveEffect is used to remove effect by force. */ - void RemoveEffect(const FGAEffectProperty& InProperty + void RemoveEffect(const FAFPropertytHandle& InProperty , const FGAEffectContext& InContext , const FGAEffectHandle& InHandle); - void InternalRemoveEffect(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); - - const TSet& GetAllEffectsHandles() const; - + void InternalRemoveEffect(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext); + void AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent); void ExecuteEffectEvent(const FGameplayTag& InEventTag); void RemoveEffectEvent(const FGameplayTag& InEventTag); @@ -174,6 +173,8 @@ TMap OnEffectEvent; void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); void MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); public: + FGAEffect* GetEffect(const FGAEffectHandle& InHandle); + /* Counted Tag Container Wrapper Start */ inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; @@ -188,6 +189,7 @@ TMap OnEffectEvent; inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } /* Counted Tag Container Wrapper Start */ + /*Network Functions - BEGIN */ protected: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index f5165b3..a20499d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -18,34 +18,12 @@ #include "GAAbilityBase.h" FAFPredictionHandle UGAAbilityBase::GetPredictionHandle() { return PredictionHandle; } -void FGAAbilityTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) -{ - if (Target && !Target->IsPendingKillOrUnreachable()) - { - FScopeCycleCounterUObject ActorScope(Target); - Target->TickAbility(DeltaTime, TickType, *this); - } -} - -FString FGAAbilityTick::DiagnosticMessage() -{ - return Target->GetFullName() + TEXT("[TickAction]"); -} UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { bReplicate = true; bIsNameStable = false; - - TickFunction.TickGroup = TG_PrePhysics; - // Default to no tick function, but if we set 'never ticks' to false (so there is a tick function) it is enabled by default - TickFunction.bCanEverTick = true; - TickFunction.bStartWithTickEnabled = true; - TickFunction.bAllowTickOnDedicatedServer = true; - TickFunction.bRunOnAnyThread = true; - - TickFunction.SetTickFunctionEnable(true); } void UGAAbilityBase::PostInitProperties() @@ -152,15 +130,11 @@ void UGAAbilityBase::UpdateAssetRegistryInfo() { AbilityTagSearch = AbilityTag.GetTagName(); } -void UGAAbilityBase::TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction) -{ - -} void UGAAbilityBase::InitAbility() { //still want to initialize, as Spec is used in multiple places. - DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)); + DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); ActivationEffect.InitializeIfNotInitialized(DefaultContext); CooldownEffect.InitializeIfNotInitialized(DefaultContext); AttributeCost.InitializeIfNotInitialized(DefaultContext); @@ -206,9 +180,7 @@ void UGAAbilityBase::InitAbility() { OwnerCamera = POwner->FindComponentByClass(); } - TickFunction.Target = this; - TickFunction.RegisterTickFunction(AbilityComponent->GetWorld()->GetCurrentLevel()); - TickFunction.SetTickFunctionEnable(true); + OnAbilityInited(); } void UGAAbilityBase::OnAttributeSetReplicated() @@ -333,7 +305,7 @@ void UGAAbilityBase::NativeCancelActivation() if (!ActivationEffectHandle.IsValid()) return; - UAFAbilityComponent* AttrComp = ActivationEffectHandle.GetContext().InstigatorComp.Get(); + UAFAbilityComponent* AttrComp = DefaultContext.InstigatorComp.Get(); AbilityComponent->ExecutingAbility = nullptr; OnConfirmDelegate.Clear(); OnConfirmDelegate.RemoveAll(this); @@ -372,8 +344,13 @@ bool UGAAbilityBase::ApplyCooldownEffect() FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); - CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(CooldownEffect, - this, POwner, this, Modifier); + CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + CooldownEffect + , CooldownEffectHandle + , this + , POwner + , this + , Modifier); ENetMode nm = AbilityComponent->GetOwner()->GetNetMode(); ENetRole role = AbilityComponent->GetOwnerRole(); @@ -390,7 +367,7 @@ void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) { //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); OnCooldownEnd(InHandle); - ActiveCooldownHandle.Reset(); + CooldownEffectHandle.Reset(); } void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) { @@ -420,8 +397,13 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); FAFFunctionModifier Modifier; - ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject(ActivationEffect, - this, POwner, this, Modifier); + ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + ActivationEffect + , ActivationEffectHandle + , this + , POwner + , this + , Modifier); //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) // ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); @@ -578,8 +560,13 @@ bool UGAAbilityBase::ApplyAbilityAttributeCost() if (CheckAbilityAttributeCost()) { - AbilityAttributeCostHandle = UGABlueprintLibrary::ApplyGameEffectToObject(AbilityAttributeCost, - this, POwner, this, Modifier); + AbilityAttributeCostHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + AbilityAttributeCost + , AbilityAttributeCostHandle + , this + , POwner + , this + , Modifier); return true; } @@ -640,7 +627,15 @@ float UGAAbilityBase::GetCurrentActivationTime() { if (ActivationEffectHandle.IsValid()) { - return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); + if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) + { + FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); + if (Effect) + { + return Effect->GetCurrentDuration(); + } + } + //return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); } return 0; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 6a96cdb..2401be8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -54,32 +54,7 @@ DECLARE_MULTICAST_DELEGATE(FGASSimpleAbilityDynamicDelegate); DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASGenericAbilityDelegate); -USTRUCT() -struct FGAAbilityTick : public FTickFunction -{ - GENERATED_USTRUCT_BODY() - /** AActor that is the target of this tick **/ - class UGAAbilityBase* Target; - - /** - * Abstract function actually execute the tick. - * @param DeltaTime - frame time to advance, in seconds - * @param TickType - kind of tick for this frame - * @param CurrentThread - thread we are executing on, useful to pass along as new tasks are created - * @param MyCompletionGraphEvent - completion event for this task. Useful for holding the completetion of this task until certain child tasks are complete. - **/ - virtual void ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) override; - /** Abstract function to describe this tick. Used to print messages about illegal cycles in the dependency graph **/ - virtual FString DiagnosticMessage() override; -}; -template<> -struct TStructOpsTypeTraits : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithCopy = false - }; -}; + USTRUCT() struct FGAActiationInfo { @@ -120,7 +95,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask { GENERATED_BODY() public: - FGAAbilityTick TickFunction; /* Since each ability is instanced per owner, and cannot be activated multiple times (ie, to run in background), @@ -191,7 +165,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask Duration of this effect equals cooldown of ability. */ UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") - FGAEffectProperty CooldownEffect; + FAFPropertytHandle CooldownEffect; FGAEffectHandle CooldownEffectHandle; /* Tags applied to the time of activation ability. @@ -205,7 +179,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask Add Periodic Effect ? (For abilities with period). */ UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") - FGAEffectProperty ActivationEffect; + FAFPropertytHandle ActivationEffect; FGAEffectHandle ActivationEffectHandle; /* @@ -213,12 +187,12 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask Attribute cost from Ability Owner attributes */ UPROPERTY(EditAnywhere, Category = "Config") - FGAEffectProperty AttributeCost; + FAFPropertytHandle AttributeCost; /* Attribute cost from ability own attributes */ UPROPERTY(EditAnywhere, Category = "Config") - FGAEffectProperty AbilityAttributeCost; + FAFPropertytHandle AbilityAttributeCost; FGAEffectHandle AbilityAttributeCostHandle; UPROPERTY(AssetRegistrySearchable) @@ -246,7 +220,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask FGameplayTagContainer ActivationBlockedTags; public: //because I'm to lazy to write all those friend states.. - virtual void TickAbility(float DeltaSeconds, ELevelTick TickType, FGAAbilityTick& ThisTickFunction); UFUNCTION() void OnActivationEffectPeriod(FGAEffectHandle InHandle); @@ -501,7 +474,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, HandleIn.GetAttributeMod()); }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty) override { Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); }; virtual FAFPredictionHandle GetPredictionHandle() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp index c263ee9..d6d246e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -146,23 +146,7 @@ void FAFAttributeBase::CalculateBonus() CurrentValue = CurrentValue + (50); ?? */ } -//check for tags. -bool FAFAttributeBase::CheckIfModsMatch(const FGAEffectHandle& InHandle, const FGAEffectMod& InMod) -{ - TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; - auto It = mods.CreateConstIterator(); - for (; It; ++It) - { - if (It->Key.HasAllAttributeTags(InHandle)) //or maybe the other way around ? - { - return true; - } - } - - if (mods.Num() <= 0) - return true; - return false; -} + bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) { TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; @@ -194,7 +178,7 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& if ( !isPeriod & IsDuration) { FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); - AttrMod.Tags.AppendTags(HandleIn.GetEffectSpec()->AttributeTags); + AttrMod.Tags.AppendTags(InProperty.GetSpec()->AttributeTags); AddBonus(ModIn, HandleIn); return ModIn.Value; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h index 249b954..cba2cf6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -98,7 +98,6 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase }; inline float GetCurrentValue() { return CurrentValue; }; void CalculateBonus(); - bool CheckIfModsMatch(const FGAEffectHandle& InHandle, const FGAEffectMod& InMod); bool CheckIfStronger(const FGAEffectMod& InMod); float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp index c4d6951..3a194a8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp @@ -50,9 +50,15 @@ float UGAAttributesBlueprintFunctionLibrary::GetAttributeFloat(AActor* Target, F return attributeInt->GetAttributes()->GetFloatValue(AttributeIn); } -void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues(APawn* Instigator, UObject* Causer, - UPARAM(ref) FGAEffectProperty& From, UObject* FromTarget, - UPARAM(ref) FGAEffectProperty& To, UObject* ToTarget) +void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues( + APawn* Instigator + , UObject* Causer + , FAFPropertytHandle From + , FGAEffectHandle FromHandle + , UObject* FromTarget + , FAFPropertytHandle To + , FGAEffectHandle ToHandle + , UObject* ToTarget) { IAFAbilityInterface* FromInterface = Cast(FromTarget); IAFAbilityInterface* ToInterface = Cast(ToTarget); @@ -61,6 +67,6 @@ void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues(APawn* Inst return; FAFFunctionModifier ModF; - UGABlueprintLibrary::ApplyGameEffectToObject(From, FromTarget, Instigator, Causer, ModF); - UGABlueprintLibrary::ApplyGameEffectToObject(To, ToTarget, Instigator, Causer, ModF); + UGABlueprintLibrary::ApplyGameEffectToObject(From, FromHandle, FromTarget, Instigator, Causer, ModF); + UGABlueprintLibrary::ApplyGameEffectToObject(To, ToHandle, ToTarget, Instigator, Causer, ModF); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h index c288148..6a9cf15 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h @@ -46,7 +46,13 @@ class ABILITYFRAMEWORK_API UGAAttributesBlueprintFunctionLibrary : public UBluep * @return value of attribute from actor. */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - static void ExchangeAttributesValues(APawn* Instigator, UObject* Causer, - UPARAM(ref) FGAEffectProperty& From, UObject* FromTarget, - UPARAM(ref) FGAEffectProperty& To, UObject* ToTarget); + static void ExchangeAttributesValues( + APawn* Instigator + , UObject* Causer + , FAFPropertytHandle From + , FGAEffectHandle FromHandle + , UObject* FromTarget + , FAFPropertytHandle To + , FGAEffectHandle ToHandle + , UObject* ToTarget); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h index 76ae53d..3225e76 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h @@ -17,10 +17,11 @@ class ABILITYFRAMEWORK_API UAFEffectApplicationRequirement : public UObject GENERATED_BODY() public: - virtual bool CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, - struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FGAEffectHandle& InHandle) + virtual bool CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) { return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp index 934cf99..8f04be7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp @@ -7,18 +7,20 @@ -bool UAFEffectCustomApplication::ApplyEffect(const FGAEffectHandle& InHandle, FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFEffectCustomApplication::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { return true; } -void UAFEffectCustomApplication::ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +void UAFEffectCustomApplication::ApplyExecute( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - InHandle.GetContext().GetTargetEffectsComponent()->ExecuteEffect(InHandle, InProperty, Modifier, InContext); + Params.GetContext().GetTargetEffectsComponent()->ExecuteEffect(InHandle, Params, Modifier); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h index b06fefe..4afe314 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h @@ -16,14 +16,17 @@ class ABILITYFRAMEWORK_API UAFEffectCustomApplication : public UObject { GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - virtual void ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual void ApplyExecute( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); virtual bool ShowPeriod() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp index aa16de6..46e7ee3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp @@ -8,19 +8,22 @@ -bool UAFAttributeStongerOverride::CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, - struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FGAEffectHandle& InHandle) +bool UAFAttributeStongerOverride::CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) { bool bCanApply = true; - FGAAttribute Attribute = InProperty.GetSpec()->AtributeModifier.Attribute; - FAFAttributeBase* AttributePtr = EffectIn->Context.TargetInterface->GetAttribute(Attribute); + FGAAttribute Attribute = Params.GetProperty().GetSpec()->AtributeModifier.Attribute; + FAFAttributeBase* AttributePtr = Params.GetContext().TargetInterface->GetAttribute(Attribute); + FGAEffectProperty& InProperty = Params.GetProperty(); + if (AttributePtr) { FGAEffectMod mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() , InProperty.GetSpec() - , InContext + , Params.GetContext() , InHandle); if (AttributePtr->CheckIfStronger(mod)) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h index 15eb56f..f2e18f5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h @@ -15,10 +15,11 @@ class ABILITYFRAMEWORK_API UAFAttributeStongerOverride : public UAFEffectApplica { GENERATED_BODY() public: - virtual bool CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, - struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FGAEffectHandle& InHandle) override; + virtual bool CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) override; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp index b55d7d6..9e44f37 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp @@ -6,12 +6,13 @@ -bool UAFEffectAlreadyApplied::CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, - struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FGAEffectHandle& InHandle) +bool UAFEffectAlreadyApplied::CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) { - if (InContainer->ContainsEffectOfClass(InProperty)) + if (InContainer->ContainsEffectOfClass(Params.Property)) { return false; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h index 41469ee..13b21b5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h @@ -14,10 +14,11 @@ class ABILITYFRAMEWORK_API UAFEffectAlreadyApplied : public UAFEffectApplication { GENERATED_BODY() public: - virtual bool CanApply(FGAEffect* EffectIn, FGAEffectProperty& InProperty, - struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FGAEffectHandle& InHandle) override; + virtual bool CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp index 0969d5c..a96c24c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -8,18 +8,18 @@ -bool UAFAtributeDurationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFAtributeDurationAdd::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); - DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.GetDuration(), false); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); - InContainer->AddEffect(InProperty, InHandle); - //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h index 7dc5b74..04eca4b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h @@ -14,10 +14,12 @@ class ABILITYFRAMEWORK_API UAFAtributeDurationAdd : public UAFEffectCustomApplic { GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); virtual bool ShowPeriod() override { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp index 63fe53f..373b41c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp @@ -6,12 +6,12 @@ -bool UAFAttributeDurationInfinite::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFAttributeDurationInfinite::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - InContainer->AddEffect(InProperty, InHandle, true); - //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h index 187516a..7707eda 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h @@ -14,10 +14,12 @@ class ABILITYFRAMEWORK_API UAFAttributeDurationInfinite : public UAFEffectCustom { GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); virtual bool ShowPeriod() override { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp index 311ad07..145e7bf 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -8,19 +8,20 @@ -bool UAFAttributeDurationOverride::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFAttributeDurationOverride::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - InContainer->RemoveEffect(InProperty); + InContainer->RemoveEffect(Params.Property); - FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); - DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.GetDuration(), false); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); - InContainer->AddEffect(InProperty, InHandle); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h index 865b129..158d374 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h @@ -14,10 +14,12 @@ class ABILITYFRAMEWORK_API UAFAttributeDurationOverride : public UAFEffectCustom { GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); virtual bool ShowPeriod() override diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp index e186577..a7bab63 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -6,25 +6,27 @@ #include "AFPeriodApplicationAdd.h" -bool UAFPeriodApplicationAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFPeriodApplicationAdd::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); - DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.GetDuration(), false); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); - FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); - PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.GetPeriod(), true); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); - InContainer->AddEffect(InProperty, InHandle); - //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); + //InContainer->AddEffect(InProperty, InHandle); + return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h index 7964305..00a1e2a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h @@ -14,14 +14,17 @@ class ABILITYFRAMEWORK_API UAFPeriodApplicationAdd : public UAFEffectCustomAppli { GENERATED_BODY() public: - bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()) override; - virtual void ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) override; + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) {}; virtual bool ShowPeriod() override diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index b96a754..c6b461d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -1,46 +1,53 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "../GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" #include "AFEffectsComponent.h" #include "AFPeriodApplicationExtend.h" -bool UAFPeriodApplicationExtend::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, const FAFFunctionModifier& Modifier) +bool UAFPeriodApplicationExtend::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); + TSet handles = InContainer->GetHandlesByClass(Params.GetProperty(), Params.GetContext()); for (const FGAEffectHandle& handle : handles) { - FGAEffect& ExtEffect = handle.GetEffect(); - FGAEffect& Effect = InHandle.GetEffect(); - FTimerManager& DurationTimer = handle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - float RemainingTime = DurationTimer.GetTimerRemaining(handle.GetEffectPtr()->DurationTimerHandle); + FGAEffect& ExtEffect = *InContainer->GetEffect(handle); + FGAEffect& Effect = const_cast(EffectIn); + + FGAEffectContext& ExtContext = const_cast(Params).GetProperty().GetContext(handle).GetRef(); + + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + float RemainingTime = DurationTimer.GetTimerRemaining(ExtEffect.DurationTimerHandle); float NewDuration = RemainingTime + Effect.GetDurationTime(); - DurationTimer.ClearTimer(handle.GetEffectPtr()->DurationTimerHandle); + DurationTimer.ClearTimer(ExtEffect.DurationTimerHandle); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(handle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); - DurationTimer.SetTimer(handle.GetEffectPtr()->DurationTimerHandle, delDuration, + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(ExtContext.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(ExtEffect.DurationTimerHandle, delDuration, NewDuration, false); } if (handles.Num() <= 0) { - FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); - DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.GetDuration(), false); + FGAEffect& Effect = const_cast(EffectIn);; + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(Effect.DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); - PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.GetPeriod(), true); + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - InContainer->AddEffect(InProperty, InHandle); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(Effect.PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); } return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h index 2cd0917..e5efa4e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h @@ -16,15 +16,17 @@ class ABILITYFRAMEWORK_API UAFPeriodApplicationExtend : public UAFEffectCustomAp GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - virtual void ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) {}; virtual bool ShowPeriod() override { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp index 9ce7e3f..7fc9e0a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -6,18 +6,19 @@ #include "AFPeriodApplicationInfiniteAdd.h" -bool UAFPeriodApplicationInfiniteAdd::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFPeriodApplicationInfiniteAdd::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); - PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.GetPeriod(), true); - InContainer->AddEffect(InProperty, InHandle, true); - //EffectIn->Context.TargetComp->ExecuteEffect(InHandle, InProperty); + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); + return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h index ee9fc23..745850a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h @@ -14,15 +14,17 @@ class ABILITYFRAMEWORK_API UAFPeriodApplicationInfiniteAdd : public UAFEffectCus { GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - virtual void ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) {}; virtual bool ShowPeriod() override diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp index e27d5fe..db10dbe 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -8,31 +8,27 @@ -bool UAFPeriodApplicationOverride::ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier) +bool UAFPeriodApplicationOverride::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) { - //TSet handles = InContainer->GetHandlesByClass(InProperty, EffectIn->Context); - //for (const FGAEffectHandle& handle : handles) - //{ - // InContainer->RemoveEffect(InProperty); - //} - InContainer->RemoveEffect(InProperty); - FTimerManager& DurationTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + InContainer->RemoveEffect(Params.Property); - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, InProperty, InContext); - DurationTimer.SetTimer(InHandle.GetEffectPtr()->DurationTimerHandle, delDuration, - InProperty.GetDuration(), false); + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - FTimerManager& PeriodTimer = InHandle.GetContext().TargetComp->GetWorld()->GetTimerManager(); + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(InHandle.GetContext().GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, InProperty, Modifier, InContext); - PeriodTimer.SetTimer(InHandle.GetEffectPtr()->PeriodTimerHandle, PeriodDuration, - InProperty.GetPeriod(), true); + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); - InContainer->AddEffect(InProperty, InHandle); - //EffectIn.Context.TargetComp->ExecuteEffect(InHandle, InProperty); return true; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h index 187ecfd..6f7e271 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h @@ -14,14 +14,17 @@ class ABILITYFRAMEWORK_API UAFPeriodApplicationOverride : public UAFEffectCustom { GENERATED_BODY() public: - virtual bool ApplyEffect(const FGAEffectHandle& InHandle, struct FGAEffect* EffectIn, - FGAEffectProperty& InProperty, struct FGAEffectContainer* InContainer, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - virtual void ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) {}; virtual bool ShowPeriod() override { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h index 2d65233..8d613d5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h @@ -15,10 +15,12 @@ class ABILITYFRAMEWORK_API UAFPeriodicApplInfiniteOverride : public UAFEffectCus GENERATED_BODY() - virtual void ExecuteEffect(const FGAEffectHandle& InHandle, - FGAEffectProperty& InProperty, - const FGAEffectContext& InContext, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) {}; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 5b3245f..e7eb637 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -1,11 +1,12 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" -#include "../AFAbilityComponent.h" +#include "AbilityFramework.h" +#include "AFAbilityComponent.h" #include "GABlueprintLibrary.h" -#include "../AFAbilityInterface.h" +#include "AFAbilityInterface.h" + #include "GAEffectExtension.h" UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) @@ -15,236 +16,272 @@ UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitial } -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToObject(UPARAM(ref) FGAEffectProperty& InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier) +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToObject( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) { - return ApplyEffectToObject(InEffect, Target, Instigator, Causer, Modifier); + return ApplyEffectToObject(InEffect, Handle, Target, Instigator, Causer, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToActor(UPARAM(ref) FGAEffectProperty& InEffect, - class AActor* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier) +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToActor( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) { - return ApplyEffectToActor(InEffect, Target, Instigator, Causer, Modifier); + return ApplyEffectToActor(InEffect, Handle, Target, Instigator, Causer, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation(UPARAM(ref) FGAEffectProperty& InEffect, - const FHitResult& Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier) +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) { - return ApplyEffectFromHit(InEffect, Target, Instigator, Causer, Modifier); + return ApplyEffectFromHit(InEffect, Handle, Target, Instigator, Causer, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty& InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier ) +FGAEffectHandle UGABlueprintLibrary::ApplyEffect( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier) { - IAFAbilityInterface* Ability = Cast(Causer); if (!Ability) { UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); return FGAEffectHandle(); } - FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - InEffect.InitializeIfNotInitialized(Context); - - if (!InEffect.IsInitialized()) - { - UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); - return FGAEffectHandle(); - } - - - UAFEffectsComponent* Target2 = Context.GetTargetEffectsComponent(); - if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) + bool bReusedParams = false; + bool bPeriodicEffect = false; + bool bReusedSpec = false; + if (Handle.IsValid() && (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) { - return FGAEffectHandle(); - } - if (Target2->DenyEffectApplication(InEffect.GetSpec()->DenyTags)) - { - return FGAEffectHandle(); + bPeriodicEffect = true; } - UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); - FGAEffect* effect = nullptr; - if (InEffect.GetDuration() <= 0 && InEffect.GetPeriod() <= 0) + FAFContextHandle Context; + FAFEffectSpecHandle EffectSpecHandle; + + if (Handle.IsValid()) { - if (!InEffect.IsHandleValid(Target)) + FAFContextHandle ExistingContext = InEffect.GetContext(Handle); + if (ExistingContext.IsValid()) { - effect = new FGAEffect(InEffect.GetClass(), Context); - AddTagsToEffect(effect); - effect->Context = Context; - } - else - { - effect = InEffect.GetHandle(Target).GetEffectPtr(); + Context = ExistingContext; + Context.SetTarget(Target); + bReusedParams = true; } + FAFEffectSpecHandle SpecHandle = InEffect.GetEffectSpec(Handle); + EffectSpecHandle = SpecHandle; + bReusedParams = true; + bReusedSpec = true; } else { - effect = new FGAEffect(InEffect.GetClass(), Context); - AddTagsToEffect(effect); - effect->Context = Context; - } - if (Ability) - { - InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); - if (effect) - { - effect->PredictionHandle = Ability->GetPredictionHandle(); - } - } - IAFAbilityInterface* InstigatorInterface = Cast(Instigator); - - FGAEffectHandle Handle = InstigatorInterface->ApplyEffectToTarget(effect, InEffect, Context, Modifier); - if (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0) - { - InEffect.AddHandle(Context.Target.Get(), Handle); + Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); } - return Handle; -} -FGAEffectHandle UGABlueprintLibrary::ApplyEffect(FGAEffectProperty* InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier) -{ - IAFAbilityInterface* Ability = Cast(Causer); - if (!Ability) + InEffect.InitializeIfNotInitialized(Context.GetRef()); + + if ((InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) { - UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); - return FGAEffectHandle(); + bPeriodicEffect = true; } - FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - InEffect->InitializeIfNotInitialized(Context); - - if (!InEffect->IsInitialized()) + if (!InEffect.IsInitialized()) { UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); return FGAEffectHandle(); } - - - - /*if (!Context.IsValid()) - { - return FGAEffectHandle(); - }*/ - UAFEffectsComponent* Target2 = Context.GetTargetEffectsComponent(); - if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) + + UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); + if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) { return FGAEffectHandle(); } - if (Target2->DenyEffectApplication(InEffect->GetSpec()->DenyTags)) + if (Target2->DenyEffectApplication(InEffect.GetSpec()->DenyTags)) { return FGAEffectHandle(); } - UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); - FGAEffect* effect = nullptr; - if (InEffect->GetDuration() <= 0 && InEffect->GetPeriod() <= 0) - { - if (!InEffect->IsHandleValid(Target)) - { - effect = new FGAEffect(InEffect->GetClass(), Context); - AddTagsToEffect(effect); - effect->Context = Context; - } - else - { - effect = InEffect->GetHandle(Target).GetEffectPtr(); - } - } - else + FGAEffect effect; + effect.World = Instigator->GetWorld(); + if (Ability) { - effect = new FGAEffect(InEffect->GetClass(), Context); - AddTagsToEffect(effect); - effect->Context = Context; + //InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); + + effect.PredictionHandle = Ability->GetPredictionHandle(); } - if (Ability) + IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + + FAFEffectParams Params(InEffect); + + if (!bReusedSpec) { - InEffect->SetPredictionHandle(Ability->GetPredictionHandle()); - if (effect) - { - effect->PredictionHandle = Ability->GetPredictionHandle(); - } + FAFEffectSpec* EffectSpec = new FAFEffectSpec(InEffect.GetClass()); + AddTagsToEffect(EffectSpec); + Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); } - IAFAbilityInterface* InstigatorInterface = Cast(Instigator); - FGAEffectHandle Handle = InstigatorInterface->ApplyEffectToTarget(effect, *InEffect, Context, Modifier); - if (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0) + else { - InEffect->AddHandle(Context.Target.Get(), Handle); + Params.EffectSpec = EffectSpecHandle; } - return Handle; + Params.bRecreated = bReusedParams; + Params.bPeriodicEffect = bPeriodicEffect; + Params.Context = Context; + + FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); + + return NewHandle; } -FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit(FGAEffectProperty& InEffect, - const FHitResult& Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier) +FGAEffectHandle UGABlueprintLibrary::ApplyEffect( + FGAEffectProperty* InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier) { - return ApplyEffect(InEffect, Target.GetActor(), Instigator, Causer, Target, Modifier); + //IAFAbilityInterface* Ability = Cast(Causer); + //if (!Ability) + //{ + // UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); + // return FGAEffectHandle(); + //} + //bool bReusedParams = false; + //bool bPeriodicEffect = false; + //bool bReusedSpec = false; + //if (Handle.IsValid() && (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0)) + //{ + // bPeriodicEffect = true; + //} + + //FAFContextHandle Context; + //FAFEffectSpecHandle EffectSpecHandle; + + //if (Handle.IsValid()) + //{ + // if (bPeriodicEffect) + // { + // FAFContextHandle* ExistingContext = InEffect->GetContext(Handle); + // if (ExistingContext) + // { + // Context = *ExistingContext; + // Context.SetTarget(Target); + // bReusedParams = true; + // } + // FAFEffectSpecHandle* SpecHandle = InEffect->GetEffectSpec(Handle); + // EffectSpecHandle = *SpecHandle; + // bReusedSpec = true; + // } + // else + // { + // Context = InEffect->GetInstantContext(); + // Context.SetTarget(Target); + + // EffectSpecHandle = InEffect->GetInstantEffectSpec(); + // bReusedParams = true; + // bReusedSpec = true; + // } + //} + //else + //{ + // Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + //} + + //InEffect->InitializeIfNotInitialized(Context.GetRef()); + + //if (!InEffect->IsInitialized()) + //{ + // UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + // return FGAEffectHandle(); + //} + + //UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); + //if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) + //{ + // return FGAEffectHandle(); + //} + //if (Target2->DenyEffectApplication(InEffect->GetSpec()->DenyTags)) + //{ + // return FGAEffectHandle(); + //} + //UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); + + //FGAEffect effect; + //effect.World = Instigator->GetWorld(); + //if (Ability) + //{ + // InEffect->SetPredictionHandle(Ability->GetPredictionHandle()); + // effect.PredictionHandle = Ability->GetPredictionHandle(); + // + //} + // + //FAFPropertytHandle Property = FAFPropertytHandle::Generate(*InEffect); + //FAFEffectParams Params(Property); + //FAFEffectSpec* EffectSpec = new FAFEffectSpec(); + ////AddTagsToEffect(EffectSpec); + //Params.Context = Context; + // + //Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); + + //IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + //FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); + FGAEffectHandle NewHandle; + return NewHandle; } - -FGAEffectHandle UGABlueprintLibrary::ApplyEffectToActor(FGAEffectProperty& InEffect, - class AActor* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier) +FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) { - FHitResult Hit(ForceInit); - return ApplyEffect(InEffect, Target, Instigator, Causer, Hit, Modifier); + return ApplyEffect(InEffect, Handle, Target.GetActor(), Instigator, Causer, Target, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject(FGAEffectProperty& InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier) +FGAEffectHandle UGABlueprintLibrary::ApplyEffectToActor( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) { FHitResult Hit(ForceInit); - return ApplyEffect(InEffect, Target, Instigator, Causer, Hit, Modifier); + return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); } -FGAEffectHandle UGABlueprintLibrary::MakeEffect(TSubclassOf SpecIn, - FGAEffectHandle HandleIn, class UObject* Target, class APawn* Instigator, - UObject* Causer, const FHitResult& HitIn) -{ - if (!SpecIn) - { - UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); - return FGAEffectHandle(); - } - - FGAEffectContext Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - if (!Context.IsValid()) - { - //if the handle is valid (valid pointer to effect and id) - //we want to preseve it and just set bad context. - if (HandleIn.IsValid()) - { - HandleIn.SetContext(Context); - return HandleIn; - } - else - { - return FGAEffectHandle(); - } - } - - UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.ToString()); - if (HandleIn.IsValid()) - { - HandleIn.SetContext(Context); - } - else - { - FGAEffect* effect = new FGAEffect(SpecIn, Context); - AddTagsToEffect(effect); - HandleIn = FGAEffectHandle::GenerateHandle(effect); - effect->Handle = HandleIn; - } - return HandleIn; +FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + FHitResult Hit(ForceInit); + return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); } -FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, +FAFContextHandle UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, AActor* InAvatar, UObject* Causer, const FHitResult& HitIn) { IAFAbilityInterface* targetAttr = Cast(Target); @@ -252,7 +289,7 @@ FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class A if (!targetAttr && !instiAttr) { UE_LOG(GameAttributesEffects, Error, TEXT("Target and Instigator does not implement IAFAbilityInterface interface")); - return FGAEffectContext(); + return FAFContextHandle(); } UAFAbilityComponent* targetComp = nullptr; UAFAbilityComponent* instiComp = nullptr; @@ -266,38 +303,46 @@ FGAEffectContext UGABlueprintLibrary::MakeContext(class UObject* Target, class A } FVector location = targetComp ? targetComp->GetOwner()->GetActorLocation() : FVector(HitIn.ImpactPoint.X, HitIn.ImpactPoint.Y, HitIn.ImpactPoint.Z); - FGAEffectContext Context( - targetAttr ? targetAttr->GetAttributes() : nullptr, - instiAttr ? instiAttr->GetAttributes() : nullptr, - location, Target, Causer, - Instigator, targetComp, instiComp, - InAvatar); - Context.HitResult = HitIn; - return Context; + FGAEffectContext* Context = new FGAEffectContext( + targetAttr ? targetAttr->GetAttributes() : nullptr + , instiAttr ? instiAttr->GetAttributes() : nullptr + , location + , Target + , Causer + , Instigator + , targetComp + , instiComp + , InAvatar); + + Context->HitResult = HitIn; + + FAFContextHandle Handle = FAFContextHandle::Generate(Context); + + return Handle; } -void UGABlueprintLibrary::AddTagsToEffect(FGAEffect* EffectIn) +void UGABlueprintLibrary::AddTagsToEffect(FAFEffectSpec* EffectIn) { if (EffectIn) { - EffectIn->OwnedTags.AppendTags(EffectIn->GetEffect()->OwnedTags); - EffectIn->ApplyTags.AppendTags(EffectIn->GetEffect()->ApplyTags); + EffectIn->AddOwnedTags(EffectIn->GetSpec()->OwnedTags); + EffectIn->AddApplyTags(EffectIn->GetSpec()->ApplyTags); } } -FGAEffectContext& UGABlueprintLibrary::GetContext(const FGAEffectHandle& InHandle) +FGAEffectContext& UGABlueprintLibrary::GetContext(const FAFContextHandle& InHandle) { - return InHandle.GetContextRef(); + return InHandle.GetRef(); } UAFAbilityComponent* UGABlueprintLibrary::GetTargetComponent(const FGAEffectHandle& InHandle) { - return InHandle.GetContextRef().InstigatorComp.Get(); + return nullptr;// InHandle.GetContextRef().InstigatorComp.Get(); } UAFAbilityComponent* UGABlueprintLibrary::GetInstigatorComponent(const FGAEffectHandle& InHandle) { - return InHandle.GetContextRef().TargetComp.Get(); + return nullptr;// InHandle.GetContextRef().TargetComp.Get(); } void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h index ff13138..62faec3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h @@ -1,7 +1,7 @@ #pragma once -#include "../Effects/GAGameEffect.h" -#include "../GAGlobalTypes.h" -#include "../Attributes/GAAttributeBase.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Attributes/GAAttributeBase.h" #include "GAEffectGlobalTypes.h" #include "GABlueprintLibrary.generated.h" @@ -11,9 +11,13 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar GENERATED_UCLASS_BODY() public: UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToObject(UPARAM(ref) FGAEffectProperty& InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier); + static FGAEffectHandle ApplyGameEffectToObject( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); /* Makes outgoing effect spec and assign handle to it. @@ -21,9 +25,13 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar and just change context of effect. */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToActor(UPARAM(ref) FGAEffectProperty& InEffect, - class AActor* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier); + static FGAEffectHandle ApplyGameEffectToActor( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); /* Makes outgoing effect spec and assign handle to it. @@ -32,43 +40,65 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToLocation(UPARAM(ref) FGAEffectProperty& InEffect, - const FHitResult& Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier); + static FGAEffectHandle ApplyGameEffectToLocation( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); - static FGAEffectHandle ApplyEffect(FGAEffectProperty& InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + static FGAEffectHandle ApplyEffect( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - static FGAEffectHandle ApplyEffect(FGAEffectProperty* InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FHitResult& HitIn, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + static FGAEffectHandle ApplyEffect( + FGAEffectProperty* InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - static FGAEffectHandle ApplyEffectFromHit(FGAEffectProperty& InEffect, - const FHitResult& Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier); + static FGAEffectHandle ApplyEffectFromHit( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); - static FGAEffectHandle ApplyEffectToActor(FGAEffectProperty& InEffect, - class AActor* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier); + static FGAEffectHandle ApplyEffectToActor( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); - static FGAEffectHandle ApplyEffectToObject(FGAEffectProperty& InEffect, - class UObject* Target, class APawn* Instigator, - UObject* Causer, const FAFFunctionModifier& Modifier); + static FGAEffectHandle ApplyEffectToObject( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); /* Create Effect but does not apply it. */ - static FGAEffectHandle MakeEffect(TSubclassOf SpecIn, - FGAEffectHandle HandleIn, class UObject* Target, class APawn* Instigator, - UObject* Causer, const FHitResult& HitIn); - - static FGAEffectContext MakeContext(class UObject* Target, class APawn* Instigator, AActor* InAvatar, + static FAFContextHandle MakeContext(class UObject* Target, class APawn* Instigator, AActor* InAvatar, UObject* Causer, const FHitResult& HitIn); - static void AddTagsToEffect(FGAEffect* EffectIn); + static void AddTagsToEffect(FAFEffectSpec* EffectIn); UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") - static FGAEffectContext& GetContext(const FGAEffectHandle& InHandle); + static FGAEffectContext& GetContext(const FAFContextHandle& InHandle); UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") static UAFAbilityComponent* GetTargetComponent(const FGAEffectHandle& InHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h index 83f99cd..265264d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h @@ -26,5 +26,5 @@ class ABILITYFRAMEWORK_API UGACustomCalculation : public UObject // float CalculateMagnitude(const FGAEffectContext& ContextIn); - virtual float NativeCalculateMagnitude(const FGAEffectHandle& HandleIn) { return 0; } + virtual float NativeCalculateMagnitude(const FGAEffectContext& ContextIn) { return 0; } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp index 8de8211..bcfbe5e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp @@ -16,9 +16,9 @@ void UGAEffectExecution::PreModifyAttribute(const FGAEffectHandle& HandleIn, FGA UE_LOG(GameAttributesEffects, Log, TEXT("Sample execution class implementation")); } void UGAEffectExecution::ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, - FGAEffectContext& Context, FGAEffectProperty& InProperty, + const FAFEffectParams& Params, const FAFFunctionModifier& Modifier) { - PreModifyAttribute(HandleIn, ModIn, Context); - Context.TargetInterface->ModifyAttribute(ModIn, HandleIn, InProperty); + PreModifyAttribute(HandleIn, ModIn, Params.GetContext()); + Params.GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty()); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h index 5d6352b..2236b08 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h @@ -17,6 +17,6 @@ class ABILITYFRAMEWORK_API UGAEffectExecution : public UObject virtual void PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context); virtual void ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, - FGAEffectContext& Context, FGAEffectProperty& InProperty, + const FAFEffectParams& Params, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp index facd31c..a099560 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp @@ -125,19 +125,19 @@ float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) const Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); return Result; } -float FGACustomCalculationModifier::GetValue(const struct FGAEffectHandle& HandleIn) +float FGACustomCalculationModifier::GetValue(const FGAEffectContext& ContextIn) { if (CustomCalculation) { - return CustomCalculation->NativeCalculateMagnitude(HandleIn); + return CustomCalculation->NativeCalculateMagnitude(ContextIn); } return 0; } -float FGACustomCalculationModifier::GetValue(const struct FGAEffectHandle& HandleIn) const +float FGACustomCalculationModifier::GetValue(const FGAEffectContext& ContextIn) const { if (CustomCalculation) { - return CustomCalculation->NativeCalculateMagnitude(HandleIn); + return CustomCalculation->NativeCalculateMagnitude(ContextIn); } return 0; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h index 467bc65..0b2fc2c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h @@ -150,6 +150,6 @@ struct FGACustomCalculationModifier : CustomCalculation(nullptr) {}; - float GetValue(const struct FGAEffectHandle& HandleIn); - float GetValue(const struct FGAEffectHandle& HandleIn) const; + float GetValue(const FGAEffectContext& ContextIn); + float GetValue(const FGAEffectContext& ContextIn) const; }; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index ea1664a..17af54a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -17,75 +17,187 @@ DEFINE_STAT(STAT_GatherModifiers); -void FGAEffectProperty::Initialize() + +void FAFEffectSpec::OnApplied() +{ + if (Extension) + { + Extension->NativeOnEffectApplied(); + } +} +void FAFEffectSpec::OnExpired() +{ + if (Extension) + { + Extension->NativeOnEffectExpired(); + } +} +void FAFEffectSpec::OnRemoved() +{ + if (Extension) + { + Extension->NativeOnEffectRemoved(); + } +} +void FAFEffectSpec::OnExecuted() { - if (SpecClass.SpecClass) + if (Extension) + { + Extension->NativeOnEffectExecuted(); + } +} +float FAFEffectSpec::GetFloatFromAttributeMagnitude( + const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext) const +{ + switch (AttributeIn.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return AttributeIn.DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeIn.AttributeBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CurveBased: + { + return AttributeIn.CurveBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CustomCalculation: { - Spec = SpecClass.SpecClass->GetDefaultObject(); + return AttributeIn.Custom.GetValue(InContext); + } + default: + break; + } + + return 0; +} +float FAFEffectSpec::GetDuration(const FGAEffectContext& InContext) +{ + return GetFloatFromAttributeMagnitude(GetSpec()->Duration, InContext); +} +float FAFEffectSpec::GetPeriod(const FGAEffectContext& InContext) +{ + return GetFloatFromAttributeMagnitude(GetSpec()->Period, InContext); +} +FGAEffectProperty::FGAEffectProperty() + : ApplicationRequirement(nullptr) + , Application(nullptr) + , Execution(nullptr) + , Spec(nullptr) + , Duration(0) + , Period(0) + , bInstant(true) +{ + ApplicationRequirement = nullptr; + Application = nullptr; + Execution = nullptr; + Spec = nullptr; + Duration= 0; + Period = 0; +}; +FGAEffectProperty::FGAEffectProperty(TSubclassOf InClass) + : ApplicationRequirement(nullptr) + , Application(nullptr) + , Execution(nullptr) + , Spec(nullptr) + , Duration(0) + , Period(0) + , bInstant(true) +{ +}; +void FGAEffectProperty::PostScriptConstruct() +{ + ApplicationRequirement = nullptr; + Application = nullptr; + Execution = nullptr; + Spec = nullptr; + Duration = 0; + Period = 0; +} +void FGAEffectProperty::Initialize(TSubclassOf EffectClass) +{ + if (EffectClass) + { + Spec = EffectClass->GetDefaultObject(); ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); Application = GetSpec()->Application.GetDefaultObject(); Execution = GetSpec()->ExecutionType.GetDefaultObject(); } } -void FGAEffectProperty::InitializeIfNotInitialized(const FGAEffectContext& InContext) +void FGAEffectProperty::InitializeIfNotInitialized(const FGAEffectContext& InContext + , TSubclassOf EffectClass) { if (!IsInitialized()) { - Initialize(); + Initialize(EffectClass); } - if (Spec) + if (Spec.IsValid()) { Duration = GetSpec()->Duration.GetFloatValue(InContext); Period = GetSpec()->Period.GetFloatValue(InContext); + + if ((Duration > 0) || (Period > 0)) + { + bInstant = false; + } } } -bool FGAEffectProperty::CanApply(FGAEffect* EffectIn +bool FGAEffectProperty::CanApply( + const struct FGAEffect& EffectIn , struct FGAEffectContainer* InContainer - , const FGAEffectContext& InContext + , const FAFEffectParams& InParams , const FGAEffectHandle& InHandle) { - return ApplicationRequirement->CanApply(EffectIn, *this, InContainer, InContext, InHandle); + return ApplicationRequirement->CanApply(EffectIn, InParams, InHandle, InContainer); } -bool FGAEffectProperty::ApplyEffect(const FGAEffectHandle& InHandle - , struct FGAEffect* EffectIn +bool FGAEffectProperty::ApplyEffect( + const FGAEffectHandle& InHandle + , const struct FGAEffect& EffectIn , struct FGAEffectContainer* InContainer - , const FGAEffectContext& InContext + , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier) { - return Application->ApplyEffect(InHandle, EffectIn, *this, InContainer, InContext, Modifier); + return Application->ApplyEffect(InHandle, EffectIn, InContainer, InParams, Modifier); } -void FGAEffectProperty::ExecuteEffect(const FGAEffectHandle& InHandle - , const FGAEffectContext& InContext +void FGAEffectProperty::ApplyExecute(const FGAEffectHandle& InHandle + , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier) { - Application->ExecuteEffect(InHandle, *this, InContext, Modifier); + Application->ApplyExecute(InHandle, InParams, Modifier); } -void FGAEffectProperty::EffectExecution(const FGAEffectHandle& HandleIn +void FGAEffectProperty::EffectExecution( + const FGAEffectHandle& HandleIn , FGAEffectMod& ModIn - , FGAEffectContext& Context + , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier) { - Execution->ExecuteEffect(HandleIn, ModIn, Context, *this, Modifier); + Execution->ExecuteEffect(HandleIn, ModIn, InParams, Modifier); } void FGAEffect::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) { - + //const_cast(InArraySerializer).RemoveFromReplication(Handle, PredictionHandle); } void FGAEffect::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) { - AppliedTime = InArraySerializer.OwningComponent->GetWorld()->TimeSeconds; - LastTickTime = InArraySerializer.OwningComponent->GetWorld()->TimeSeconds; - Extension = nullptr; - Handle = FGAEffectHandle::GenerateHandle(this); + World = InArraySerializer.OwningComponent->GetWorld(); + AppliedTime = World->TimeSeconds; + LastTickTime = World->TimeSeconds; + + + Handle = FGAEffectHandle::GenerateHandle(); - const_cast(InArraySerializer).ApplyFromPrediction(Handle, PredictionHandle); + //const_cast(InArraySerializer).ApplyFromReplication(Handle, PredictionHandle); } void FGAEffect::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) { } + float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) { switch (CalculationType) @@ -104,7 +216,7 @@ float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) } case EGAMagnitudeCalculation::CustomCalculation: { - //return Custom.GetValue(*this); + return Custom.GetValue(Context); } default: return 0; @@ -133,7 +245,7 @@ float FAFStatics::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn } case EGAMagnitudeCalculation::CustomCalculation: { - return AttributeIn.Custom.GetValue(InHandle); + return AttributeIn.Custom.GetValue(InContext); } default: break; @@ -171,7 +283,7 @@ FGAEffectMod FAFStatics::GetAttributeModifier(FGAAttributeModifier& ModInfoIn case EGAMagnitudeCalculation::CustomCalculation: { return FGAEffectMod(ModInfoIn.Attribute, - ModInfoIn.Magnitude.Custom.GetValue(InHandle), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + ModInfoIn.Magnitude.Custom.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); } default: @@ -180,115 +292,43 @@ FGAEffectMod FAFStatics::GetAttributeModifier(FGAAttributeModifier& ModInfoIn } return ModOut; } -FGAEffect::FGAEffect(TSubclassOf GameEffectIn, - const FGAEffectContext& ContextIn) - : GameEffectClass(GameEffectIn), - Context(ContextIn) -{ - OwnedTags = GetEffect()->OwnedTags; - Extension = nullptr; - if (GetEffect()->Extension) - { - Extension = NewObject(Context.Target.Get(), GetEffect()->Extension); - Extension->OwningComponent = Context.GetTargetEffectsComponent(); - } - if (ContextIn.TargetComp.IsValid()) - { - TargetWorld = ContextIn.TargetComp->GetWorld(); - AppliedTime = TargetWorld->TimeSeconds; - LastTickTime = TargetWorld->TimeSeconds; - } - else if (ContextIn.InstigatorComp.IsValid()) - { - TargetWorld = ContextIn.InstigatorComp->GetWorld(); - AppliedTime = TargetWorld->TimeSeconds; - LastTickTime = TargetWorld->TimeSeconds; - } -} FGAEffect::~FGAEffect() { - if (Extension) - { - Extension->MarkPendingKill(); - } -} -void FGAEffect::SetContext(const FGAEffectContext& ContextIn) -{ - Context = ContextIn; } -void FGAEffect::OnApplied() -{ - AppliedTime = TargetWorld->TimeSeconds; - if (Extension) - { - Extension->NativeOnEffectApplied(); - } -} -void FGAEffect::OnExecuted() -{ - if (Extension) - { - Extension->NativeOnEffectExecuted(); - } -} -void FGAEffect::OnExpired() -{ - if (Extension) - { - Extension->NativeOnEffectExpired(); - } -} -void FGAEffect::OnRemoved() -{ - if (Extension) - { - Extension->NativeOnEffectRemoved(); - } -} float FGAEffect::GetDurationTime() const { - return GetFloatFromAttributeMagnitude(GetEffect()->Duration); + return Duration;// GetFloatFromAttributeMagnitude(GetEffect()->Duration); } float FGAEffect::GetPeriodTime() const { - return GetFloatFromAttributeMagnitude(GetEffect()->Period); + return Period;// GetFloatFromAttributeMagnitude(GetEffect()->Period); } -float FGAEffect::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const + +float FGAEffect::GetCurrentDuration() const { - switch (AttributeIn.CalculationType) - { - case EGAMagnitudeCalculation::Direct: - { - return AttributeIn.DirectModifier.GetValue(); - } - case EGAMagnitudeCalculation::AttributeBased: + if (World) { - return AttributeIn.AttributeBased.GetValue(Context); + float CurrentTime = World->TimeSeconds; + return CurrentTime - AppliedTime; } - case EGAMagnitudeCalculation::CurveBased: - { - return AttributeIn.CurveBased.GetValue(Context); - } - case EGAMagnitudeCalculation::CustomCalculation: - { - return AttributeIn.Custom.GetValue(Handle); - } - default: - break; - } - + return 0; } - -float FGAEffect::GetCurrentDuration() const +FTimerManager& FAFEffectParams::GetTargetTimerManager() { - float CurrentTime = TargetWorld->TimeSeconds; - return CurrentTime - AppliedTime; + return Context.GetPtr()->TargetComp->GetWorld()->GetTimerManager(); +} +UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() +{ + return Context.GetPtr()->GetTargetEffectsComponent(); +} +UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() const +{ + return Context.GetPtr()->GetTargetEffectsComponent(); } - void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams) { /*if (!EffectCue) @@ -305,53 +345,75 @@ void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams }*/ } -FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty - , const FGAEffectContext& InContext +FGAEffectHandle FGAEffectContainer::ApplyEffect( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { FGAEffectHandle Handle; + FGAEffectProperty& InProperty = Params.GetProperty(); + bool bHasDuration = InProperty.GetDuration() > 0; bool bHasPeriod = InProperty.GetPeriod() > 0; + + //InProperty.DataTest->ID++; + ENetRole role = OwningComponent->GetOwnerRole(); ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); - - if (bHasDuration || bHasPeriod) + if (!Params.bRecreated) { - Handle = FGAEffectHandle::GenerateHandle(EffectIn); + Handle = FGAEffectHandle::GenerateHandle(); } - if (InProperty.CanApply(EffectIn, this, InContext, Handle)) + else { - if(!bHasDuration && !bHasPeriod) //instatnt effect. + Handle = InHandle; + } + if (InProperty.CanApply(EffectIn, this, Params, Handle)) + { + if(!Params.bPeriodicEffect) //instatnt effect. { - if (InProperty.IsHandleValid(InContext.Target.Get())) - { - Handle = InProperty.GetHandle(InContext.Target.Get()); - if (InProperty.ApplyEffect(Handle, - EffectIn, this, InContext)) - { - InProperty.ExecuteEffect(Handle, InContext, Modifier); - // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); - } - } - else + const_cast(EffectIn).SetHandle(Handle); + if (InProperty.ApplyEffect(Handle, + EffectIn, this, Params)) { - Handle = FGAEffectHandle::GenerateHandle(EffectIn); - EffectIn->Handle = Handle; - if (InProperty.ApplyEffect(Handle, - EffectIn, this, InContext)) - { - InProperty.ExecuteEffect(Handle, InContext, Modifier); - // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); - } - } + Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() + , Handle + , Params.Context + , Params.EffectSpec); + + InProperty.ApplyExecute(Handle, Params, Modifier); + + // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); + } } else { - EffectIn->Handle = Handle; + const_cast(EffectIn).SetHandle(Handle); if (InProperty.ApplyEffect(Handle, - EffectIn, this, InContext)) + EffectIn, this, Params)) { - InProperty.ExecuteEffect(Handle, InContext, Modifier); + FAFEffectSpec& Spec = Params.GetSpec(); + FGAEffectContext& Context = Params.GetContext(); + + Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() + , Handle + , Params.Context + , Params.EffectSpec); + + AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &const_cast(EffectIn), InProperty); + + const_cast(EffectIn).AppliedTime = OwningComponent->GetWorld()->TimeSeconds; + const_cast(EffectIn).LastTickTime = OwningComponent->GetWorld()->TimeSeconds; + const_cast(EffectIn).Duration = Spec.GetDuration(Context); + const_cast(EffectIn).Period = Spec.GetPeriod(Context); + + + MarkItemDirty(const_cast(EffectIn)); + ActiveEffectInfos.Add(EffectIn); + MarkArrayDirty(); + + //InProperty.ApplyExecute(Handle, Params, Modifier); //generate it only on client, and apply prediction key from client. //if server replicates with valid key, then nothing happens. //if not we try to rewind effect application. @@ -359,31 +421,23 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr //server will overridem them anyway. bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; - UE_LOG(AbilityFramework, Log, TEXT("%s :: FGAEffectContainer::EffectApplied %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Handle.GetEffectSpec()->GetName() ); } } } - if (bHasDuration || bHasPeriod) - { - EffectIn->PredictionHandle = InProperty.GetPredictionHandle(); - EffectIn->AppliedTime = OwningComponent->GetWorld()->TimeSeconds; - EffectIn->LastTickTime = OwningComponent->GetWorld()->TimeSeconds; - MarkItemDirty(*EffectIn); - ActiveEffectInfos.Add(*EffectIn); - MarkArrayDirty(); - - HandleByPrediction.Add(InProperty.GetPredictionHandle(), Handle); - PredictionByHandle.Add(Handle, InProperty.GetPredictionHandle()); - } + FGAEffectContext& InContext = Params.GetContext(); + if (InProperty.GetSpec()->IfHaveTagEffect.RequiredTag.IsValid() && InContext.GetTargetEffectsComponent()->HasTag(InProperty.GetSpec()->IfHaveTagEffect.RequiredTag)) { + for (TSubclassOf& Effect : InProperty.GetSpec()->IfHaveTagEffect.Effects) { FGAEffectProperty prop(Effect); - UGABlueprintLibrary::ApplyEffect(prop, InContext.Target.Get(), InContext.Instigator.Get(), InContext.Causer.Get(), InContext.HitResult); + //Hack. We need a way store handles for conditional effects. + FGAEffectHandle Handle; + //UGABlueprintLibrary::ApplyEffect(Params.Property, Handle, InContext.Target.Get(), InContext.Instigator.Get(), InContext.Causer.Get(), InContext.HitResult); } } @@ -391,22 +445,6 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect(FGAEffect* EffectIn, FGAEffectPr } -EGAEffectAggregation FGAEffectContainer::GetEffectAggregation(const FGAEffectHandle& HandleIn) const -{ - UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); - return Spec->EffectAggregation; -} - -TSet FGAEffectContainer::GetHandlesByAttribute(const FGAEffectHandle& HandleIn) -{ - TSet Handles; - if (TSet* ptr = EffectByAttribute.Find(HandleIn.GetAttribute())) - { - Handles = *ptr; - } - return Handles; -} - TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectProperty& InProperty , const FGAEffectContext& InContext) { @@ -445,200 +483,53 @@ TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectPrope return Handles; } -void FGAEffectContainer::AddEffect(FGAEffectProperty& InProperty, const FGAEffectHandle& HandleIn, bool bInfinite) -{ - TSet& AttributeEffect = EffectByAttribute.FindOrAdd(HandleIn.GetAttribute()); - AttributeEffect.Add(HandleIn); - ActiveEffectHandles.Add(HandleIn); - AddEffectByClass(HandleIn); - UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); - FObjectKey key(InProperty.GetClass()); - TArray& handles = EffectByClass.FindOrAdd(key); - handles.Add(HandleIn); - - if (bInfinite) - { - InfiniteEffects.Add(HandleIn); - } -} -void FGAEffectContainer::AddEffectByClass(const FGAEffectHandle& HandleIn) -{ - UGAGameEffectSpec* Spec = HandleIn.GetEffectSpec(); - EGAEffectAggregation Aggregation = Spec->EffectAggregation; - UClass* EffectClass = Spec->GetClass(); - TSet Handles; - UAFEffectsComponent* Target = HandleIn.GetContextRef().GetTargetEffectsComponent(); - switch (Aggregation) - { - case EGAEffectAggregation::AggregateByInstigator: - { - UAFAbilityComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); - - - TMap>& EffectByClassMap = InstigatorEffectByClass.FindOrAdd(Instigator); - TSet& instigatorEffect = EffectByClassMap.FindOrAdd(EffectClass); - instigatorEffect.Add(HandleIn); - if (Target) - { - Target->AddTagContainer(Spec->ApplyTags); - } - break; - } - case EGAEffectAggregation::AggregateByTarget: - { - TSet& TargetEffects = TargetEffectByClass.FindOrAdd(EffectClass); - TargetEffects.Add(HandleIn); - if (Target) - { - Target->AddTagContainer(Spec->ApplyTags); - } - break; - } - default: - break; - } -} -void FGAEffectContainer::RemoveFromAttribute(const FGAEffectHandle& HandleIn) -{ - TSet* AttributeEffect = EffectByAttribute.Find(HandleIn.GetAttribute()); - IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; - if (AttributeEffect) - { - AttributeEffect->Remove(HandleIn); - if (AttributeEffect->Num() <= 0) - { - EffectByAttribute.Remove(HandleIn.GetAttribute()); - } - } - - //UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::RemoveFromAttribute %s = %f"), *HandleIn.GetAttribute().ToString(), Target->GetAttributeValue(HandleIn.GetAttribute())); - Target->RemoveBonus(HandleIn.GetAttribute(), HandleIn, HandleIn.GetAttributeMod()); - //UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::RemoveFromAttribute %s = %f"), *HandleIn.GetAttribute().ToString(), Target->GetAttributeValue(HandleIn.GetAttribute())); -} -void FGAEffectContainer::RemoveEffectProtected(const FGAEffectHandle& HandleIn - , const FGAEffectProperty& InProperty) -{ - RemoveFromAttribute(HandleIn); - - const_cast(InProperty).RemoveHandle(HandleIn); - - - - InfiniteEffects.Remove(HandleIn); - TArray* handles = EffectByClass.Find(FObjectKey(InProperty.GetClass())); - if (handles && handles->Num() > 0) - { - handles->Remove(HandleIn); - if (handles->Num() <= 0) - { - EffectByClass.Remove(FObjectKey(InProperty.GetClass())); - } - } - FGAEffectHandle* Out = ActiveEffectHandles.Find(HandleIn); - if (Out) - { - //FString EffectInfoLog(TEXT("FGAEffectContainer::RemoveEffect ")); - //EffectInfoLog += Out->GetEffectTag().ToString(); - //AddLogDebugInfo(EffectInfoLog, OwningComponent->GetWorld()); - FGAEffect* Effect = Out->GetEffectPtr(); - MarkItemDirty(*Effect); - ActiveEffectInfos.Remove(Out->GetEffect()); - MarkArrayDirty(); - } - ActiveEffectHandles.Remove(HandleIn); - FAFPredictionHandle* PredHandle = PredictionByHandle.Find(HandleIn); - if(PredHandle) - { - PredictedEffectInfos.Remove(*PredHandle); - HandleByPrediction.Remove(*PredHandle); - PredictionByHandle.Remove(HandleIn); - } -} -void FGAEffectContainer::RemoveInstigatorEffect(const FGAEffectHandle& HandleIn - , const FGAEffectProperty& InProperty) +void FGAEffectContainer::AddEffect( + const FGAEffectHandle& InHandle + , const FAFPredictionHandle& InPredHandle + , FGAEffect* InEffect + , const FGAEffectProperty& InProperty + , bool bInfinite) { - UAFAbilityComponent* Instigator = HandleIn.GetContextRef().InstigatorComp.Get(); - UClass* EffectClass = HandleIn.GetEffectSpec()->GetClass(); - TMap>* InstigatorEffect = InstigatorEffectByClass.Find(Instigator); - TSet* HandlesToRemove = InstigatorEffect->Find(EffectClass); - IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; - FGAEffect* Effect = HandleIn.GetEffectPtr(); - if (HandlesToRemove) - { - HandlesToRemove->Remove(HandleIn); - if (HandlesToRemove->Num() <= 0) - { - InstigatorEffect->Remove(EffectClass); - } - } - if (Effect) - { - Target->RemoveTagContainer(Effect->ApplyTags); - FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); - DurationTimer.ClearTimer(Effect->DurationTimerHandle); - DurationTimer.ClearTimer(Effect->PeriodTimerHandle); - } - RemoveEffectProtected(HandleIn, InProperty); + HandleByPrediction.Add(InPredHandle, InHandle); + PredictionByHandle.Add(InHandle, InPredHandle); + PredictedEffectInfos.Add(InPredHandle, InEffect); + UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UClass* SpecClass = Spec->GetClass(); + FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); -} + TSet& Effects = EffectByAttribute.FindOrAdd(Spec->AtributeModifier.Attribute); + Effects.Add(InHandle); -void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty) -{ - UGAGameEffectSpec* Spec = InProperty.GetSpec(); - EGAEffectAggregation Aggregation = Spec->EffectAggregation; - //TSet* handles = EffectByClass.Find(FObjectKey(HandleIn.GetClass()));//GetHandlesByClass(HandleIn, InContext); + FObjectKey EffectKey(SpecClass); + TArray& EffectClass = EffectByClass.FindOrAdd(EffectKey); + EffectClass.Add(InHandle); - if (!ActiveEffectHandles.Contains(InHandle)) - { - UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *InHandle.GetEffect().ToString()); - return; - } - switch (Aggregation) + switch (Spec->EffectAggregation) { case EGAEffectAggregation::AggregateByInstigator: { - RemoveInstigatorEffect(InHandle, InProperty); + TMap>& InstEffectClass = InstigatorEffectByClass.FindOrAdd(Context.Instigator.Get()); + TSet& EffectClass2 = InstEffectClass.FindOrAdd(SpecClass); + EffectClass2.Add(InHandle); break; } case EGAEffectAggregation::AggregateByTarget: { - RemoveTargetEffect(InHandle, InProperty); + TSet& EffectClass = TargetEffectByClass.FindOrAdd(SpecClass); + EffectClass.Add(InHandle); break; } - default: - break; } + + ActiveEffects.Add(InHandle, InEffect); } -void FGAEffectContainer::RemoveTargetEffect(const FGAEffectHandle& HandleIn - , const FGAEffectProperty& InProperty) +void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty) { - UClass* EffectClass = HandleIn.GetEffectSpec()->GetClass(); - TSet* Handles = TargetEffectByClass.Find(EffectClass); - IAFAbilityInterface* Target = HandleIn.GetContextRef().TargetInterface; - - FGAEffect* Effect = HandleIn.GetEffectPtr(); - - if (Handles) - { - Handles->Remove(HandleIn); - if (Handles->Num() <= 0) - { - TargetEffectByClass.Remove(EffectClass); - } - } - - RemoveEffectProtected(HandleIn, InProperty); - if (Effect) - { - Target->RemoveTagContainer(Effect->ApplyTags); - FTimerManager& DurationTimer = Effect->Context.TargetComp->GetWorld()->GetTimerManager(); - DurationTimer.ClearTimer(Effect->DurationTimerHandle); - DurationTimer.ClearTimer(Effect->PeriodTimerHandle); - } + RemoveEffectInternal(InProperty, InHandle); } -TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num) +TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num) { UGAGameEffectSpec* Spec = HandleIn.GetSpec(); EGAEffectAggregation Aggregation = Spec->EffectAggregation; @@ -654,37 +545,19 @@ TArray FGAEffectContainer::RemoveEffect(const FGAEffectProperty if (handles->IsValidIndex(0)) { FGAEffectHandle OutHandle = (*handles)[idx]; - if (OutHandle.IsValid()) - { - if (!ActiveEffectHandles.Contains(OutHandle)) - { - UE_LOG(GameAttributes, Log, TEXT("RemoveEffect Effect %s Is not applied"), *OutHandle.GetEffect().ToString()); - continue; - } - switch (Aggregation) - { - case EGAEffectAggregation::AggregateByInstigator: - { - RemoveInstigatorEffect(OutHandle, HandleIn); - break; - } - case EGAEffectAggregation::AggregateByTarget: - { - RemoveTargetEffect(OutHandle, HandleIn); - break; - } - default: - break; - } - } + RemoveEffectInternal(HandleIn, OutHandle); + const_cast(HandleIn).CleanUp(OutHandle); } } + + + return copy; } bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) { - if (ActiveEffectHandles.Contains(HandleIn)) + if (ActiveEffects.Contains(HandleIn)) { return true; } @@ -692,13 +565,13 @@ bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) } bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) const { - if (ActiveEffectHandles.Contains(HandleIn)) + if (ActiveEffects.Contains(HandleIn)) { return true; } return false; } -bool FGAEffectContainer::ContainsEffectOfClass(const FGAEffectProperty& InProperty) +bool FGAEffectContainer::ContainsEffectOfClass(const FAFPropertytHandle& InProperty) { FObjectKey key(InProperty.GetClass()); if (EffectByClass.Contains(key)) @@ -708,11 +581,82 @@ bool FGAEffectContainer::ContainsEffectOfClass(const FGAEffectProperty& InProper return false; } -void FGAEffectContainer::ApplyFromPrediction(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle) -{ - +void FGAEffectContainer::ApplyFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle, FGAEffect* InEffect) +{ + //AddEffect(InHandle, InPredHandle, InEffect); +} +void FGAEffectContainer::RemoveFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle) +{ + //FGAEffect* Effect = ActiveEffects[InHandle]; + //APawn* Instigator = Effect->GetContext().Instigator.Get(); + //UObject* Target = Effect->GetContext().Target.Get(); + + //HandleByPrediction.Remove(InPredHandle); + //PredictionByHandle.Remove(InHandle); + //PredictedEffectInfos.Remove(InPredHandle); + + //FGAAttribute Attribute = Effect->GetEffect()->AtributeModifier.Attribute; + + //TSet* Effects = EffectByAttribute.Find(Attribute); + //if (Effects) + //{ + // Effects->Remove(InHandle); + // if (Effects->Num() == 0) + // { + // EffectByAttribute.Remove(Attribute); + // } + //} + + //FObjectKey EffectKey(Effect->GameEffectClass); + //TArray* EffectClass = EffectByClass.Find(EffectKey); + //if (EffectClass) + //{ + // EffectClass->Remove(InHandle); + // if (EffectClass->Num() == 0) + // { + // EffectByClass.Remove(EffectKey); + // } + //} + + //switch (Effect->GetEffect()->EffectAggregation) + //{ + //case EGAEffectAggregation::AggregateByInstigator: + //{ + // TMap>* InstEffectClass = InstigatorEffectByClass.Find(Instigator); + // if (InstEffectClass) + // { + // TSet* EffectClass2 = InstEffectClass->Find(Effect->GameEffectClass); + // if (EffectClass2) + // { + // EffectClass2->Remove(InHandle); + // if (EffectClass2->Num() == 0) + // { + // InstEffectClass->Remove(Effect->GameEffectClass); + // } + // } + // if (InstEffectClass->Num() == 0) + // { + // InstigatorEffectByClass.Remove(Instigator); + // } + // } + // + // break; + //} + //case EGAEffectAggregation::AggregateByTarget: + //{ + // TSet* EffectClass2 = TargetEffectByClass.Find(Effect->GameEffectClass); + // if (EffectClass2) + // { + // EffectClass2->Remove(InHandle); + // if (EffectClass2->Num() == 0) + // { + // TargetEffectByClass.Remove(Effect->GameEffectClass); + // } + // } + // break; + //} + //} } - UWorld* FGAEffectContainer::GetWorld() const { if (OwningComponent) @@ -731,19 +675,23 @@ UGAGameEffectSpec::UGAGameEffectSpec() float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) const { - if (InHandle.IsValid()) + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) { - float Duration = InHandle.GetEffectPtr()->GetDurationTime(); - return FMath::Clamp(Duration - InHandle.GetEffectPtr()->GetCurrentDuration(), 0, Duration); + const FGAEffect* Ptr = *Effect; + float Duration = Ptr->GetDurationTime(); + return FMath::Clamp(Duration - Ptr->GetCurrentDuration(), 0, Duration); } return 0; } float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const { - if (InHandle.IsValid()) + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) { - float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); - float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); + const FGAEffect* Ptr = *Effect; + float CurrentDuration = Ptr->GetCurrentDuration(); + float MaxDuration = Ptr->GetDurationTime(); float CurrentTime = ((CurrentDuration / MaxDuration) - 1) * (-1); @@ -753,16 +701,22 @@ float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHa } float FGAEffectContainer::GetCurrentTime(const FGAEffectHandle& InHandle) const { - if (InHandle.IsValid()) - return InHandle.GetEffectPtr()->GetCurrentDuration(); + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) + { + const FGAEffect* Ptr = *Effect; + return Ptr->GetCurrentDuration(); + } return 0; } float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const { - if (InHandle.IsValid()) + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) { - float CurrentDuration = InHandle.GetEffectPtr()->GetCurrentDuration(); - float MaxDuration = InHandle.GetEffectPtr()->GetDurationTime(); + const FGAEffect* Ptr = *Effect; + float CurrentDuration = Ptr->GetCurrentDuration(); + float MaxDuration = Ptr->GetDurationTime(); return CurrentDuration * 1 / MaxDuration; } return 0; @@ -770,4 +724,90 @@ float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHand float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const { return 0; +} + +void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle) +{ + FGAEffect* Effect = ActiveEffects[InHandle]; + UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UClass* SpecClass = Spec->GetClass(); + FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); + + FTimerManager& DurationTimer = Context.TargetComp->GetWorld()->GetTimerManager(); + DurationTimer.ClearTimer(Effect->DurationTimerHandle); + DurationTimer.ClearTimer(Effect->PeriodTimerHandle); + + APawn* Instigator = Context.Instigator.Get(); + UObject* Target = Context.Target.Get(); + FAFPredictionHandle PredHandle = PredictionByHandle[InHandle]; + + HandleByPrediction.Remove(PredHandle); + PredictionByHandle.Remove(InHandle); + PredictedEffectInfos.Remove(PredHandle); + + FGAAttribute Attribute = Spec->AtributeModifier.Attribute; + EGAAttributeMod AttributeMod = Spec->AtributeModifier.AttributeMod;; + + TSet* Effects = EffectByAttribute.Find(Spec->AtributeModifier.Attribute); + if (Effects) + { + IAFAbilityInterface* Target = Context.TargetInterface; + Target->RemoveBonus(Attribute, InHandle, AttributeMod); + Effects->Remove(InHandle); + if (Effects->Num() == 0) + { + EffectByAttribute.Remove(Spec->AtributeModifier.Attribute); + } + } + + FObjectKey EffectKey(SpecClass); + TArray* EffectClass = EffectByClass.Find(EffectKey); + if (EffectClass) + { + EffectClass->Remove(InHandle); + if (EffectClass->Num() == 0) + { + EffectByClass.Remove(EffectKey); + } + } + + switch (Spec->EffectAggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + TMap>* InstEffectClass = InstigatorEffectByClass.Find(Instigator); + if (InstEffectClass) + { + TSet* EffectClass2 = InstEffectClass->Find(SpecClass); + if (EffectClass2) + { + EffectClass2->Remove(InHandle); + if (EffectClass2->Num() == 0) + { + InstEffectClass->Remove(SpecClass); + } + } + if (InstEffectClass->Num() == 0) + { + InstigatorEffectByClass.Remove(Instigator); + } + } + + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + TSet* EffectClass2 = TargetEffectByClass.Find(SpecClass); + if (EffectClass2) + { + EffectClass2->Remove(InHandle); + if (EffectClass2->Num() == 0) + { + TargetEffectByClass.Remove(SpecClass); + } + } + break; + } + } + ActiveEffects.Remove(InHandle); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index d4a9a3f..19749ef 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -276,7 +276,7 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject Base effect class to extend from when creating effect blueprints. */ UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFEffectSpec : public UGAGameEffectSpec +class ABILITYFRAMEWORK_API UAFEffectSpecBase : public UGAGameEffectSpec { GENERATED_BODY() public: @@ -317,92 +317,272 @@ struct ABILITYFRAMEWORK_API FGAEffectClass } }; +USTRUCT(BlueprintType) +struct FAFContextHandle +{ + GENERATED_BODY() +private: + TSharedPtr DataPtr; + uint32 ID; +public: + static FAFContextHandle Generate(FGAEffectContext* InContext) + { + static uint32 id = 0; + id++; + + TSharedPtr PropPtr = MakeShareable(InContext); + FAFContextHandle Handle(PropPtr, id); + + return Handle; + } + + FAFContextHandle() + : ID(0) + {}; +protected: + FAFContextHandle(TSharedPtr InProperty, uint32 InID) + : DataPtr(InProperty) + , ID(InID) + {}; + +public: + bool IsValid() + { + return DataPtr.IsValid(); + } + + FGAEffectContext& GetRef() + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectContext& GetRef() const + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectContext* GetPtr() + { + return DataPtr.Get(); + } + FGAEffectContext* GetPtr() const + { + return DataPtr.Get(); + } + + void SetTarget(UObject* NewTarget) + { + DataPtr->SetTarget(NewTarget); + } + + bool operator==(const FAFContextHandle& Other) const + { + return ID == Other.ID; + } + + bool operator==(const FObjectKey& Other) const + { + return *DataPtr.Get() == Other; + } + bool operator==(UObject* Other) const + { + return *DataPtr.Get() == Other; + } + + friend uint32 GetTypeHash(const FAFContextHandle& InHandle) + { + return InHandle.ID; + } +}; + +template<> +struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + }; +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFEffectSpec +{ + GENERATED_BODY() +private: + UPROPERTY() + class UGAEffectExtension* Extension; + + TSubclassOf SpecClass; +public: + + FGameplayTagContainer OwnedTags; + FGameplayTagContainer ApplyTags; + FGameplayTagContainer RequiredTags; + +public: + FAFEffectSpec() + : Extension(nullptr) + {} + + FAFEffectSpec(TSubclassOf InSpecClass) + : Extension(nullptr) + , SpecClass(InSpecClass) + {} + + void OnApplied(); + void OnExpired(); + void OnRemoved(); + void OnExecuted(); + + void AddOwnedTags(const FGameplayTagContainer& InTags) + { + OwnedTags.AppendTags(InTags); + } + void AddApplyTags(const FGameplayTagContainer& InTags) + { + ApplyTags.AppendTags(InTags); + } + + UGAGameEffectSpec* GetSpec() + { + return SpecClass.GetDefaultObject(); + } + + float GetFloatFromAttributeMagnitude( + const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext) const; + + float GetDuration(const FGAEffectContext& InContext); + float GetPeriod(const FGAEffectContext& InContext); + +}; +USTRUCT(BlueprintType) +struct FAFEffectSpecHandle +{ + GENERATED_BODY() +public: + TSharedPtr SpecPtr; + uint32 ID; + +public: + static FAFEffectSpecHandle Generate(FAFEffectSpec* Effect) + { + static uint32 id = 0; + id++; + + TSharedPtr PropPtr = MakeShareable(Effect); + FAFEffectSpecHandle Handle(PropPtr, id); + + return Handle; + } + + FAFEffectSpecHandle() + : ID(0) + {} + FAFEffectSpecHandle(TSharedPtr Ptr, uint32 InID) + : SpecPtr(Ptr) + , ID(InID) + {} + + bool IsValid() + { + return SpecPtr.IsValid(); + } + + FAFEffectSpec& GetRef() + { + return SpecPtr.ToSharedRef().Get(); + } + FAFEffectSpec& GetRef() const + { + return SpecPtr.ToSharedRef().Get(); + } +}; +template<> +struct TStructOpsTypeTraits< FAFEffectSpecHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + }; +}; + + + /* - Special effect container, which contains Effect class and Handle to already instanced effect - from this class. + Container for: + 1. Effect handles applied from this property, sorted per target. + 2. Their contexts (each effect have it's own context). + 3. Targets affected by effect from this container (and which effect). + + Also contains hard pointers to base classes/assets used by effect (Execution, Application, Specification). */ + +struct FAFEffectParams; USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectProperty { GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Effect") - FGAEffectClass SpecClass; - UPROPERTY() - class UAFEffectApplicationRequirement* ApplicationRequirement; - UPROPERTY() - class UAFEffectCustomApplication* Application; - UPROPERTY() - class UGAEffectExecution* Execution; - UPROPERTY() - class UGAGameEffectSpec* Spec; - UPROPERTY() - FAFPredictionHandle PredictionHandle; protected: - UPROPERTY() - float Duration; - UPROPERTY() - float Period; - - /* - Handle to effect created from SpecClass - This handle is only created and kept for instant effects, - so we don't create new object every time instant effect is created - as potentially there can be quite a lot of allocations. + + TWeakObjectPtr ApplicationRequirement; + TWeakObjectPtr Application; + TWeakObjectPtr Execution; + TWeakObjectPtr Spec; + FAFPredictionHandle PredictionHandle; + + float Duration; + float Period; + bool bInstant; + /* + Handle to effect created from SpecClass + This handle is only created and kept for instant effects, + so we don't create new object every time instant effect is created + as potentially there can be quite a lot of allocations. */ /* - Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. + Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. */ -protected: + + FAFContextHandle InstantContext; + FAFEffectSpecHandle InstantEffectSpec; + + TMap EffectSpecs; + //Cached context per created effect. + TMap Contexts; //possibly multiple handles per target ? TMap Handles; TMap HandleToTarget; - TMap Contexts; TMap EffectCues; public: - FGAEffectProperty() - : ApplicationRequirement(nullptr), - Application(nullptr), - Execution(nullptr), - Spec(nullptr), - Duration(0), - Period(0) - {}; + FGAEffectProperty(); - FGAEffectProperty(TSubclassOf InClass) - : SpecClass(InClass), - ApplicationRequirement(nullptr), - Application(nullptr), - Execution(nullptr), - Spec(nullptr), - Duration(0), - Period(0) - {}; - - TSubclassOf GetClass() const { return SpecClass.SpecClass; } - const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } - UGAGameEffectSpec* GetSpec() const { return Spec; } + FGAEffectProperty(TSubclassOf InClass); + void PostScriptConstruct(); - bool CanApply(FGAEffect* EffectIn + UGAGameEffectSpec* GetSpec() { return Spec.Get(); } + UGAGameEffectSpec* GetSpec() const { return Spec.Get(); } + + bool CanApply( + const struct FGAEffect& EffectIn , struct FGAEffectContainer* InContainer - , const FGAEffectContext& InContext + , const FAFEffectParams& InParams , const FGAEffectHandle& InHandle); bool ApplyEffect(const FGAEffectHandle& InHandle - , struct FGAEffect* EffectIn + , const struct FGAEffect& EffectIn , struct FGAEffectContainer* InContainer - , const FGAEffectContext& InContext + , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - void ExecuteEffect(const FGAEffectHandle& InHandle - , const FGAEffectContext& InContext + void ApplyExecute(const FGAEffectHandle& InHandle + , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); void EffectExecution(const FGAEffectHandle& HandleIn , FGAEffectMod& ModIn - , FGAEffectContext& Context + , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); //intentionally non const. @@ -410,8 +590,10 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty //void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} - void Initialize(); - void InitializeIfNotInitialized(const FGAEffectContext& InContext); + void Initialize(TSubclassOf EffectClass); + void InitializeIfNotInitialized(const FGAEffectContext& InContext + , TSubclassOf EffectClass); + inline float GetPeriod() const { @@ -421,6 +603,30 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { return Duration; } + + void RegisterHandle( + UObject* Target + , const FGAEffectHandle& InHandle + , const FAFContextHandle& Context + , const FAFEffectSpecHandle& Spec) + { + if (bInstant) + { + InstantContext = Context; + InstantEffectSpec = Spec; + return; + } + if (HandleToTarget.Contains(InHandle)) + { + UE_LOG(GameAttributes, Log, TEXT("FGAEffectProperty::RegisterHandle Handle already registered \n")); + return; + } + + AddHandle(Target, InHandle); + AddContext(InHandle, Context); + AddEffectSpec(InHandle, Spec); + } + void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) { FObjectKey key(Target); @@ -445,6 +651,80 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty return FGAEffectHandle(); } + FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) + { + if (bInstant) + { + return InstantContext; + } + FAFContextHandle* Ctx = Contexts.Find(InHandle); + if (Ctx) + { + return *Ctx; + } + return InstantContext; + } + const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const + { + if (bInstant) + { + return InstantContext; + } + const FAFContextHandle* Ctx = Contexts.Find(InHandle); + if (Ctx) + { + return *Ctx; + } + return InstantContext; + } + + void AddContext(const FGAEffectHandle& InHandle, const FAFContextHandle& ContextHandle) + { + Contexts.Add(InHandle, ContextHandle); + } + + void RemoveContext(const FGAEffectHandle& InHandle) + { + Contexts.Remove(InHandle); + } + + FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) + { + if (bInstant) + { + return InstantEffectSpec; + } + FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); + if (Spec) + { + return *Spec; + } + return InstantEffectSpec; + } + const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const + { + if (bInstant) + { + return InstantEffectSpec; + } + const FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); + if (Spec) + { + return *Spec; + } + return InstantEffectSpec; + } + + void AddEffectSpec(const FGAEffectHandle& InHandle, const FAFEffectSpecHandle& ContextHandle) + { + EffectSpecs.Add(InHandle, ContextHandle); + } + + void RemoveEffectSpec(const FGAEffectHandle& InHandle) + { + EffectSpecs.Remove(InHandle); + } + inline FAFPredictionHandle GetPredictionHandle() const { return PredictionHandle; @@ -478,10 +758,17 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { FObjectKey key(Target); Handles.Remove(key); - Contexts.Remove(InHandle); } } + void CleanUp(const FGAEffectHandle& InHandle) + { + RemoveContext(InHandle); + EffectCues.Remove(InHandle); + RemoveHandle(InHandle); + RemoveEffectSpec(InHandle); + } + void SetPredictionHandle(const FAFPredictionHandle& InHandle) { PredictionHandle = InHandle; @@ -492,24 +779,140 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty return Spec->AtributeModifier; } + + const bool IsInitialized() const + { + return ApplicationRequirement.IsValid() && Application.IsValid() && Execution.IsValid() && Spec.IsValid(); + } + /*const bool IsValidHandle() const + { + return Handle.IsValid(); + }*/ + +}; +template<> +struct TStructOpsTypeTraits< FGAEffectProperty > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + WithPostScriptConstruct = true, + }; +}; + +USTRUCT(BlueprintType) +struct FAFPropertytHandle +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Effect") + FGAEffectClass SpecClass; + + TSharedPtr DataPtr; + //TSharedRef Test; + + uint32 ID; +public: + FAFPropertytHandle() + : ID(0) + { + if (!DataPtr.IsValid()) + { + DataPtr = MakeShareable(new FGAEffectProperty()); + } + }; + + FAFPropertytHandle(const FAFPropertytHandle& Other) + { + SpecClass = Other.SpecClass; + DataPtr = Other.DataPtr; + }; + + + + void PostScriptConstruct() + { + } + /*FAFPropertytHandle(TSharedRef InPtr, uint32 InID) + : Test(InPtr) + , ID(InID) + {}*/ + + TSubclassOf GetClass() const { return SpecClass.SpecClass; } + const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } +public: + + void InitializeIfNotInitialized(const FGAEffectContext& InContext) + { + DataPtr->InitializeIfNotInitialized(InContext, SpecClass.SpecClass); + } + FGAEffectProperty & GetRef() + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectProperty& GetRef() const + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectProperty* GetPtr() const + { + return DataPtr.Get(); + } + FObjectKey GetClassKey() const { return FObjectKey(GetClass()); } - - const bool IsValid() const + inline float GetPeriod() const { - return SpecClass.SpecClass ? true : false; + return DataPtr->GetPeriod(); + } + inline float GetDuration() const + { + return DataPtr->GetDuration(); + } + + UGAGameEffectSpec* GetSpec() + { + return DataPtr->GetSpec(); + } + UGAGameEffectSpec* GetSpec() const + { + return DataPtr->GetSpec(); + } + FGAEffectHandle GetHandle(UObject* From) + { + return DataPtr->GetHandle(From); + } + FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) + { + return DataPtr->GetContext(InHandle); + } + const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const + { + return DataPtr->GetContext(InHandle); + } + FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) + { + return DataPtr->GetEffectSpec(InHandle); + } + const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const + { + return DataPtr->GetEffectSpec(InHandle); + } + void CleanUp(const FGAEffectHandle& InHandle) + { + DataPtr->CleanUp(InHandle); } const bool IsInitialized() const { - return ApplicationRequirement && Application && Execution && Spec; + return DataPtr->IsInitialized(); } - /*const bool IsValidHandle() const + const bool IsValid() const { - return Handle.IsValid(); - }*/ - const bool operator==(const FGAEffectProperty& Other) const + return SpecClass.SpecClass ? true : false; + } + const bool operator==(const FAFPropertytHandle& Other) const { return SpecClass == Other.SpecClass; } @@ -517,10 +920,13 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { return SpecClass == OtherClass; } - void operator=(const FGAEffectProperty& Other) + FAFPropertytHandle& operator=(const FAFPropertytHandle& Rhs) { - SpecClass = Other.SpecClass; - //Handle = Other.Handle; + if (this == &Rhs) + return *this; + DataPtr = Rhs.DataPtr; + SpecClass = Rhs.SpecClass; + return *this; } void operator=(const TSubclassOf& Other) { @@ -532,6 +938,58 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty } }; +template<> +struct TStructOpsTypeTraits< FAFPropertytHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + WithPostScriptConstruct = true, + }; +}; + +struct FAFEffectParams +{ + //make this private and allow assign only trough constructr. + FAFContextHandle Context; + FAFPropertytHandle Property; + FAFEffectSpecHandle EffectSpec; + bool bRecreated; + bool bPeriodicEffect; +public: + FAFEffectParams(FAFPropertytHandle InProperty) + : bRecreated(false) + , Property(InProperty) + {}; + + FGAEffectContext & GetContext() + { + return Context.GetRef(); + } + FGAEffectContext& GetContext() const + { + return Context.GetRef(); + } + + FGAEffectProperty& GetProperty() const + { + return Property.GetRef(); + } + + FAFEffectSpec& GetSpec() + { + return EffectSpec.SpecPtr.ToSharedRef().Get(); + } + FAFEffectSpec& GetSpec() const + { + return EffectSpec.SpecPtr.ToSharedRef().Get(); + } + FTimerManager& GetTargetTimerManager(); + + UAFEffectsComponent* GetTargetEffectsComponent(); + UAFEffectsComponent* GetTargetEffectsComponent() const; + +}; struct FAFStatics { @@ -556,101 +1014,43 @@ enum class ERepInfoType : uint8 RemotePredicted, Server }; + USTRUCT() struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, TSharedFromThis { - GENERATED_BODY() - /* Cached pointer to original effect spec. */ - - UPROPERTY(NotReplicated) - class UGAEffectExtension* Extension; - UWorld* TargetWorld; - /* - Calculated mods ready to be applied. - These are perlimenarly calculcated mods, - which can be furhter modified by Calculation object. - */ -public: - - //Spec from which this effect originated. - UPROPERTY() - TSubclassOf GameEffectClass; + FGAEffectHandle Handle; UPROPERTY() FAFPredictionHandle PredictionHandle; - UPROPERTY() - FGAEffectContext Context; - - FGameplayTagContainer OwnedTags; - FGameplayTagContainer ApplyTags; - FGameplayTagContainer RequiredTags; - - FGAEffectHandle Handle; mutable FTimerHandle PeriodTimerHandle; mutable FTimerHandle DurationTimerHandle; - //FGAEffectMod AttributeMod; -//because I'm fancy like that and like to make spearate public for fields and functions. + UWorld* World; + public: float AppliedTime; float LastTickTime; + float Period; + float Duration; public: void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); - void SetContext(const FGAEffectContext& ContextIn); - - class UAFAbilityComponent* GetInstigatorComp() { return Context.InstigatorComp.Get(); } - class UAFAbilityComponent* GetTargetComp() { return Context.TargetComp.Get(); } - inline void AddOwnedTags(const FGameplayTagContainer& TagsIn) { OwnedTags.AppendTags(TagsIn); } - inline void AddApplyTags(const FGameplayTagContainer& TagsIn) { ApplyTags.AppendTags(TagsIn); } - void OnApplied(); - void OnExpired(); - void OnRemoved(); - void OnExecuted(); - + inline void SetHandle(const FGAEffectHandle& InHandle) + { + Handle = InHandle; + } + float GetDurationTime() const; float GetPeriodTime() const; float GetCurrentDuration() const; - float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const; + //float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const; - UGAGameEffectSpec* GetEffect() - { - return GameEffectClass.GetDefaultObject(); - } - UGAGameEffectSpec* GetEffect() const - { - return GameEffectClass.GetDefaultObject(); - } - FGAEffectContext& GetContext() - { - return Context; - } - const FGAEffectContext& GetContext() const - { - return Context; - } - - bool IsValid() const - { - return GameEffectClass != nullptr; - } - FString ToString() - { - if (GameEffectClass) - { - return GameEffectClass->GetName(); - } - return FString(); - } FGAEffect() - : GameEffectClass(nullptr) {} - FGAEffect(TSubclassOf GameEffectIn, - const FGAEffectContext& ContextIn); ~FGAEffect(); @@ -711,10 +1111,11 @@ struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer TArray Effects; }; + USTRUCT() struct ABILITYFRAMEWORK_API FGAGameCue { - GENERATED_USTRUCT_BODY() + GENERATED_BODY() //Handle to effect, which spawned this cue. @@ -740,8 +1141,6 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer UPROPERTY() TArray ActiveEffectInfos; - TMap> HandleToEffect; - UPROPERTY() TMap HandleByPrediction; @@ -757,10 +1156,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TMap> EffectByClass; - //TQueue dupa; - /* All effects. */ - UPROPERTY() - TSet ActiveEffectHandles; + TMap ActiveEffects; /* Contains effects with infinite duration. Infinite effects are considred to be special case, where they can only be self spplied @@ -806,39 +1202,38 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer * @param Modifier - optional modifier which can be applied to effect. * @return Handle to Effect @ UAFAbilityComponent::ApplyEffectToSelf */ - FGAEffectHandle ApplyEffect(FGAEffect* EffectIn, FGAEffectProperty& InProperty - , const FGAEffectContext& InContext + FGAEffectHandle ApplyEffect( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - TArray RemoveEffect(const FGAEffectProperty& HandleIn, int32 Num = 1); + TArray RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num = 1); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectProperty& InProperty); - - inline int32 GetEffectsNum() const { return ActiveEffectHandles.Num(); }; - - EGAEffectAggregation GetEffectAggregation(const FGAEffectHandle& HandleIn) const; + void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty); - TSet GetHandlesByAttribute(const FGAEffectHandle& HandleIn); + inline int32 GetEffectsNum() const { return ActiveEffectInfos.Num(); }; TSet GetHandlesByClass(const FGAEffectProperty& InProperty, const FGAEffectContext& InContext); - void AddEffect(FGAEffectProperty& InProperty, const FGAEffectHandle& HandleIn, bool bInfinite = false); - void AddEffectByClass(const FGAEffectHandle& HandleIn); + void AddEffect( + const FGAEffectHandle& InHandle + , const FAFPredictionHandle& InPredHandle + , FGAEffect* InEffect + , const FGAEffectProperty& InProperty + , bool bInfinite = false); - void RemoveFromAttribute(const FGAEffectHandle& HandleIn); - void RemoveEffectProtected(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); - void RemoveInstigatorEffect(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); - void RemoveTargetEffect(const FGAEffectHandle& HandleIn, const FGAEffectProperty& InProperty); //modifiers void ApplyEffectsFromMods() {}; void DoesQualify() {}; bool IsEffectActive(const FGAEffectHandle& HandleIn); bool IsEffectActive(const FGAEffectHandle& HandleIn) const; - bool ContainsEffectOfClass(const FGAEffectProperty& InProperty); + bool ContainsEffectOfClass(const FAFPropertytHandle& InProperty); - void ApplyFromPrediction(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle); + void ApplyFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle, FGAEffect* InEffect); + void RemoveFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle); bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { @@ -846,11 +1241,6 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); } - const TSet& GetAllEffectHandles() const - { - return ActiveEffectHandles; - } - UWorld* GetWorld() const; ///Helpers @@ -861,7 +1251,12 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const; float GetEndTime(const FGAEffectHandle& InHandle) const; - TSharedPtr GetEffect(const FGAEffectHandle& InHandle) { return HandleToEffect[InHandle]; } + FGAEffect* GetEffect(const FGAEffectHandle& InHandle) + { + return ActiveEffects[InHandle]; + } +private: + void RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle); }; template<> struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp index ce2ca49..ff8bdb1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp @@ -35,103 +35,52 @@ FGAEffectContext::FGAEffectContext(TWeakObjectPtr Targe InstigatorInterface = Cast(Instigator.Get()); IAFAbilityInterface* CauserInterface = Cast(Causer.Get()); } -FGAEffectHandle::FGAEffectHandle(uint32 HandleIn, FGAEffect* EffectIn) - : Handle(HandleIn), - EffectPtr(EffectIn) +void FGAEffectContext::SetTarget(UObject* NewTarget) { -} - -FGAEffectHandle::~FGAEffectHandle() -{ - Reset(); -} -FGAEffectContext& FGAEffectHandle::GetContextRef() { return EffectPtr->Context; } -FGAEffectContext& FGAEffectHandle::GetContextRef() const { return EffectPtr->Context; } - -UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() { return EffectPtr->GetEffect(); } -UGAGameEffectSpec* FGAEffectHandle::GetEffectSpec() const { return EffectPtr->GetEffect(); } - -uint32 FGAEffectHandle::GetHandle() const { return Handle; } - -FGAEffect& FGAEffectHandle::GetEffect() { return *EffectPtr; } -FGAEffect& FGAEffectHandle::GetEffect() const { return *EffectPtr; } - -//FGAEffect& FGAEffectHandle::GetEffectRef() { return *EffectPtr; } -//FGAEffect& FGAEffectHandle::GetEffectRef() const { return *EffectPtr; }; - -FGAEffect* FGAEffectHandle::GetEffectPtr() { return EffectPtr; }; -FGAEffect* FGAEffectHandle::GetEffectPtr() const { return EffectPtr; }; - -void FGAEffectHandle::SetContext(const FGAEffectContext& ContextIn) { EffectPtr->SetContext(ContextIn); } -void FGAEffectHandle::SetContext(const FGAEffectContext& ContextIn) const { EffectPtr->SetContext(ContextIn); } - -FGAEffectContext& FGAEffectHandle::GetContext() { return EffectPtr->Context; } -FGAEffectContext& FGAEffectHandle::GetContext() const { return EffectPtr->Context; } - -/* Executes effect trough provided execution class. */ - -FGAEffectHandle FGAEffectHandle::GenerateHandle(FGAEffect* EffectIn) -{ - static uint32 Handle; - Handle++; - return FGAEffectHandle(Handle, EffectIn); -} -void FGAEffectHandle::AppendOwnedTags(const FGameplayTagContainer& TagsIn) -{ - GetEffectPtr()->OwnedTags.AppendTags(TagsIn); -} -void FGAEffectHandle::AppendOwnedTags(const FGameplayTagContainer& TagsIn) const -{ - GetEffectPtr()->OwnedTags.AppendTags(TagsIn); -} + IAFAbilityInterface* ATI = Cast(NewTarget); + if (!ATI) + { + return; + } -bool FGAEffectHandle::HasAllTags(const FGameplayTagContainer& TagsIn) const -{ - return EffectPtr->OwnedTags.HasAll(TagsIn); + TargetComp = ATI->GetAbilityComp(); + Target = NewTarget; + TargetInterface = ATI; + TargetAttributes = ATI->GetAttributes(); } -bool FGAEffectHandle::HasAllTagsExact(const FGameplayTagContainer& TagsIn) const +FGAEffectHandle::FGAEffectHandle() + : Handle(0) { - return EffectPtr->OwnedTags.HasAllExact(TagsIn); + Handle = 0; } -bool FGAEffectHandle::HasAllAttributeTags(const FGAEffectHandle& HandleIn) const +FGAEffectHandle::FGAEffectHandle(uint32 HandleIn) + : Handle(HandleIn) { - return GetEffectSpec()->AttributeTags.HasAll(HandleIn.GetEffectSpec()->AttributeTags); } -bool FGAEffectHandle::HasAllAttributeTagsExact(const FGAEffectHandle& HandleIn) const +void FGAEffectHandle::PostScriptConstruct() { - return GetEffectSpec()->AttributeTags.HasAllExact(HandleIn.GetEffectSpec()->AttributeTags); + Handle = 0; } -FGameplayTagContainer& FGAEffectHandle::GetOwnedTags() const -{ - return EffectPtr->OwnedTags; -} -FGAEffectMod FGAEffectHandle::GetAttributeModifier() const +FGAEffectHandle::~FGAEffectHandle() { - return FGAEffectMod();// EffectPtr->GetAttributeModifier(); } -FGAAttribute FGAEffectHandle::GetAttribute() const -{ - return GetEffectSpec()->AtributeModifier.Attribute; -} -EGAAttributeMod FGAEffectHandle::GetAttributeMod() const +/* Executes effect trough provided execution class. */ + +FGAEffectHandle FGAEffectHandle::GenerateHandle() { - return GetEffectSpec()->AtributeModifier.AttributeMod; + static int32 Handle; + Handle++; + return FGAEffectHandle(Handle); } bool FGAEffectHandle::IsValid() const { - return (Handle != INDEX_NONE) && EffectPtr != nullptr;// && EffectPtr->Context.IsValid(); + return (Handle > 0);// && EffectPtr->Context.IsValid(); } -//void FGAEffectHandle::operator=(const FGAEffectHandle& Other) -//{ -// Handle = Other.Handle; -// //EffectPtr = Other.EffectPtr; -//} void FGAEffectHandle::Reset() { - Handle = INDEX_NONE; - EffectPtr = nullptr; + Handle = 0; } FAFPredictionHandle FAFPredictionHandle::GenerateClientHandle(UAFAbilityComponent* InComponent) @@ -164,6 +113,36 @@ void FGAHashedGameplayTagContainer::GenerateFNameKey() Key = *RetString; } +void FGAEffectContext::operator=(const FGAEffectContext& Other) +{ + HitResult = Other.HitResult; + TargetHitLocation = Other.TargetHitLocation; + TargetAttributes = Other.TargetAttributes; + InstigatorAttributes = Other.InstigatorAttributes; + Target = Other.Target; + Causer = Other.Causer; + Instigator = Other.Instigator; + Avatar = Other.Avatar; + TargetComp = Other.TargetComp; + InstigatorComp = Other.InstigatorComp; + TargetInterface = Other.TargetInterface; + InstigatorInterface = Other.InstigatorInterface; +} +FGAEffectContext::FGAEffectContext(const FGAEffectContext& Other) +{ + HitResult = Other.HitResult; + TargetHitLocation = Other.TargetHitLocation; + TargetAttributes = Other.TargetAttributes; + InstigatorAttributes = Other.InstigatorAttributes; + Target = Other.Target; + Causer = Other.Causer; + Instigator = Other.Instigator; + Avatar = Other.Avatar; + TargetComp = Other.TargetComp; + InstigatorComp = Other.InstigatorComp; + TargetInterface = Other.TargetInterface; + InstigatorInterface = Other.InstigatorInterface; +} void FGAEffectContext::Reset() { Target.Reset(); @@ -171,6 +150,8 @@ void FGAEffectContext::Reset() Instigator.Reset(); TargetComp.Reset(); InstigatorComp.Reset(); + TargetInterface = nullptr; + InstigatorInterface = nullptr; } class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index 5edc9ec..e569acc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -230,6 +230,8 @@ struct ABILITYFRAMEWORK_API FGAEffectContext class IAFAbilityInterface* TargetInterface; class IAFAbilityInterface* InstigatorInterface; + + void SetTarget(UObject* NewTarget); template inline T* GetTarget() { @@ -270,7 +272,15 @@ struct ABILITYFRAMEWORK_API FGAEffectContext return ret; } + bool operator==(UObject* Other) const + { + return FObjectKey(Target.Get()) == FObjectKey(Other); + } + bool operator==(const FObjectKey& Other) const + { + return FObjectKey(Target.Get()) == Other; + } void Reset(); @@ -284,9 +294,12 @@ struct ABILITYFRAMEWORK_API FGAEffectContext class UAFEffectsComponent* GetTargetEffectsComponent(); class UAFEffectsComponent* GetTargetEffectsComponent() const; + void operator=(const FGAEffectContext& Other); FGAEffectContext() {} + FGAEffectContext(const FGAEffectContext& Other); + FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, @@ -297,6 +310,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContext ~FGAEffectContext(); }; + struct FGAEffect; class UGAGameEffectSpec; struct FGAEffectMod; @@ -308,47 +322,14 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle GENERATED_BODY() protected: //just to be safe we don't run out of numbers.. - UPROPERTY() - uint32 Handle; //Fname Guid ? - - FGAEffect* EffectPtr; + UPROPERTY(VisibleAnywhere, Transient) + int32 Handle; //Fname Guid ? public: - - FGAEffectContext& GetContextRef(); - FGAEffectContext& GetContextRef() const; - - UGAGameEffectSpec* GetEffectSpec(); - UGAGameEffectSpec* GetEffectSpec() const; - - uint32 GetHandle() const; - - FGAEffect& GetEffect(); - FGAEffect& GetEffect() const; - - //FGAEffect& GetEffectRef(); - //FGAEffect& GetEffectRef() const; - - FGAEffect* GetEffectPtr(); - FGAEffect* GetEffectPtr() const; - - void SetContext(const FGAEffectContext& ContextIn); - void SetContext(const FGAEffectContext& ContextIn) const; - - FGAEffectContext& GetContext(); - FGAEffectContext& GetContext() const; - - void AppendOwnedTags(const FGameplayTagContainer& TagsIn); - void AppendOwnedTags(const FGameplayTagContainer& TagsIn) const; - struct FGAEffectMod GetAttributeModifier() const; - FGAAttribute GetAttribute() const; - EGAAttributeMod GetAttributeMod() const; - - static FGAEffectHandle GenerateHandle(FGAEffect* EffectIn); - bool HasAllTags(const FGameplayTagContainer& TagsIn) const; - bool HasAllTagsExact(const FGameplayTagContainer& TagsIn) const; - bool HasAllAttributeTags(const FGAEffectHandle& HandleIn) const; - bool HasAllAttributeTagsExact(const FGAEffectHandle& HandleIn) const; - FGameplayTagContainer& GetOwnedTags() const; + int32 GetHandle() const + { + return Handle; + } + static FGAEffectHandle GenerateHandle(); bool operator==(const FGAEffectHandle& Other) const { return Handle == Other.Handle; @@ -357,11 +338,6 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle { return Handle != Other.Handle; } - void operator=(const FGAEffectHandle& Other) - { - Handle = Other.Handle; - EffectPtr = Other.EffectPtr; - } //FGAEffectHandle& operator=(const FGAEffectHandle& Other) //{ @@ -377,24 +353,22 @@ struct ABILITYFRAMEWORK_API FGAEffectHandle return InHandle.Handle; } - FGAEffectHandle() - : Handle(INDEX_NONE) - , EffectPtr(nullptr) - {} + FGAEffectHandle(); - FGAEffectHandle(uint32 HandleIn, FGAEffect* EffectIn); + FGAEffectHandle(uint32 HandleIn); + void PostScriptConstruct(); public: ~FGAEffectHandle(); }; // -//template<> -//struct TStructOpsTypeTraits< FGAEffectHandle > : public TStructOpsTypeTraitsBase2 -//{ -// enum -// { -// WithCopy = true, -// }; -//}; +template<> +struct TStructOpsTypeTraits< FGAEffectHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithPostScriptConstruct = true, + }; +}; USTRUCT() struct FAFPredictionHandle @@ -781,19 +755,6 @@ struct ABILITYFRAMEWORK_API FGACountedTagContainer }; -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFContextHandle -{ - GENERATED_BODY() -protected: - TSharedPtr Data; -public: - FAFContextHandle() - { - - } -}; - USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FGAEffectCueParams { diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp index b2fede4..d4e59de 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp @@ -83,12 +83,13 @@ void FAbilityFrameworkEditor::StartupModule() FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); PropertyModule.RegisterCustomPropertyTypeLayout("GAAttribute", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAAttributeDetailCustomization::MakeInstance)); - PropertyModule.RegisterCustomPropertyTypeLayout("GAEffectProperty", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); + //PropertyModule.RegisterCustomPropertyTypeLayout("GAEffectProperty", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); + PropertyModule.RegisterCustomPropertyTypeLayout("AFPropertytHandle", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); TSharedPtr GAAttributePanelGraphPinFactory = MakeShareable(new FGAAttributePanelGraphPinFactory()); FEdGraphUtilities::RegisterVisualPinFactory(GAAttributePanelGraphPinFactory); - PropertyModule.RegisterCustomClassLayout("AFEffectSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFEffectSpecBase", FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); PropertyModule.RegisterCustomClassLayout("AFAbilityActivationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); PropertyModule.RegisterCustomClassLayout("AFAbilityCooldownSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); @@ -112,7 +113,7 @@ void FAbilityFrameworkEditor::ShutdownModule() { BlueprintEditorTabBinding = nullptr; FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); - PropertyModule.UnregisterCustomClassLayout("AFEffectSpec"); + PropertyModule.UnregisterCustomClassLayout("AFEffectSpecBase"); PropertyModule.UnregisterCustomClassLayout("AFAbilityActivationSpec"); PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodSpec"); PropertyModule.UnregisterCustomClassLayout("AFAbilityCooldownSpec"); @@ -120,7 +121,8 @@ void FAbilityFrameworkEditor::ShutdownModule() PropertyModule.UnregisterCustomClassLayout("AFAbilityInfiniteDurationSpec"); PropertyModule.UnregisterCustomPropertyTypeLayout("GAAttribute"); - PropertyModule.UnregisterCustomPropertyTypeLayout("GAEffectProperty"); + //PropertyModule.UnregisterCustomPropertyTypeLayout("GAEffectProperty"); + PropertyModule.UnregisterCustomPropertyTypeLayout("AFPropertytHandle"); UGAEffectCueSequence::OnInitializeSequence().Remove(OnInitializeSequenceHandle); BlueprintEditorTabBinding = nullptr; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp index ccfc252..c84d883 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp @@ -177,7 +177,7 @@ class SEffectBlueprintCreateDialog : public SCompoundWidget TSharedPtr Filter = MakeShareable(new FEffectBlueprintParentFilter); // All child child classes of UGameplayAbility are valid. - Filter->AllowedChildrenOfClasses.Add(UAFEffectSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFEffectSpecBase::StaticClass()); Filter->AllowedChildrenOfClasses.Add(UAFAbilityActivationSpec::StaticClass()); Filter->AllowedChildrenOfClasses.Add(UAFAbilityCooldownSpec::StaticClass()); Filter->AllowedChildrenOfClasses.Add(UAFAbilityPeriodSpec::StaticClass()); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp index d8dbbe5..23e5682 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp @@ -553,7 +553,7 @@ FReply FGAEffectClassStructWidget::MakeNewBlueprint() } else { - MetaClass.Add(UAFEffectSpec::StaticClass()); + MetaClass.Add(UAFEffectSpecBase::StaticClass()); } TSharedRef Dialog = SNew(SEffectCreateDialog).MetaClass(MetaClass); Dialog->ConfigureProperties(this); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp index 0841a9e..3b0417f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp @@ -42,7 +42,7 @@ void FGAEffectDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) for (TWeakObjectPtr obj : Objects) { - if (UAFEffectSpec* Spec = Cast(obj.Get())) + if (UAFEffectSpecBase* Spec = Cast(obj.Get())) { /*if (!Spec->IsA(UAFAbilityActivationSpec::StaticClass()) && !Spec->IsA(UAFAbilityPeriodSpec::StaticClass()) diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 9898586..230365d 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -45,8 +45,16 @@ AARCharacter::AARCharacter() // Create a camera boom (pulls in towards the player if there is a collision) CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); CameraBoom->SetupAttachment(RootComponent); - CameraBoom->TargetArmLength = 300.0f; // The camera follows at this distance behind the character + CameraBoom->TargetArmLength = 250; // The camera follows at this distance behind the character CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller + CameraBoom->SocketOffset = FVector(0, 30, 95); + CameraBoom->TargetOffset = FVector(0, 0, -95); + CameraBoom->bEnableCameraLag = true; + CameraBoom->bEnableCameraRotationLag = true; + CameraBoom->CameraLagSpeed = 8; + CameraBoom->CameraRotationLagSpeed = 7; + CameraBoom->CameraLagMaxDistance = 10; + CameraBoom->ProbeSize = 0.05f; // Create a follow camera FollowCamera = CreateDefaultSubobject(TEXT("FollowCamera")); @@ -86,7 +94,7 @@ AARCharacter::AARCharacter() //EquipedMainWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetNotIncludingScale); WeaponEquipedMain->SetupAttachment(GetMesh(), WeaponSocket::EquipedMainWeapon); - + bUseControllerRotationYaw = true; // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) From f1465149cbb56ca4ad9172b7c8136c63a1c61194 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 00:39:47 +0100 Subject: [PATCH 059/187] fixed draggable window and Effect going out of scope before added to list of Active Effects --- ActionRPGGame.uproject | 21 ++ Config/DefaultEngine.ini | 21 +- Content/Blueprints/Test_CameraManager.uasset | Bin 0 -> 19753 bytes .../AbilityFramework/AFEffectsComponent.cpp | 4 +- .../AbilityFramework/AFEffectsComponent.h | 2 +- .../Abilities/GAAbilityBase.cpp | 4 +- .../Abilities/GAAbilityBase.h | 10 +- .../AbilityFramework/AbilityFramework.cpp | 5 + .../AbilityFramework/AbilityFramework.h | 8 +- .../Attributes/GAAttributeBase.cpp | 34 +-- .../Attributes/GAAttributeBase.h | 6 +- .../Attributes/GAAttributesBase.cpp | 5 + .../AbilityFramework/Effects/GAGameEffect.cpp | 33 +-- .../AbilityFramework/Effects/GAGameEffect.h | 9 +- .../Source/AbilityFramework/GAGlobalTypes.h | 19 -- .../GAEffectClassStructWidget.cpp | 32 ++- .../GAEffectClassStructWidget.h | 3 +- .../GAEffectPropertyStructCustomization.cpp | 9 +- .../DraggableWindow/SDraggableWindowWidget.h | 7 +- Source/ActionRPGGame/ARCharacter.cpp | 266 +++++++++++++++++- Source/ActionRPGGame/ARCharacter.h | 93 +++++- .../ARCharacterMovementComponent.cpp | 7 + .../ARCharacterMovementComponent.h | 20 ++ Source/ActionRPGGame/ARPlayerController.cpp | 42 +-- Source/ActionRPGGame/ActionRPGGame.Build.cs | 7 + 25 files changed, 542 insertions(+), 125 deletions(-) create mode 100644 Content/Blueprints/Test_CameraManager.uasset create mode 100644 Source/ActionRPGGame/ARCharacterMovementComponent.cpp create mode 100644 Source/ActionRPGGame/ARCharacterMovementComponent.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 6dd6e58..4c10893 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -165,6 +165,27 @@ { "Name": "GLTFImporter", "Enabled": true + }, + { + "Name": "SteamAudio", + "Enabled": true + }, + { + "Name": "ResonanceAudio", + "Enabled": false + }, + { + "Name": "CodeView", + "Enabled": true + }, + { + "Name": "SignificanceManager", + "Enabled": true + }, + { + "Name": "CustomAnimNode", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" } ], "TargetPlatforms": [ diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index aeb6fb7..47f9b72 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -24,6 +24,8 @@ r.ClearCoatNormal=True r.DefaultFeature.LensFlare=True r.GenerateLandscapeGIData=True r.TemporalAA.Upsampling=False +bDefaultParticleCutouts=True +r.SupportMaterialLayers=True [/Script/Engine.StreamingSettings] s.AsyncLoadingThreadEnabled=True @@ -121,6 +123,9 @@ ActiveTilesUpdateInterval=1.000000 +SupportedAgents=(Name="Default",Color=(B=0,G=255,R=140,A=164),DefaultQueryExtent=(X=50.000000,Y=50.000000,Z=250.000000),NavigationDataClassName=/Script/Engine.RecastNavMesh,AgentRadius=35.000000,AgentHeight=144.000000,AgentStepHeight=-1.000000,NavWalkingSearchHeightScale=0.500000,PreferredNavData=Class'"/Script/Engine.RecastNavMesh"',bCanCrouch=True,bCanJump=True,bCanWalk=True,bCanSwim=True,bCanFly=False) DirtyAreasUpdateFreq=60.000000 +[/Script/Engine.AnimationSettings] +bTickAnimationOnSkeletalMeshInit=True + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -134,6 +139,7 @@ bEnablePCM=True bEnableStabilization=True bWarnMissingLocks=True bEnable2DPhysics=False +PhysicErrorCorrection=(LinearDeltaThresholdSq=5.000000,LinearInterpAlpha=0.200000,LinearRecipFixTime=1.000000,AngularDeltaThreshold=0.628319,AngularInterpAlpha=0.100000,AngularRecipFixTime=1.000000,BodySpeedThresholdSq=0.200000) LockedAxis=Invalid DefaultDegreesOfFreedom=Full3D BounceThresholdVelocity=200.000000 @@ -151,15 +157,20 @@ bSuppressFaceRemapTable=False bSupportUVFromHitResults=False bDisableActiveActors=False bDisableCCD=False -bEnableEnhancedDeterminism=False +bEnableEnhancedDeterminism=True MaxPhysicsDeltaTime=0.033333 -bSubstepping=False -bSubsteppingAsync=False -MaxSubstepDeltaTime=0.016667 -MaxSubsteps=6 +bSubstepping=True +bSubsteppingAsync=True +MaxSubstepDeltaTime=0.033000 +MaxSubsteps=2 SyncSceneSmoothingFactor=0.000000 AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 +[/Script/Engine.GarbageCollectionSettings] +gc.TimeBetweenPurgingPendingKillObjects=30.000000 +gc.NumRetriesBeforeForcingGC=0 +gc.ActorClusteringEnabled=True +gc.BlueprintClusteringEnabled=True diff --git a/Content/Blueprints/Test_CameraManager.uasset b/Content/Blueprints/Test_CameraManager.uasset new file mode 100644 index 0000000000000000000000000000000000000000..46950210eb30f82f1614ee0e31bd51ca88ee5ead GIT binary patch literal 19753 zcmeHP3v^V~x!$875P_mapuRXDh)Bpg;iW>7nS@6|0!gTf+~j2DOfoQ;8Rnb;LWQDM zs#RO5dh3$v?V@^dNflIlEp08{i`8nY6|LT?)%sv9sP@)seU#VzzkT+9&Piq_34zcei zyee-r!QLx+ZO5>>YsWsa{)L}xnSZD(hhVd`{mGN6 ze*E^Tmqy&a|Bc*pMi6XtsSpFHUKo!VR1FYuI+po_K!>UsfocAtqKcA&@{;KV(*mUx zm4)Sjit>s;XHsdXflDo`PF)dkzWx_8Hr>hW|{eo zhG{id5-_RP>M^~|NQ&*}Ue^K3;OUPdKRgKlAa5wK}3k4EFG{YKQVBJr3w^3m`=lK!H#GTzZ) z#H@-`Yirb~kHlg|NUY48STiaOxg=snsEt@O;erb$0$XFW>A}uwBSr?Xj8J7%H_drw zdCF>!CnJ__MOGQY`e8~x!)?6KFhY&-`c$&bXjoxH7aL(yeDB`NW+BoXON)^+iieHy zLb~!0lQ$=(LQ|(lbt)1PFAO@p>1$r-yqIMqV|uj7H0ol}POJ>~mv4MV4RJn9&A#DE>&IhBB|b*qeIG7>VXQn8@4>xfTp zTzV!j#I!ORAH%z$3PEV2hm&|SlGOzeDS>Uikg79Z~eFC zB5oC3r=!+0Tz@-`^+*@4@>2jfxLTY7^LjK@Nzc&hOmCsJw={)kCxcS?h< zy=8C3V1flg_P`ww-?y@%i_{Aps~6@HX5y=k<>fO=*~! zGf8?$QQW`n@XI!bREHCwi(b8b4s;BxBIz_+r@dc{-HwzYVK!*lUA|?A5DB8eXe5nT z&=6a<{9zk%xv|Cwip%#OJRLC=j>dIMjO@Jqc?^;&TsiCxZ2kQq(BWYqshh$-`Me9E z7=v97cU^k$G<4`Tus06AxDly9_LqZt%azZqf++H$vi@)Fa6S+0C3-RfBS;rscqHc# zR3@Y&*Ij$c=EF7%ieTDisirWmzVr-GQ9u?h5VL5wZQe8Rd}Qnz-Lz~+vX4zM^z0K} zgaK=fj#eWnnO;Bk!H2=X2G#3iKTE9Nx9$RrP8;Ydz5e0HW+Oan4NLdymM-4gu=6Ga zQ*AtyiW-Xz8ibTH>vgMLB*tH-gD|)_>RkDk!SkUalu>zGv`lFJ7(@Y+M*7W925e(M zecZf6B&$9&;6Su6#bbvzM`2JoPk(aa?qLYTxIHBq3x03}mnwFR1t0q0B>U2lqWtv- z_rnZzR=bh3XQL-SSb9LVOj(JPg-J#Zzo8x9uf?dU*Mlo)x)f&hHK!rJsOy?|5ZRBE zj>n*xzXT_RXp96`hy{xd{u*(QROKX2G4c`pHptqb zuQEbQBF5^vaM&~~arrYJ_#ODA@pwmhM?6K5(LCygXJIFqwp=oE$Ap>@2NK-ap6Y0g z>5-^RD&zN^v=c6|Gmtp)_;st{+=j}AX82PS?s;i9v}}k_4yT}qnN~6-ry_erB1TSG ztU;LuE9rP})~@6PDTZw8fD6PA4?>Legf32+xo|VaOgf5k{e-KpeIBveXsmIE-ha=u z9zmQ@kkHh6|4SQSy{@`FP*eOM!lRL<*2YLeJhXq%&m{k(9y7!7WQS{^4f_wh3P(4l zp$f#!SMAA#Hcd1r+pz4ar&u$^>E~=I#%xa$aWaElY9DM75Snv{96Q_oeZ8E0m(T(& zo-Fcz+=W?ieV8(!Tm4wL)@TrmjyT&9wieFA%>C(cdm`fh->HpcWDo}Wj)~jEeq~Xq{Gr~xH@%> zihad8cySEl+KZ#@oh+Gfh)Wc1!}`LW$j2y*V|_m)T)T}DpVRrL^sg>Ot2#j@il}q! znvSLrIfowiW8L{0%R!Vv`hP~A39;cg@WFmqk&~6KE-IW=^l3UK)Esbu2wiH8qXESNu- z&t64rl!s4G^ck0l&&M7fDTycbg!6MSbHX^#NMmCp+}0zTqA>R4?WoQ)^O)n`e zolzul^Gs~NQFREgEpD^6B++q!OwkFD1QyAUs8}ieogj&P zlo@SXWW%$qTrZrgdZb61PmEBwI*Ke;*Cx73kW~<6E2+g`)oL=?2vUT_`2-oHpf0EW zY0Pv$+mKqjw7oEvf=AW~o{`148c{4|1f5JCYjM2nqkL&oa{W0@TrR3gyR zRII1gJeoMxvbFWm9L7@m#A)h$iKwU1vw|c8^~|w{5zSVtknIu_0kcGd>=h=N5Sf+q z-%jUo$_aMt`Y2o395dnALtMK&jxG~155MGUQGBv>T>hDGIZC!uRPEY^&)A|~|9Quu zOaEAPU|Be_=90gcQ{4Gz-nXSm$8ZMDF8_GdcZQfr`QI;(WuiiqifMGLrl_1oS*4h~ zUP4&FN@bfF^14h+CrqW7K~#8rAFG}$vo{C2-s&04-pH=+sY>4}vYeYYyu4ZjeCeZA zoo&@))rYghT#CK5GJCsO!VBY!mRB_l=e-uR>7)f9A$iajvS}15w{ktUV<`$3~GV3BkDDT>7YNmPl{@++{V$I(kkI$ zYL!p3MnJBH+6j{oZS*&e#ujE4aKnf|KV--bNwuxp>cMOZ0c1;Wf-6 zC5gKNbRj%TX15+=>PhAlX@%oB(l<;pWBzQVYpfE!rmTFdQghY>hc=?Viuk0&*QLF& z!uQcG&K`5wTb!<1@HiH}GmevVoDXaZ`jz(d^C9_vE%E3Lf2NXyt;!O*HP4?|dv&!i zue^`d!rXs8MP~)cjdeU^&jvsHINJ_PPK00CcG>V_d$k=$e3)h%tPg!c zQ+?RJ|EQ~7)-(HR*TuMN+j_YUHYv`qlXGXYzO)_Jt2cNxH;uAIA*~1eRF}~Dtd!~* zw5q9;E4dkTHCD(unQua~9u~SdE0((`Ha+IruPn^@Mw7mC8 zcy<>)dM?e593C6}&Bd;K?%u^+{ zQhfXAA90U-TtwM?8bOK`rdVe85{mH|bQYjL?9Fk+J=}s`<>!^7>oMo$x`Dbu0&mz zs_Qa&y;OMHPE)w)s_hJQU8wkg19;fHm_wn%qmcXrdC-peAa5~@=@-)M$}r|p^`@IsA$oenk$yB8MM#{!GW_7Zy6@VUsc$G$^8&ffNN|9bJ3v;HAbId10(k zv6R`S)fab2tQKeS8NnKZ_u^aKV%DXvRxecgt-2x4h77F ztoXV@W@Lz`D^Qy4itduB0!h*zH=SB2SRXuAfRaWQ2I7Yu(~$V}KO+0tPjuiEPjsMg zV_MYMkBF2?a4!wb|II0Z6M zX^}@dcpEYBQ-wT_8+ETID*$WiI1x%*tdK3LX0t@qb=K+4qO`~( zy&k0Ma#g2Qa}1 z-loOFVJ#7fnVJ>XT2ql|NDHf%59wtZt256rXNzLoYhYcv>C9{2Id^;2raPbB^XR(W zSFyp+A9)W26UUyj|90DJKZ@3DefH7eKY!_-TQk8H%GUNlKA-11M?t()oknmV`^f?J zaMI4Jr<#$y5c;nAs95VWTEfXx{Az;f}q#zmP1uiSXLyAxPEbrfG zOd#e^ScmLmqS|hlK3zUTh=1|{GwWBwJ6?O>%G$f$x$@PzUo79w)`ZD;Er=On=K4cr zU+mhs;NGQccWpR1^>ij!KL!jt5$t*^eGWj#riK6O!qtN=n)9E*$lV*GznYy1_GK9` zknNU>t{50RGr#(lJ;k*TZ1}~2Ot4yyg^nN>$=4P&`8r^ZJZkp)jhg$Srf9g(2RF4)_SE;&O)oIln1v$D!@p9FRm1H(8 z3f}8tv1E53JRv%w?(TQB%XW3VF^mbJKPR^#bpFEjKV5QX@w~dnzgoUy?66yNGQqwq zapct@hh&GW&}A(BqhPyEuS(-_QX7Fc7*HGpmX;ZNU`on}K%8bo5L`wPd&1!{5f~~6 zVDAgfntIc_QeuU`Ta)tb2g8)_dsHRq-TKw>Dk=PY@iv zXmcoLY|&QJi}mCv+BfQWSzU|UpEZDcY|lt=u0}7?YsMNKuMlZEyh>km(N^ox74*Rv zauYdN*Q{iujXr0Tms5qt_-2TyN&5DOAxy2EK5#(oTFEoAUyv2dLccv?;e#~Pg*ZiX zDM}1&(%gtONm1v3aqr7&B3?04 zQMaiN6R~BOHJl`;X!Z>}=6?O5QsR$h7)_!c9-qL(v}>m?O_#i&n9AOO}Y z&f}==^@~~FoHa^yOuzZyZRI`3Cz(*vCJ(%Fd8Um^M-C;#7=;X~nvH1RJi Effect = GameEffectContainer.GetEffect(HandleIn); EffectSpec.OnExpired(); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); @@ -320,7 +320,7 @@ bool UAFEffectsComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InT return bAllowApplication; } -FGAEffect* UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) +TSharedPtr UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) { return *GameEffectContainer.ActiveEffects.Find(InHandle); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index 8577da5..e87fcd3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -173,7 +173,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); void MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); public: - FGAEffect* GetEffect(const FGAEffectHandle& InHandle); + TSharedPtr GetEffect(const FGAEffectHandle& InHandle); /* Counted Tag Container Wrapper Start */ inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index a20499d..38bab37 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -629,8 +629,8 @@ float UGAAbilityBase::GetCurrentActivationTime() { if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) { - FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); - if (Effect) + TSharedPtr Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); + if (Effect.IsValid()) { return Effect->GetCurrentDuration(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 2401be8..7f0f4f7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -476,7 +476,15 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - , FGAEffectProperty& InProperty) override { Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); }; + , FGAEffectProperty& InProperty) override + { + if (!Attributes) + { + UE_LOG(AFAbilities, Log, TEXT("ModifyAttribute Ability Attributes INVALID")); + return; + } + Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); + }; virtual FAFPredictionHandle GetPredictionHandle() override; /* IAFAbilityInterface End **/ UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp index 3360292..25f3d4f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp @@ -6,6 +6,11 @@ DEFINE_LOG_CATEGORY(AbilityFramework); DEFINE_LOG_CATEGORY(GameAttributesGeneral); DEFINE_LOG_CATEGORY(GameAttributes); DEFINE_LOG_CATEGORY(GameAttributesEffects); + +DEFINE_LOG_CATEGORY(AFAttributes); +DEFINE_LOG_CATEGORY(AFEffects); +DEFINE_LOG_CATEGORY(AFAbilities); + FAFEffectTimerManager* FAFEffectTimerManager::Instance = nullptr; DECLARE_CYCLE_STAT(TEXT("EffectTimer.Run"), STAT_EffectTimerRun, STATGROUP_EffectTimer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h index 4ae9424..eca4711 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h @@ -143,4 +143,10 @@ DECLARE_LOG_CATEGORY_EXTERN(GameAttributesGeneral, Log, All); DECLARE_LOG_CATEGORY_EXTERN(GameAttributes, Log, All); -DECLARE_LOG_CATEGORY_EXTERN(GameAttributesEffects, Log, All); \ No newline at end of file +DECLARE_LOG_CATEGORY_EXTERN(GameAttributesEffects, Log, All); + + + +DECLARE_LOG_CATEGORY_EXTERN(AFAttributes, Log, All); +DECLARE_LOG_CATEGORY_EXTERN(AFEffects, Log, All); +DECLARE_LOG_CATEGORY_EXTERN(AFAbilities, Log, All); \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp index d6d246e..77ff541 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp @@ -175,7 +175,7 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& float returnValue = -1; bool isPeriod = InProperty.GetPeriod() > 0; bool IsDuration = InProperty.GetDuration() > 0; - if ( !isPeriod & IsDuration) + if ( !InProperty.GetIsInstant()) { FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); AttrMod.Tags.AppendTags(InProperty.GetSpec()->AttributeTags); @@ -237,38 +237,6 @@ void FAFAttributeBase::AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); modsTemp = ModIn; - //switch (Stacking) - //{ - // case EAFAttributeStacking::Add: - // { - // TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; - // FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); - // modsTemp = ModIn; - // break; - // } - // case EAFAttributeStacking::Override: - // { - // if (CheckIfModsMatch(Handle, ModIn)) - // { - // RemoveBonus(Handle, ModIn.AttributeMod); - // TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; - // FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); - // modsTemp = ModIn; - // } - // break; - // } - // case EAFAttributeStacking::StrongerOverride: - // { - // if (CheckIfStronger(ModIn)) - // { - // RemoveBonus(Handle, ModIn.AttributeMod); - // TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; - // FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); - // modsTemp = ModIn; - // } - // break; - // } - //} CalculateBonus(); } void FAFAttributeBase::RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h index cba2cf6..650b95c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h @@ -73,10 +73,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase float CurrentValue; UPROPERTY() float BonusValue; - - //UPROPERTY(EditAnywhere) - // EAFAttributeStacking Stacking; - + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") TSubclassOf ExtensionClass; @@ -103,7 +100,6 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); void SetExtensionClass(TSubclassOf InExtensionClass) { ExtensionClass = InExtensionClass; }; - //EAFAttributeStacking GetStacking() const { return Stacking; } }; template<> struct TStructOpsTypeTraits : public TStructOpsTypeTraitsBase2 diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp index 6c7d0a9..4a59378 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp @@ -104,6 +104,11 @@ UStructProperty* UGAAttributesBase::GetStructAttribute(const FGAAttribute& Name) } FAFAttributeBase* UGAAttributesBase::GetAttribute(const FGAAttribute& Name) { + if (!Name.IsValid()) + { + UE_LOG(GameAttributesEffects, Log, TEXT("GetAttribute INVALID NAME")); + return nullptr; + } UStructProperty* tempStruct = FindField(this->GetClass(), Name.AttributeName); FAFAttributeBase* attr = nullptr; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 17af54a..50c0cb5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -401,17 +401,16 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( , Params.Context , Params.EffectSpec); - AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &const_cast(EffectIn), InProperty); - const_cast(EffectIn).AppliedTime = OwningComponent->GetWorld()->TimeSeconds; const_cast(EffectIn).LastTickTime = OwningComponent->GetWorld()->TimeSeconds; const_cast(EffectIn).Duration = Spec.GetDuration(Context); const_cast(EffectIn).Period = Spec.GetPeriod(Context); - - MarkItemDirty(const_cast(EffectIn)); - ActiveEffectInfos.Add(EffectIn); + int32 newItem = ActiveEffectInfos.Add(EffectIn); MarkArrayDirty(); + AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &ActiveEffectInfos[newItem], InProperty); + + //InProperty.ApplyExecute(Handle, Params, Modifier); //generate it only on client, and apply prediction key from client. @@ -521,7 +520,9 @@ void FGAEffectContainer::AddEffect( } } - ActiveEffects.Add(InHandle, InEffect); + ActiveEffects.Add(InHandle, MakeShareable(InEffect)); + FGAEffectContainer* sss = this; + int dbg = 0; } void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty) @@ -535,7 +536,7 @@ TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandl EGAEffectAggregation Aggregation = Spec->EffectAggregation; FObjectKey key(HandleIn.GetClass()); TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); - + FGAEffectContainer* sss = this; if (!handles) return TArray(); TArray copy = *handles; @@ -675,10 +676,10 @@ UGAGameEffectSpec::UGAGameEffectSpec() float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) const { - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + const TSharedPtr* Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = *Effect; + const FGAEffect* Ptr = (*Effect).Get(); float Duration = Ptr->GetDurationTime(); return FMath::Clamp(Duration - Ptr->GetCurrentDuration(), 0, Duration); } @@ -686,10 +687,10 @@ float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) cons } float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const { - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + const TSharedPtr* Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = *Effect; + const FGAEffect* Ptr = (*Effect).Get(); float CurrentDuration = Ptr->GetCurrentDuration(); float MaxDuration = Ptr->GetDurationTime(); @@ -701,20 +702,20 @@ float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHa } float FGAEffectContainer::GetCurrentTime(const FGAEffectHandle& InHandle) const { - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + const TSharedPtr* Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = *Effect; + const FGAEffect* Ptr = (*Effect).Get(); return Ptr->GetCurrentDuration(); } return 0; } float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const { - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + const TSharedPtr* Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = *Effect; + const FGAEffect* Ptr = (*Effect).Get(); float CurrentDuration = Ptr->GetCurrentDuration(); float MaxDuration = Ptr->GetDurationTime(); return CurrentDuration * 1 / MaxDuration; @@ -728,7 +729,7 @@ float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle) { - FGAEffect* Effect = ActiveEffects[InHandle]; + TSharedPtr Effect = ActiveEffects[InHandle]; UGAGameEffectSpec* Spec = InProperty.GetSpec(); UClass* SpecClass = Spec->GetClass(); FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 19749ef..7b7d98c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -594,7 +594,10 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty void InitializeIfNotInitialized(const FGAEffectContext& InContext , TSubclassOf EffectClass); - + bool GetIsInstant() const + { + return bInstant; + } inline float GetPeriod() const { return Period; @@ -1156,7 +1159,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TMap> EffectByClass; - TMap ActiveEffects; + TMap> ActiveEffects; /* Contains effects with infinite duration. Infinite effects are considred to be special case, where they can only be self spplied @@ -1251,7 +1254,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const; float GetEndTime(const FGAEffectHandle& InHandle) const; - FGAEffect* GetEffect(const FGAEffectHandle& InHandle) + TSharedPtr GetEffect(const FGAEffectHandle& InHandle) { return ActiveEffects[InHandle]; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index e569acc..da340d9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -583,25 +583,6 @@ struct FGAEffectMod inline bool HasAllTagsIncludingChildren(const FGameplayTagContainer& TagsIn) const { return TagsIn.HasAll(AttributeTags); -// bool has = true; -// TArray GameplayTags; -// AttributeTags.GetGameplayTagArray(GameplayTags); -// for (const FGameplayTag& OtherTag : TagsIn) -// { -// /*for (const FGameplayTag& ChildTag : AttributeTags) -// { -// FGameplayTagContainer test = UGameplayTagsManager::Get().RequestGameplayTagChildren(ChildTag); -//*/ -// if (!ChildTags.HasAnyExact(TagsIn)) -// { -// if (!GameplayTags.Contains(OtherTag)) -// { -// has = false; -// } -// } -// //} -// } -// return has; } const bool operator==(const FGAEffectMod& Other) const { diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp index 23e5682..0aef518 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp @@ -297,8 +297,9 @@ FGAEffectClassStructWidget::~FGAEffectClassStructWidget() } -TSharedRef FGAEffectClassStructWidget::CreateEffectClassWidget() +TSharedRef FGAEffectClassStructWidget::CreateEffectClassWidget(UObject* OwnerObject) { + OuterObject = OwnerObject; //TAttribute EffectName;// (); //EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectClassStructWidget::GetClassName)); return SNew(SHorizontalBox) @@ -563,32 +564,53 @@ FReply FGAEffectClassStructWidget::MakeNewBlueprint() // Pre-generate a unique asset name to fill out the path picker dialog with. FString OuterName; + FString OuterName2; + if (StructPropertyHandle.IsValid()) { UProperty* prop = StructPropertyHandle->GetProperty(); OuterName = prop->GetOuter()->GetName(); OuterName = prop->GetPathName(); + OuterName = StructPropertyHandle->GeneratePathToProperty(); } - FString NewNameSuggestion = FString::Printf(TEXT("AFE_%s_"), *OuterName); + + UPackage* OuterMost = OuterObject->GetOutermost(); + FString AssetName = OuterObject->GetName(); + FString Path = OuterMost->GetFullName(); + FJsonSerializableArray OutArray; + Path = Path.RightChop(7); + Path.ParseIntoArrayWS(OutArray, TEXT("/")); + FString OutAsset = OutArray[OutArray.Num() - 1]; + OutArray.RemoveAt(OutArray.Num() - 1); + // OutArray.RemoveAt(0); + FString OutPath = "/"; + for (const FString& str : OutArray) + { + OutPath += str; + OutPath += "/"; + } + OutPath += FString::Printf(TEXT("E_%s_"), *OutAsset); + FString NewNameSuggestion = "";// FString::Printf(TEXT("E_%s_"), *OutAsset); UClass* BlueprintClass = UGAGameEffectSpec::StaticClass(); UClass* BlueprintGeneratedClass = UGAEffectBlueprint::StaticClass(); IKismetCompilerInterface& KismetCompilerModule = FModuleManager::LoadModuleChecked("KismetCompiler"); KismetCompilerModule.GetBlueprintTypesForClass(UGAGameEffectSpec::StaticClass(), BlueprintClass, BlueprintGeneratedClass); - FString PackageName = FString(TEXT("/Game/Blueprints/")) + NewNameSuggestion; + FString PackageName = OutPath + NewNameSuggestion; + FString OutPackageName; FString Name; FAssetToolsModule& AssetToolsModule = FModuleManager::LoadModuleChecked("AssetTools"); - AssetToolsModule.Get().CreateUniqueAssetName(PackageName, TEXT(""), PackageName, Name); + AssetToolsModule.Get().CreateUniqueAssetName(PackageName, NewNameSuggestion, OutPackageName, Name); TSharedPtr PickAssetPathWidget = SNew(SDlgPickAssetPath) .Title(FText::FromString("Create New Effect")) - .DefaultAssetPath(FText::FromString(PackageName)); + .DefaultAssetPath(FText::FromString(OutPath)); UBlueprint* Blueprint = nullptr; if (EAppReturnType::Ok == PickAssetPathWidget->ShowModal()) { diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h index b7666ed..f7e557f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h @@ -19,6 +19,7 @@ class FGAEffectClassStructWidget : public TSharedFromThis EffectEditorWindow; UBlueprint* EditedBlueprint; + UObject* OuterObject; public: FGAEffectClassStructWidget() {}; FGAEffectClassStructWidget(TSharedPtr InStructPropertyHandle, @@ -28,7 +29,7 @@ class FGAEffectClassStructWidget : public TSharedFromThis ParentClass; - TSharedRef CreateEffectClassWidget(); + TSharedRef CreateEffectClassWidget(UObject* OwnerObject); void SetHandles(TSharedPtr InStructPropertyHandle, TSharedPtr InEffectPropertyHandle) { diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp index 5d81d1f..a10c616 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp @@ -46,6 +46,12 @@ FGAEffectPropertyStructCustomization::~FGAEffectPropertyStructCustomization() void FGAEffectPropertyStructCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) { + const TArray>& objs = StructCustomizationUtils.GetPropertyUtilities()->GetSelectedObjects(); + UObject* Owner = nullptr; + if (objs.Num() > 0) + { + Owner = objs[0].Get(); + } StructPropertyHandle = InStructPropertyHandle; TAttribute EffectName;// (); EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectPropertyStructCustomization::GetClassName)); @@ -59,6 +65,7 @@ void FGAEffectPropertyStructCustomization::CustomizeHeader(TSharedRef ClassInStruct = EffectPropertyHandle->GetChildHandle(TEXT("SpecClass")); EffectClassWidget = MakeShareable(new FGAEffectClassStructWidget()); EffectClassWidget->SetHandles(EffectPropertyHandle, ClassInStruct); + HeaderRow .NameContent() [ @@ -71,7 +78,7 @@ void FGAEffectPropertyStructCustomization::CustomizeHeader(TSharedRefCreateEffectClassWidget() + EffectClassWidget->CreateEffectClassWidget(Owner) ] ]; } diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h index 95bbca8..2377228 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h @@ -55,8 +55,8 @@ class SWindowBox : public SPanel class FBoxSlot : public TSupportsOneChildMixin, public TSupportsContentAlignmentMixin, public TSupportsContentPaddingMixin { public: - FBoxSlot() - : TSupportsOneChildMixin() + FBoxSlot(SWidget* InOwner) + : TSupportsOneChildMixin(nullptr) , TSupportsContentAlignmentMixin(HAlign_Fill, VAlign_Fill) { } @@ -85,6 +85,9 @@ class SWindowBox : public SPanel FBoxSlot ChildSlot; public: + SWindowBox() + : ChildSlot(this) + {} void Construct(const FArguments& InArgs); /** See WidthOverride attribute */ void SetWidthOverride(float InWidthOverride); diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 230365d..1ab32f7 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -13,6 +13,7 @@ #include "Weapons/ARWeaponBase.h" #include "Weapons/ARWeaponPawnManagerComponent.h" +#include "ARCharacterMovementComponent.h" #include "ARPlayerController.h" ////////////////////////////////////////////////////////////////////////// @@ -22,26 +23,37 @@ const FName WeaponSocket::HolsteredRightWeapon = TEXT("spine_RightWeaponSocket") const FName WeaponSocket::HolsteredLeftWeapon = TEXT("spine_LeftWeaponSocket"); const FName WeaponSocket::EquipedMainWeapon = TEXT("hand_rSocket"); -AARCharacter::AARCharacter() +AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer.SetDefaultSubobjectClass(ACharacter::CharacterMovementComponentName)) { // Set size for collision capsule GetCapsuleComponent()->InitCapsuleSize(42.f, 96.0f); // set our turn rates for input - BaseTurnRate = 45.f; - BaseLookUpRate = 45.f; - + BaseTurnRate = 5.f; + BaseLookUpRate = 25.f; + bStopDistancePredicted = false; // Don't rotate when the controller rotates. Let that just affect the camera. bUseControllerRotationPitch = false; bUseControllerRotationYaw = false; bUseControllerRotationRoll = false; // Configure character movement - GetCharacterMovement()->bOrientRotationToMovement = true; // Character moves in the direction of input... - GetCharacterMovement()->RotationRate = FRotator(0.0f, 540.0f, 0.0f); // ...at this rotation rate - GetCharacterMovement()->JumpZVelocity = 600.f; + GetCharacterMovement()->bOrientRotationToMovement = false; // Character moves in the direction of input... + GetCharacterMovement()->bUseControllerDesiredRotation = true; + GetCharacterMovement()->RotationRate = FRotator(0.0f, 180.0f, 0.0f); // ...at this rotation rate + GetCharacterMovement()->JumpZVelocity = 400.f; GetCharacterMovement()->AirControl = 0.2f; + GetCharacterMovement()->MaxAcceleration = 200.0f; + GetCharacterMovement()->BrakingFriction = 1.0; + GetCharacterMovement()->bUseSeparateBrakingFriction = true; + GetCharacterMovement()->Mass = 80.0f; + GetCharacterMovement()->GroundFriction = 1.0f; + GetCharacterMovement()->MaxWalkSpeed = 270.0f; + GetCharacterMovement()->MaxWalkSpeedCrouched = 150.0f; + GetCharacterMovement()->BrakingDecelerationWalking = 150.0f; + // Create a camera boom (pulls in towards the player if there is a collision) CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); CameraBoom->SetupAttachment(RootComponent); @@ -107,6 +119,246 @@ void AARCharacter::BeginPlay() Weapons->SetPOwner(this); } +FString DirToString(EFourCardinalDirection dir) +{ + switch (dir) + { + case EFourCardinalDirection::N: + return "N"; + case EFourCardinalDirection::E: + return "E"; + case EFourCardinalDirection::S: + return "S"; + case EFourCardinalDirection::W: + return "W"; + default: + break; + } + return "Invalid"; +} + +float AARCharacter::GetAnimOrient() +{ + return CurrentOrient; +} +float AARCharacter::GetAnimOrientN() { return OrientN; }; +float AARCharacter::GetAnimOrientE() { return OrientE; }; +float AARCharacter::GetAnimOrientS() { return OrientS; }; +float AARCharacter::GetAnimOrientW() { return OrientW; }; + +EFCardinalDirection AARCharacter::GetCardianlDirection() +{ + int32 dir = static_cast(FourDirections); + + return static_cast(dir); +} +void AARCharacter::Tick(float DeltaSeconds) +{ + Super::Tick(DeltaSeconds); + + UCharacterMovementComponent* CMC = GetCharacterMovement(); + + if (!CMC) + return; + FVector CharLocation = GetActorLocation(); + + FVector CurrentAcceleration = CMC->GetCurrentAcceleration(); + FVector CurrentVelocity = CMC->Velocity; + + FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal(); + FVector LineEnd = (AccelerationDirection * 80.0f) + GetActorLocation(); + + ::DrawDebugLine(GetWorld(), GetActorLocation(), LineEnd, FColor::Red, false, -1.0f, 0, 10); + + FVector VelocityDirection = CurrentVelocity.GetSafeNormal(); + + float Vel = (CurrentVelocity.Size() / CMC->GetMaxSpeed()) * 100; + + FVector VelocityEnd = (VelocityDirection * Vel) + GetActorLocation(); + + ::DrawDebugLine(GetWorld(), GetActorLocation()+FVector(0,0,10), VelocityEnd + FVector(0, 0, 10), FColor::Blue, false, -1.0f, 0, 10); + + FTransform Transform = GetTransform(); + FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); + FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); + + FQuat QRot = LocalAcceleration.ToOrientationQuat(); + FRotator Rot = FRotator(QRot); + float Angle = Rot.Yaw;// FMath::RadiansToDegrees(FMath::Atan2(LocalVelocity.Y, LocalVelocity.X)); + float Angle2 = (FMath::RoundToInt(Angle) + 360) % 360; + FVector Right = GetActorRightVector(); + FVector Forward = GetActorForwardVector(); + + + FQuat QAngle = FQuat::FindBetweenNormals(Forward, LocalVelocity); + + FRotator RAngle(QAngle); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 145), "RAngle: " + FString::FormatAsNumber(RAngle.Yaw), nullptr, FColor::Red, 0, true); + + + FVector V1 = (Forward + Right).GetSafeNormal2D(); + FVector V2 = (Forward + (Right * (-1))).GetSafeNormal2D(); + + + int32 Octant = FMath::RoundToInt((Angle2)) % 8; + EigthDirections = static_cast(Octant); + float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); + int32 Dir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; + + EFourCardinalDirection NewDir = static_cast(Dir); + + + switch (EigthDirections) + { + case EEightCardinalDirection::S: + break; + case EEightCardinalDirection::NE: + break; + case EEightCardinalDirection::W: + break; + case EEightCardinalDirection::SE: + break; + case EEightCardinalDirection::N: + break; + case EEightCardinalDirection::SW: + break; + case EEightCardinalDirection::E: + break; + case EEightCardinalDirection::NW: + { + /*if(OldFourDirections == EFourCardinalDirection::W) + NewDir = EFourCardinalDirection::N;*/ + break; + } + default: + break; + } + + if (NewDir != FourDirections) + { + OldFourDirections = FourDirections; + } + FourDirections = NewDir; + + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 135), "OldFourDirections: " + DirToString(OldFourDirections), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 140), "FourDirections: " + DirToString(FourDirections), nullptr, FColor::Red, 0, true); + + float VelAccelDot = FVector::DotProduct(LocalVelocity, LocalAcceleration); + int32 intDot = FMath::RoundToInt(VelAccelDot); + OrientationDOT = VelAccelDot; + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 150), "VelAccelDot: " + FString::FormatAsNumber(intDot), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 155), "FVelAccelDot: " + FString::Printf(TEXT("%f"), VelAccelDot), nullptr, FColor::Red, 0, true); + + + float TargetForward = FVector::DotProduct(CurrentVelocity, Forward); + ForwardDirection = FMath::FInterpConstantTo(ForwardDirection, TargetForward, DeltaSeconds, 100.0f); + + float LateralForward = FVector::DotProduct(CurrentVelocity, Right); + LateralDirection = FMath::FInterpConstantTo(LateralDirection, LateralForward, DeltaSeconds, 100.0f); + + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 165), "ForwardDirection: " + FString::Printf(TEXT("%f"), ForwardDirection), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 170), "LateralDirection: " + FString::Printf(TEXT("%f"), LateralDirection), nullptr, FColor::Red, 0, true); + + FString SVelocity = "V: " + FString::Printf(TEXT("%d"), FMath::RoundToInt(CurrentVelocity.Size())) + " LV: " + FString::Printf(TEXT("%f"), LocalVelocity.Size()); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 90), SVelocity, nullptr, FColor::Red, 0, true); + + FString SAcceleration = "A: " + FString::Printf(TEXT("%d"), FMath::RoundToInt(CurrentAcceleration.Size())) + " LA: " + FString::Printf(TEXT("%f"), LocalAcceleration.Size()); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 95), SAcceleration, nullptr, FColor::Red, 0, true); + + FVector LocalVel = Transform.InverseTransformVector(CurrentVelocity); + + OldOrient = CurrentOrient; + FQuat VelQuat = LocalVelocity.ToOrientationQuat(); + //FRotator VelRot = VelQuat.GetAngle(); + float VelAngle = FMath::RadiansToDegrees(VelQuat.GetAngle()); + switch (FourDirections) + { + case EFourCardinalDirection::E: + { + FQuat LeftQuat = FQuat::FindBetween(Right, CurrentVelocity); + OrientE = FRotator(LeftQuat).Yaw; + CurrentOrient = OrientE; + + break; + } + case EFourCardinalDirection::N: + { + FQuat ForwardQuat = FQuat::FindBetween(Forward, CurrentVelocity); + OrientN = FRotator(ForwardQuat).Yaw; + float sign = FMath::Sign(OldOrient); + CurrentOrient = OrientN; + break; + } + case EFourCardinalDirection::W: + { + FQuat RightQuat = FQuat::FindBetween(Right*(-1), CurrentVelocity); + OrientW = FRotator(RightQuat).Yaw; + CurrentOrient = OrientW; + break; + } + case EFourCardinalDirection::S: + { + FQuat BackQuat = FQuat::FindBetween(Forward*(-1), CurrentVelocity); + OrientS = FRotator(BackQuat).Yaw; + + CurrentOrient = OrientW; + break; + } + default: + break; + } + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 105), "OrientN: " + FString::FormatAsNumber(OrientN) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 110), "OrientS: " + FString::FormatAsNumber(OrientS) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct((-1)*Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 115), "OrientE: " + FString::FormatAsNumber(OrientE) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right, VelocityDirection)), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 120), "OrientW: " + FString::FormatAsNumber(OrientW) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right*(-1), VelocityDirection)), nullptr, FColor::Red, 0, true); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 125), "CurrentOrient: " + FString::FormatAsNumber(CurrentOrient), nullptr, FColor::Red, 0, true); + +// FMath::RadiansToDegrees(FMath::Atan2(LocalVelocity.Y, LocalVelocity.X)); + float VelAngle2 = (FMath::RoundToInt(VelAngle) + 360) / 360; + + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 130), "VelAngle2: " + FString::FormatAsNumber(VelAngle2), nullptr, FColor::Red, 0, true); + + float DeltaVelocity = CurrentVelocity.Size()* DeltaSeconds; + if (!CurrentAcceleration.IsZero()) + { + bStopDistancePredicted = false; + } + if (CurrentAcceleration.Size() <= 0 + && CurrentVelocity.Size() < CMC->MaxWalkSpeed*0.75) + { + bStartedLocomotion = false; + } + + if (CurrentAcceleration.Size() > 0 + && CurrentVelocity.Size() > 0) + { + bStartedLocomotion = true; + } + + FVector FinalDestination = (AccelerationDirection * 400) + CharLocation; + float AccelSpeed = CurrentAcceleration.Size(); + if (!bStopDistancePredicted && CurrentAcceleration.IsZero()) + { + bStopDistancePredicted = true; + float CurVel = CurrentVelocity.SizeSquared(); + float StopDistance = (CurVel / (4*CMC->GroundFriction *CMC->BrakingFrictionFactor * CMC->BrakingDecelerationWalking)); + FVector Forward = VelocityDirection; + FVector StopLocation = (Forward*StopDistance) + CharLocation; + DrawDebugSphere(GetWorld(), StopLocation, 6, 8, FColor::Green, false, 2, 0, 2); + } + + DrawDebugSphere(GetWorld(), FinalDestination, 6, 8, FColor::Red, false, -1, 0, 2); + float Offset = 20; + for (float Idx = 1; Idx < 20; Idx++) + { + FVector BetweenDestination = (AccelerationDirection * Offset) + CharLocation; + Offset += 20; + //DrawDebugSphere(GetWorld(), BetweenDestination, 6, 8, FColor::Red, false, -1, 0, 2); + } + FString SAngle = FString("Angle: ") + FString::FormatAsNumber(Angle2); + DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 80), SAngle, nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 60), "4: Fourtant : " + FString::FormatAsNumber(Fourtant), nullptr, FColor::Red, 0, true); +} ////////////////////////////////////////////////////////////////////////// // Input diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 5cad90e..056b96d 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -9,8 +9,51 @@ #include "AFEffectsComponent.h" #include "AFAbilityComponent.h" #include "AFAbilityInterface.h" +#include "OrionInterface.h" +#include "OrionAnimComponent.h" #include "ARCharacter.generated.h" +UENUM(BlueprintType) +enum class EEightCardinalDirection : uint8 +{ + N = 0, + SW = 1, + E = 2, + NW = 3, + S = 4, + NE = 5, + W = 6, + SE = 7 +}; + +UENUM(BlueprintType) +enum class EFourCardinalDirection : uint8 +{ + N = 0, + E = 1, + S = 2, + W = 3 +}; + +UENUM(BlueprintType) +enum class EPivotDirectionChange : uint8 +{ + NtoE = 0, + NtoW = 1, + NToS = 2, +}; + +USTRUCT(BlueprintType) +struct FCardinalDirection +{ + GENERATED_BODY() + + UPROPERTY(BlueprintReadOnly) + EFourCardinalDirection CaridnalDirections; + + EEightCardinalDirection HelperDirections; +}; + USTRUCT(BlueprintType) struct FARCameraTransform { @@ -29,7 +72,7 @@ struct WeaponSocket static const FName EquipedMainWeapon; }; UCLASS(config=Game) -class AARCharacter : public ACharacter, public IAFAbilityInterface +class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrionInterface { GENERATED_BODY() @@ -65,15 +108,59 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponEquipedMain; + + public: UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") FARCameraTransform CameraTransform; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + bool bStopDistancePredicted; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + bool bStartedLocomotion; + + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + EEightCardinalDirection EigthDirections; + + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + EFourCardinalDirection OldFourDirections; + + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + EFourCardinalDirection FourDirections; + + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + float MovingAngle; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + float OrientN; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + float OrientS; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + float OrientE; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + float OrientW; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Character Animation") + float OrientInterpolationSpeed; + + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Character Animation") + float OrientationDOT; + + float ForwardDirection; + float LateralDirection; + UPROPERTY(BlueprintReadOnly, Category = "Character Animation") + float CurrentOrient; + float OldOrient; public: - AARCharacter(); + AARCharacter(const FObjectInitializer& ObjectInitializer); + float GetAnimOrient() final; + EFCardinalDirection GetCardianlDirection() final; + float GetAnimOrientN() final; + float GetAnimOrientE() final; + float GetAnimOrientS() final; + float GetAnimOrientW() final; virtual void BeginPlay() override; - + virtual void Tick(float DeltaSeconds) override; /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) float BaseTurnRate; diff --git a/Source/ActionRPGGame/ARCharacterMovementComponent.cpp b/Source/ActionRPGGame/ARCharacterMovementComponent.cpp new file mode 100644 index 0000000..f07a2ee --- /dev/null +++ b/Source/ActionRPGGame/ARCharacterMovementComponent.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARCharacterMovementComponent.h" + + + + diff --git a/Source/ActionRPGGame/ARCharacterMovementComponent.h b/Source/ActionRPGGame/ARCharacterMovementComponent.h new file mode 100644 index 0000000..5b3d714 --- /dev/null +++ b/Source/ActionRPGGame/ARCharacterMovementComponent.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/CharacterMovementComponent.h" +#include "ARCharacterMovementComponent.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARCharacterMovementComponent : public UCharacterMovementComponent +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 751068d..8314e09 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -51,24 +51,30 @@ void AARPlayerController::SetPawn(APawn* InPawn) bInputBount = true; } //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. - FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); - AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); - TArray NextWeap; - NextWeap.Add(InputNextWeapon); - AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr, NextWeap); - - FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); - AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); - TArray PrevWeap; - PrevWeap.Add(InputPreviousWeapon); - AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); - - FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytHolstersWeapon, InputHolsterWeapon); - AbilityComp->AddOnAbilityReadyDelegate(AbilitytHolstersWeapon, del3); - TArray HolsterInput; - HolsterInput.Add(InputHolsterWeapon); - AbilityComp->NativeAddAbilityFromTag(AbilitytHolstersWeapon, nullptr, HolsterInput); - + if (AbilitytNextWeapon.IsValid()) + { + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); + AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); + TArray NextWeap; + NextWeap.Add(InputNextWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr, NextWeap); + } + if (AbilitytPreviousWeapon.IsValid()) + { + FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); + AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); + TArray PrevWeap; + PrevWeap.Add(InputPreviousWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); + } + if (AbilitytHolstersWeapon.IsValid()) + { + FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytHolstersWeapon, InputHolsterWeapon); + AbilityComp->AddOnAbilityReadyDelegate(AbilitytHolstersWeapon, del3); + TArray HolsterInput; + HolsterInput.Add(InputHolsterWeapon); + AbilityComp->NativeAddAbilityFromTag(AbilitytHolstersWeapon, nullptr, HolsterInput); + } } WeaponManager->POwner = InPawn; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 8a44f10..ac12157 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -10,6 +10,9 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) PublicIncludePaths.AddRange( new string[] { "AbilityFramework", + "OrionAnimation", + "OrionAnimation/Private", + "OrionAnimation/Public", "AbilityFramework/Abilities", "AbilityFramework/Attributes", "AbilityFramework/Effects", @@ -26,6 +29,9 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) PrivateIncludePaths.AddRange( new string[] { "AbilityFramework", + "OrionAnimation", + "OrionAnimation/Private", + "OrionAnimation/Public", "AbilityFramework/Abilities", "AbilityFramework/Attributes", "AbilityFramework/Effects", @@ -49,6 +55,7 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "GameplayTags", "AbilityFramework", "AssetRegistry", + "OrionAnimation", //"Sockets", //"OnlineSubsystemUtils", "ActorSequence", From fa13475f5ee35030bec452bd367144c5253eb6a3 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 00:53:29 +0100 Subject: [PATCH 060/187] changed TSharedPtr to raw pointer --- .../AbilityFramework/AFEffectsComponent.cpp | 4 ++-- .../AbilityFramework/AFEffectsComponent.h | 2 +- .../Abilities/GAAbilityBase.cpp | 4 ++-- .../AbilityFramework/Effects/GAGameEffect.cpp | 20 +++++++++---------- .../AbilityFramework/Effects/GAGameEffect.h | 4 ++-- 5 files changed, 17 insertions(+), 17 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 542f369..46f1859 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -181,7 +181,7 @@ void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn FGAEffectProperty& InProperty = Params.GetProperty(); FGAEffectContext& InContext = Params.GetContext(); FAFEffectSpec& EffectSpec = Params.GetSpec(); - TSharedPtr Effect = GameEffectContainer.GetEffect(HandleIn); + FGAEffect* Effect = GameEffectContainer.GetEffect(HandleIn); EffectSpec.OnExpired(); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); @@ -320,7 +320,7 @@ bool UAFEffectsComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InT return bAllowApplication; } -TSharedPtr UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) +FGAEffect* UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) { return *GameEffectContainer.ActiveEffects.Find(InHandle); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index e87fcd3..8577da5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -173,7 +173,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); void MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); public: - TSharedPtr GetEffect(const FGAEffectHandle& InHandle); + FGAEffect* GetEffect(const FGAEffectHandle& InHandle); /* Counted Tag Container Wrapper Start */ inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 38bab37..a20499d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -629,8 +629,8 @@ float UGAAbilityBase::GetCurrentActivationTime() { if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) { - TSharedPtr Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); - if (Effect.IsValid()) + FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); + if (Effect) { return Effect->GetCurrentDuration(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 50c0cb5..d889ca9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -520,7 +520,7 @@ void FGAEffectContainer::AddEffect( } } - ActiveEffects.Add(InHandle, MakeShareable(InEffect)); + ActiveEffects.Add(InHandle, InEffect); FGAEffectContainer* sss = this; int dbg = 0; } @@ -676,10 +676,10 @@ UGAGameEffectSpec::UGAGameEffectSpec() float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) const { - const TSharedPtr* Effect = ActiveEffects.Find(InHandle); + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = (*Effect).Get(); + const FGAEffect* Ptr = *Effect; float Duration = Ptr->GetDurationTime(); return FMath::Clamp(Duration - Ptr->GetCurrentDuration(), 0, Duration); } @@ -687,10 +687,10 @@ float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) cons } float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const { - const TSharedPtr* Effect = ActiveEffects.Find(InHandle); + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = (*Effect).Get(); + const FGAEffect* Ptr = *Effect; float CurrentDuration = Ptr->GetCurrentDuration(); float MaxDuration = Ptr->GetDurationTime(); @@ -702,20 +702,20 @@ float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHa } float FGAEffectContainer::GetCurrentTime(const FGAEffectHandle& InHandle) const { - const TSharedPtr* Effect = ActiveEffects.Find(InHandle); + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = (*Effect).Get(); + const FGAEffect* Ptr = *Effect; return Ptr->GetCurrentDuration(); } return 0; } float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const { - const TSharedPtr* Effect = ActiveEffects.Find(InHandle); + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); if (Effect) { - const FGAEffect* Ptr = (*Effect).Get(); + const FGAEffect* Ptr = *Effect; float CurrentDuration = Ptr->GetCurrentDuration(); float MaxDuration = Ptr->GetDurationTime(); return CurrentDuration * 1 / MaxDuration; @@ -729,7 +729,7 @@ float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle) { - TSharedPtr Effect = ActiveEffects[InHandle]; + FGAEffect* Effect = ActiveEffects[InHandle]; UGAGameEffectSpec* Spec = InProperty.GetSpec(); UClass* SpecClass = Spec->GetClass(); FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 7b7d98c..bd3ff36 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -1159,7 +1159,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TMap> EffectByClass; - TMap> ActiveEffects; + TMap ActiveEffects; /* Contains effects with infinite duration. Infinite effects are considred to be special case, where they can only be self spplied @@ -1254,7 +1254,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const; float GetEndTime(const FGAEffectHandle& InHandle) const; - TSharedPtr GetEffect(const FGAEffectHandle& InHandle) + FGAEffect* GetEffect(const FGAEffectHandle& InHandle) { return ActiveEffects[InHandle]; } From b02c32d34662eb317139c369d2f2600a2c3c861d Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 01:04:13 +0100 Subject: [PATCH 061/187] removing dead code --- .../AbilityFramework/AFAssetManager.cpp | 8 -------- .../Source/AbilityFramework/AFAssetManager.h | 20 ------------------- .../AbilityFramework/Effects/GAEffectSet.cpp | 8 -------- .../AbilityFramework/Effects/GAEffectSet.h | 20 ------------------- 4 files changed, 56 deletions(-) delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp deleted file mode 100644 index 24126a3..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAssetManager.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h deleted file mode 100644 index 0019a7c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAssetManager.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Engine/AssetManager.h" -#include "AFAssetManager.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFAssetManager : public UAssetManager -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp deleted file mode 100644 index f2fedef..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../AbilityFramework.h" -#include "GAEffectSet.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h deleted file mode 100644 index dfb591f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectSet.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Engine/DataAsset.h" -#include "GAEffectSet.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAEffectSet : public UDataAsset -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray> Specs; - - -}; From 61faa90bccbd03cbd412b523f62608d26f5e3658 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 12:31:38 +0100 Subject: [PATCH 062/187] added early out to ApplyEffect function. Uses new function in Application Class to check if effect should be applied --- Config/DefaultEngine.ini | 14 ++++++-------- .../Source/AbilityFramework/AFEffectsComponent.h | 7 +++++++ .../Effects/AFEffectCustomApplication.h | 5 +++++ .../Effects/GABlueprintLibrary.cpp | 14 ++++++++++++-- .../AbilityFramework/Effects/GAGameEffect.cpp | 10 ++++++++++ .../Source/AbilityFramework/Effects/GAGameEffect.h | 6 ++++++ .../GAEffectClassStructWidget.cpp | 2 +- 7 files changed, 47 insertions(+), 11 deletions(-) diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 47f9b72..5e70f79 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -88,9 +88,6 @@ s.AsyncLoadingThreadEnabled=True +CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") -[/Script/Engine.Engine] -AssetManagerClassName=/Script/AbilityFramework.AFAssetManager - [/Script/Engine.UserInterfaceSettings] bLoadWidgetsOnDedicatedServer=False @@ -126,6 +123,12 @@ DirtyAreasUpdateFreq=60.000000 [/Script/Engine.AnimationSettings] bTickAnimationOnSkeletalMeshInit=True +[/Script/Engine.GarbageCollectionSettings] +gc.TimeBetweenPurgingPendingKillObjects=30.000000 +gc.NumRetriesBeforeForcingGC=0 +gc.ActorClusteringEnabled=True +gc.BlueprintClusteringEnabled=True + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -168,9 +171,4 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 -[/Script/Engine.GarbageCollectionSettings] -gc.TimeBetweenPurgingPendingKillObjects=30.000000 -gc.NumRetriesBeforeForcingGC=0 -gc.ActorClusteringEnabled=True -gc.BlueprintClusteringEnabled=True diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index 8577da5..e0a7a22 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -190,6 +190,13 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent /* Counted Tag Container Wrapper Start */ + /* Game Effect Container WRAPPER */ + bool IsEffectActive(TSubclassOf EffectClass) + { + return GameEffectContainer.IsEffectActive(EffectClass); + } + + /* Game Effect Container WRAPPER */ /*Network Functions - BEGIN */ protected: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h index 4afe314..24fd308 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h @@ -28,6 +28,11 @@ class ABILITYFRAMEWORK_API UAFEffectCustomApplication : public UObject , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + virtual bool CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) + { + return true; + } + virtual bool ShowPeriod() { return false; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index e7eb637..9519dc8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -5,7 +5,10 @@ #include "GABlueprintLibrary.h" + #include "AFAbilityInterface.h" +#include "GAGameEffect.h" +#include "AFEffectCustomApplication.h" #include "GAEffectExtension.h" @@ -64,7 +67,12 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); return FGAEffectHandle(); } - + + IAFAbilityInterface* TargetInterface = Cast(Target); + if (!InEffect.GetClass().GetDefaultObject()->Application.GetDefaultObject()->CanApply(TargetInterface, InEffect.GetClass())) + { + return FGAEffectHandle(); + } bool bReusedParams = false; bool bPeriodicEffect = false; bool bReusedSpec = false; @@ -96,7 +104,9 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( } InEffect.InitializeIfNotInitialized(Context.GetRef()); + UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); + if ((InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) { bPeriodicEffect = true; @@ -108,7 +118,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( return FGAEffectHandle(); } - UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); + if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) { return FGAEffectHandle(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index d889ca9..b081663 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -811,4 +811,14 @@ void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProper } } ActiveEffects.Remove(InHandle); +} + +bool FGAEffectContainer::IsEffectActive(TSubclassOf EffectClass) +{ + FObjectKey EffectKey(EffectClass); + if (EffectByClass.Contains(EffectKey)) + { + return true; + } + return false; } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index bd3ff36..0748c14 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -454,6 +454,11 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec float GetDuration(const FGAEffectContext& InContext); float GetPeriod(const FGAEffectContext& InContext); + const TSubclassOf& GetEffectClass() + { + return SpecClass; + } + }; USTRUCT(BlueprintType) struct FAFEffectSpecHandle @@ -1258,6 +1263,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer { return ActiveEffects[InHandle]; } + bool IsEffectActive(TSubclassOf EffectClass); private: void RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp index 0aef518..3ee44fb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp @@ -163,7 +163,7 @@ class SEffectCreateDialog : public SCompoundWidget // Fill in options FClassViewerInitializationOptions Options; Options.Mode = EClassViewerMode::ClassPicker; - + Options.bShowDisplayNames = true; // Only allow parenting to base blueprints. Options.bIsBlueprintBaseOnly = true; From 022dc28ec1265562200c425cd00759601847d0d2 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 12:52:48 +0100 Subject: [PATCH 063/187] ARG-9 Add missing files --- .../AFAtributeDurationUnique.cpp | 38 +++++++++++++++++++ .../AFAtributeDurationUnique.h | 34 +++++++++++++++++ 2 files changed, 72 insertions(+) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp new file mode 100644 index 0000000..d38c4e1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFAbilityInterface.h" +#include "AFAtributeDurationUnique.h" + + + + +bool UAFAtributeDurationUnique::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + if (InContainer->IsEffectActive(Params.GetSpec().GetEffectClass())) + { + return false; + } + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + return true; +} + +bool UAFAtributeDurationUnique::CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) +{ + if (!Target) + return false; + + return !Target->GetEffectsComponent()->IsEffectActive(EffectClass); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h new file mode 100644 index 0000000..ea378c1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAtributeDurationUnique.generated.h" + +/** + * Adds New duration Effect. + */ +UCLASS(meta = (DisplayName = "Duration Add Unique")) +class ABILITYFRAMEWORK_API UAFAtributeDurationUnique : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) override; + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return true; + } +}; From 485707539558fb7f71bba772856730f41722177f Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 21:59:02 +0100 Subject: [PATCH 064/187] added check before revmoing effect, to see if we are trying to remove valid effect --- Config/DefaultGameplayTags.ini | 2 ++ .../Source/AbilityFramework/AFEffectsComponent.cpp | 4 ++++ .../Effects/CustomApplications/AFAtributeDurationUnique.h | 2 +- 3 files changed, 7 insertions(+), 1 deletion(-) diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index e739edd..165eeaa 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -7,6 +7,8 @@ NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") ++GameplayTagList=(Tag="Ability.EffectInstance",DevComment="") ++GameplayTagList=(Tag="Ability.EffectInstance.Damage",DevComment="") +GameplayTagList=(Tag="Ability.Input.GolsterWeapon",DevComment="") +GameplayTagList=(Tag="Ability.Input.HolsterWeapon",DevComment="") +GameplayTagList=(Tag="Ability.Input.Jump",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 46f1859..7c93df5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -215,6 +215,10 @@ void UAFEffectsComponent::RemoveEffect(const FAFPropertytHandle& InProperty , const FGAEffectContext& InContext , const FGAEffectHandle& InHandle) { + if (!InProperty.IsValid()) + { + UE_LOG(AFEffects, Log, TEXT("RemoveEffect - Trying to Remove invalid effect.")); + } //if (GetOwnerRole() == ENetRole::ROLE_Authority // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h index ea378c1..be69075 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h @@ -7,7 +7,7 @@ #include "AFAtributeDurationUnique.generated.h" /** - * Adds New duration Effect. + * Adds New Unique duration Effect. If effect of the same class is already applied to target, new effect will be ignored. */ UCLASS(meta = (DisplayName = "Duration Add Unique")) class ABILITYFRAMEWORK_API UAFAtributeDurationUnique : public UAFEffectCustomApplication From 020c5710bb14b83f74bd0df7a0f69b40a5d82fd1 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 21:59:36 +0100 Subject: [PATCH 065/187] missing change --- .../Source/AbilityFramework/AFEffectsComponent.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 7c93df5..4d7d200 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -218,6 +218,7 @@ void UAFEffectsComponent::RemoveEffect(const FAFPropertytHandle& InProperty if (!InProperty.IsValid()) { UE_LOG(AFEffects, Log, TEXT("RemoveEffect - Trying to Remove invalid effect.")); + return; } //if (GetOwnerRole() == ENetRole::ROLE_Authority // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) From 6a475b4b74757a6a5f3275bfcb21fc254b22a256 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 22:09:05 +0100 Subject: [PATCH 066/187] EffectSpec will now properly create Effect Extension --- .../AbilityFramework/Effects/GABlueprintLibrary.cpp | 2 +- .../Source/AbilityFramework/Effects/GAGameEffect.cpp | 6 ++++++ .../Source/AbilityFramework/Effects/GAGameEffect.h | 11 +++++------ 3 files changed, 12 insertions(+), 7 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 9519dc8..106a16e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -143,7 +143,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( if (!bReusedSpec) { - FAFEffectSpec* EffectSpec = new FAFEffectSpec(InEffect.GetClass()); + FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); AddTagsToEffect(EffectSpec); Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index b081663..49ecfc5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -46,6 +46,12 @@ void FAFEffectSpec::OnExecuted() Extension->NativeOnEffectExecuted(); } } +FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& Context, TSubclassOf InSpecClass) + : SpecClass(InSpecClass) +{ + Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); +} + float FAFEffectSpec::GetFloatFromAttributeMagnitude( const FGAMagnitude& AttributeIn , const FGAEffectContext& InContext) const diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 0748c14..8da2b6e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -402,14 +402,16 @@ struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBas }; }; - +/* + +*/ USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FAFEffectSpec { GENERATED_BODY() private: UPROPERTY() - class UGAEffectExtension* Extension; + class UGAEffectExtension* Extension; //week ptr ? TSubclassOf SpecClass; public: @@ -423,10 +425,7 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : Extension(nullptr) {} - FAFEffectSpec(TSubclassOf InSpecClass) - : Extension(nullptr) - , SpecClass(InSpecClass) - {} + FAFEffectSpec(const FAFContextHandle& Context, TSubclassOf InSpecClass); void OnApplied(); void OnExpired(); From be1baeef7158ce18a1d978092c939082cacb2fe5 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 22:09:55 +0100 Subject: [PATCH 067/187] compile fix --- .../Source/AbilityFramework/Effects/GAGameEffect.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 49ecfc5..8d8d196 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -49,7 +49,7 @@ void FAFEffectSpec::OnExecuted() FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& Context, TSubclassOf InSpecClass) : SpecClass(InSpecClass) { - Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); + Extension = NewObject<|UGAEffectExtension>(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); } float FAFEffectSpec::GetFloatFromAttributeMagnitude( From 66c4a7adb5c8b58c85753b95cdea8f149f89e06b Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 7 Mar 2018 22:11:37 +0100 Subject: [PATCH 068/187] another compile fix --- .../Source/AbilityFramework/Effects/GAGameEffect.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 8d8d196..775e7ed 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -49,7 +49,7 @@ void FAFEffectSpec::OnExecuted() FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& Context, TSubclassOf InSpecClass) : SpecClass(InSpecClass) { - Extension = NewObject<|UGAEffectExtension>(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); + Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); } float FAFEffectSpec::GetFloatFromAttributeMagnitude( From 5f2cb79a6bf8e07bef165edf532be7a96f59589c Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 8 Mar 2018 23:27:00 +0100 Subject: [PATCH 069/187] ARG-10 fixed issue where Effect Execution was garbage collected from EffectSpec --- ActionRPGGame.uproject | 5 +++++ .../Abilities/GAAbilityBase.cpp | 8 +++---- .../AbilityFramework/Effects/GAGameEffect.cpp | 3 ++- .../AbilityFramework/Effects/GAGameEffect.h | 22 +++++++++++-------- 4 files changed, 24 insertions(+), 14 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 4c10893..7cab892 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -186,6 +186,11 @@ "Name": "CustomAnimNode", "Enabled": true, "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" + }, + { + "Name": "Substance", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" } ], "TargetPlatforms": [ diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index a20499d..95a0b7b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -242,7 +242,7 @@ void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) void UGAAbilityBase::OnCooldownEffectExpired() { - UE_LOG(AbilityFramework, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); + UE_LOG(AFAbilities, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); if (CooldownEffectHandle.IsValid()) { @@ -270,13 +270,13 @@ void UGAAbilityBase::NativeOnAbilityActivationCancel() } void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) { - UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); + UE_LOG(AFAbilities, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); OnPeriod(); } void UGAAbilityBase::FinishAbility() { - UE_LOG(AbilityFramework, Log, TEXT("FinishExecution in ability %s"), *GetName()); + UE_LOG(AFAbilities, Log, TEXT("FinishExecution in ability %s"), *GetName()); OnAbilityFinished(); NativeFinishAbility(); AbilityState = EAFAbilityState::Waiting; @@ -284,7 +284,7 @@ void UGAAbilityBase::FinishAbility() } void UGAAbilityBase::NativeFinishAbility() { - UE_LOG(AbilityFramework, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); + UE_LOG(AFAbilities, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); AbilityComponent->ExecutingAbility = nullptr; OnConfirmDelegate.Clear(); OnConfirmDelegate.RemoveAll(this); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 775e7ed..36047ff 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -46,9 +46,10 @@ void FAFEffectSpec::OnExecuted() Extension->NativeOnEffectExecuted(); } } -FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& Context, TSubclassOf InSpecClass) +FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass) : SpecClass(InSpecClass) { + Context = InContext; Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 8da2b6e..90fb100 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -2,6 +2,8 @@ //#include "GAGlobalTypes.h" #include "GAEffectGlobalTypes.h" #include "GameplayTagContainer.h" +#include "UObject/ObjectMacros.h" +#include "UObject/GCObject.h" #include "GAGameEffect.generated.h" DECLARE_STATS_GROUP(TEXT("GameEffect"), STATGROUP_GameEffect, STATCAT_Advanced); @@ -405,13 +407,12 @@ struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBas /* */ -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFEffectSpec + +struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject { - GENERATED_BODY() private: - UPROPERTY() - class UGAEffectExtension* Extension; //week ptr ? + FAFContextHandle Context; + UGAEffectExtension* Extension; //week ptr ? TSubclassOf SpecClass; public: @@ -425,7 +426,7 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : Extension(nullptr) {} - FAFEffectSpec(const FAFContextHandle& Context, TSubclassOf InSpecClass); + FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass); void OnApplied(); void OnExpired(); @@ -458,6 +459,11 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec return SpecClass; } + virtual void AddReferencedObjects(FReferenceCollector& Collector) override + { + Collector.AddReferencedObject(Extension, Context.GetPtr()->Target.Get()); + } + }; USTRUCT(BlueprintType) struct FAFEffectSpecHandle @@ -522,11 +528,9 @@ struct TStructOpsTypeTraits< FAFEffectSpecHandle > : public TStructOpsTypeTraits */ struct FAFEffectParams; -USTRUCT(BlueprintType) + struct ABILITYFRAMEWORK_API FGAEffectProperty { - GENERATED_BODY() - protected: TWeakObjectPtr ApplicationRequirement; From e6dd0023aa48039f8de494105d723a3d39357aab Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 9 Mar 2018 00:06:49 +0100 Subject: [PATCH 070/187] check if extension class is valid before trying to create it --- .../Source/AbilityFramework/Effects/GABlueprintLibrary.cpp | 1 + .../Source/AbilityFramework/Effects/GAGameEffect.cpp | 3 ++- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 106a16e..87afc4c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -84,6 +84,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( FAFContextHandle Context; FAFEffectSpecHandle EffectSpecHandle; + //only reused Spec and Context if effect is instant ? if (Handle.IsValid()) { FAFContextHandle ExistingContext = InEffect.GetContext(Handle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 36047ff..25f6e9a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -50,7 +50,8 @@ FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); + if(InSpecClass.GetDefaultObject()->Extension) + Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); } float FAFEffectSpec::GetFloatFromAttributeMagnitude( From 556748f8ef5e5e6e73907fe87b8fdb8cc5c54367 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 9 Mar 2018 00:09:24 +0100 Subject: [PATCH 071/187] set extension to nullptr --- .../Source/AbilityFramework/Effects/GAGameEffect.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 25f6e9a..56d78ba 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -50,6 +50,7 @@ FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOfExtension) Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); } From ec165f34994a80495b40bde1fc0b6472af2349cb Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 9 Mar 2018 00:26:17 +0100 Subject: [PATCH 072/187] attach camera boom to socket on skeletal mesh --- Source/ActionRPGGame/ARCharacter.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 1ab32f7..3f35102 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -56,7 +56,9 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) // Create a camera boom (pulls in towards the player if there is a collision) CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); - CameraBoom->SetupAttachment(RootComponent); + //CameraBoom->SetupAttachment(GetMesh()); + CameraBoom->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, TEXT("headSocket")); + CameraBoom->TargetArmLength = 250; // The camera follows at this distance behind the character CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller CameraBoom->SocketOffset = FVector(0, 30, 95); From dcb7c506c383d72f539a1a670a8fb482b1013e98 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 9 Mar 2018 21:56:28 +0100 Subject: [PATCH 073/187] change name to better reflect functionality --- .../Source/AbilityFramework/Effects/GAGameEffect.cpp | 2 +- .../Source/AbilityFramework/Effects/GAGameEffect.h | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 56d78ba..76449e3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -178,7 +178,7 @@ void FGAEffectProperty::ApplyExecute(const FGAEffectHandle& InHandle Application->ApplyExecute(InHandle, InParams, Modifier); } -void FGAEffectProperty::EffectExecution( +void FGAEffectProperty::ExecuteEffect( const FGAEffectHandle& HandleIn , FGAEffectMod& ModIn , const FAFEffectParams& InParams diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 90fb100..8b8963f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -588,7 +588,7 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - void EffectExecution(const FGAEffectHandle& HandleIn + void ExecuteEffect(const FGAEffectHandle& HandleIn , FGAEffectMod& ModIn , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); From 423d80381d06db43c1ba05c8333fb530d55373a7 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 9 Mar 2018 22:16:27 +0100 Subject: [PATCH 074/187] fixed issue where clicking Edit button on effect property caused invalid layout display --- Config/DefaultGameplayTags.ini | 3 + .../AbilityFramework/AFEffectsComponent.cpp | 4 +- .../AFEffectCustomizationCommon.cpp | 4 +- .../GAEffectClassStructWidget.cpp | 3 +- .../GAEffectDetails.cpp | 3 +- .../AFEffectCustomizationCommon.cpp | 114 ++++++++++++++++++ 6 files changed, 125 insertions(+), 6 deletions(-) create mode 100644 enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 165eeaa..6d1169d 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -38,6 +38,9 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="AI.WoodCollected",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +GameplayTagList=(Tag="Damage",DevComment="") ++GameplayTagList=(Tag="Effect.InstancedDuration",DevComment="") ++GameplayTagList=(Tag="EffectEvent.Expired.InstancedDuration",DevComment="") ++GameplayTagList=(Tag="Fire",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 4d7d200..0148303 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -156,8 +156,6 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn , Context , HandleIn); - //execute period regardless if this periodic effect ? Or maybe change name OnEffectExecuted ? - EffectSpec.OnExecuted(); ExecuteEffectEvent(Property.GetSpec()->OnPeriodEvent); @@ -165,7 +163,7 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn if (CueHandle) MulticastExecuteEffectCue(*CueHandle); - Property.EffectExecution(HandleIn, Mod, Params, Modifier); + Property.ExecuteEffect(HandleIn, Mod, Params, Modifier); PostExecuteEffect(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp index 4fb874d..ea1ff60 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp @@ -4,6 +4,7 @@ #include "Effects/GAGameEffect.h" #include "DetailLayoutBuilder.h" #include "DetailCategoryBuilder.h" +#include "IDetailGroup.h" #include "AFEffectCustomizationCommon.h" FAFEffectCustomizationCommon::FAFEffectCustomizationCommon() @@ -16,8 +17,8 @@ FAFEffectCustomizationCommon::~FAFEffectCustomizationCommon() void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, TSharedPtr& InProperty, FName InCategory) { - IDetailCategoryBuilder& DurationCategory = DetailLayout.EditCategory(InCategory); + TSharedPtr DurationCalcTypeProp = InProperty->GetChildHandle("CalculationType"); uint8 CalcType = 0; @@ -40,6 +41,7 @@ void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& D TSharedPtr Value = DirectModifier->GetChildHandle("Value"); DurationCategory.AddProperty(Value.ToSharedRef()); + //DetailGroup. break; } case 1: //AttributeBased diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp index 3ee44fb..2eedb36 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp @@ -711,7 +711,8 @@ FReply FGAEffectClassStructWidget::OnEditButtonClicked() } else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass())) { - DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + // DetailView->UnregisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass()); + // DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); } } if(!Class) diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp index 3b0417f..b96e65c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp @@ -107,5 +107,6 @@ void FGAEffectDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) } void FGAEffectDetails::OnDurationPolicyChange() { - MyDetailLayout->ForceRefreshDetails(); + if(MyDetailLayout) + MyDetailLayout->ForceRefreshDetails(); } \ No newline at end of file diff --git a/enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp b/enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp new file mode 100644 index 0000000..580c6d5 --- /dev/null +++ b/enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp @@ -0,0 +1,114 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFrameworkEditor.h" +#include "Effects/GAGameEffect.h" +#include "DetailLayoutBuilder.h" +#include "DetailCategoryBuilder.h" +#include "IDetailGroup.h" +#include "AFEffectCustomizationCommon.h" + +FAFEffectCustomizationCommon::FAFEffectCustomizationCommon() +{ +} + +FAFEffectCustomizationCommon::~FAFEffectCustomizationCommon() +{ +} +void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, + TSharedPtr& InProperty, FName InCategory) +{ + IDetailCategoryBuilder& DurationCategory = DetailLayout.EditCategory(InCategory); + //DurationCategory. + //DurationCategory.HeaderContent(SNew(STextBlock).Text(FText::FromName(InCategory))); + //IDetailGroup& DetailGroup = DurationCategory.AddGroup(InCategory,FText::FromName(InCategory), false, true); + + TSharedPtr DurationCalcTypeProp = InProperty->GetChildHandle("CalculationType"); + + uint8 CalcType = 0; + DurationCalcTypeProp->GetValue(CalcType); + + TSharedPtr DirectModifier = InProperty->GetChildHandle("DirectModifier"); + TSharedPtr AttributeBased = InProperty->GetChildHandle("AttributeBased"); + TSharedPtr CurveBased = InProperty->GetChildHandle("CurveBased"); + TSharedPtr Custom = InProperty->GetChildHandle("Custom"); + + DurationCategory.AddProperty(DurationCalcTypeProp.ToSharedRef()); + switch (CalcType) + { + case 0: //Direct + { + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Value = DirectModifier->GetChildHandle("Value"); + DurationCategory.AddProperty(Value.ToSharedRef()); + //DetailGroup. + break; + } + case 1: //AttributeBased + { + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Source = AttributeBased->GetChildHandle("Source"); + TSharedPtr Attribute = AttributeBased->GetChildHandle("Attribute"); + TSharedPtr Coefficient = AttributeBased->GetChildHandle("Coefficient"); + TSharedPtr PreMultiply = AttributeBased->GetChildHandle("PreMultiply"); + TSharedPtr PostMultiply = AttributeBased->GetChildHandle("PostMultiply"); + TSharedPtr PostCoefficient = AttributeBased->GetChildHandle("PostCoefficient"); + TSharedPtr bUseSecondaryAttribute = AttributeBased->GetChildHandle("bUseSecondaryAttribute"); + TSharedPtr SecondarySource = AttributeBased->GetChildHandle("SecondarySource"); + TSharedPtr SecondaryAttribute = AttributeBased->GetChildHandle("SecondaryAttribute"); + + DurationCategory.AddProperty(Source.ToSharedRef()); + DurationCategory.AddProperty(Attribute.ToSharedRef()); + DurationCategory.AddProperty(Coefficient.ToSharedRef()); + DurationCategory.AddProperty(PreMultiply.ToSharedRef()); + DurationCategory.AddProperty(PostMultiply.ToSharedRef()); + DurationCategory.AddProperty(PostCoefficient.ToSharedRef()); + DurationCategory.AddProperty(bUseSecondaryAttribute.ToSharedRef()); + DurationCategory.AddProperty(SecondarySource.ToSharedRef()); + DurationCategory.AddProperty(SecondaryAttribute.ToSharedRef()); + + break; + } + case 2: //CurveBased + { + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Source = CurveBased->GetChildHandle("Source"); + TSharedPtr Attribute = CurveBased->GetChildHandle("Attribute"); + TSharedPtr CurveTable = CurveBased->GetChildHandle("CurveTable"); + + DurationCategory.AddProperty(Source.ToSharedRef()); + DurationCategory.AddProperty(Attribute.ToSharedRef()); + DurationCategory.AddProperty(CurveTable.ToSharedRef()); + break; + } + case 3: //CustomCalculation + { + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(Custom); + + TSharedPtr CustomCalculation = Custom->GetChildHandle("CustomCalculation"); + DurationCategory.AddProperty(CustomCalculation.ToSharedRef()); + break; + } + } +} +void FAFEffectCustomizationCommon::HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName) +{ + UProperty* prop = UGAGameEffectSpec::StaticClass()->FindPropertyByName(InName); + + TSharedPtr Property = DetailLayout.GetProperty(InName, UGAGameEffectSpec::StaticClass()); + DetailLayout.HideProperty(Property); +} \ No newline at end of file From f963fbcea7ec700a60432d7bb5160e0edbe1ddf6 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Mar 2018 00:32:43 +0100 Subject: [PATCH 075/187] ARG-6 Effect Extension now support GameplayTasks properly. Simple task for listetning for effect events is working --- Config/DefaultGameplayTags.ini | 1 + .../AbilityFramework/AFEffectsComponent.cpp | 51 ++++++-- .../AbilityFramework/AFEffectsComponent.h | 14 ++- .../Effects/EffectTasks/AFEffectTask.h | 14 ++- .../EffectTasks/AFEffectTask_EffectEvent.cpp | 14 ++- .../EffectTasks/AFEffectTask_EffectEvent.h | 2 +- .../Effects/GABlueprintLibrary.cpp | 2 +- .../Effects/GAEffectExtension.cpp | 71 +++++------ .../Effects/GAEffectExtension.h | 36 +++--- .../AbilityFramework/Effects/GAGameEffect.cpp | 9 +- .../AFEffectCustomizationCommon.cpp | 114 ------------------ 11 files changed, 133 insertions(+), 195 deletions(-) delete mode 100644 enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 6d1169d..08107d6 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -7,6 +7,7 @@ NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") ++GameplayTagList=(Tag="Ability.DurationInstance",DevComment="") +GameplayTagList=(Tag="Ability.EffectInstance",DevComment="") +GameplayTagList=(Tag="Ability.EffectInstance.Damage",DevComment="") +GameplayTagList=(Tag="Ability.Input.GolsterWeapon",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 0148303..0507b00 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -15,7 +15,8 @@ #include "Effects/GABlueprintLibrary.h" // Sets default values for this component's properties -UAFEffectsComponent::UAFEffectsComponent() +UAFEffectsComponent::UAFEffectsComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) { // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features // off to improve performance if you don't need them. @@ -61,10 +62,12 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( for (const FGameplayTag& Tag : AppliedEventTags) { - if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + if (TArray* Events = EffectEvents.Find(Tag)) { - Event->Broadcast(Data); + for (const FAFEventDelegate& Event : *Events) + Event.Execute(Data); } + } if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) { @@ -142,9 +145,13 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn FAFEventData Data; for (const FGameplayTag& Tag : ExecuteEventTags) { - if (FAFEventDelegate* Event = EffectEvents.Find(Tag)) + if (TArray* Events = EffectEvents.Find(Tag)) { - Event->Broadcast(Data); + TArray& EventsRef = *Events; + for (const FAFEventDelegate& Event : EventsRef) + { + Event.Execute(Data); + } } } @@ -280,24 +287,48 @@ void UAFEffectsComponent::RemoveEffectEvent(const FGameplayTag& InEventTag) UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); OnEffectEvent.Remove(InEventTag); } -FAFEventDelegate& UAFEffectsComponent::GetTagEvent(FGameplayTag TagIn) +TArray& UAFEffectsComponent::GetTagEvent(FGameplayTag TagIn) { - FAFEventDelegate& Delegate = EffectEvents.FindChecked(TagIn); + TArray& Delegate = EffectEvents.FindChecked(TagIn); return Delegate; } void UAFEffectsComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) { - FAFEventDelegate* Delegate = EffectEvents.Find(TagIn); + TArray* Delegate = EffectEvents.Find(TagIn); if (Delegate) { - if (Delegate->IsBound()) + for (const FAFEventDelegate& Event : *Delegate) { - Delegate->Broadcast(InEventData); + if (Event.IsBound()) + { + Event.Execute(InEventData); + } } } } +void UAFEffectsComponent::AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) +{ + TArray& Events = EffectEvents.FindOrAdd(EventTag); + Events.Add(EventDelegate); +} + +void UAFEffectsComponent::RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) +{ + TArray* Events = EffectEvents.Find(EventTag); + if (Events) + { + + int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) + { + return Other.GetHandle() == EventDelegate; + }); + + Events->RemoveAt(Idx, 1, true); + } +} + bool UAFEffectsComponent::IsEffectActive(const FGAEffectHandle& InHandle) const { return GameEffectContainer.IsEffectActive(InHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index e0a7a22..4267b46 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" +#include "GameplayTasksComponent.h" #include "GameplayTags.h" #include "GameplayTagAssetInterface.h" @@ -16,10 +17,10 @@ #include "AFEffectsComponent.generated.h" DECLARE_DELEGATE(FAFEffectEvent); -DECLARE_MULTICAST_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); +DECLARE_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent +class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent//public UActorComponent { GENERATED_BODY() private: @@ -43,7 +44,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent TMap OnEffectApplyToTarget; TMap OnEffectApplyToSelf; - TMap EffectEvents; + TMap> EffectEvents; TMap PropertyByHandle; TMap EffectToCue; @@ -52,7 +53,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent public: // Sets default values for this component's properties - UAFEffectsComponent(); + UAFEffectsComponent(const FObjectInitializer& ObjectInitializer); protected: // Called when the game starts @@ -136,7 +137,10 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent void RemoveEffectEvent(const FGameplayTag& InEventTag); bool IsEffectActive(const FGAEffectHandle& InHandle) const; - FAFEventDelegate& GetTagEvent(FGameplayTag TagIn); + + void AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); + void RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); + TArray& GetTagEvent(FGameplayTag TagIn); void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); public: bool DenyEffectApplication(const FGameplayTagContainer& InTags); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index a63c2e2..0330719 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -29,15 +29,17 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask T* MyObj = NewObject(WorldContextObject); UGAEffectExtension* ThisAbility = CastChecked(WorldContextObject); - /* if (UGAAbilityTask* CachedTask = ThisAbility->GetAbilityTask(InTaskName)) + if (UAFEffectTask** CachedTask = ThisAbility->Tasks.Find(InTaskName)) { - return Cast(CachedTask); - }*/ + return Cast(*CachedTask); + } //MyObj->Effect = ThisAbility; - //MyObj->EffectsComponent = ThisAbility->OwningComponent; - //MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); - //MyObj->InstanceName = InstanceName; + MyObj->EffectsComponent = ThisAbility->OwningComponent; + MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); + MyObj->InstanceName = InstanceName; //ThisAbility->AddAbilityTask(InTaskName, MyObj); + ThisAbility->Tasks.Add(InTaskName, MyObj); + //ThisAbility->Dupa.Add(MyObj); return MyObj; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp index b6b1802..d386bdc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -2,6 +2,7 @@ #include "AbilityFramework.h" #include "../../AFAbilityInterface.h" +#include "AFEffectsComponent.h" #include "AFEffectTask_EffectEvent.h" @@ -13,13 +14,13 @@ UAFEffectTask_EffectEvent::UAFEffectTask_EffectEvent(const FObjectInitializer& O } -UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UObject* OwningExtension, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) { - auto MyObj = NewEffectTask(OwningExtension); + auto MyObj = NewEffectTask(OwningExtension, TaskName); MyObj->Tag = Tag; MyObj->SetExternalTarget(OptionalExternalTarget); MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - + return MyObj; } @@ -28,7 +29,10 @@ void UAFEffectTask_EffectEvent::Activate() UAFEffectsComponent* ASC = GetTargetASC(); if (ASC) { - MyHandle = ASC->EffectEvents.FindOrAdd(Tag).AddUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); + //(this, &UAFEffectTask_EffectEvent::GameplayEventCallback + FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); + MyHandle = Delegate.GetHandle(); + ASC->AddEvent(Tag, Delegate); } Super::Activate(); @@ -75,7 +79,7 @@ void UAFEffectTask_EffectEvent::OnDestroy(bool AbilityEnding) UAFEffectsComponent* ASC = GetTargetASC(); if (ASC && MyHandle.IsValid()) { - ASC->EffectEvents.FindOrAdd(Tag).Remove(MyHandle); + ASC->RemoveEvent(Tag, MyHandle); } Super::OnDestroy(AbilityEnding); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h index c123a25..1a7cea5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -21,7 +21,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask FAFEffectEventDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectEvent* ListenEffectEvent(UObject* OwningExtension, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + static UAFEffectTask_EffectEvent* ListenEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp index 87afc4c..b8c4ed5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp @@ -85,7 +85,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( FAFEffectSpecHandle EffectSpecHandle; //only reused Spec and Context if effect is instant ? - if (Handle.IsValid()) + if (Handle.IsValid() && !bPeriodicEffect) { FAFContextHandle ExistingContext = InEffect.GetContext(Handle); if (ExistingContext.IsValid()) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp index 0f1b6cc..08ea366 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp @@ -1,7 +1,8 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" -#include "../AFAbilityComponent.h" +#include "AbilityFramework.h" +#include "AFEffectsComponent.h" +#include "Effects/EffectTasks/AFEffectTask.h" #include "GAEffectExtension.h" UGAEffectExtension::UGAEffectExtension(const FObjectInitializer& ObjectInitializer) @@ -33,39 +34,39 @@ void UGAEffectExtension::NativeOnEffectRemoved() OnEffectRemoved(); } /** GameplayTaskOwnerInterface - Begin */ -//void UGAEffectExtension::OnGameplayTaskInitialized(UGameplayTask& Task) -//{ -// //if (UGAAbilityTask* task = Cast(&Task)) -// //{ -// // task->Ability = this; -// //} -//} -//UGameplayTasksComponent* UGAEffectExtension::GetGameplayTasksComponent(const UGameplayTask& Task) const -//{ -// return OwningComponent; -//} -///** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ -//void UGAEffectExtension::OnGameplayTaskActivated(UGameplayTask& Task) -//{ -// UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); -// ActiveTasks.Add(&Task); -// //AbilityComponent->OnGameplayTaskActivated(Task); -//} -///** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ -//void UGAEffectExtension::OnGameplayTaskDeactivated(UGameplayTask& Task) -//{ -// UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); -// ActiveTasks.Remove(&Task); -// //AbilityComponent->OnGameplayTaskDeactivated(Task); -//} -//AActor* UGAEffectExtension::GetGameplayTaskOwner(const UGameplayTask* Task) const -//{ -// return OwningComponent->GetOwner(); -//} -//AActor* UGAEffectExtension::GetGameplayTaskAvatar(const UGameplayTask* Task) const -//{ -// return Avatar; -//} +void UGAEffectExtension::OnGameplayTaskInitialized(UGameplayTask& Task) +{ + if (UAFEffectTask* task = Cast(&Task)) + { + task->Effect = this; + } +} +UGameplayTasksComponent* UGAEffectExtension::GetGameplayTasksComponent(const UGameplayTask& Task) const +{ + return OwningComponent; +} +/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ +void UGAEffectExtension::OnGameplayTaskActivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Add(&Task); + //AbilityComponent->OnGameplayTaskActivated(Task); +} +/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ +void UGAEffectExtension::OnGameplayTaskDeactivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Remove(&Task); + //AbilityComponent->OnGameplayTaskDeactivated(Task); +} +AActor* UGAEffectExtension::GetGameplayTaskOwner(const UGameplayTask* Task) const +{ + return OwningComponent->GetOwner(); +} +AActor* UGAEffectExtension::GetGameplayTaskAvatar(const UGameplayTask* Task) const +{ + return OwningComponent->GetOwner(); +} /** GameplayTaskOwnerInterface - end */ UWorld* UGAEffectExtension::GetWorld() const diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h index f185909..4640cc3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h @@ -19,7 +19,7 @@ Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). */ UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject //, public IGameplayTaskOwnerInterface +class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplayTaskOwnerInterface { GENERATED_BODY() public: @@ -30,7 +30,11 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject //, public IGamep UPROPERTY() class AActor* Avatar; - TSet ActiveTasks; + UPROPERTY() + TSet ActiveTasks; + + UPROPERTY() + TMap Tasks; public: UGAEffectExtension(const FObjectInitializer& ObjectInitializer); @@ -61,25 +65,25 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject //, public IGamep void NativeOnEffectRemoved(); /** GameplayTaskOwnerInterface - Begin */ - //virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; - ///** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ - ///** Get owner of a task or default one when task is null */ - //virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; + virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; + /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ + /** Get owner of a task or default one when task is null */ + virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; - ///** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ - //virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; + /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ + virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; - ///** Get default priority for running a task */ - //virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; + /** Get default priority for running a task */ + virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; - ///** Notify called after GameplayTask finishes initialization (not active yet) */ - //virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; + /** Notify called after GameplayTask finishes initialization (not active yet) */ + virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; - ///** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ - //virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ + virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - ///** Notify called after GameplayTask changes state from Active (finishing or pausing) */ - //virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; + /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ + virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; /** GameplayTaskOwnerInterface - end */ virtual UWorld* GetWorld() const override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 76449e3..630502c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -51,8 +51,11 @@ FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOfExtension) + if (InSpecClass.GetDefaultObject()->Extension) + { Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); + Extension->OwningComponent = Context.GetPtr()->TargetInterface->GetEffectsComponent(); + } } float FAFEffectSpec::GetFloatFromAttributeMagnitude( @@ -433,7 +436,9 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( } } - + //right place ? + Params.GetSpec().OnApplied(); + FGAEffectContext& InContext = Params.GetContext(); if (InProperty.GetSpec()->IfHaveTagEffect.RequiredTag.IsValid() diff --git a/enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp b/enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp deleted file mode 100644 index 580c6d5..0000000 --- a/enc_temp_folder/3b5a84dac6b4c7d3e6963bed5c9c0/AFEffectCustomizationCommon.cpp +++ /dev/null @@ -1,114 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFrameworkEditor.h" -#include "Effects/GAGameEffect.h" -#include "DetailLayoutBuilder.h" -#include "DetailCategoryBuilder.h" -#include "IDetailGroup.h" -#include "AFEffectCustomizationCommon.h" - -FAFEffectCustomizationCommon::FAFEffectCustomizationCommon() -{ -} - -FAFEffectCustomizationCommon::~FAFEffectCustomizationCommon() -{ -} -void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, - TSharedPtr& InProperty, FName InCategory) -{ - IDetailCategoryBuilder& DurationCategory = DetailLayout.EditCategory(InCategory); - //DurationCategory. - //DurationCategory.HeaderContent(SNew(STextBlock).Text(FText::FromName(InCategory))); - //IDetailGroup& DetailGroup = DurationCategory.AddGroup(InCategory,FText::FromName(InCategory), false, true); - - TSharedPtr DurationCalcTypeProp = InProperty->GetChildHandle("CalculationType"); - - uint8 CalcType = 0; - DurationCalcTypeProp->GetValue(CalcType); - - TSharedPtr DirectModifier = InProperty->GetChildHandle("DirectModifier"); - TSharedPtr AttributeBased = InProperty->GetChildHandle("AttributeBased"); - TSharedPtr CurveBased = InProperty->GetChildHandle("CurveBased"); - TSharedPtr Custom = InProperty->GetChildHandle("Custom"); - - DurationCategory.AddProperty(DurationCalcTypeProp.ToSharedRef()); - switch (CalcType) - { - case 0: //Direct - { - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(Custom); - - TSharedPtr Value = DirectModifier->GetChildHandle("Value"); - DurationCategory.AddProperty(Value.ToSharedRef()); - //DetailGroup. - break; - } - case 1: //AttributeBased - { - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(Custom); - - TSharedPtr Source = AttributeBased->GetChildHandle("Source"); - TSharedPtr Attribute = AttributeBased->GetChildHandle("Attribute"); - TSharedPtr Coefficient = AttributeBased->GetChildHandle("Coefficient"); - TSharedPtr PreMultiply = AttributeBased->GetChildHandle("PreMultiply"); - TSharedPtr PostMultiply = AttributeBased->GetChildHandle("PostMultiply"); - TSharedPtr PostCoefficient = AttributeBased->GetChildHandle("PostCoefficient"); - TSharedPtr bUseSecondaryAttribute = AttributeBased->GetChildHandle("bUseSecondaryAttribute"); - TSharedPtr SecondarySource = AttributeBased->GetChildHandle("SecondarySource"); - TSharedPtr SecondaryAttribute = AttributeBased->GetChildHandle("SecondaryAttribute"); - - DurationCategory.AddProperty(Source.ToSharedRef()); - DurationCategory.AddProperty(Attribute.ToSharedRef()); - DurationCategory.AddProperty(Coefficient.ToSharedRef()); - DurationCategory.AddProperty(PreMultiply.ToSharedRef()); - DurationCategory.AddProperty(PostMultiply.ToSharedRef()); - DurationCategory.AddProperty(PostCoefficient.ToSharedRef()); - DurationCategory.AddProperty(bUseSecondaryAttribute.ToSharedRef()); - DurationCategory.AddProperty(SecondarySource.ToSharedRef()); - DurationCategory.AddProperty(SecondaryAttribute.ToSharedRef()); - - break; - } - case 2: //CurveBased - { - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(Custom); - - TSharedPtr Source = CurveBased->GetChildHandle("Source"); - TSharedPtr Attribute = CurveBased->GetChildHandle("Attribute"); - TSharedPtr CurveTable = CurveBased->GetChildHandle("CurveTable"); - - DurationCategory.AddProperty(Source.ToSharedRef()); - DurationCategory.AddProperty(Attribute.ToSharedRef()); - DurationCategory.AddProperty(CurveTable.ToSharedRef()); - break; - } - case 3: //CustomCalculation - { - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(Custom); - - TSharedPtr CustomCalculation = Custom->GetChildHandle("CustomCalculation"); - DurationCategory.AddProperty(CustomCalculation.ToSharedRef()); - break; - } - } -} -void FAFEffectCustomizationCommon::HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName) -{ - UProperty* prop = UGAGameEffectSpec::StaticClass()->FindPropertyByName(InName); - - TSharedPtr Property = DetailLayout.GetProperty(InName, UGAGameEffectSpec::StaticClass()); - DetailLayout.HideProperty(Property); -} \ No newline at end of file From 2c2c66321650a601db7b9a02815fb922b7415098 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Mar 2018 12:34:19 +0100 Subject: [PATCH 076/187] ARG-13 added more granular and varied events generated by effects --- Config/DefaultGameplayTags.ini | 1 + .../AbilityFramework/AFEffectsComponent.cpp | 86 +++++++++++++++--- .../AbilityFramework/AFEffectsComponent.h | 24 ++++- .../AFEffectTask_AppliedEffectEvent.cpp | 86 ++++++++++++++++++ .../AFEffectTask_AppliedEffectEvent.h | 49 +++++++++++ .../AFEffectTask_EffectAppliedToSelf.cpp | 84 ++++++++++++++++++ .../AFEffectTask_EffectAppliedToSelf.h | 50 +++++++++++ .../AFEffectTask_EffectAppliedToTarget.cpp | 87 +++++++++++++++++++ .../AFEffectTask_EffectAppliedToTarget.h | 50 +++++++++++ .../AFEffectTask_ExecutedEffectEvent.cpp | 86 ++++++++++++++++++ .../AFEffectTask_ExecutedEffectEvent.h | 49 +++++++++++ .../AbilityFramework/Effects/GAGameEffect.cpp | 5 ++ .../AbilityFramework/Effects/GAGameEffect.h | 4 + 13 files changed, 646 insertions(+), 15 deletions(-) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 08107d6..a01e5d5 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -41,6 +41,7 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Damage",DevComment="") +GameplayTagList=(Tag="Effect.InstancedDuration",DevComment="") +GameplayTagList=(Tag="EffectEvent.Expired.InstancedDuration",DevComment="") ++GameplayTagList=(Tag="Event.Executed.Damage.Fire",DevComment="") +GameplayTagList=(Tag="Fire",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index 0507b00..a76739d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -69,6 +69,8 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( } } + OnAppliedToSelf.Broadcast(Params.Context, Params.Property, Params.EffectSpec); + if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) { Delegate->ExecuteIfBound(); @@ -102,13 +104,15 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( MulticastApplyEffectCue(CueParams, CueHandle); } + OnAppliedToTarget.Broadcast(Params.Context, Params.Property, Params.EffectSpec); + if (InContext.TargetComp.IsValid()) { FGAEffectHandle Handle; Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InHandle, Params, Modifier); - if (!PropertyByHandle.Contains(Handle)) - PropertyByHandle.Add(Handle, &InProperty); - + //if (!PropertyByHandle.Contains(Handle)) + // PropertyByHandle.Add(Handle, &InProperty); + EffectToCue.Add(Handle, CueHandle); return Handle; @@ -145,14 +149,7 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn FAFEventData Data; for (const FGameplayTag& Tag : ExecuteEventTags) { - if (TArray* Events = EffectEvents.Find(Tag)) - { - TArray& EventsRef = *Events; - for (const FAFEventDelegate& Event : EventsRef) - { - Event.Execute(Data); - } - } + TriggerExecuteEvent(Tag, Data); } //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); @@ -308,6 +305,73 @@ void UAFEffectsComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEve } } +void UAFEffectsComponent::AddAppliedEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) +{ + TArray& Events = AppliedEvents.FindOrAdd(EventTag); + Events.Add(EventDelegate); +} +void UAFEffectsComponent::RemoveAppliedEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) +{ + TArray* Events = AppliedEvents.Find(EventTag); + if (Events) + { + int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) + { + return Other.GetHandle() == EventDelegate; + }); + + Events->RemoveAt(Idx, 1, true); + } +} +void UAFEffectsComponent::TriggerAppliedEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + TArray* Delegate = AppliedEvents.Find(TagIn); + if (Delegate) + { + for (const FAFEventDelegate& Event : *Delegate) + { + if (Event.IsBound()) + { + Event.Execute(InEventData); + } + } + } +} + +void UAFEffectsComponent::AddExecuteEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) +{ + TArray& Events = ExecutedEvents.FindOrAdd(EventTag); + Events.Add(EventDelegate); +} +void UAFEffectsComponent::RemoveExecuteEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) +{ + TArray* Events = ExecutedEvents.Find(EventTag); + if (Events) + { + int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) + { + return Other.GetHandle() == EventDelegate; + }); + + Events->RemoveAt(Idx, 1, true); + } +} +void UAFEffectsComponent::TriggerExecuteEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + TArray* Delegate = ExecutedEvents.Find(TagIn); + if (Delegate) + { + for (const FAFEventDelegate& Event : *Delegate) + { + if (Event.IsBound()) + { + Event.Execute(InEventData); + } + } + } +} + + void UAFEffectsComponent::AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) { TArray& Events = EffectEvents.FindOrAdd(EventTag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index 4267b46..057be33 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -19,6 +19,8 @@ DECLARE_DELEGATE(FAFEffectEvent); DECLARE_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); +DECLARE_MULTICAST_DELEGATE_ThreeParams(FAFApplicationDelegate, FAFContextHandle, FAFPropertytHandle, FAFEffectSpecHandle); + UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent//public UActorComponent { @@ -46,11 +48,15 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent/ TMap OnEffectApplyToSelf; TMap> EffectEvents; - TMap PropertyByHandle; TMap EffectToCue; TMap OnEffectEvent; + TMap> AppliedEvents; + TMap> ExecutedEvents; +public: + FAFApplicationDelegate OnAppliedToTarget; + FAFApplicationDelegate OnAppliedToSelf; public: // Sets default values for this component's properties UAFEffectsComponent(const FObjectInitializer& ObjectInitializer); @@ -77,7 +83,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent/ * TMap OnEffectEvent - event is called before application; * TMap OnEffectApplyToSelf - event is called before application; * - * @param EffectIn* - Effect to apply + * @param EffectIn& - Effect to apply * @param InProperty - cached effect information * @param InContext - Context about effect application. Target, instigator, causer. * @param Modifier - optional modifier which can be applied to effect. @@ -97,7 +103,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent/ * Try launch events: * TMap OnEffectApplyToTarget - event is called before application * - * @param EffectIn* - Effect to apply + * @param EffectIn& - Effect to apply * @param InProperty - cached effect information * @param InContext - Context about effect application. Target, instigator, causer. * @param Modifier - optional modifier which can be applied to effect. @@ -137,11 +143,21 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent/ void RemoveEffectEvent(const FGameplayTag& InEventTag); bool IsEffectActive(const FGAEffectHandle& InHandle) const; - +public: void AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); void RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); TArray& GetTagEvent(FGameplayTag TagIn); void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + + void AddAppliedEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); + void RemoveAppliedEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); + void TriggerAppliedEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + + + void AddExecuteEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); + void RemoveExecuteEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); + void TriggerExecuteEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + public: bool DenyEffectApplication(const FGameplayTagContainer& InTags); bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp new file mode 100644 index 0000000..1df2db9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp @@ -0,0 +1,86 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_AppliedEffectEvent.h" + + + + +UAFEffectTask_AppliedEffectEvent::UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_AppliedEffectEvent* UAFEffectTask_AppliedEffectEvent::ListenAppliedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->Tag = Tag; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_AppliedEffectEvent::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_AppliedEffectEvent::GameplayEventCallback + FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_AppliedEffectEvent::GameplayEventCallback); + MyHandle = Delegate.GetHandle(); + ASC->AddAppliedEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_AppliedEffectEvent::GameplayEventCallback(FAFEventData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_AppliedEffectEvent::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_AppliedEffectEvent::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} + +void UAFEffectTask_AppliedEffectEvent::OnDestroy(bool AbilityEnding) +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC && MyHandle.IsValid()) + { + ASC->RemoveAppliedEvent(Tag, MyHandle); + } + + Super::OnDestroy(AbilityEnding); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h new file mode 100644 index 0000000..996ed71 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h @@ -0,0 +1,49 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "../../GAGlobalTypes.h" +#include "AFEffectTask_AppliedEffectEvent.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_AppliedEffectEvent* ListenAppliedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFEventData Payload); + + void OnDestroy(bool AbilityEnding) override; + + FGameplayTag Tag; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp new file mode 100644 index 0000000..0288262 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp @@ -0,0 +1,84 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_EffectAppliedToSelf.h" + + + + +UAFEffectTask_EffectAppliedToSelf::UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_EffectAppliedToSelf* UAFEffectTask_EffectAppliedToSelf::ListenEffectAppliedToSelf(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_EffectAppliedToSelf::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + MyHandle = ASC->OnAppliedToSelf.AddUObject(this, &UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback);//AddExecuteEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Context, Property, Spec); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_EffectAppliedToSelf::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_EffectAppliedToSelf::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} + +void UAFEffectTask_EffectAppliedToSelf::OnDestroy(bool AbilityEnding) +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC && MyHandle.IsValid()) + { + ASC->OnAppliedToSelf.Remove(MyHandle); + } + + Super::OnDestroy(AbilityEnding); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h new file mode 100644 index 0000000..bc7cbd3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "AFEffectTask_EffectAppliedToSelf.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_EffectAppliedToSelf* ListenEffectAppliedToSelf(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec); + + void OnDestroy(bool AbilityEnding) override; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp new file mode 100644 index 0000000..741e4f6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp @@ -0,0 +1,87 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_EffectAppliedToTarget.h" + + + + +UAFEffectTask_EffectAppliedToTarget::UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_EffectAppliedToTarget* UAFEffectTask_EffectAppliedToTarget::ListenEffectAppliedToTarget(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_EffectAppliedToTarget::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback + //FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback); + //MyHandle = Delegate.GetHandle(); + MyHandle = ASC->OnAppliedToTarget.AddUObject(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback);//AddExecuteEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Context, Property, Spec); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_EffectAppliedToTarget::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_EffectAppliedToTarget::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} + +void UAFEffectTask_EffectAppliedToTarget::OnDestroy(bool AbilityEnding) +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC && MyHandle.IsValid()) + { + ASC->OnAppliedToTarget.Remove(MyHandle); + } + + Super::OnDestroy(AbilityEnding); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h new file mode 100644 index 0000000..e231316 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "AFEffectTask_EffectAppliedToTarget.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_EffectAppliedToTarget* ListenEffectAppliedToTarget(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec); + + void OnDestroy(bool AbilityEnding) override; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp new file mode 100644 index 0000000..6aec49b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp @@ -0,0 +1,86 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_ExecutedEffectEvent.h" + + + + +UAFEffectTask_ExecutedEffectEvent::UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_ExecutedEffectEvent* UAFEffectTask_ExecutedEffectEvent::ListenExecutedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->Tag = Tag; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_ExecutedEffectEvent::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback + FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback); + MyHandle = Delegate.GetHandle(); + ASC->AddExecuteEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback(FAFEventData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_ExecutedEffectEvent::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_ExecutedEffectEvent::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} + +void UAFEffectTask_ExecutedEffectEvent::OnDestroy(bool AbilityEnding) +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC && MyHandle.IsValid()) + { + ASC->RemoveExecuteEvent(Tag, MyHandle); + } + + Super::OnDestroy(AbilityEnding); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h new file mode 100644 index 0000000..e437d45 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h @@ -0,0 +1,49 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "../../GAGlobalTypes.h" +#include "AFEffectTask_ExecutedEffectEvent.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_ExecutedEffectEvent : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_ExecutedEffectEvent* ListenExecutedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFEventData Payload); + + void OnDestroy(bool AbilityEnding) override; + + FGameplayTag Tag; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 630502c..3e57bcf 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -438,6 +438,11 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( } //right place ? Params.GetSpec().OnApplied(); + + FAFEventData EventData; + const FGameplayTagContainer& AppliedEvents = InProperty.GetSpec()->AppliedEventTags; + for(const FGameplayTag& Event : AppliedEvents) + OwningComponent->TriggerAppliedEvent(Event, EventData); FGAEffectContext& InContext = Params.GetContext(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 8b8963f..0e172d8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -959,8 +959,10 @@ struct TStructOpsTypeTraits< FAFPropertytHandle > : public TStructOpsTypeTraitsB }; }; +USTRUCT() struct FAFEffectParams { + GENERATED_BODY() //make this private and allow assign only trough constructr. FAFContextHandle Context; FAFPropertytHandle Property; @@ -968,6 +970,8 @@ struct FAFEffectParams bool bRecreated; bool bPeriodicEffect; public: + FAFEffectParams() + {}; FAFEffectParams(FAFPropertytHandle InProperty) : bRecreated(false) , Property(InProperty) From 5cdc03b8cf68228d04e113f4b4cbece0a960766d Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Mar 2018 15:08:44 +0100 Subject: [PATCH 077/187] ARG-16 aded 3 functions to access EffectSpec from blueprint --- .../Effects/AFEffectSpecFunctionLibrary.cpp | 50 ++++++++++++++++ .../Effects/AFEffectSpecFunctionLibrary.h | 57 +++++++++++++++++++ .../AbilityFramework/Effects/GAGameEffect.cpp | 1 + .../AbilityFramework/Effects/GAGameEffect.h | 4 ++ 4 files changed, 112 insertions(+) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp new file mode 100644 index 0000000..5d1704c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectSpecFunctionLibrary.h" + + + +void UAFEffectSpecFunctionLibrary::AppendOwnedTags(FAFEffectSpecHandle Spec, const FGameplayTagContainer& InTags) +{ + Spec.GetPtr()->OwnedTags.AppendTags(InTags); +} + +void UAFEffectSpecFunctionLibrary::CompareOwnedTags(FAFEffectSpecHandle Spec + , EAFTagContainerCompare Mode + , const FGameplayTagContainer& InTags + , EAFTagCompareResult& Result) +{ + switch (Mode) + { + case EAFTagContainerCompare::HasAny: + Spec.GetPtr()->OwnedTags.HasAny(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagContainerCompare::HasAnyExact: + Spec.GetPtr()->OwnedTags.HasAnyExact(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagContainerCompare::HasAll: + Spec.GetPtr()->OwnedTags.HasAll(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagContainerCompare::HasAllExact: + Spec.GetPtr()->OwnedTags.HasAllExact(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + default: + break; + } +} + +void UAFEffectSpecFunctionLibrary::CompareOwnedTag(FAFEffectSpecHandle Spec + , EAFTagCompare Mode + , FGameplayTag InTag + , EAFTagCompareResult& Result) +{ + switch (Mode) + { + case EAFTagCompare::HasTag: + Spec.GetPtr()->OwnedTags.HasTag(InTag) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagCompare::HasTagExact: + Spec.GetPtr()->OwnedTags.HasTagExact(InTag) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h new file mode 100644 index 0000000..7a9aa21 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h @@ -0,0 +1,57 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Kismet/BlueprintFunctionLibrary.h" +#include "Effects/GAGameEffect.h" +#include "AFEffectSpecFunctionLibrary.generated.h" +UENUM(BlueprintType) +enum class EAFTagCompareResult : uint8 +{ + Match, + NoMatch, +}; +UENUM() +enum class EAFTagContainerCompare : uint8 +{ + HasAny, + HasAnyExact, + HasAll, + HasAllExact, +}; + +UENUM() +enum class EAFTagCompare : uint8 +{ + HasTag, + HasTagExact +}; + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectSpecFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Spec") + static void AppendOwnedTags(FAFEffectSpecHandle Spec, const FGameplayTagContainer& InTags); + + + UFUNCTION(BlueprintCallable, meta = (ExpandEnumAsExecs = "Result"), Category = "AbilityFramework|Effects|Spec") + static void CompareOwnedTags(FAFEffectSpecHandle Spec + , EAFTagContainerCompare Mode + , const FGameplayTagContainer& InTags + , EAFTagCompareResult& Result); + + + UFUNCTION(BlueprintCallable, meta = (ExpandEnumAsExecs = "Result"), Category = "AbilityFramework|Effects|Spec") + static void CompareOwnedTag(FAFEffectSpecHandle Spec + , EAFTagCompare Mode + , FGameplayTag InTag + , EAFTagCompareResult& Result); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 3e57bcf..7e8d8e9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -56,6 +56,7 @@ FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); Extension->OwningComponent = Context.GetPtr()->TargetInterface->GetEffectsComponent(); } + OwnedTags.AppendTags(InSpecClass.GetDefaultObject()->OwnedTags); } float FAFEffectSpec::GetFloatFromAttributeMagnitude( diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 0e172d8..bc9c097 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -498,6 +498,10 @@ struct FAFEffectSpecHandle return SpecPtr.IsValid(); } + TSharedPtr GetPtr() + { + return SpecPtr; + } FAFEffectSpec& GetRef() { return SpecPtr.ToSharedRef().Get(); From 8f9864e6ba951b2cf62b17dcff285f606b00b0bc Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Mar 2018 19:28:59 +0100 Subject: [PATCH 078/187] disbaled debug drawing --- Source/ActionRPGGame/ARCharacter.cpp | 40 ++++++++++++++-------------- 1 file changed, 20 insertions(+), 20 deletions(-) diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 3f35102..10af9d7 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -170,7 +170,7 @@ void AARCharacter::Tick(float DeltaSeconds) FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal(); FVector LineEnd = (AccelerationDirection * 80.0f) + GetActorLocation(); - ::DrawDebugLine(GetWorld(), GetActorLocation(), LineEnd, FColor::Red, false, -1.0f, 0, 10); + //::DrawDebugLine(GetWorld(), GetActorLocation(), LineEnd, FColor::Red, false, -1.0f, 0, 10); FVector VelocityDirection = CurrentVelocity.GetSafeNormal(); @@ -178,7 +178,7 @@ void AARCharacter::Tick(float DeltaSeconds) FVector VelocityEnd = (VelocityDirection * Vel) + GetActorLocation(); - ::DrawDebugLine(GetWorld(), GetActorLocation()+FVector(0,0,10), VelocityEnd + FVector(0, 0, 10), FColor::Blue, false, -1.0f, 0, 10); + //::DrawDebugLine(GetWorld(), GetActorLocation()+FVector(0,0,10), VelocityEnd + FVector(0, 0, 10), FColor::Blue, false, -1.0f, 0, 10); FTransform Transform = GetTransform(); FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); @@ -195,7 +195,7 @@ void AARCharacter::Tick(float DeltaSeconds) FQuat QAngle = FQuat::FindBetweenNormals(Forward, LocalVelocity); FRotator RAngle(QAngle); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 145), "RAngle: " + FString::FormatAsNumber(RAngle.Yaw), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 145), "RAngle: " + FString::FormatAsNumber(RAngle.Yaw), nullptr, FColor::Red, 0, true); FVector V1 = (Forward + Right).GetSafeNormal2D(); @@ -242,14 +242,14 @@ void AARCharacter::Tick(float DeltaSeconds) } FourDirections = NewDir; - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 135), "OldFourDirections: " + DirToString(OldFourDirections), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 140), "FourDirections: " + DirToString(FourDirections), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 135), "OldFourDirections: " + DirToString(OldFourDirections), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 140), "FourDirections: " + DirToString(FourDirections), nullptr, FColor::Red, 0, true); float VelAccelDot = FVector::DotProduct(LocalVelocity, LocalAcceleration); int32 intDot = FMath::RoundToInt(VelAccelDot); OrientationDOT = VelAccelDot; - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 150), "VelAccelDot: " + FString::FormatAsNumber(intDot), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 155), "FVelAccelDot: " + FString::Printf(TEXT("%f"), VelAccelDot), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 150), "VelAccelDot: " + FString::FormatAsNumber(intDot), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 155), "FVelAccelDot: " + FString::Printf(TEXT("%f"), VelAccelDot), nullptr, FColor::Red, 0, true); float TargetForward = FVector::DotProduct(CurrentVelocity, Forward); @@ -258,14 +258,14 @@ void AARCharacter::Tick(float DeltaSeconds) float LateralForward = FVector::DotProduct(CurrentVelocity, Right); LateralDirection = FMath::FInterpConstantTo(LateralDirection, LateralForward, DeltaSeconds, 100.0f); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 165), "ForwardDirection: " + FString::Printf(TEXT("%f"), ForwardDirection), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 170), "LateralDirection: " + FString::Printf(TEXT("%f"), LateralDirection), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 165), "ForwardDirection: " + FString::Printf(TEXT("%f"), ForwardDirection), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 170), "LateralDirection: " + FString::Printf(TEXT("%f"), LateralDirection), nullptr, FColor::Red, 0, true); FString SVelocity = "V: " + FString::Printf(TEXT("%d"), FMath::RoundToInt(CurrentVelocity.Size())) + " LV: " + FString::Printf(TEXT("%f"), LocalVelocity.Size()); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 90), SVelocity, nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 90), SVelocity, nullptr, FColor::Red, 0, true); FString SAcceleration = "A: " + FString::Printf(TEXT("%d"), FMath::RoundToInt(CurrentAcceleration.Size())) + " LA: " + FString::Printf(TEXT("%f"), LocalAcceleration.Size()); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 95), SAcceleration, nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 95), SAcceleration, nullptr, FColor::Red, 0, true); FVector LocalVel = Transform.InverseTransformVector(CurrentVelocity); @@ -309,16 +309,16 @@ void AARCharacter::Tick(float DeltaSeconds) default: break; } - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 105), "OrientN: " + FString::FormatAsNumber(OrientN) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 110), "OrientS: " + FString::FormatAsNumber(OrientS) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct((-1)*Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 115), "OrientE: " + FString::FormatAsNumber(OrientE) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right, VelocityDirection)), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 120), "OrientW: " + FString::FormatAsNumber(OrientW) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right*(-1), VelocityDirection)), nullptr, FColor::Red, 0, true); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 125), "CurrentOrient: " + FString::FormatAsNumber(CurrentOrient), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 105), "OrientN: " + FString::FormatAsNumber(OrientN) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 110), "OrientS: " + FString::FormatAsNumber(OrientS) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct((-1)*Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 115), "OrientE: " + FString::FormatAsNumber(OrientE) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right, VelocityDirection)), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 120), "OrientW: " + FString::FormatAsNumber(OrientW) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right*(-1), VelocityDirection)), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 125), "CurrentOrient: " + FString::FormatAsNumber(CurrentOrient), nullptr, FColor::Red, 0, true); // FMath::RadiansToDegrees(FMath::Atan2(LocalVelocity.Y, LocalVelocity.X)); float VelAngle2 = (FMath::RoundToInt(VelAngle) + 360) / 360; - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 130), "VelAngle2: " + FString::FormatAsNumber(VelAngle2), nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 130), "VelAngle2: " + FString::FormatAsNumber(VelAngle2), nullptr, FColor::Red, 0, true); float DeltaVelocity = CurrentVelocity.Size()* DeltaSeconds; if (!CurrentAcceleration.IsZero()) @@ -346,10 +346,10 @@ void AARCharacter::Tick(float DeltaSeconds) float StopDistance = (CurVel / (4*CMC->GroundFriction *CMC->BrakingFrictionFactor * CMC->BrakingDecelerationWalking)); FVector Forward = VelocityDirection; FVector StopLocation = (Forward*StopDistance) + CharLocation; - DrawDebugSphere(GetWorld(), StopLocation, 6, 8, FColor::Green, false, 2, 0, 2); + //DrawDebugSphere(GetWorld(), StopLocation, 6, 8, FColor::Green, false, 2, 0, 2); } - DrawDebugSphere(GetWorld(), FinalDestination, 6, 8, FColor::Red, false, -1, 0, 2); + //DrawDebugSphere(GetWorld(), FinalDestination, 6, 8, FColor::Red, false, -1, 0, 2); float Offset = 20; for (float Idx = 1; Idx < 20; Idx++) { @@ -358,7 +358,7 @@ void AARCharacter::Tick(float DeltaSeconds) //DrawDebugSphere(GetWorld(), BetweenDestination, 6, 8, FColor::Red, false, -1, 0, 2); } FString SAngle = FString("Angle: ") + FString::FormatAsNumber(Angle2); - DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 80), SAngle, nullptr, FColor::Red, 0, true); + //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 80), SAngle, nullptr, FColor::Red, 0, true); //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 60), "4: Fourtant : " + FString::FormatAsNumber(Fourtant), nullptr, FColor::Red, 0, true); } ////////////////////////////////////////////////////////////////////////// From 4611683f211d391118acf62090c9d36ac055cc37 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 10 Mar 2018 20:41:36 +0100 Subject: [PATCH 079/187] ARG-17 added ability to apply other effects when main effect is applied --- .../AbilityFramework/Effects/GAGameEffect.cpp | 19 ++++++++----- .../AbilityFramework/Effects/GAGameEffect.h | 27 ++++++++++++++++--- 2 files changed, 35 insertions(+), 11 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 7e8d8e9..3409fab 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -446,19 +446,24 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( OwningComponent->TriggerAppliedEvent(Event, EventData); FGAEffectContext& InContext = Params.GetContext(); - - if (InProperty.GetSpec()->IfHaveTagEffect.RequiredTag.IsValid() - && InContext.GetTargetEffectsComponent()->HasTag(InProperty.GetSpec()->IfHaveTagEffect.RequiredTag)) + TArray& Effects = InProperty.GetSpec()->IfHaveTagEffect.Effects; + for (FAFConditionalEffect& Effect : Effects) { - - for (TSubclassOf& Effect : InProperty.GetSpec()->IfHaveTagEffect.Effects) + if (Effect.RequiredTag.IsValid() + && InContext.GetTargetEffectsComponent()->HasTag(Effect.RequiredTag)) { - FGAEffectProperty prop(Effect); //Hack. We need a way store handles for conditional effects. + FAFPropertytHandle PropertyNew(Effect.Effect); FGAEffectHandle Handle; - //UGABlueprintLibrary::ApplyEffect(Params.Property, Handle, InContext.Target.Get(), InContext.Instigator.Get(), InContext.Causer.Get(), InContext.HitResult); + Handle = UGABlueprintLibrary::ApplyEffect(PropertyNew + , Handle + , InContext.Target.Get() + , InContext.Instigator.Get() + , InContext.Causer.Get() + , InContext.HitResult); } } + return Handle; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index bc9c097..98cbcd6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -95,16 +95,22 @@ struct ABILITYFRAMEWORK_API FAFCueContainer }; USTRUCT(BlueprintType) -struct FAFConditionalEffectContainer +struct FAFConditionalEffect { GENERATED_BODY() -public: /* If target have this tag apply specified effects */ UPROPERTY(EditAnywhere) FGameplayTag RequiredTag; - UPROPERTY(EditAnywhere) - TArray> Effects; + TSubclassOf Effect; +}; +USTRUCT(BlueprintType) +struct FAFConditionalEffectContainer +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Effects; }; @@ -837,6 +843,16 @@ struct FAFPropertytHandle } }; + FAFPropertytHandle(TSubclassOf InSpecClass) + : ID(0) + { + SpecClass = InSpecClass; + if (!DataPtr.IsValid()) + { + DataPtr = MakeShareable(new FGAEffectProperty()); + } + }; + FAFPropertytHandle(const FAFPropertytHandle& Other) { SpecClass = Other.SpecClass; @@ -1201,6 +1217,9 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer TMap> TargetEffectByClass; + //Conditonally applied effects. Only duration/periodic. + //TMap ConditionalEffects; + UPROPERTY(NotReplicated) class UAFEffectsComponent* OwningComponent; public: From ad488c3c6a44521dc41148981047ffd2ce3fa179 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 22 Mar 2018 00:23:36 +0100 Subject: [PATCH 080/187] working on prototype HUD --- Source/ActionRPGGame/UI/ARHUDWidget.cpp | 12 -- Source/ActionRPGGame/UI/ARHUDWidget.h | 9 +- Source/ActionRPGGame/UI/ARUIComponent.cpp | 35 +++- Source/ActionRPGGame/UI/ARUIComponent.h | 23 +++ ...et.cpp => ARAbilityListSlotDragWidget.cpp} | 10 +- ...Widget.h => ARAbilityListSlotDragWidget.h} | 6 +- .../Abilities/ARAbilityListSlotDropWidget.cpp | 15 ++ ...Widget.h => ARAbilityListSlotDropWidget.h} | 4 +- .../UI/Abilities/ARAbilityListWidget.cpp | 15 ++ .../UI/Abilities/ARAbilityListWidget.h | 35 ++++ .../ARAbilityManagerSlotDropWidget.cpp | 15 -- .../ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp | 25 +++ .../ActionRPGGame/UI/HUD/AREnemyHealthBar.h | 24 +++ .../ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp | 5 + Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h | 17 ++ .../UI/HUD/ARHUDCrosshairInfo.cpp | 4 + .../ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h | 17 ++ .../ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp | 7 + Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h | 44 +++++ Source/ActionRPGGame/UI/SARCrosshairBase.cpp | 16 ++ Source/ActionRPGGame/UI/SARCrosshairBase.h | 20 ++ Source/ActionRPGGame/UI/SARDrawTestWidget.cpp | 185 ++++++++++++++++++ Source/ActionRPGGame/UI/SARDrawTestWidget.h | 35 ++++ 23 files changed, 535 insertions(+), 43 deletions(-) rename Source/ActionRPGGame/UI/Abilities/{ARAbilityManagerSlotDragWidget.cpp => ARAbilityListSlotDragWidget.cpp} (72%) rename Source/ActionRPGGame/UI/Abilities/{ARAbilityManagerSlotDragWidget.h => ARAbilityListSlotDragWidget.h} (81%) create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp rename Source/ActionRPGGame/UI/Abilities/{ARAbilityManagerSlotDropWidget.h => ARAbilityListSlotDropWidget.h} (79%) create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp create mode 100644 Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp create mode 100644 Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.h create mode 100644 Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp create mode 100644 Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h create mode 100644 Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.cpp create mode 100644 Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h create mode 100644 Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp create mode 100644 Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h create mode 100644 Source/ActionRPGGame/UI/SARCrosshairBase.cpp create mode 100644 Source/ActionRPGGame/UI/SARCrosshairBase.h create mode 100644 Source/ActionRPGGame/UI/SARDrawTestWidget.cpp create mode 100644 Source/ActionRPGGame/UI/SARDrawTestWidget.h diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.cpp b/Source/ActionRPGGame/UI/ARHUDWidget.cpp index 5ea9e85..10376e6 100644 --- a/Source/ActionRPGGame/UI/ARHUDWidget.cpp +++ b/Source/ActionRPGGame/UI/ARHUDWidget.cpp @@ -1,15 +1,3 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARHUDWidget.h" - - - - -void UARHUDWidget::NativeConstruct() -{ - Super::NativeConstruct(); - UPanelWidget* RootWidget = Cast(GetRootWidget()); - MainGrid = WidgetTree->ConstructWidget(UUniformGridPanel::StaticClass(), TEXT("MainGrid")); - RootWidget->AddChild(MainGrid); - // Bind delegates here. -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.h b/Source/ActionRPGGame/UI/ARHUDWidget.h index 112e6ac..eb25915 100644 --- a/Source/ActionRPGGame/UI/ARHUDWidget.h +++ b/Source/ActionRPGGame/UI/ARHUDWidget.h @@ -6,6 +6,8 @@ #include "Blueprint/UserWidget.h" #include "Blueprint/WidgetTree.h" #include "Components/UniformGridPanel.h" + +#include "UI/HUD/ARHUDPlayerInfo.h" #include "ARHUDWidget.generated.h" /** @@ -16,9 +18,6 @@ class ACTIONRPGGAME_API UARHUDWidget : public UUserWidget { GENERATED_BODY() protected: - UUniformGridPanel* MainGrid; -public: - virtual void NativeConstruct() override; - - + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARHUDPlayerInfo* PlayerInfo; }; diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 2357d2f..d192e22 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -5,13 +5,16 @@ #include "ARPlayerController.h" #include "Inventory/ARInventoryManagerWidget.h" + + + // Sets default values for this component's properties UARUIComponent::UARUIComponent() { // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; - + EnemyHealthBarClass = UAREnemyHealthBar::StaticClass(); // ... } @@ -38,6 +41,36 @@ void UARUIComponent::BeginPlay() InventoryManagerWidget->SetVisibility(ESlateVisibility::Collapsed); InventoryManagerWidget->AddToViewport(); } + + if (EnemyHealthBarClass) + { + EnemyHealthBarWidget = CreateWidget(MyPC, EnemyHealthBarClass); + EnemyHealthBarWidget->SetVisibility(ESlateVisibility::Collapsed); + EnemyHealthBarWidget->AddToViewport(); + } + + if (HUDWidgetClass) + { + HUDWidget = CreateWidget(MyPC, HUDWidgetClass); + HUDWidget->AddToViewport(); + } + + //DrawWidget = SNew(SHorizontalBox) + // +SHorizontalBox::Slot() + // .HAlign(EHorizontalAlignment::HAlign_Fill) + // .VAlign(EVerticalAlignment::VAlign_Center) + // [ + // SNew(SVerticalBox) + // +SVerticalBox::Slot() + // .HAlign(EHorizontalAlignment::HAlign_Center) + // .VAlign(EVerticalAlignment::VAlign_Fill) + // [ + // SAssignNew(CrosshairWidget2, SARDrawTestWidget) + // ] + // ]; + + //CrosshairWidget2->Brush = &Brush; + //GEngine->GameViewport->AddViewportWidgetContent(DrawWidget.ToSharedRef()); } } diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index 8c81ccf..e3289da 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -4,6 +4,10 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" +#include "UI/HUD/AREnemyHealthBar.h" +#include "ARHUDWidget.h" +#include "SARDrawTestWidget.h" + #include "ARUIComponent.generated.h" @@ -12,6 +16,9 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent { GENERATED_BODY() protected: + UPROPERTY(EditAnywhere, Category="Cross Hair") + FSlateBrush Brush; + UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf CrosshairClass; @@ -23,6 +30,22 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY() class UARInventoryManagerWidget* InventoryManagerWidget; + + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf EnemyHealthBarClass; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets") + UAREnemyHealthBar* EnemyHealthBarWidget; + + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf HUDWidgetClass; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets") + UARHUDWidget* HUDWidget; + + + TSharedPtr DrawWidget; + TSharedPtr CrosshairWidget2; public: // Sets default values for this component's properties UARUIComponent(); diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp similarity index 72% rename from Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp rename to Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp index b085552..508d6ea 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp @@ -1,19 +1,19 @@ // Fill out your copyright notice in the Description page of Project Settings. -#include "ARAbilityManagerSlotDragWidget.h" +#include "ARAbilityListSlotDragWidget.h" #include "Blueprint/WidgetBlueprintLibrary.h" #include "ARAbilityDragVisual.h" -#include "../../Abilities/ARAbilityManagerComponent.h" +#include "Abilities/ARAbilityManagerComponent.h" -FReply UARAbilityManagerSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry +FReply UARAbilityListSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) { return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; //return FReply::Unhandled(); } -void UARAbilityManagerSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry +void UARAbilityListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) { UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); @@ -21,7 +21,7 @@ void UARAbilityManagerSlotDragWidget::NativeOnDragDetected(const FGeometry& InGe { APlayerController* MyPC = Cast(AbilityManager->GetOwner()); UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); - DragIcon->AbilityManager = AbilityManager; + //DragIcon->AbilityManager = AbilityManager; DragDropOp->Payload = this; DragDropOp->DefaultDragVisual = DragIcon; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h similarity index 81% rename from Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.h rename to Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h index 242bff5..446cb65 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDragWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h @@ -5,16 +5,16 @@ #include "CoreMinimal.h" #include "UI/ARAbilityWidget.h" #include "AMTypes.h" -#include "ARAbilityManagerSlotDragWidget.generated.h" +#include "ARAbilityListSlotDragWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARAbilityManagerSlotDragWidget : public UARAbilityWidget +class ACTIONRPGGAME_API UARAbilityListSlotDragWidget : public UARAbilityWidget { GENERATED_BODY() -protected: +public: UPROPERTY(EditAnywhere, Category = "Config") FGameplayTag AbilityTag; public: diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp new file mode 100644 index 0000000..5efe42a --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityListSlotDropWidget.h" + +#include "ARAbilityListSlotDragWidget.h" +#include "Abilities/ARAbilityManagerComponent.h" + +bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UARAbilityListSlotDragWidget* Payload = Cast(InOperation->Payload); + + AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); + return true; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h similarity index 79% rename from Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h rename to Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h index f6361ee..a390003 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h @@ -5,13 +5,13 @@ #include "CoreMinimal.h" #include "UI/ARAbilityWidget.h" #include "AMTypes.h" -#include "ARAbilityManagerSlotDropWidget.generated.h" +#include "ARAbilityListSlotDropWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARAbilityManagerSlotDropWidget : public UARAbilityWidget +class ACTIONRPGGAME_API UARAbilityListSlotDropWidget : public UARAbilityWidget { GENERATED_BODY() protected: diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp new file mode 100644 index 0000000..2d27779 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityListWidget.h" +#include "ARAbilityListSlotDragWidget.h" + +#include "ARPlayerController.h" + +void UARAbilityListWidget::AddItem(TSubclassOf DragWidgetClass, const FGameplayTag& Ability) +{ + UARAbilityListSlotDragWidget* Item = CreateWidget(ARPC.Get(), DragWidgetClass); + Item->AbilityTag = Ability; + Items.Add(Item); + + ItemContainer->AddChild(Item); +} diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h new file mode 100644 index 0000000..6f4147c --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h @@ -0,0 +1,35 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "Components/WrapBox.h" +#include "ARAbilityListWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityListWidget : public UUserWidget +{ + GENERATED_BODY() +public: + TWeakObjectPtr ARPC; +protected: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UWrapBox* ItemContainer; + + //Currently Equiped abilities + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARAbilityListSlotDropWidget* Ability001Group001; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARAbilityListSlotDropWidget* Ability002Group001; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARAbilityListSlotDropWidget* Ability003Group001; + + UPROPERTY() + TArray Items; +public: + void AddItem(TSubclassOf DragWidgetClass, const FGameplayTag& Ability); +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp deleted file mode 100644 index 15dcede..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerSlotDropWidget.cpp +++ /dev/null @@ -1,15 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityManagerSlotDropWidget.h" - -#include "ARAbilityManagerSlotDragWidget.h" -#include "../../Abilities/ARAbilityManagerComponent.h" - -bool UARAbilityManagerSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - UARAbilityManagerSlotDragWidget* Payload = Cast(InOperation->Payload); - - AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); - return false; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp b/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp new file mode 100644 index 0000000..945c0ca --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AREnemyHealthBar.h" + + + + +void UAREnemyHealthBar::ReleaseSlateResources(bool bReleaseChildren) +{ + Super::ReleaseSlateResources(bReleaseChildren); +/* + MyTextBlock.Reset(); + HealthBar.Reset();*/ +} + +//TSharedRef UAREnemyHealthBar::RebuildWidget() +//{ +// MyTextBlock = SNew(STextBlock); +// MyTextBlock->SetText(FText::FromString("Test Widget")); +// +// HealthBar = SNew(SProgressBar); +// +// +// return MyTextBlock.ToSharedRef(); +//} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.h b/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.h new file mode 100644 index 0000000..ab149f2 --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Notifications/SProgressBar.h" +#include "AREnemyHealthBar.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UAREnemyHealthBar : public UUserWidget +{ + GENERATED_BODY() +public: + virtual void ReleaseSlateResources(bool bReleaseChildren) override; + //virtual TSharedRef RebuildWidget() override; +protected: +// TSharedPtr MyTextBlock; +// TSharedPtr HealthBar; +}; diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp new file mode 100644 index 0000000..6791db9 --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp @@ -0,0 +1,5 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHUDCrosshair.h" +#include "ARPlayerController.h" + diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h new file mode 100644 index 0000000..a7a4093 --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h @@ -0,0 +1,17 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARHUDCrosshair.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHUDCrosshair : public UARUMGWidgetBase +{ + GENERATED_BODY() +}; diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.cpp b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.cpp new file mode 100644 index 0000000..f955416 --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.cpp @@ -0,0 +1,4 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHUDCrosshairInfo.h" +#include "ARPlayerController.h" diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h new file mode 100644 index 0000000..46ae60f --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h @@ -0,0 +1,17 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARHUDCrosshairInfo.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHUDCrosshairInfo : public UARUMGWidgetBase +{ + GENERATED_BODY() +}; diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp new file mode 100644 index 0000000..c6fa8ce --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHUDPlayerInfo.h" + + + + diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h new file mode 100644 index 0000000..92dc524 --- /dev/null +++ b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h @@ -0,0 +1,44 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "Components/ProgressBar.h" + +#include "UI/Weapons/ARWeaponSlotWidget.h" +#include "UI/Abilities/ARAbilitySlotWidget.h" +#include "ARHUDPlayerInfo.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHUDPlayerInfo : public UUserWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UProgressBar* PlayerHealth; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UProgressBar* PlayerStamina; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UProgressBar* PlayerEnergy; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARAbilitySlotWidget* AbilityGroup001Slot001; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARAbilitySlotWidget* AbilityGroup001Slot002; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARAbilitySlotWidget* AbilityGroup001Slot003; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARWeaponSlotWidget* Weapon001; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARWeaponSlotWidget* Weapon002; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARWeaponSlotWidget* Weapon003; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UARWeaponSlotWidget* Weapon004; + +}; diff --git a/Source/ActionRPGGame/UI/SARCrosshairBase.cpp b/Source/ActionRPGGame/UI/SARCrosshairBase.cpp new file mode 100644 index 0000000..5618cda --- /dev/null +++ b/Source/ActionRPGGame/UI/SARCrosshairBase.cpp @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SARCrosshairBase.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SARCrosshairBase::Construct(const FArguments& InArgs) +{ + /* + ChildSlot + [ + // Populate the widget + ]; + */ +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Source/ActionRPGGame/UI/SARCrosshairBase.h b/Source/ActionRPGGame/UI/SARCrosshairBase.h new file mode 100644 index 0000000..068a0ca --- /dev/null +++ b/Source/ActionRPGGame/UI/SARCrosshairBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +/** + * + */ +class ACTIONRPGGAME_API SARCrosshairBase : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SARCrosshairBase) + {} + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); +}; diff --git a/Source/ActionRPGGame/UI/SARDrawTestWidget.cpp b/Source/ActionRPGGame/UI/SARDrawTestWidget.cpp new file mode 100644 index 0000000..3e5a1e3 --- /dev/null +++ b/Source/ActionRPGGame/UI/SARDrawTestWidget.cpp @@ -0,0 +1,185 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SARDrawTestWidget.h" +#include "Rendering/DrawElements.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SARDrawTestWidget::Construct(const FArguments& InArgs) +{ + + ProgressStep = 0.25f; + Progress = 0.0f; + /* + ChildSlot + [ + // Populate the widget + ]; + */ +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION +SARDrawTestWidget::SARDrawTestWidget() +{ + Brush = nullptr; +} +int32 SARDrawTestWidget::OnPaint(const FPaintArgs& Args + , const FGeometry& AllottedGeometry + , const FSlateRect& MyCullingRect + , FSlateWindowElementList& OutDrawElements + , int32 LayerId + , const FWidgetStyle& InWidgetStyle + , bool bParentEnabled) const +{ + /*TArray PointsUp; + PointsUp.Add(FVector2D(10, 0)); + PointsUp.Add(FVector2D(20, 0)); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsUp, ESlateDrawEffect::None, FLinearColor::White, true, 2); + + TArray PointsDown; + PointsDown.Add(FVector2D(-10, 0)); + PointsDown.Add(FVector2D(-20, 0)); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsDown, ESlateDrawEffect::None, FLinearColor::White, true, 2); + + TArray PointsLeft; + PointsLeft.Add(FVector2D(0, 10)); + PointsLeft.Add(FVector2D(0, 20)); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsLeft, ESlateDrawEffect::None, FLinearColor::White, true, 2); + + + TArray PointsRight; + PointsRight.Add(FVector2D(0, -10)); + PointsRight.Add(FVector2D(0, -20)); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsRight, ESlateDrawEffect::None, FLinearColor::White, true, 2);*/ + + + float X = FMath::Sin(FMath::DegreesToRadians(60.0f)); + float Y = FMath::Cos(FMath::DegreesToRadians(60.0f)); + FVector2D Dir(X, Y); + TArray PointsRight; + PointsRight.Add(Dir*10); + + + PointsRight.Add(Dir*30); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsRight, ESlateDrawEffect::None, FLinearColor::White, true, 2); + + float X2 = FMath::Sin(FMath::DegreesToRadians(-60.0f)); + float Y2 = FMath::Cos(FMath::DegreesToRadians(-60.0f)); + FVector2D Dir2(X2, Y2); + TArray PointsLeft; + PointsLeft.Add(FVector2D(Dir2 * 10)); + PointsLeft.Add(Dir2 * 30); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsLeft, ESlateDrawEffect::None, FLinearColor::White, true, 2); + + float X3 = FMath::Sin(FMath::DegreesToRadians(180.0f)); + float Y3 = FMath::Cos(FMath::DegreesToRadians(180.0f)); + FVector2D Dir3(X3, Y3); + TArray PointsTop; + PointsTop.Add(FVector2D(Dir3 * 10)); + PointsTop.Add(Dir3 * 30); + FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), PointsTop, ESlateDrawEffect::None, FLinearColor::White, true, 2); + + if (Brush) + { + FSlateLayoutTransform Transform(FVector2D(0, 0)); + FSlateDrawElement::MakeBox(OutDrawElements + , LayerId + , AllottedGeometry.ToPaintGeometry(FVector2D(128,128), Transform) + , Brush); + } + + + float Step = 3.0f; + int32 Steps = 30; + + //{ + // TArray CirclePoints; + // for (int32 Idx = 0; Idx < Steps; Idx++) + // { + // float XC = FMath::Sin(FMath::DegreesToRadians(Idx*Step) - 120); + // float YC = FMath::Cos(FMath::DegreesToRadians(Idx*Step) - 120); + // FVector2D CDir(XC, YC); + // CirclePoints.Add(FVector2D(CDir*40.0f)); + // } + // FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), CirclePoints, ESlateDrawEffect::None, FLinearColor::White, true, 12); + //} + //{ + // TArray ProgressPoints; + // for (int32 Idx = 0; Idx < Steps; Idx++) + // { + // float XC = FMath::Sin(FMath::DegreesToRadians(Idx*Step *Progress) - 120); + // float YC = FMath::Cos(FMath::DegreesToRadians(Idx*Step *Progress) - 120); + // FVector2D CDir(XC, YC); + // ProgressPoints.Add(FVector2D(CDir*40.0f)); + // } + // FSlateDrawElement::MakeLines(OutDrawElements, LayerId + 1, AllottedGeometry.ToPaintGeometry(), ProgressPoints, ESlateDrawEffect::None, FLinearColor::Red, true, 12); + //} + + //{ + // TArray CirclePoints; + // for (int32 Idx = 0; Idx < Steps; Idx++) + // { + // float XC = FMath::Sin(FMath::DegreesToRadians(Idx*Step) + 120); + // float YC = FMath::Cos(FMath::DegreesToRadians(Idx*Step) + 120); + // FVector2D CDir(XC, YC); + // CirclePoints.Add(FVector2D(CDir*40.0f)); + // } + // /* FPaintGeometry PG = AllottedGeometry.ToPaintGeometry(); + // FSlateRenderTransform RT; + + // PG.AppendTransform()*/ + // FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), CirclePoints, ESlateDrawEffect::None, FLinearColor::White, true, 12); + //} + //{ + // TArray ProgressPoints; + // for (int32 Idx = 0; Idx < Steps; Idx++) + // { + // float XC = FMath::Sin(FMath::DegreesToRadians(Idx*Step *Progress) + 120); + // float YC = FMath::Cos(FMath::DegreesToRadians(Idx*Step *Progress) + 120); + // FVector2D CDir(XC, YC); + // ProgressPoints.Add(FVector2D(CDir*40.0f)); + // } + // FSlateDrawElement::MakeLines(OutDrawElements, LayerId + 1, AllottedGeometry.ToPaintGeometry(), ProgressPoints, ESlateDrawEffect::None, FLinearColor::Red, true, 12); + //} + + //{ + // TArray CirclePoints; + // for (int32 Idx = 0; Idx < Steps; Idx++) + // { + // float XC = FMath::Sin(FMath::DegreesToRadians(Idx*Step) + 20); + // float YC = FMath::Cos(FMath::DegreesToRadians(Idx*Step) + 20); + // FVector2D CDir(XC, YC); + // CirclePoints.Add(FVector2D(CDir*40.0f)); + // } + // /* FPaintGeometry PG = AllottedGeometry.ToPaintGeometry(); + // FSlateRenderTransform RT; + + // PG.AppendTransform()*/ + // FSlateDrawElement::MakeLines(OutDrawElements, LayerId, AllottedGeometry.ToPaintGeometry(), CirclePoints, ESlateDrawEffect::None, FLinearColor::White, true, 12); + //} + //{ + // TArray ProgressPoints; + // for (int32 Idx = 0; Idx < Steps; Idx++) + // { + // float XC = FMath::Sin(FMath::DegreesToRadians(Idx*Step *Progress) + 20); + // float YC = FMath::Cos(FMath::DegreesToRadians(Idx*Step *Progress) + 20); + // FVector2D CDir(XC, YC); + // ProgressPoints.Add(FVector2D(CDir*40.0f)); + // } + // FSlateDrawElement::MakeLines(OutDrawElements, LayerId + 1, AllottedGeometry.ToPaintGeometry(), ProgressPoints, ESlateDrawEffect::None, FLinearColor::Red, true, 12); + //} + + return LayerId; +} +void SARDrawTestWidget::Tick(const FGeometry& AllottedGeometry + , const double InCurrentTime + , const float InDeltaTime) +{ + if (Progress > 1.0f) + { + Progress = 0; + } + else + { + Progress += (ProgressStep*InDeltaTime); + } +} diff --git a/Source/ActionRPGGame/UI/SARDrawTestWidget.h b/Source/ActionRPGGame/UI/SARDrawTestWidget.h new file mode 100644 index 0000000..3b2a91a --- /dev/null +++ b/Source/ActionRPGGame/UI/SARDrawTestWidget.h @@ -0,0 +1,35 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +/** + * + */ +class ACTIONRPGGAME_API SARDrawTestWidget : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SARDrawTestWidget) + {} + SLATE_END_ARGS() + SARDrawTestWidget(); + float Progress; + float ProgressStep; + FSlateBrush* Brush; + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + + virtual int32 OnPaint(const FPaintArgs& Args + , const FGeometry& AllottedGeometry + , const FSlateRect& MyCullingRect + , FSlateWindowElementList& OutDrawElements + , int32 LayerId + , const FWidgetStyle& InWidgetStyle + , bool bParentEnabled) const override; + + virtual void Tick(const FGeometry& AllottedGeometry + , const double InCurrentTime + , const float InDeltaTime) override; +}; From 713dd607fafbac5a63152fa6bcf4bf317e825fb5 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 22 Mar 2018 00:25:52 +0100 Subject: [PATCH 081/187] fixes --- ActionRPGGame.uproject | 12 +++++- Config/DefaultEngine.ini | 4 ++ Config/DefaultGameplayTags.ini | 1 + .../AbilityFramework/Effects/GAGameEffect.cpp | 2 - Source/ActionRPGGame/ARCharacter.cpp | 4 ++ Source/ActionRPGGame/ARCharacter.h | 2 + Source/ActionRPGGame/ARPlayerController.cpp | 40 +++++++++++++++++++ Source/ActionRPGGame/ARPlayerController.h | 3 ++ .../Abilities/ARAbilityManagerComponent.cpp | 12 ++++-- .../Abilities/ARAbilityManagerComponent.h | 18 +++++++-- Source/ActionRPGGame/ActionRPGGame.Build.cs | 6 +++ 11 files changed, 95 insertions(+), 9 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 7cab892..e7a5fe1 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -15,7 +15,9 @@ "Engine", "AIModule", "UMG", - "CoreUObject" + "CoreUObject", + "Slate", + "SlateCore" ] }, { @@ -191,6 +193,14 @@ "Name": "Substance", "Enabled": true, "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" + }, + { + "Name": "GameLiftServerSDK", + "Enabled": true + }, + { + "Name": "NoesisGUI", + "Enabled": true } ], "TargetPlatforms": [ diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 5e70f79..d1cbf4f 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -90,6 +90,8 @@ s.AsyncLoadingThreadEnabled=True [/Script/Engine.UserInterfaceSettings] bLoadWidgetsOnDedicatedServer=False +UIScaleRule=ShortestSide +UIScaleCurve=(EditorCurveData=(PreInfinityExtrap=RCCE_Constant,PostInfinityExtrap=RCCE_Constant,DefaultValue=340282346638528859811704183484516925440.000000,Keys=((Time=395.331543,Value=0.450000),(Time=668.674805,Value=0.670000),(Time=870.085693,Value=1.000000),(Time=8640.000000,Value=8.000000))),ExternalCurve=None) [/Script/AIModule.AISystem] HotSpotManagerClassName=/Script/AIModule.AIHotSpotManager @@ -171,4 +173,6 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 +[/Script/NoesisRuntime.NoesisSettings] +GlyphTextureSize=x4096 diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index a01e5d5..993be27 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -5,6 +5,7 @@ WarnOnInvalidTags=True FastReplication=False NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 ++GameplayTagList=(Tag="Ability.AbilityCooldow01.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.DurationInstance",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp index 3409fab..64304ce 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp @@ -423,8 +423,6 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( MarkArrayDirty(); AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &ActiveEffectInfos[newItem], InProperty); - - //InProperty.ApplyExecute(Handle, Params, Modifier); //generate it only on client, and apply prediction key from client. //if server replicates with valid key, then nothing happens. diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 10af9d7..6479af1 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -84,6 +84,10 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) Weapons = CreateDefaultSubobject(TEXT("Weapons")); + LegsCloth = CreateDefaultSubobject(TEXT("LegsCloth")); + LegsCloth->SetupAttachment(GetMesh()); + //LegsCloth->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetIncludingScale); + WeaponHolsteredRight = CreateDefaultSubobject(TEXT("WeaponHolsteredRight")); //HolsteredRightWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform); WeaponHolsteredRight->SetupAttachment(GetMesh(), WeaponSocket::HolsteredRightWeapon); diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 056b96d..e1e85bb 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -95,6 +95,8 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UPROPERTY(EditAnywhere, Category = "Default Abilities") TArray AbilitiesToGive; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* LegsCloth; //Weapons UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponHolsteredRight; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 8314e09..a423cf6 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -114,3 +114,43 @@ void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGamepl Inputs.Add(InInputTag); AbilityComp->SetAbilityToAction(InAbilityTag, Inputs, FAFOnAbilityReady()); } + +#if WITH_EDITOR +/* Get Screen Percentage */ +static const auto CVarScreenPercentage = IConsoleManager::Get().FindTConsoleVariableDataFloat(TEXT("r.SCreenPercentage")); +#endif WITH_EDITOR + +float AARPlayerController::GetObjectScreenRadius(AActor* InActor) +{ + float ScreenRadius; + int32 Width, Height; + FVector Viewlocation; + FRotator ViewRotation; // Not Used, but required for Function call + float CamFOV = 90.0f; //TODO: Replace With Function that returns camera FOV +#if WITH_EDITOR + float ScreenPerc = CVarScreenPercentage->GetValueOnGameThread() / 100.0f; +#endif WITH_EDITOR + + /* Get the size of the viewport, and the player cameras location. */ + GetViewportSize(Width, Height); + GetPlayerViewPoint(Viewlocation, ViewRotation); + +#if WITH_EDITOR + /* Factor in Screen Percentage & Quality Settings */ + Width *= ScreenPerc; + Height *= ScreenPerc; +#endif WITH_EDITOR + + /* Easy Way To Return The Size, Create a vector and scale it. Alternative would be to use FMath::Max3 */ + float SRad = FVector2D(Width, Height).Size(); + + /* Get Object Bounds (R) */ + float BoundingRadius = InActor->GetRootComponent()->Bounds.SphereRadius; + float DistanceToObject = FVector(InActor->GetActorLocation() - Viewlocation).Size(); + + /* Get Projected Screen Radius */ + ScreenRadius = FMath::Atan(BoundingRadius / DistanceToObject); + ScreenRadius *= SRad / FMath::DegreesToRadians(CamFOV); + + return ScreenRadius; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 413a8fd..690760e 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -48,4 +48,7 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController void InputShowHideAbilityManager(); void InputShowHideInventory(); void OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag); + + UFUNCTION(BlueprintPure, Category = "Hud") + float GetObjectScreenRadius(AActor* InActor); }; diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index 850fc50..ca82502 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -7,8 +7,8 @@ #include "DWBPFunctionLibrary.h" #include "SDraggableWindowWidget.h" - -#include "../UI/Abilities/ARAbilityManagerWidget.h" +#include "ARPlayerController.h" +#include "UI/Abilities/ARAbilityListWidget.h" // Sets default values for this component's properties UARAbilityManagerComponent::UARAbilityManagerComponent() @@ -32,8 +32,14 @@ void UARAbilityManagerComponent::BeginPlay() // ... if (ManagerWidgetClass) { - ManagerWidget = CreateWidget(OwnerPC, ManagerWidgetClass); + ManagerWidget = CreateWidget(OwnerPC, ManagerWidgetClass); ManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + ManagerWidget->ARPC = Cast(GetOwner()); + for (const FARAbilityItem& Ability : AvailableAbilities) + { + ManagerWidget->AddItem(DragWidgetClass, Ability.Ability); + } + ManagerWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(ManagerWidget, "Ability Manager"); ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); //ManagerWidget->AddToViewport(); diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h index 52a8ee7..8197352 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -13,7 +13,14 @@ #include "ARAbilityManagerComponent.generated.h" - +USTRUCT(BlueprintType) +struct FARAbilityItem +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FGameplayTag Ability; +}; UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerComponent { @@ -23,11 +30,16 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom TSubclassOf DragVisualClass; UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf ManagerWidgetClass; + TSubclassOf ManagerWidgetClass; + UPROPERTY(EditAnywhere, Category = "Widget Config") + TSubclassOf DragWidgetClass; UPROPERTY() - class UARAbilityManagerWidget* ManagerWidget; + class UARAbilityListWidget* ManagerWidget; + + UPROPERTY(EditAnywhere) + TArray AvailableAbilities; FDWWWindowHandle ManagerWindowHandle; public: diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index ac12157..9716be8 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -62,10 +62,16 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AbilityManager", "DraggableWindow" }); + PrivateDependencyModuleNames.AddRange(new string[] { "Noesis", "NoesisRuntime" }); if (Target.Type == TargetRules.TargetType.Editor) { PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" }); PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); } + + if (Target.Type == TargetRules.TargetType.Server) + { + PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); + } } } From 23c3b0c19604952ab438299ccf1d59013886d589 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 22 Mar 2018 18:51:01 +0100 Subject: [PATCH 082/187] new tags, bindings and gitignote --- .gitignore | 2 ++ Config/DefaultEngine.ini | 5 +-- Config/DefaultGameplayTags.ini | 4 +++ Config/DefaultInput.ini | 61 ++++++++++++++++++---------------- 4 files changed, 41 insertions(+), 31 deletions(-) diff --git a/.gitignore b/.gitignore index 891ee34..34cf27d 100644 --- a/.gitignore +++ b/.gitignore @@ -246,6 +246,8 @@ Binaries/ Plugins/ Plugins/* Content/* +Substance/ +Substance/* !Content/Blueprints/ !Plugins/AbilityFramework/Source !Plugins/AbilityFrameworkEditor/Source diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index d1cbf4f..f67c99c 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -131,6 +131,9 @@ gc.NumRetriesBeforeForcingGC=0 gc.ActorClusteringEnabled=True gc.BlueprintClusteringEnabled=True +[/Script/NoesisRuntime.NoesisSettings] +GlyphTextureSize=x4096 + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 @@ -173,6 +176,4 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 -[/Script/NoesisRuntime.NoesisSettings] -GlyphTextureSize=x4096 diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 993be27..46e8533 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -45,6 +45,10 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Event.Executed.Damage.Fire",DevComment="") +GameplayTagList=(Tag="Fire",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") ++GameplayTagList=(Tag="Input.Ability02",DevComment="") ++GameplayTagList=(Tag="Input.Ability02.Activate",DevComment="") ++GameplayTagList=(Tag="Input.Ability03",DevComment="") ++GameplayTagList=(Tag="Input.Ability03.Activate",DevComment="") +GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") +GameplayTagList=(Tag="Input.UI.Holster",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 4334455..395d014 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -32,39 +32,42 @@ bF11TogglesFullscreen=True bUseMouseForTouch=False bEnableMouseSmoothing=True bEnableFOVScaling=True -FOVScale=0.011110 -DoubleClickTime=0.200000 bCaptureMouseOnLaunch=True -DefaultViewportMouseCaptureMode=CapturePermanently_IncludingInitialMouseDown bDefaultViewportMouseLock=False -DefaultViewportMouseLockMode=LockOnCapture -+ActionMappings=(ActionName="Jump",Key=SpaceBar,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Jump",Key=Gamepad_FaceButton_Bottom,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Input.Gun.Shoot",Key=LeftMouseButton,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Input.Ability01.Activate",Key=One,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Input.Gun.Reload",Key=R,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="SwitchAbilitySet",Key=B,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="InputAbilityManager",Key=K,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Input.UI.WeaponNext",Key=MouseScrollUp,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Input.UI.WeaponPrevious",Key=MouseScrollDown,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="InputInventory",Key=I,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+ActionMappings=(ActionName="Input.UI.Holster",Key=O,bShift=False,bCtrl=False,bAlt=False,bCmd=False) -+AxisMappings=(AxisName="MoveForward",Key=W,Scale=1.000000) -+AxisMappings=(AxisName="MoveForward",Key=S,Scale=-1.000000) -+AxisMappings=(AxisName="MoveForward",Key=Up,Scale=1.000000) -+AxisMappings=(AxisName="MoveForward",Key=Down,Scale=-1.000000) -+AxisMappings=(AxisName="MoveForward",Key=Gamepad_LeftY,Scale=1.000000) -+AxisMappings=(AxisName="MoveRight",Key=A,Scale=-1.000000) -+AxisMappings=(AxisName="MoveRight",Key=D,Scale=1.000000) -+AxisMappings=(AxisName="MoveRight",Key=Gamepad_LeftX,Scale=1.000000) -+AxisMappings=(AxisName="TurnRate",Key=Gamepad_RightX,Scale=1.000000) -+AxisMappings=(AxisName="TurnRate",Key=Left,Scale=-1.000000) -+AxisMappings=(AxisName="TurnRate",Key=Right,Scale=1.000000) -+AxisMappings=(AxisName="Turn",Key=MouseX,Scale=1.000000) -+AxisMappings=(AxisName="LookUpRate",Key=Gamepad_RightY,Scale=1.000000) -+AxisMappings=(AxisName="LookUp",Key=MouseY,Scale=-1.000000) bAlwaysShowTouchInterface=False bShowConsoleOnFourFingerTap=True +bEnableGestureRecognizer=False +DefaultViewportMouseCaptureMode=CapturePermanently_IncludingInitialMouseDown +DefaultViewportMouseLockMode=LockOnCapture +FOVScale=0.011110 +DoubleClickTime=0.200000 ++ActionMappings=(ActionName="Jump",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=SpaceBar) ++ActionMappings=(ActionName="Jump",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Gamepad_FaceButton_Bottom) ++ActionMappings=(ActionName="Input.Gun.Shoot",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=LeftMouseButton) ++ActionMappings=(ActionName="Input.Gun.Reload",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=R) ++ActionMappings=(ActionName="SwitchAbilitySet",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=B) ++ActionMappings=(ActionName="InputAbilityManager",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=K) ++ActionMappings=(ActionName="Input.UI.WeaponNext",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollUp) ++ActionMappings=(ActionName="Input.UI.WeaponPrevious",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollDown) ++ActionMappings=(ActionName="InputInventory",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=I) ++ActionMappings=(ActionName="Input.UI.Holster",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=O) ++ActionMappings=(ActionName="Input.Ability01Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=One) ++ActionMappings=(ActionName="Input.Ability02.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Two) ++ActionMappings=(ActionName="Input.Ability03.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Three) ++AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=W) ++AxisMappings=(AxisName="MoveForward",Scale=-1.000000,Key=S) ++AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=Up) ++AxisMappings=(AxisName="MoveForward",Scale=-1.000000,Key=Down) ++AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=Gamepad_LeftY) ++AxisMappings=(AxisName="MoveRight",Scale=-1.000000,Key=A) ++AxisMappings=(AxisName="MoveRight",Scale=1.000000,Key=D) ++AxisMappings=(AxisName="MoveRight",Scale=1.000000,Key=Gamepad_LeftX) ++AxisMappings=(AxisName="TurnRate",Scale=1.000000,Key=Gamepad_RightX) ++AxisMappings=(AxisName="TurnRate",Scale=-1.000000,Key=Left) ++AxisMappings=(AxisName="TurnRate",Scale=1.000000,Key=Right) ++AxisMappings=(AxisName="Turn",Scale=1.000000,Key=MouseX) ++AxisMappings=(AxisName="LookUpRate",Scale=1.000000,Key=Gamepad_RightY) ++AxisMappings=(AxisName="LookUp",Scale=-1.000000,Key=MouseY) DefaultTouchInterface=/Engine/MobileResources/HUD/DefaultVirtualJoysticks.DefaultVirtualJoysticks ConsoleKey=None -ConsoleKeys=Tilde From 867dfaf76814f8b2c74e62162a2ebcd70eeb9b80 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 22 Mar 2018 18:58:23 +0100 Subject: [PATCH 083/187] added bool to indicate if window should be destroyed on closing or just being hidden --- .../Source/DraggableWindow/SDraggableWindowWidget.cpp | 8 +++++++- .../Source/DraggableWindow/SDraggableWindowWidget.h | 1 + .../ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp | 1 + 3 files changed, 9 insertions(+), 1 deletion(-) diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp index fe4e4f6..a930314 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp @@ -156,6 +156,7 @@ void SDraggableWindowWidget::Construct(const FArguments& InArgs) { CurrentSize = FVector2D(1, 1); ResizingState = EDDWState::NoResize; + bDestroyOnClose = true; SetVisibility(EVisibility::SelfHitTestInvisible); FSimpleDelegate OnPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnPressed); FSimpleDelegate OnReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnReleased); @@ -590,7 +591,12 @@ void SDraggableWindowWidget::SetHandle(const FDWWWindowHandle& InHandle) } void SDraggableWindowWidget::OnCloseButtonPressed() { - FDWManager::Get().RemoveWindow(Handle); + if(bDestroyOnClose) + FDWManager::Get().RemoveWindow(Handle); + else + { + SetVisibility(EVisibility::Collapsed); + } } void SDraggableWindowWidget::OnPressed() { diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h index 2377228..13e96bc 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h +++ b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h @@ -128,6 +128,7 @@ class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget friend struct FDWWWindowHandle; friend class SDraggableDesktopWidget; friend class FDWManager; + bool bDestroyOnClose; protected: EDDWState ResizingState; diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index ca82502..d419392 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -41,6 +41,7 @@ void UARAbilityManagerComponent::BeginPlay() } ManagerWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(ManagerWidget, "Ability Manager"); + ManagerWindowHandle.Window.Pin()->bDestroyOnClose = false; ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); //ManagerWidget->AddToViewport(); } From ddf126cce44e790b7d96e53a154e8c106f57b15e Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 22 Mar 2018 20:12:16 +0100 Subject: [PATCH 084/187] ability manager will now display abilities icons --- .../Abilities/ARAbilityListSlotDragWidget.cpp | 47 ++++++++++++++++++- .../Abilities/ARAbilityListSlotDragWidget.h | 6 +++ .../Abilities/ARAbilityListSlotDropWidget.cpp | 6 ++- .../Abilities/ARAbilityListSlotDropWidget.h | 3 ++ .../UI/Abilities/ARAbilityListWidget.cpp | 2 +- 5 files changed, 60 insertions(+), 4 deletions(-) diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp index 508d6ea..492c311 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp @@ -5,6 +5,8 @@ #include "ARAbilityDragVisual.h" #include "Abilities/ARAbilityManagerComponent.h" +#include "Abilities/ARAbilityBase.h" +#include "Abilities/ARAbilityUIData.h" FReply UARAbilityListSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) @@ -20,12 +22,53 @@ void UARAbilityListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeome if (DragDropOp) { APlayerController* MyPC = Cast(AbilityManager->GetOwner()); - UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); + //UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); //DragIcon->AbilityManager = AbilityManager; DragDropOp->Payload = this; - DragDropOp->DefaultDragVisual = DragIcon; + DragDropOp->DefaultDragVisual = IconImage; OutOperation = DragDropOp; } } + +void UARAbilityListSlotDragWidget::OnItemAdded() +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("AbilityTagSearch", AbilityTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityListSlotDragWidget::OnItemLoaded, PrimaryAssetId); + + Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } + } +} + +void UARAbilityListSlotDragWidget::OnItemLoaded(FPrimaryAssetId InPrimaryAssetId) +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); + TSubclassOf AbilityClass = Cast(loaded); + if (AbilityClass) + { + IconImage->SetBrushFromTexture(AbilityClass.GetDefaultObject()->UIData->Icon); + } + + { + Manager->UnloadPrimaryAsset(InPrimaryAssetId); + } + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h index 446cb65..4f69c68 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h @@ -17,6 +17,9 @@ class ACTIONRPGGAME_API UARAbilityListSlotDragWidget : public UARAbilityWidget public: UPROPERTY(EditAnywhere, Category = "Config") FGameplayTag AbilityTag; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* IconImage; public: virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) override; @@ -28,4 +31,7 @@ class ACTIONRPGGAME_API UARAbilityListSlotDragWidget : public UARAbilityWidget return AbilityTag; } + void OnItemAdded(); +protected: + void OnItemLoaded(FPrimaryAssetId InPrimaryAssetId); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp index 5efe42a..0e21731 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp @@ -9,7 +9,11 @@ bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) { UARAbilityListSlotDragWidget* Payload = Cast(InOperation->Payload); - + FSlateBrush brush = Payload->IconImage->Brush; + AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); + + IconImage->SetBrush(brush); + return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h index a390003..a19830d 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h @@ -19,6 +19,9 @@ class ACTIONRPGGAME_API UARAbilityListSlotDropWidget : public UARAbilityWidget EAMGroup AbilityGroup; UPROPERTY(EditAnywhere, Category = "Config") EAMSlot AbilitySlot; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* IconImage; public: virtual bool NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp index 2d27779..7d28091 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp @@ -10,6 +10,6 @@ void UARAbilityListWidget::AddItem(TSubclassOf(ARPC.Get(), DragWidgetClass); Item->AbilityTag = Ability; Items.Add(Item); - + Item->OnItemAdded(); ItemContainer->AddChild(Item); } From 552530aab0b849068f2d7a564747b89e4f720f58 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 22 Mar 2018 23:20:15 +0100 Subject: [PATCH 085/187] added widget to show ability cooldown on crosshair --- Config/DefaultInput.ini | 2 +- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 2 +- Source/ActionRPGGame/UI/ARAbilityWidget.h | 4 +-- .../UI/Abilities/ARAbilityCrosshairInfo.cpp | 31 +++++++++++++++++++ .../UI/Abilities/ARAbilityCrosshairInfo.h | 29 +++++++++++++++++ .../UI/Abilities/ARAbilityInfoWidget.cpp | 15 +++++++++ .../UI/Abilities/ARAbilityInfoWidget.h | 7 +++++ .../UI/Abilities/ARAbilitySlotWidget.cpp | 20 ++++++------ 8 files changed, 96 insertions(+), 14 deletions(-) create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp create mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 395d014..9c13984 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -51,7 +51,7 @@ DoubleClickTime=0.200000 +ActionMappings=(ActionName="Input.UI.WeaponPrevious",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollDown) +ActionMappings=(ActionName="InputInventory",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=I) +ActionMappings=(ActionName="Input.UI.Holster",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=O) -+ActionMappings=(ActionName="Input.Ability01Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=One) ++ActionMappings=(ActionName="Input.Ability01.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=One) +ActionMappings=(ActionName="Input.Ability02.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Two) +ActionMappings=(ActionName="Input.Ability03.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Three) +AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=W) diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index df26e91..e262ccd 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -39,7 +39,7 @@ UTexture2D* UARAbilityWidget::GetIcon() if (Icon) return Icon; - if (!AbilityManager) + if (!AbilityManager.IsValid()) return nullptr; //return nullptr; diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index 8750211..a75cc05 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -19,8 +19,8 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase { GENERATED_BODY() public: - UPROPERTY() - class UARAbilityManagerComponent* AbilityManager; + + TWeakObjectPtr AbilityManager; UPROPERTY(EditAnywhere, Category = "Config") UTexture2D* Icon; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp new file mode 100644 index 0000000..e4b6887 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARAbilityCrosshairInfo.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "Abilities/GAAbilityBase.h" +#include "ARPlayerController.h" +#include "Abilities/ARAbilityBase.h" +#include "Abilities/ARAbilityManagerComponent.h" + +void UARAbilityCrosshairInfo::NativePreConstruct() +{ + Super::NativePreConstruct(); + + CrosshairImage->SetBrushFromMaterial(CrosshairMaterial); +} +void UARAbilityCrosshairInfo::NativeConstruct() +{ + Super::NativeConstruct(); + + CrosshairImage->SetBrushFromMaterial(CrosshairMaterial); +} + +void UARAbilityCrosshairInfo::NativeTick(const FGeometry& MyGeometry, float InDeltaTime) +{ + Super::NativeTick(MyGeometry, InDeltaTime); + + float CooldownRemaining = FMath::GetMappedRangeValueClamped(FVector2D(0, 1), FVector2D(1, 0), GetRemainingCooldown()); + + CrosshairImage->GetDynamicMaterial()->SetScalarParameterValue(TEXT("Percentage"), CooldownRemaining); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h new file mode 100644 index 0000000..4cbc484 --- /dev/null +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARUMGWidgetBase.h" +#include "GameplayTags.h" +#include "Abilities/GAAbilityBase.h" +#include "ARAbilityInfoWidget.h" +#include "ARAbilityCrosshairInfo.generated.h" +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARAbilityCrosshairInfo : public UARAbilityInfoWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Config") + UMaterialInterface* CrosshairMaterial; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* CrosshairImage; +public: + virtual void NativePreConstruct() override; + virtual void NativeConstruct() override; + virtual void NativeTick(const FGeometry& MyGeometry, float InDeltaTime) override; +}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp index 724863a..c1f877e 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp @@ -5,3 +5,18 @@ #include "AFAbilityComponent.h" #include "Abilities/GAAbilityBase.h" #include "ARPlayerController.h" +#include "Abilities/ARAbilityBase.h" +#include "Abilities/ARAbilityManagerComponent.h" + +float UARAbilityInfoWidget::GetRemainingCooldown() const +{ + if (!AbilityManager.IsValid()) + return 0; + + UGAAbilityBase* Ability = AbilityManager->GetAbility(AbilityGroup, AbilitySlot); + if (Ability) + { + return Ability->GetCooldownRemainingTimeNormalized(); + } + return 0; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h index 0e652c2..d2e3121 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h @@ -16,4 +16,11 @@ UCLASS() class ACTIONRPGGAME_API UARAbilityInfoWidget : public UARAbilityWidget { GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Ability") + EAMSlot AbilitySlot; + UPROPERTY(EditAnywhere, Category = "Ability") + EAMGroup AbilityGroup; + + float GetRemainingCooldown() const; }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp index d738f09..573ebd7 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp @@ -10,35 +10,35 @@ float UARAbilitySlotWidget::GetActivationRemainingTime() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationRemainingTime() : 0; } float UARAbilitySlotWidget::GetActivationRemainingTimeNormalized() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationRemainingTimeNormalized() : 0; } float UARAbilitySlotWidget::GetActivationCurrentTime() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationCurrentTime() : 0; } float UARAbilitySlotWidget::GetActivationCurrentTimeNormalized() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationCurrentTimeNormalized() : 0; } float UARAbilitySlotWidget::GetActivationEndTime() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetActivationEndTime() : 0; @@ -46,35 +46,35 @@ float UARAbilitySlotWidget::GetActivationEndTime() float UARAbilitySlotWidget::GetCooldownRemainingTime() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownRemainingTime() : 0; } float UARAbilitySlotWidget::GetCooldownRemainingTimeNormalized() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownRemainingTimeNormalized() : 0; } float UARAbilitySlotWidget::GetCooldownCurrentTime() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownCurrentTime() : 0; } float UARAbilitySlotWidget::GetCooldownCurrentTimeNormalized() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownCurrentTimeNormalized() : 0; } float UARAbilitySlotWidget::GetCooldownEndTime() { - if (!AbilityManager) + if (!AbilityManager.IsValid()) return 0; UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); return Ability ? Ability->GetCooldownEndTime() : 0; From be59737b6893af61c27c6109d8c4af3ce77459c9 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 23 Mar 2018 20:42:36 +0100 Subject: [PATCH 086/187] add base classes for weapon managing GUI --- Source/ActionRPGGame/ARPlayerController.cpp | 2 +- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 14 ---- Source/ActionRPGGame/UI/ARAbilityWidget.h | 8 +- .../UI/Abilities/ARAbilityListWidget.h | 7 ++ .../UI/Weapons/ARWeaponBaseWidget.h | 5 +- .../UI/Weapons/ARWeaponListSlotDragWidget.cpp | 73 +++++++++++++++++++ ...gWidget.h => ARWeaponListSlotDragWidget.h} | 14 +++- .../UI/Weapons/ARWeaponListSlotDropWidget.cpp | 20 +++++ ...pWidget.h => ARWeaponListSlotDropWidget.h} | 7 +- .../UI/Weapons/ARWeaponListWidget.cpp | 37 ++++++++++ .../UI/Weapons/ARWeaponListWidget.h | 39 ++++++++++ .../Weapons/ARWeaponManagerSlotDragWidget.cpp | 31 -------- .../Weapons/ARWeaponManagerSlotDropWidget.cpp | 18 ----- .../UI/Weapons/ARWeaponManagerWidget.cpp | 25 ------- .../UI/Weapons/ARWeaponManagerWidget.h | 23 ------ .../Weapons/ARWeaponManagerComponent.cpp | 43 ++++++++++- .../Weapons/ARWeaponManagerComponent.h | 21 +++++- 17 files changed, 257 insertions(+), 130 deletions(-) create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp rename Source/ActionRPGGame/UI/Weapons/{ARWeaponManagerSlotDragWidget.h => ARWeaponListSlotDragWidget.h} (66%) create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp rename Source/ActionRPGGame/UI/Weapons/{ARWeaponManagerSlotDropWidget.h => ARWeaponListSlotDropWidget.h} (68%) create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index a423cf6..9d99176 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -97,7 +97,7 @@ void AARPlayerController::InputShowHideAbilityManager() } void AARPlayerController::InputShowHideInventory() { - UIComponent->ShowHideInventory(); + WeaponManager->ShowHideAbilityManager(); } void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) { diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp index e262ccd..dac3b9f 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp @@ -32,17 +32,3 @@ void UARAbilityWidget::NativeConstruct() } Super::NativeConstruct(); } - - -UTexture2D* UARAbilityWidget::GetIcon() -{ - if (Icon) - return Icon; - - if (!AbilityManager.IsValid()) - return nullptr; - - //return nullptr; - UARAbilityBase* Ability = nullptr;// Cast(AbilityManager->GetAbility(Group, AbilitySlot)); - return Ability ? Ability->UIData->Icon : nullptr; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index a75cc05..a7c3234 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -20,14 +20,8 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase GENERATED_BODY() public: - TWeakObjectPtr AbilityManager; - - UPROPERTY(EditAnywhere, Category = "Config") - UTexture2D* Icon; + TWeakObjectPtr AbilityManager; virtual void NativePreConstruct() override; virtual void NativeConstruct() override; - - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - UTexture2D* GetIcon(); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h index 6f4147c..0f4f279 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h @@ -28,6 +28,13 @@ class ACTIONRPGGAME_API UARAbilityListWidget : public UUserWidget UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) class UARAbilityListSlotDropWidget* Ability003Group001; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARAbilityListSlotDropWidget* Ability001Group002; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARAbilityListSlotDropWidget* Ability002Group002; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARAbilityListSlotDropWidget* Ability003Group002; + UPROPERTY() TArray Items; public: diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h index 9d37b27..b56ab50 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h @@ -13,9 +13,8 @@ UCLASS() class ACTIONRPGGAME_API UARWeaponBaseWidget : public UARUMGWidgetBase { GENERATED_BODY() -protected: - UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") - class UARWeaponManagerComponent* WeaponManager; + public: + TWeakObjectPtr WeaponManager; public: void NativePreConstruct(); diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp new file mode 100644 index 0000000..2669fb6 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp @@ -0,0 +1,73 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponListSlotDragWidget.h" +#include "Blueprint/WidgetBlueprintLibrary.h" + +#include "ARAbilityDragVisual.h" +#include "Weapons/ARItemWeapon.h" +#include "Weapons/ARWeaponManagerComponent.h" + +FReply UARWeaponListSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) +{ + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + //return FReply::Unhandled(); +} + +void UARWeaponListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) +{ + UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); + if (DragDropOp) + { + APlayerController* MyPC = Cast(WeaponManager->GetOwner()); + //UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); + //DragIcon->AbilityManager = AbilityManager; + + DragDropOp->Payload = this; + //DragDropOp->DefaultDragVisual = DragIcon; + + OutOperation = DragDropOp; + } +} + +void UARWeaponListSlotDragWidget::OnItemAdded() +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + FGameplayTag AbilityTag = WeaponManager->WeaponClasses[WeaponIdx].GetDefaultObject()->Ability; + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("AbilityTagSearch", AbilityTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARWeaponListSlotDragWidget::OnItemLoaded, PrimaryAssetId); + + Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } + } +} + +void UARWeaponListSlotDragWidget::OnItemLoaded(FPrimaryAssetId InPrimaryAssetId) +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); + TSubclassOf AbilityClass = Cast(loaded); + if (AbilityClass) + { + IconImage->SetBrushFromTexture(AbilityClass.GetDefaultObject()->UIData->Icon); + } + + { + Manager->UnloadPrimaryAsset(InPrimaryAssetId); + } + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h similarity index 66% rename from Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h rename to Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h index 1fc7f7d..8cff988 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h @@ -4,18 +4,23 @@ #include "CoreMinimal.h" #include "UI/Weapons/ARWeaponBaseWidget.h" -#include "ARWeaponManagerSlotDragWidget.generated.h" +#include "Components/Image.h" +#include "ARWeaponListSlotDragWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARWeaponManagerSlotDragWidget : public UARWeaponBaseWidget +class ACTIONRPGGAME_API UARWeaponListSlotDragWidget : public UARWeaponBaseWidget { GENERATED_BODY() -protected: +public: UPROPERTY(BlueprintReadWrite, meta=(ExposeOnSpawn), Category = "Weapon Widget") int32 WeaponIdx; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* IconImage; + public: virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) override; @@ -26,4 +31,7 @@ class ACTIONRPGGAME_API UARWeaponManagerSlotDragWidget : public UARWeaponBaseWid { return WeaponIdx; } + void OnItemAdded(); +protected: + void OnItemLoaded(FPrimaryAssetId InPrimaryAssetId); }; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp new file mode 100644 index 0000000..0f43820 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponListSlotDropWidget.h" + +#include "AFAbilityComponent.h" + +#include "Weapons/ARWeaponManagerComponent.h" +#include "Weapons/ARWeaponAbilityBase.h" +#include "ARWeaponListSlotDragWidget.h" + +bool UARWeaponListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UARWeaponListSlotDragWidget* Payload = Cast(InOperation->Payload); + FSlateBrush Brush = Payload->IconImage->Brush; + + IconImage->SetBrush(Brush); + WeaponManager->AddWeaponToManager(WeaponSlot, EAMSlot::Slot001, Payload->GetWeapon()); + return true; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h similarity index 68% rename from Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h rename to Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h index 911bc37..83c5381 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h @@ -5,18 +5,21 @@ #include "CoreMinimal.h" #include "ARWeaponBaseWidget.h" #include "AMTypes.h" -#include "ARWeaponManagerSlotDropWidget.generated.h" +#include "ARWeaponListSlotDropWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARWeaponManagerSlotDropWidget : public UARWeaponBaseWidget +class ACTIONRPGGAME_API UARWeaponListSlotDropWidget : public UARWeaponBaseWidget { GENERATED_BODY() protected: UPROPERTY(EditAnywhere, Category = "Config") EAMGroup WeaponSlot; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* IconImage; public: virtual bool NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp new file mode 100644 index 0000000..4e792ba --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp @@ -0,0 +1,37 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponListWidget.h" + +#include "ARPlayerController.h" +#include "Weapons/ARWeaponManagerComponent.h" + + + +void UARWeaponListWidget::NativePreConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + ARPC = MyPC; + WeaponManager = MyPC->WeaponManager; + } + Super::NativePreConstruct(); +} +void UARWeaponListWidget::NativeConstruct() +{ + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + ARPC = MyPC; + WeaponManager = MyPC->WeaponManager; + } + Super::NativeConstruct(); +} +void UARWeaponListWidget::AddItem(TSubclassOf DragWidgetClass, int32 WeaponIdx) +{ + UARWeaponListSlotDragWidget* Item = CreateWidget(ARPC.Get(), DragWidgetClass); + Item->WeaponManager = WeaponManager; + Item->WeaponIdx = WeaponIdx; + Items.Add(Item); + Item->OnItemAdded(); + ItemContainer->AddChild(Item); +} + diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h new file mode 100644 index 0000000..2ba9532 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "ARWeaponListWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponListWidget : public UUserWidget +{ + GENERATED_BODY() +public: + TWeakObjectPtr WeaponManager; + TWeakObjectPtr ARPC; +protected: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UWrapBox* ItemContainer; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARWeaponListSlotDropWidget* RightWeapon; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARWeaponListSlotDropWidget* LeftWeapon; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARWeaponListSlotDropWidget* BackDownWeapon; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UARWeaponListSlotDropWidget* SideLeftWeapon; +protected: + + UPROPERTY() + TArray Items; +public: + void NativePreConstruct(); + void NativeConstruct(); +public: + void AddItem(TSubclassOf DragWidgetClass, int32 WeaponIdx); +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp deleted file mode 100644 index 44fbec9..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDragWidget.cpp +++ /dev/null @@ -1,31 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponManagerSlotDragWidget.h" -#include "Blueprint/WidgetBlueprintLibrary.h" - -#include "ARAbilityDragVisual.h" -#include "../../Weapons/ARWeaponManagerComponent.h" - -FReply UARWeaponManagerSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) -{ - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; - //return FReply::Unhandled(); -} - -void UARWeaponManagerSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) -{ - UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); - if (DragDropOp) - { - APlayerController* MyPC = Cast(WeaponManager->GetOwner()); - //UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); - //DragIcon->AbilityManager = AbilityManager; - - DragDropOp->Payload = this; - //DragDropOp->DefaultDragVisual = DragIcon; - - OutOperation = DragDropOp; - } -} diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp deleted file mode 100644 index f80ca84..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerSlotDropWidget.cpp +++ /dev/null @@ -1,18 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponManagerSlotDropWidget.h" - -#include "AFAbilityComponent.h" - -#include "../../Weapons/ARWeaponManagerComponent.h" -#include "../../Weapons/ARWeaponAbilityBase.h" -#include "ARWeaponManagerSlotDragWidget.h" - -bool UARWeaponManagerSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - UARWeaponManagerSlotDragWidget* Payload = Cast(InOperation->Payload); - - WeaponManager->AddWeaponToManager(WeaponSlot, EAMSlot::Slot001, Payload->GetWeapon()); - return false; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp deleted file mode 100644 index 67be10d..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.cpp +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponManagerWidget.h" - -#include "../../ARPlayerController.h" -#include "../../Weapons/ARWeaponManagerComponent.h" - - - -void UARWeaponManagerWidget::NativePreConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - WeaponManager = MyPC->WeaponManager; - } - Super::NativePreConstruct(); -} -void UARWeaponManagerWidget::NativeConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - WeaponManager = MyPC->WeaponManager; - } - Super::NativeConstruct(); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h deleted file mode 100644 index b4c4047..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponManagerWidget.h +++ /dev/null @@ -1,23 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "ARWeaponManagerWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponManagerWidget : public UUserWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(BlueprintReadOnly, Category = "Weapon Manager") - class UARWeaponManagerComponent* WeaponManager; - -public: - void NativePreConstruct(); - void NativeConstruct(); -}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 4780cc5..efab2c3 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -5,7 +5,12 @@ #include "AFAbilityComponent.h" #include "ARWeaponAbilityBase.h" #include "ARItemWeapon.h" -#include "../ARCharacter.h" +#include "ARCharacter.h" +#include "UI/Weapons/ARWeaponListWidget.h" + +#include "DWBPFunctionLibrary.h" +#include "SDraggableWindowWidget.h" + #include "Engine/World.h" // Sets default values for this component's properties @@ -35,6 +40,24 @@ void UARWeaponManagerComponent::BeginPlay() if (!AbilityComp) return; + if (WeaponListClass) + { + WeaponListWidget = CreateWidget(MyPC, WeaponListClass); + WeaponListWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + WeaponListWidget->ARPC = Cast(GetOwner()); + WeaponListWidget->WeaponManager = this; + int32 Idx = 0; + for (const TSubclassOf& Weapon : WeaponClasses) + { + WeaponListWidget->AddItem(DragSlotClass, Idx); + Idx++; + } + + WeaponListWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(WeaponListWidget, "Weapon List"); + WeaponListWindowHandle.Window.Pin()->bDestroyOnClose = false; + WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); + } + //POwner = MyPC->GetPawn(); } @@ -391,3 +414,21 @@ void UARWeaponManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag SetAbility(InGroup, EAMSlot::Slot001, Ability); SetAbilityTag(InGroup, EAMSlot::Slot001, InAbilityTag);*/ } + + +void UARWeaponManagerComponent::ShowHideAbilityManager() +{ + if (!WeaponListWidget) + return; + + EVisibility Visibility = WeaponListWindowHandle.Window.Pin()->GetVisibility(); + + if (Visibility == EVisibility::Collapsed) + { + WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::SelfHitTestInvisible); + } + else if (Visibility == EVisibility::SelfHitTestInvisible) + { + WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 9fbecdb..7eda862 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -44,6 +44,7 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp GENERATED_BODY() protected: static constexpr int32 MAX_WEAPONS = 4; //maximum weapon + empty hands +public: UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> WeaponClasses; @@ -53,7 +54,22 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UPROPERTY(EditAnywhere, Category = "Attachment Config") FName EquipSocketName; UPROPERTY(EditAnywhere, Category = "Attachment Config") - TArray WeaponAttachment; + TArray WeaponAttachment; + + //Widgets + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf WeaponListClass; + + + UPROPERTY(BlueprintReadOnly, Category = "Widgets") + UARWeaponListWidget* WeaponListWidget; + + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf DragSlotClass; + + + FDWWWindowHandle WeaponListWindowHandle; + public: UPROPERTY() class APawn* POwner; @@ -127,5 +143,6 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp FGameplayTag FindNextValid(); FGameplayTag FindPreviousValid(); - + public: + void ShowHideAbilityManager(); }; From 2b81f2d1124772e0b79a4447f936d2515dd259fe Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 23 Mar 2018 23:32:25 +0100 Subject: [PATCH 087/187] add check to see if the index is valid --- .../Source/AbilityManager/AMAbilityManagerComponent.cpp | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index fcd8ad0..51c9243 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -80,7 +80,12 @@ void UAMAbilityManagerComponent::BP_EquipAbility(const FGameplayTag& InAbilityTa } FGameplayTag UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) { - return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; + if (AbilityTagsSet.IsValidIndex(AMEnumToInt(InGroup)) + && AbilityTagsSet[AMEnumToInt(InGroup)].IsValidIndex(AMEnumToInt(InSlot))) + { + return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; + } + return FGameplayTag(); } void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, FGameplayTag InAbilityTag) { From 732eb5056809531883cf8f51f096ecc3763f904b Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Sat, 24 Mar 2018 09:53:09 +0100 Subject: [PATCH 088/187] fixing compilation issues with latest master --- ActionRPGGame.uproject | 4 ---- .../Source/AbilityFramework/AbilityFramework.Build.cs | 3 ++- .../AbilityFramework/Effects/GAEffectCueSequence.cpp | 4 ++-- .../Source/AbilityFramework/Effects/GAEffectCueSequence.h | 5 +++-- .../AbilityFrameworkEditor/AbilityFrameworkEditor.cpp | 8 ++++++-- Source/ActionRPGGame/ActionRPGGame.Build.cs | 1 - 6 files changed, 13 insertions(+), 12 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index e7a5fe1..9460b16 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -197,10 +197,6 @@ { "Name": "GameLiftServerSDK", "Enabled": true - }, - { - "Name": "NoesisGUI", - "Enabled": true } ], "TargetPlatforms": [ diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index 47e74e2..cc2a4ed 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -53,7 +53,8 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) PrivateDependencyModuleNames.AddRange( new string[] { - "ActorSequence" + "ActorSequence", + "TimeManagement" // ... add private dependencies that you statically link with here ... } ); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp index 86ed0f2..b373f14 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp @@ -65,13 +65,13 @@ UGAEffectCueSequence* UGAEffectCueSequence::GetNullAnimation() return NullAnimation; } #endif //WITH_EDITOR -float UGAEffectCueSequence::GetStartTime() const +FFrameNumber UGAEffectCueSequence::GetStartTime() const { return MovieScene->GetPlaybackRange().GetLowerBoundValue(); } -float UGAEffectCueSequence::GetEndTime() const +FFrameNumber UGAEffectCueSequence::GetEndTime() const { return MovieScene->GetPlaybackRange().GetUpperBoundValue(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h index 3f21841..c61235f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h @@ -7,6 +7,7 @@ #include "MovieScene.h" #include "LazyObjectPtr.h" #include "ActorSequence.h" +#include "FrameNumber.h" #include "GAEffectCueSequence.generated.h" UCLASS(BlueprintType, DefaultToInstanced) @@ -49,7 +50,7 @@ class ABILITYFRAMEWORK_API UGAEffectCueSequence : public UMovieSceneSequence public: inline UMovieScene* GetMovieScene() { return MovieScene; } UFUNCTION(BlueprintCallable, Category = "Animation") - float GetStartTime() const; + FFrameNumber GetStartTime() const; /** * Get the end time of this animation. @@ -58,7 +59,7 @@ class ABILITYFRAMEWORK_API UGAEffectCueSequence : public UMovieSceneSequence * @see GetStartTime */ UFUNCTION(BlueprintCallable, Category = "Animation") - float GetEndTime() const; + FFrameNumber GetEndTime() const; virtual void BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) override; virtual bool CanPossessObject(UObject& Object, UObject* InPlaybackContext) const override; virtual UMovieScene* GetMovieScene() const override; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp index d4e59de..342153e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp @@ -64,13 +64,17 @@ void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequenc { auto* ProjectSettings = GetDefault(); AGAEffectCue* Cue = Cast(Sequence->GetOuter()); + + if (Cue) { - Sequence->GetMovieScene()->SetPlaybackRange(Cue->StartTime, Cue->EndTime); + TRange Frames(static_cast(Cue->StartTime), static_cast(Cue->EndTime)); + Sequence->GetMovieScene()->SetPlaybackRange(Frames, true); } else { - Sequence->GetMovieScene()->SetPlaybackRange(ProjectSettings->DefaultStartTime, ProjectSettings->DefaultStartTime + ProjectSettings->DefaultDuration); + TRange Frames; + Sequence->GetMovieScene()->SetPlaybackRange(Frames, true); } } /** IModuleInterface implementation */ diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 9716be8..8deb862 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -62,7 +62,6 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AbilityManager", "DraggableWindow" }); - PrivateDependencyModuleNames.AddRange(new string[] { "Noesis", "NoesisRuntime" }); if (Target.Type == TargetRules.TargetType.Editor) { PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" }); From 034ba5fa55f6b9fddc776aaca2cce973f94d5b5b Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 27 Mar 2018 23:06:18 +0200 Subject: [PATCH 089/187] more UI work --- ActionRPGGame.uproject | 4 ++ Source/ActionRPGGame/ARCharacter.cpp | 42 +++++++++++++++++-- Source/ActionRPGGame/ARCharacter.h | 27 ++++++++++++ Source/ActionRPGGame/ARPlayerController.cpp | 22 +++++++++- Source/ActionRPGGame/ARPlayerController.h | 4 ++ Source/ActionRPGGame/UI/ARAbilityWidget.h | 1 - Source/ActionRPGGame/UI/ARHUDWidget.h | 3 ++ Source/ActionRPGGame/UI/ARUIComponent.h | 2 +- .../Abilities/ARAbilityListSlotDropWidget.cpp | 6 ++- .../UI/Abilities/ARAbilitySlotWidget.cpp | 7 ++++ .../UI/Abilities/ARAbilitySlotWidget.h | 8 ++++ Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h | 19 ++++++--- 12 files changed, 131 insertions(+), 14 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 9460b16..7f03574 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -197,6 +197,10 @@ { "Name": "GameLiftServerSDK", "Enabled": true + }, + { + "Name": "LiveLink", + "Enabled": true } ], "TargetPlatforms": [ diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 6479af1..81bedcb 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -54,15 +54,17 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) GetCharacterMovement()->MaxWalkSpeedCrouched = 150.0f; GetCharacterMovement()->BrakingDecelerationWalking = 150.0f; + GetArrowComponent()->bIsEditorOnly = true; + // Create a camera boom (pulls in towards the player if there is a collision) CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); //CameraBoom->SetupAttachment(GetMesh()); CameraBoom->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, TEXT("headSocket")); - CameraBoom->TargetArmLength = 250; // The camera follows at this distance behind the character + CameraBoom->TargetArmLength = 265; // The camera follows at this distance behind the character CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller - CameraBoom->SocketOffset = FVector(0, 30, 95); - CameraBoom->TargetOffset = FVector(0, 0, -95); + CameraBoom->SocketOffset = FVector(0, 25, 95); + CameraBoom->TargetOffset = FVector(0, 0, -75); CameraBoom->bEnableCameraLag = true; CameraBoom->bEnableCameraRotationLag = true; CameraBoom->CameraLagSpeed = 8; @@ -84,9 +86,41 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) Weapons = CreateDefaultSubobject(TEXT("Weapons")); + Head = CreateDefaultSubobject(TEXT("Head")); + Head->SetupAttachment(GetMesh()); + Head->SetMasterPoseComponent(GetMesh()); + + Shoulders = CreateDefaultSubobject(TEXT("Shoulders")); + Shoulders->SetupAttachment(GetMesh()); + Shoulders->SetMasterPoseComponent(GetMesh()); + + Arms = CreateDefaultSubobject(TEXT("Arms")); + Arms->SetupAttachment(GetMesh()); + Arms->SetMasterPoseComponent(GetMesh()); + + Hands = CreateDefaultSubobject(TEXT("Hands")); + Hands->SetupAttachment(GetMesh()); + Hands->SetMasterPoseComponent(GetMesh()); + + Torso = CreateDefaultSubobject(TEXT("Torso")); + Torso->SetupAttachment(GetMesh()); + Torso->SetMasterPoseComponent(GetMesh()); + + Legs = CreateDefaultSubobject(TEXT("Legs")); + Legs->SetupAttachment(GetMesh()); + Legs->SetMasterPoseComponent(GetMesh()); + + Feets = CreateDefaultSubobject(TEXT("Feets")); + Feets->SetupAttachment(GetMesh()); + Feets->SetMasterPoseComponent(GetMesh()); + + Backpack = CreateDefaultSubobject(TEXT("Backpack")); + Backpack->SetupAttachment(GetMesh()); + Backpack->SetMasterPoseComponent(GetMesh()); + LegsCloth = CreateDefaultSubobject(TEXT("LegsCloth")); LegsCloth->SetupAttachment(GetMesh()); - //LegsCloth->AttachToComponent(GetMesh(), FAttachmentTransformRules::SnapToTargetIncludingScale); + //LegsCloth->SetMasterPoseComponent(GetMesh()); WeaponHolsteredRight = CreateDefaultSubobject(TEXT("WeaponHolsteredRight")); //HolsteredRightWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform); diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index e1e85bb..fb0fce1 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -95,8 +95,35 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UPROPERTY(EditAnywhere, Category = "Default Abilities") TArray AbilitiesToGive; + //Character parts: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Head; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Shoulders; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Arms; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Hands; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Torso; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Legs; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Feets; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) + USkeletalMeshComponent* Backpack; + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Character Parts", meta = (AllowPrivateAccess = "true")) USkeletalMeshComponent* LegsCloth; + + //Weapons UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponHolsteredRight; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 9d99176..e0ae778 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -153,4 +153,24 @@ float AARPlayerController::GetObjectScreenRadius(AActor* InActor) ScreenRadius *= SRad / FMath::DegreesToRadians(CamFOV); return ScreenRadius; -} \ No newline at end of file +} +void AARPlayerController::GetObjectBoundSphere(float Distance, AActor* InActor, FVector& Origin, float& Radius, float& Scale + , float& SphereRadius) +{ + const FMinimalViewInfo& ViewInfo = PlayerCameraManager->GetLastFrameCameraCachePOV(); + FMatrix Proj = ViewInfo.CalculateProjectionMatrix(); + const float ScreenMultiple = FMath::Max(0.5f * Proj.M[0][0], 0.5f * Proj.M[1][1]); + if (ACharacter* Character = Cast(InActor)) + { + Origin = Character->GetMesh()->Bounds.Origin; + Radius = Character->GetMesh()->Bounds.SphereRadius; + Scale = ScreenMultiple; + SphereRadius = ScreenMultiple * Radius / FMath::Max(1.0f, Distance); + return; + } + + Scale = ScreenMultiple; + Origin = InActor->GetRootComponent()->Bounds.Origin; + Radius = InActor->GetRootComponent()->Bounds.SphereRadius; + SphereRadius = ScreenMultiple * Radius / FMath::Max(1.0f, Distance); +} diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 690760e..abd7223 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -51,4 +51,8 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UFUNCTION(BlueprintPure, Category = "Hud") float GetObjectScreenRadius(AActor* InActor); + + UFUNCTION(BlueprintPure, Category = "Hud") + void GetObjectBoundSphere(float Distance, AActor* InActor, FVector& Origin, float& Radius, float& Scale + , float& SphereRadius); }; diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h index a7c3234..5d160c4 100644 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ b/Source/ActionRPGGame/UI/ARAbilityWidget.h @@ -19,7 +19,6 @@ class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase { GENERATED_BODY() public: - TWeakObjectPtr AbilityManager; virtual void NativePreConstruct() override; diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.h b/Source/ActionRPGGame/UI/ARHUDWidget.h index eb25915..2ae7340 100644 --- a/Source/ActionRPGGame/UI/ARHUDWidget.h +++ b/Source/ActionRPGGame/UI/ARHUDWidget.h @@ -18,6 +18,9 @@ class ACTIONRPGGAME_API UARHUDWidget : public UUserWidget { GENERATED_BODY() protected: + + TWeakObjectPtr UIComponent; +public: UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UARHUDPlayerInfo* PlayerInfo; }; diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index e3289da..bc5d93d 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -39,7 +39,7 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf HUDWidgetClass; - +public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") UARHUDWidget* HUDWidget; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp index 0e21731..f8ecad6 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp @@ -4,6 +4,7 @@ #include "ARAbilityListSlotDragWidget.h" #include "Abilities/ARAbilityManagerComponent.h" +#include "UI/ARUIComponent.h" bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) @@ -14,6 +15,9 @@ bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); IconImage->SetBrush(brush); - + if (AbilitySlot == EAMSlot::Slot001) + { + UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot001->AbilityIcon->SetBrush(brush); //DAT BAD + } return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp index 573ebd7..f734089 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp @@ -8,6 +8,13 @@ #include "ARAbilityBase.h" #include "ARAbilityUIData.h" +void UARAbilitySlotWidget::NativeTick(const FGeometry& MyGeometry, float InDeltaTime) +{ + Super::NativeTick(MyGeometry, InDeltaTime); + + CooldownBar->SetPercent(GetCooldownRemainingTimeNormalized()); +} + float UARAbilitySlotWidget::GetActivationRemainingTime() { if (!AbilityManager.IsValid()) diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h index 33a64a5..05c2cff 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h @@ -20,6 +20,14 @@ class ACTIONRPGGAME_API UARAbilitySlotWidget : public UARAbilityWidget UPROPERTY(EditAnywhere, Category = "Config") EAMSlot AbilitySlot; public: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UProgressBar* CooldownBar; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* AbilityIcon; +public: + + virtual void NativeTick(const FGeometry& MyGeometry, float InDeltaTime) override; + UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") float GetActivationRemainingTime(); UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h index 92dc524..f376e75 100644 --- a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h +++ b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h @@ -24,7 +24,7 @@ class ACTIONRPGGAME_API UARHUDPlayerInfo : public UUserWidget UProgressBar* PlayerStamina; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UProgressBar* PlayerEnergy; - +public: UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UARAbilitySlotWidget* AbilityGroup001Slot001; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) @@ -33,12 +33,19 @@ class ACTIONRPGGAME_API UARHUDPlayerInfo : public UUserWidget UARAbilitySlotWidget* AbilityGroup001Slot003; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARWeaponSlotWidget* Weapon001; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARWeaponSlotWidget* Weapon002; + UARAbilitySlotWidget* AbilityGroup002Slot001; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARWeaponSlotWidget* Weapon003; + UARAbilitySlotWidget* AbilityGroup002Slot002; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARWeaponSlotWidget* Weapon004; + UARAbilitySlotWidget* AbilityGroup002Slot003; + + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARWeaponSlotWidget* Weapon001; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARWeaponSlotWidget* Weapon002; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARWeaponSlotWidget* Weapon003; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARWeaponSlotWidget* Weapon004; }; From 9395ffeb16f28b302fbf4c10e3cd5bd8c65cc1a0 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 28 Mar 2018 21:06:42 +0200 Subject: [PATCH 090/187] Added ability to switch ability groups --- Config/DefaultGameplayTags.ini | 5 ++ Config/DefaultInput.ini | 2 + .../AbilityFramework/AFAbilityComponent.cpp | 63 ++++++++++++++++-- .../AbilityFramework/AFAbilityComponent.h | 23 ++++++- Source/ActionRPGGame/ARPlayerController.cpp | 19 ++++++ Source/ActionRPGGame/ARPlayerController.h | 10 +++ .../Abilities/ARAbilityManagerComponent.cpp | 65 +++++++++++++++++++ .../Abilities/ARAbilityManagerComponent.h | 10 +++ .../UI/Abilities/ARAbilityCrosshairInfo.cpp | 4 ++ .../UI/Abilities/ARAbilityCrosshairInfo.h | 3 + .../Abilities/ARAbilityListSlotDropWidget.cpp | 35 +++++++++- .../ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp | 16 ++++- Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h | 9 ++- 13 files changed, 250 insertions(+), 14 deletions(-) diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 46e8533..cc5d7cc 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -6,6 +6,7 @@ FastReplication=False NumBitsForContainerSize=6 NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.AbilityCooldow01.Cooldown",DevComment="") ++GameplayTagList=(Tag="Ability.AbilityCooldown02.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.Corruption",DevComment="") +GameplayTagList=(Tag="Ability.Corruption.Cooldown",DevComment="") +GameplayTagList=(Tag="Ability.DurationInstance",DevComment="") @@ -16,6 +17,8 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Input.Jump",DevComment="") +GameplayTagList=(Tag="Ability.Input.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.Input.PreviousWeapon",DevComment="") ++GameplayTagList=(Tag="Ability.Input.SetAbilityGroup01",DevComment="") ++GameplayTagList=(Tag="Ability.Input.SetAbilityGroup02",DevComment="") +GameplayTagList=(Tag="Ability.Input.SwitchAbilities",DevComment="") +GameplayTagList=(Tag="Ability.Rifle",DevComment="") +GameplayTagList=(Tag="Ability.Rifle.Activate",DevComment="") @@ -52,6 +55,8 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Input.Gun.Reload",DevComment="") +GameplayTagList=(Tag="Input.Gun.Shoot",DevComment="") +GameplayTagList=(Tag="Input.UI.Holster",DevComment="") ++GameplayTagList=(Tag="Input.UI.SetAbilityGroup01",DevComment="") ++GameplayTagList=(Tag="Input.UI.SetAbilityGroup02",DevComment="") +GameplayTagList=(Tag="Input.UI.WeaponNext",DevComment="") +GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 9c13984..a4810aa 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -54,6 +54,8 @@ DoubleClickTime=0.200000 +ActionMappings=(ActionName="Input.Ability01.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=One) +ActionMappings=(ActionName="Input.Ability02.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Two) +ActionMappings=(ActionName="Input.Ability03.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Three) ++ActionMappings=(ActionName="Input.UI.SetAbilityGroup01",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Zero) ++ActionMappings=(ActionName="Input.UI.SetAbilityGroup02",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Nine) +AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=W) +AxisMappings=(AxisName="MoveForward",Scale=-1.000000,Key=S) +AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=Up) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index ac99f37..a575183 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -257,15 +257,15 @@ void FGASAbilityItem::PostReplicatedChange(const struct FGASAbilityContainer& In { } -void FGASAbilityContainer::SetBlockedInput(const FGameplayTag& InInput, bool bBlock) +void FGASAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) { - if (BlockedInput.Contains(InInput)) + if (BlockedInput.Contains(InActionName)) { - BlockedInput[InInput] = bBlock; + BlockedInput[InActionName] = bBlock; } else { - BlockedInput.Add(InInput, bBlock); + BlockedInput.Add(InActionName, bBlock); } } UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn, @@ -359,7 +359,7 @@ void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InputTag); AbilityTag = InAbilityTag; - TArray& ActionTag = AbilityToAction.FindOrAdd(InputTag); + TArray& ActionTag = AbilityToAction.FindOrAdd(InAbilityTag); ActionTag.Add(InputTag); } if (!AbilitiesComp.IsValid()) @@ -461,9 +461,9 @@ void UAFAbilityComponent::BindInputs(class UInputComponent* InputComponent) BindAbilityToAction(InputComponent, Tag); } } -void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InInput, bool bBlock) +void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) { - AbilityContainer.SetBlockedInput(InInput, bBlock); + AbilityContainer.SetBlockedInput(InActionName, bBlock); } void UAFAbilityComponent::BP_BindAbilityToAction(FGameplayTag ActionName) { @@ -548,6 +548,55 @@ void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(FGameplay NotifyOnAbilityInputReady(AbilityTag); } +void UAFAbilityComponent::SetAbilitiesToActions(const TArray& InAbilitiesActions + , const TArray& InputDelegate) +{ + for (const FAFAbilityActionSet& Set : InAbilitiesActions) + { + for (const FGameplayTag& Tag : Set.AbilityInputs) + { + if (AbilityContainer.IsAbilityBoundToAction(Tag).IsValid()) + { + RemoveAbilityFromAction(Set.AbilityTag, FGameplayTag()); + } + } + } + for (const FAFAbilityActionSet& Set : InAbilitiesActions) + { + AbilityContainer.SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs); + } + ENetRole role = GetOwnerRole(); + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + && role == ENetRole::ROLE_AutonomousProxy) + { + for (int32 Idx = 0; Idx < InAbilitiesActions.Num(); Idx++) + { + if (InputDelegate[Idx].IsBound()) + { + AddOnAbilityInputReadyDelegate(InAbilitiesActions[Idx].AbilityTag, InputDelegate[Idx]); + } + } + + ServerSetAbilitiesToActions(InAbilitiesActions); + } +} + +void UAFAbilityComponent::ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions) +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + for (const FAFAbilityActionSet& Set : InAbilitiesActions) + { + SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs, FAFOnAbilityReady()); + } + } +} +bool UAFAbilityComponent::ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions) +{ + return true; +} + void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) { NativeInputPressed(ActionName); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index f48dfd9..914fd81 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -155,7 +155,7 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer TMap TagToAbility; - void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, AActor* InAvatar); void RemoveAbility(const FGameplayTag& AbilityIn); @@ -252,6 +252,18 @@ struct TStructOpsTypeTraits< FAFReplicatedAttributeContainer > : public TStructO }; }; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAbilityActionSet +{ + GENERATED_BODY() +public: + UPROPERTY() + FGameplayTag AbilityTag; + UPROPERTY() + TArray AbilityInputs; +}; + UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface { @@ -562,7 +574,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, TMap BlockedInput; //TSharedPtr AbilityLoadedHandle; void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar); - void SetBlockedInput(const FGameplayTag& InInput, bool bBlock); + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); void BindInputs(class UInputComponent* InputComponent); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") void BP_BindAbilityToAction(FGameplayTag ActionName); @@ -586,6 +598,13 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag); + void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); + UFUNCTION(Server, Reliable, WithValidation) + void ServerSetAbilitiesToActions(const TArray& InAbilitiesActions); + void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); + bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") void BP_InputPressed(FGameplayTag ActionName); diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index e0ae778..31b769c 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -43,6 +43,8 @@ void AARPlayerController::SetPawn(APawn* InPawn) AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputHolsterWeapon); + AbilityComp->BindAbilityToAction(InputComponent, InputSetAbilityGroup01); + AbilityComp->BindAbilityToAction(InputComponent, InputSetAbilityGroup02); InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); @@ -75,6 +77,23 @@ void AARPlayerController::SetPawn(APawn* InPawn) HolsterInput.Add(InputHolsterWeapon); AbilityComp->NativeAddAbilityFromTag(AbilitytHolstersWeapon, nullptr, HolsterInput); } + + if (SetAbilityGroup01.IsValid()) + { + FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, SetAbilityGroup01, InputSetAbilityGroup01); + AbilityComp->AddOnAbilityReadyDelegate(SetAbilityGroup01, del3); + TArray HolsterInput; + HolsterInput.Add(InputSetAbilityGroup01); + AbilityComp->NativeAddAbilityFromTag(SetAbilityGroup01, nullptr, HolsterInput); + } + if (SetAbilityGroup02.IsValid()) + { + FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, SetAbilityGroup02, InputSetAbilityGroup02); + AbilityComp->AddOnAbilityReadyDelegate(SetAbilityGroup02, del3); + TArray HolsterInput; + HolsterInput.Add(InputSetAbilityGroup02); + AbilityComp->NativeAddAbilityFromTag(SetAbilityGroup02, nullptr, HolsterInput); + } } WeaponManager->POwner = InPawn; diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index abd7223..c7ae2cb 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -38,6 +38,16 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag AbilitytHolstersWeapon; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag InputSetAbilityGroup01; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag SetAbilityGroup01; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag InputSetAbilityGroup02; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") + FGameplayTag SetAbilityGroup02; + bool bInputBount; public: AARPlayerController(const FObjectInitializer& ObjectInitializer); diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index d419392..2d99386 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -72,4 +72,69 @@ void UARAbilityManagerComponent::ShowHideAbilityManager() { ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); } +} + +void UARAbilityManagerComponent::SetCurrentSet(int32 SetIndex) +{ + SelectGroup(AMIntToEnum(SetIndex)); + EAMGroup Group = AMIntToEnum(SetIndex); //ActiveGroup + + + + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + if (!AbilityComp) + return; + + //UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponAbility)); + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + TArray AbilityActionSet; + TArray InputReadyDelegates; + for (int32 Idx = 0; Idx < AbilityTagsSet[SetIndex].Num(); Idx++) + { + TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); + FGameplayTag NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); + + FAFAbilityActionSet Set; + Set.AbilityInputs = WeaponInput; + Set.AbilityTag = NextWeaponAbility; + + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARAbilityManagerComponent::OnInputReady, + NextWeaponAbility, WeaponInput); + + AbilityActionSet.Add(Set); + InputReadyDelegates.Add(ReadyDelegate); + } + + AbilityComp->SetAbilitiesToActions(AbilityActionSet, InputReadyDelegates); + } + else + { + TArray AbilityActionSet; + TArray InputReadyDelegates; + + for (int32 Idx = 0; Idx < AbilityTagsSet[SetIndex].Num(); Idx++) + { + TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); + FGameplayTag NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); + + FAFAbilityActionSet Set; + Set.AbilityInputs = WeaponInput; + Set.AbilityTag = NextWeaponAbility; + + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARAbilityManagerComponent::OnInputReady, + NextWeaponAbility, WeaponInput); + + AbilityActionSet.Add(Set); + InputReadyDelegates.Add(ReadyDelegate); + } + AbilityComp->SetAbilitiesToActions(AbilityActionSet, InputReadyDelegates); + OnAbilitySetChanged.Broadcast(AMIntToEnum(SetIndex)); + } +} + +void UARAbilityManagerComponent::OnInputReady(FGameplayTag WeaponAbilityTag, TArray InInputTags) +{ + OnAbilitySetChanged.Broadcast(ActiveGroup); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h index 8197352..3c62416 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -13,6 +13,8 @@ #include "ARAbilityManagerComponent.generated.h" +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAROnAbilitySetChanged, EAMGroup, Group); + USTRUCT(BlueprintType) struct FARAbilityItem { @@ -42,6 +44,9 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom TArray AvailableAbilities; FDWWWindowHandle ManagerWindowHandle; +public: + UPROPERTY(BlueprintAssignable) + FAROnAbilitySetChanged OnAbilitySetChanged; public: // Sets default values for this component's properties UARAbilityManagerComponent(); @@ -60,4 +65,9 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom { return DragVisualClass; } + + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Ability Manager") + void SetCurrentSet(int32 SetIndex); + + void OnInputReady(FGameplayTag WeaponAbilityTag, TArray InInputTags); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp index e4b6887..41b86d0 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp @@ -19,6 +19,10 @@ void UARAbilityCrosshairInfo::NativeConstruct() Super::NativeConstruct(); CrosshairImage->SetBrushFromMaterial(CrosshairMaterial); + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + MyPC->AbilityManager->OnAbilitySetChanged.AddDynamic(this, &UARAbilityCrosshairInfo::OnAbilityGroupChanged); + } } void UARAbilityCrosshairInfo::NativeTick(const FGeometry& MyGeometry, float InDeltaTime) diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h index 4cbc484..22b46bf 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h @@ -26,4 +26,7 @@ class ACTIONRPGGAME_API UARAbilityCrosshairInfo : public UARAbilityInfoWidget virtual void NativePreConstruct() override; virtual void NativeConstruct() override; virtual void NativeTick(const FGeometry& MyGeometry, float InDeltaTime) override; + + UFUNCTION(BlueprintImplementableEvent, Category = "ActionRPGGame|UI") + void OnAbilityGroupChanged(EAMGroup CurrentGroup); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp index f8ecad6..9c20354 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp @@ -15,9 +15,40 @@ bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); IconImage->SetBrush(brush); - if (AbilitySlot == EAMSlot::Slot001) + if (AbilityGroup == EAMGroup::Group001) { - UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot001->AbilityIcon->SetBrush(brush); //DAT BAD + switch (AbilitySlot) + { + case EAMSlot::Slot001: + UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot001->AbilityIcon->SetBrush(brush); //DAT BAD + break; + case EAMSlot::Slot002: + UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot002->AbilityIcon->SetBrush(brush); //DAT BAD + break; + case EAMSlot::Slot003: + UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot003->AbilityIcon->SetBrush(brush); //DAT BAD + break; + default: + break; + } } + else if (AbilityGroup == EAMGroup::Group002) + { + switch (AbilitySlot) + { + case EAMSlot::Slot001: + UIComponent->HUDWidget->PlayerInfo->AbilityGroup002Slot001->AbilityIcon->SetBrush(brush); //DAT BAD + break; + case EAMSlot::Slot002: + UIComponent->HUDWidget->PlayerInfo->AbilityGroup002Slot002->AbilityIcon->SetBrush(brush); //DAT BAD + break; + case EAMSlot::Slot003: + UIComponent->HUDWidget->PlayerInfo->AbilityGroup002Slot003->AbilityIcon->SetBrush(brush); //DAT BAD + break; + default: + break; + } + } + return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp index c6fa8ce..28eb3fe 100644 --- a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp +++ b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp @@ -2,6 +2,18 @@ #include "ARHUDPlayerInfo.h" +#include "ARPlayerController.h" +#include "Abilities/ARAbilityManagerComponent.h" - - +void UARHUDPlayerInfo::NativePreConstruct() +{ + Super::NativePreConstruct(); +} +void UARHUDPlayerInfo::NativeConstruct() +{ + Super::NativeConstruct(); + if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) + { + MyPC->AbilityManager->OnAbilitySetChanged.AddDynamic(this, &UARHUDPlayerInfo::OnAbilityGroupChanged); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h index f376e75..cbd6668 100644 --- a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h +++ b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h @@ -6,6 +6,7 @@ #include "Blueprint/UserWidget.h" #include "Components/ProgressBar.h" +#include "UI/ARUMGWidgetBase.h" #include "UI/Weapons/ARWeaponSlotWidget.h" #include "UI/Abilities/ARAbilitySlotWidget.h" #include "ARHUDPlayerInfo.generated.h" @@ -14,7 +15,7 @@ * */ UCLASS() -class ACTIONRPGGAME_API UARHUDPlayerInfo : public UUserWidget +class ACTIONRPGGAME_API UARHUDPlayerInfo : public UARUMGWidgetBase { GENERATED_BODY() protected: @@ -48,4 +49,10 @@ class ACTIONRPGGAME_API UARHUDPlayerInfo : public UUserWidget //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) // UARWeaponSlotWidget* Weapon004; + virtual void NativePreConstruct() override; + virtual void NativeConstruct() override; + + UFUNCTION(BlueprintImplementableEvent, Category = "ActionRPGGame|UI") + void OnAbilityGroupChanged(EAMGroup CurrentGroup); + }; From 8cd34ecf52c13bff2c9ac2eff0f8f71c59aaf1f4 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 28 Mar 2018 21:48:59 +0200 Subject: [PATCH 091/187] added server side confirmation for ability group selection --- .../AMAbilityManagerComponent.cpp | 52 ++++++++++++++++++- .../AMAbilityManagerComponent.h | 8 +++ .../Abilities/ARAbilityManagerComponent.cpp | 22 ++++---- .../Abilities/ARAbilityManagerComponent.h | 2 + 4 files changed, 72 insertions(+), 12 deletions(-) diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 51c9243..2c2383e 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -298,10 +298,58 @@ void UAMAbilityManagerComponent::SelectGroup(EAMGroup InGroup) if (AMEnumToInt(InGroup) > Groups.Num()) { ActiveGroup = EAMGroup::Group001; - return; } - ActiveGroup = InGroup; + else + { + ActiveGroup = InGroup; + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerSelectGroup(InGroup); + } + else + { + OnGroupSelectionConfirmed(InGroup, true); + } } +void UAMAbilityManagerComponent::ServerSelectGroup_Implementation(EAMGroup InGroup) +{ + if (AMEnumToInt(InGroup) > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = InGroup; + } + if (ActiveGroup != InGroup) + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); + } + else + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); + } +} +bool UAMAbilityManagerComponent::ServerSelectGroup_Validate(EAMGroup InGroup) +{ + return true; +} + + +void UAMAbilityManagerComponent::ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess) +{ + if (bPredictionSuccess) + { + OnGroupSelectionConfirmed(InGroup, true); + } + else + { + ActiveGroup = InGroup; + OnGroupSelectionConfirmed(InGroup, false); + } +} + class UAFAbilityComponent* UAMAbilityManagerComponent::GetAbilityComponent() { diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index 3292301..fe930f3 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -162,9 +162,17 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; + virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; UFUNCTION(BlueprintCallable) void SelectGroup(EAMGroup InGroup); + UFUNCTION(Server, Reliable, WithValidation) + void ServerSelectGroup(EAMGroup InGroup); + void ServerSelectGroup_Implementation(EAMGroup InGroup); + bool ServerSelectGroup_Validate(EAMGroup InGroup); + UFUNCTION(Client, Reliable) + void ClientSelectGroup(EAMGroup InGroup, bool bPredictionSuccess); + void ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess); void AddOnAbilityReadyEvent(const FGameplayTag& Ability, const FSimpleDelegate& Delegate) diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index 2d99386..18ca938 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -76,22 +76,24 @@ void UARAbilityManagerComponent::ShowHideAbilityManager() void UARAbilityManagerComponent::SetCurrentSet(int32 SetIndex) { + //add server/client checks. SelectGroup(AMIntToEnum(SetIndex)); - EAMGroup Group = AMIntToEnum(SetIndex); //ActiveGroup - - +} + +void UARAbilityManagerComponent::OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) +{ + EAMGroup Group = ValidGroup; //ActiveGroup + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); if (!AbilityComp) return; - //UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponAbility)); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { TArray AbilityActionSet; TArray InputReadyDelegates; - for (int32 Idx = 0; Idx < AbilityTagsSet[SetIndex].Num(); Idx++) + for (int32 Idx = 0; Idx < AbilityTagsSet[AMEnumToInt(ValidGroup)].Num(); Idx++) { TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); FGameplayTag NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); @@ -106,15 +108,15 @@ void UARAbilityManagerComponent::SetCurrentSet(int32 SetIndex) AbilityActionSet.Add(Set); InputReadyDelegates.Add(ReadyDelegate); } - + AbilityComp->SetAbilitiesToActions(AbilityActionSet, InputReadyDelegates); } else { TArray AbilityActionSet; TArray InputReadyDelegates; - - for (int32 Idx = 0; Idx < AbilityTagsSet[SetIndex].Num(); Idx++) + + for (int32 Idx = 0; Idx < AbilityTagsSet[AMEnumToInt(ValidGroup)].Num(); Idx++) { TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); FGameplayTag NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); @@ -130,7 +132,7 @@ void UARAbilityManagerComponent::SetCurrentSet(int32 SetIndex) InputReadyDelegates.Add(ReadyDelegate); } AbilityComp->SetAbilitiesToActions(AbilityActionSet, InputReadyDelegates); - OnAbilitySetChanged.Broadcast(AMIntToEnum(SetIndex)); + OnAbilitySetChanged.Broadcast(ValidGroup); } } diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h index 3c62416..1c4fdf0 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -69,5 +69,7 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Ability Manager") void SetCurrentSet(int32 SetIndex); + virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; + void OnInputReady(FGameplayTag WeaponAbilityTag, TArray InInputTags); }; From 125c438a51200427efd0950924183a50540a10c1 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Wed, 28 Mar 2018 23:34:19 +0200 Subject: [PATCH 092/187] prevent overiding current abilities input when equiping ability into inactive group --- .../Source/AbilityManager/AMAbilityManagerComponent.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 2c2383e..d1b580e 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -106,7 +106,7 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit return; TArray IAbilityInput; - //if(bBindInput) + if(ActiveGroup == InGroup) IAbilityInput = GetInputTag(InGroup, InSlot); FAFOnAbilityReady del; From 4fc41f7742c5c0b3567a7363aa7e20aa07b4554a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 29 Mar 2018 21:40:42 +0200 Subject: [PATCH 093/187] exposed event when ability group/set is changing to crosshair widget --- Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h index d2e3121..905b683 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h @@ -17,9 +17,9 @@ class ACTIONRPGGAME_API UARAbilityInfoWidget : public UARAbilityWidget { GENERATED_BODY() protected: - UPROPERTY(EditAnywhere, Category = "Ability") + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Ability") EAMSlot AbilitySlot; - UPROPERTY(EditAnywhere, Category = "Ability") + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Ability") EAMGroup AbilityGroup; float GetRemainingCooldown() const; From 4e71034ae2519af19339063c2b5cc491f7117125 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 30 Mar 2018 23:37:49 +0200 Subject: [PATCH 094/187] added ability task for line trace (does not support netowrking yet), fixed task caching and reuse (previously tasks were destroyed and not reinitialized properly) --- .../Abilities/Tasks/GAAbilityTask.h | 25 ++++++++++++++++--- .../GAEK2Node_LatentAbilityTaskCall.cpp | 1 + .../Abilities/ARAbilityListSlotDropWidget.cpp | 1 + 3 files changed, 23 insertions(+), 4 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 37e6930..6e9bb0a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -40,18 +40,22 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask { check(WorldContextObject); - T* MyObj = NewObject(WorldContextObject); + T* MyObj = nullptr; UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); if (UGAAbilityTask* CachedTask = ThisAbility->GetAbilityTask(InTaskName)) { - CachedTask->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); - return Cast(CachedTask); + MyObj = Cast(CachedTask); + } + else + { + MyObj = NewObject(WorldContextObject); + ThisAbility->AddAbilityTask(InTaskName, MyObj); } MyObj->Ability = ThisAbility; MyObj->AbilityComponent = ThisAbility->AbilityComponent; MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); MyObj->InstanceName = InstanceName; - ThisAbility->AddAbilityTask(InTaskName, MyObj); + return MyObj; } @@ -73,4 +77,17 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; protected: void EndAbilityTask(); + + void OnDestroy(bool bInOwnerFinished) override + { + ensure(TaskState != EGameplayTaskState::Finished && !IsPendingKill()); + TaskState = EGameplayTaskState::Finished; + + if (TasksComponent.IsValid()) + { + TasksComponent->OnGameplayTaskDeactivated(*this); + } + + //MarkPendingKill(); + } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp index 8fbc0f2..73b1eb0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -17,6 +17,7 @@ UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGameplayTask, ReadyForActivation); if (HasAnyFlags(RF_ClassDefaultObject) == true) { UK2Node_LatentGameplayTaskCall::RegisterSpecializedTaskNodeClass(GetClass()); diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp index 9c20354..28274c4 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp @@ -20,6 +20,7 @@ bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry switch (AbilitySlot) { case EAMSlot::Slot001: + //probabaly should just bind delgate from widget and track ability change. UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot001->AbilityIcon->SetBrush(brush); //DAT BAD break; case EAMSlot::Slot002: From 69888cc74df1f637cee364c1d709ee58f6cad0e4 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 2 Apr 2018 21:37:41 +0200 Subject: [PATCH 095/187] more work on ability tracing tasks --- .../AbilityFramework/AFAbilityComponent.cpp | 15 + .../AbilityFramework/AFAbilityComponent.h | 12 + .../Abilities/Tasks/GAAbilityTask.cpp | 49 +- .../Abilities/Tasks/GAAbilityTask.h | 52 +- .../GAAbilityTask_TargetDataLineTrace.cpp | 219 ++++++ .../Tasks/GAAbilityTask_TargetDataLineTrace.h | 107 +++ .../AFAbilityComponent.h | 693 ++++++++++++++++++ 7 files changed, 1121 insertions(+), 26 deletions(-) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h create mode 100644 enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index a575183..4c64f91 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -213,7 +213,22 @@ void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContain TagContainer = ABInterface->NativeGetEffectsComponent()->AppliedTags.AllTags; } } +void UAFAbilityComponent::OnGameplayTaskActivated(UGameplayTask& Task) +{ + Super::OnGameplayTaskActivated(Task); + if (UGAAbilityTask* ABTask = Cast(&Task)) + { + if (ABTask->IsReplicated()) + { + if (SimulatedTasks.Contains(&Task) == false) + { + SimulatedTasks.Add(&Task); + bIsNetDirty = true; + } + } + } +} const bool FGASAbilityItem::operator==(const FGameplayTag& AbilityTag) const { return Ability->AbilityTag == AbilityTag; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 914fd81..65adb79 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -415,6 +415,18 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, IGameplayTagAssetInterface End */ + // BEGIN IGameplayTaskOwnerInterface + /* + Overrided because I'm not using GameplayTasks as they were meant to. + Create tasks, hold for it for a while and then destroy it (even for replicated tasks). + Instead I cache tasks off, and reuse them, which mean I don't want to fail at check if tasks is already simulated (because it is). + Instead if tasks is already simulating I simply skip adding it. + + I also want to manually remove tasks, when they ability that owns them is removed. + */ + virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + // END IGameplayTaskOwnerInterface + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp index e6b3bb0..fd3b10c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp @@ -7,6 +7,7 @@ UGAAbilityTask::UGAAbilityTask(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { + bIsReplicated = false; bTickingTask = false; bSimulatedTask = false; bIsSimulating = false; @@ -36,27 +37,27 @@ void UGAAbilityTask::EndAbilityTask() } -int32 UGAAbilityTask::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) -{ - if (HasAnyFlags(RF_ClassDefaultObject)) - { - return FunctionCallspace::Local; - } - check(AbilityComponent.IsValid()); - return AbilityComponent->GetFunctionCallspace(Function, Parameters, Stack); -} -bool UGAAbilityTask::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) -{ - check(!HasAnyFlags(RF_ClassDefaultObject)); - check(AbilityComponent.IsValid()); - - - UNetDriver* NetDriver = AbilityComponent->GetOwner()->GetNetDriver(); - if (NetDriver) - { - NetDriver->ProcessRemoteFunction(AbilityComponent->GetOwner(), Function, Parameters, OutParms, Stack, this); - return true; - } - - return false; -} \ No newline at end of file +//int32 UGAAbilityTask::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) +//{ +// if (HasAnyFlags(RF_ClassDefaultObject)) +// { +// return FunctionCallspace::Local; +// } +// check(AbilityComponent.IsValid()); +// return AbilityComponent->GetFunctionCallspace(Function, Parameters, Stack); +//} +//bool UGAAbilityTask::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) +//{ +// check(!HasAnyFlags(RF_ClassDefaultObject)); +// check(AbilityComponent.IsValid()); +// +// +// UNetDriver* NetDriver = AbilityComponent->GetOwner()->GetNetDriver(); +// if (NetDriver) +// { +// NetDriver->ProcessRemoteFunction(AbilityComponent->GetOwner(), Function, Parameters, OutParms, Stack, this); +// return true; +// } +// +// return false; +//} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 6e9bb0a..62fbd0d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -25,6 +25,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask GENERATED_UCLASS_BODY() friend struct FAFAbilityTaskMessageTick; public: + uint8 bIsReplicated : 1; /* Ability owning this task */ TWeakObjectPtr Ability; /* Ability owning this task */ @@ -72,9 +73,14 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask static_assert(DelayedFalse(), "UAbilityTask::NewTask should never be used. Use NewAbilityTask instead"); } + bool IsReplicated() + { + return bIsReplicated; + } + //network overrides: - int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; - virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + //int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; + //virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; protected: void EndAbilityTask(); @@ -90,4 +96,46 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask //MarkPendingKill(); } + + bool IsClient() + { + APawn* POwner = Ability->POwner; + if (POwner->GetNetMode() == ENetMode::NM_Client) + { + return true; + } + return false; + } + + bool IsServer() + { + APawn* POwner = Ability->POwner; + if (POwner->GetNetMode() == ENetMode::NM_DedicatedServer + || POwner->GetNetMode() == ENetMode::NM_ListenServer) + { + return true; + } + return false; + } + bool IsServerOrStandalone() + { + APawn* POwner = Ability->POwner; + if (POwner->GetNetMode() == ENetMode::NM_DedicatedServer + || POwner->GetNetMode() == ENetMode::NM_ListenServer + || POwner->GetNetMode() == ENetMode::NM_Standalone) + { + return true; + } + return false; + } + + bool IsAuthority() + { + APawn* POwner = Ability->POwner; + if (POwner->Role >= ENetRole::ROLE_Authority) + { + return true; + } + return false; + } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp new file mode 100644 index 0000000..7dd4c9e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp @@ -0,0 +1,219 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Abilities/GAAbilityBase.h" +#include "GAAbilityTask_TargetDataLineTrace.h" + + +UGAAbilityTask_TargetDataLineTrace* UGAAbilityTask_TargetDataLineTrace::CreateTargetDataLineTrace(UObject* WorldContextObject + , FName InTaskName + , ETraceTypeQuery InTraceChannel + , USkeletalMeshComponent* InSocketComponent + , FName InSocketName + , bool bDrawDebug + , EAFConfirmType ConfirmTypeIn + , float Range) +{ + auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); + + if (MyObj) + { + MyObj->TraceChannel = InTraceChannel; + MyObj->Range = Range; + MyObj->ConfirmType = ConfirmTypeIn; + MyObj->SocketComponent = InSocketComponent; + MyObj->SocketName = InSocketName; + MyObj->bIsTickable = false; + MyObj->bDrawDebug = bDrawDebug; + } + return MyObj; +} +UGAAbilityTask_TargetDataLineTrace::UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bSimulatedTask = false; + bIsReplicated = true; +} +void UGAAbilityTask_TargetDataLineTrace::Activate() +{ + LocalHitResult.Reset(1, false); + FHitResult HitData; + switch (ConfirmType) + { + case EAFConfirmType::Instant: + { + HitData = LineTrace(); + LocalHitResult = HitData; + //OnClient... Is called on both Client and server and is result of local simulation + //unconfirmed by server. This result might get overrided when data from server arrive to client + //it's good to spawn some cosmetic effects, but shouldn't be used to actually confirm hit result on client. + + //OnServer.. is confirmed by server that we got hit (or not), and should be used to show client confirmation + //for hits. + if (IsServerOrStandalone()) + { + OnClientReceiveTargetData.Broadcast(HitData); + OnServerReceiveTargetData.Broadcast(HitData); + EndTask(); + } + else + { + OnClientReceiveTargetData.Broadcast(HitData); + } + break; + } + case EAFConfirmType::WaitForConfirm: + { + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetDataLineTrace::OnConfirm); + bIsTickable = true; + } + if (!Ability->OnConfirmCastingEndedDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmCastingEndedDelegate.AddUObject(this, &UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm); + } + } + break; + } + } + if (HitData.IsValidBlockingHit()) + { + if (AbilityComponent->GetOwnerRole() < ROLE_Authority) + { + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + + PC->PlayerState->RecalculateAvgPing(); + float ExactPing = PC->PlayerState->ExactPing; + + FAFLineTraceData TraceData; + TraceData.ExactPing = ExactPing; + TraceData.HitActor = HitData.GetActor(); + TraceData.HitLocation = HitData.Location; + + ServerConfirmHitInfo(TraceData); + } + } +} + +void UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData) +{ + int test = 0; + FAFLineTraceConfirmData ConfirmData; + ConfirmData.bConfirmed = true; + ConfirmData.HitActor = LocalHitResult.GetActor(); + ConfirmData.HitLocation = LocalHitResult.Location; + ClientConfirmHitInfo(ConfirmData); +} +bool UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Validate(FAFLineTraceData TraceData) +{ + return true; +} + +void UGAAbilityTask_TargetDataLineTrace::ClientConfirmHitInfo_Implementation(FAFLineTraceConfirmData ConfirmData) +{ + if (ConfirmData.bConfirmed) + { + OnServerReceiveTargetData.Broadcast(LocalHitResult); + } + else + { + LocalHitResult.Actor = ConfirmData.HitActor; + LocalHitResult.Location = ConfirmData.HitLocation; + LocalHitResult.ImpactPoint = ConfirmData.HitLocation; + OnServerReceiveTargetData.Broadcast(LocalHitResult); + } +} + +// --------------------------------------------------------------------------------------- + +void UGAAbilityTask_TargetDataLineTrace::OnConfirm() +{ + FHitResult Hit = LineTrace(); + OnConfirmed.Broadcast(Hit); + Ability->OnConfirmDelegate.RemoveAll(this); +} +void UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm() +{ + FHitResult Hit = LineTrace(); + OnClientReceiveTargetData.Broadcast(Hit); + bIsTickable = false; + EndTask(); +} +void UGAAbilityTask_TargetDataLineTrace::Tick(float DeltaTime) +{ + //FHitResult HitOut = LineTrace(); +} + +FHitResult UGAAbilityTask_TargetDataLineTrace::LineTrace() +{ + FHitResult HitOut; + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + + + UCameraComponent* Camera = Ability->OwnerCamera; + FVector TraceStart; + FRotator UnusedRot; + if (PC) + { + PC->PlayerCameraManager->GetCameraViewPoint(TraceStart, UnusedRot); +// TraceStart = Camera->GetComponentLocation(); + } + else + { + UnusedRot = P->GetBaseAimRotation(); + TraceStart = P->GetPawnViewLocation(); + } + + FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; + UWorld* World = GetWorld(); + FCollisionQueryParams ColParams; + ColParams.AddIgnoredActor(P); + FCollisionResponseParams ColResp; + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, CollisionChannel, ColParams, ColResp); + if (HitOut.bBlockingHit) + { + FHitResult NewHit; + FVector Start = SocketComponent->GetSocketLocation(SocketName); + FVector NewDir = (HitOut.Location - Start).GetSafeNormal(); + float Distance = FVector::Dist(Start, HitOut.Location); + FVector End = Start + (NewDir * Range); + World->LineTraceSingleByChannel(NewHit, Start, End, CollisionChannel, ColParams, ColResp); + UE_LOG(AbilityFramework, Log, TEXT("UGAAbilityTask_TargetDataLineTrace::LineTrace Corrected")); + if (bDrawDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1.0f); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, false, 1.0f); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, false, 1.0f); + } + } + } + else + { + FHitResult NewHit; + FVector Start = SocketComponent->GetSocketLocation(SocketName); + FVector NewDir = (TraceEnd - Start).GetSafeNormal(); + float Distance = Range - FVector::Dist(TraceStart, Start); + FVector End = Start + (NewDir * Distance); + + World->LineTraceSingleByChannel(NewHit, Start, End, CollisionChannel, ColParams, ColResp); + UE_LOG(AbilityFramework, Log, TEXT("UGAAbilityTask_TargetDataLineTrace::LineTrace")); + if (bDrawDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1.0f); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, false, 1.0f); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, false, 1.0f); + } + } + } + return HitOut; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h new file mode 100644 index 0000000..c8beb76 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h @@ -0,0 +1,107 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "Components/SkeletalMeshComponent.h" +#include "GAAbilityTask_TargetDataLineTrace.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnTargetReceived, const FHitResult&, HitResult); + +UENUM() +enum class EAFConfirmType : uint8 +{ + Instant, + WaitForConfirm +}; + +USTRUCT() +struct FAFLineTraceData +{ + GENERATED_BODY() + UPROPERTY() + float ExactPing; + UPROPERTY() + AActor* HitActor; + UPROPERTY() + FVector HitLocation; +}; +USTRUCT() +struct FAFLineTraceConfirmData +{ + GENERATED_BODY() + + UPROPERTY() + uint8 bConfirmed : 1; + UPROPERTY() + AActor* HitActor; + UPROPERTY() + FVector HitLocation; +}; +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataLineTrace : public UGAAbilityTask, public FTickableGameObject +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnConfirmed; + + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnClientReceiveTargetData; + + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnServerReceiveTargetData; + + ETraceTypeQuery TraceChannel; + USkeletalMeshComponent* SocketComponent; + FName SocketName; + EAFConfirmType ConfirmType; + + float Range; + bool bIsTickable; + bool bDrawDebug; + + //Result of trace from either server or client simulation + FHitResult LocalHitResult; +public: + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_TargetDataLineTrace* CreateTargetDataLineTrace(UObject* WorldContextObject + , FName InTaskName + , ETraceTypeQuery InTraceChannel + , USkeletalMeshComponent* InSocketComponent + , FName InSocketName + , bool bDrawDebug + , EAFConfirmType ConfirmTypeIn + , float Range); + + UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer); + + virtual void Activate() override; + + UFUNCTION(Server, Reliable, WithValidation) + void ServerConfirmHitInfo(FAFLineTraceData TraceData); + void ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData); + bool ServerConfirmHitInfo_Validate(FAFLineTraceData TraceData); + + UFUNCTION(Client, Reliable) + void ClientConfirmHitInfo(FAFLineTraceConfirmData ConfirmData); + void ClientConfirmHitInfo_Implementation(FAFLineTraceConfirmData ConfirmData); + + UFUNCTION() + void OnConfirm(); + + UFUNCTION() + void OnCastEndedConfirm(); + + /* FTickableGameObject Begin */ + virtual void Tick(float DeltaTime) override; + virtual bool IsTickable() const override { return bIsTickable; } + virtual TStatId GetStatId() const override { RETURN_QUICK_DECLARE_CYCLE_STAT(UGAAbilityTask_TargetData, STATGROUP_Tickables); }; + /* FTickableGameObject End */ + +protected: + FHitResult LineTrace(); +}; diff --git a/enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h b/enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h new file mode 100644 index 0000000..84b4f19 --- /dev/null +++ b/enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h @@ -0,0 +1,693 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "GameplayTaskOwnerInterface.h" +#include "GameplayTaskTypes.h" +#include "GameplayTask.h" +#include "GameplayTasksComponent.h" +#include "GameplayTags.h" +#include "AFAbilityTypes.h" + +#include "Attributes/GAAttributeBase.h" +#include "Attributes/GAAttributesBase.h" +#include "Effects/GAEffectCueGlobals.h" + +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" + +#include "GameplayTagAssetInterface.h" + +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" + +#include "AFAbilityComponent.generated.h" + +DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); + +DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); + + +DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); + +DECLARE_DELEGATE(FAFOnAbilityReady); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); +DECLARE_DELEGATE(FAFGenericAttributeDelegate); + + +//UAFAssetManager* GetAssetManager() +//{ +// return Cast(UAssetManager::GetIfValid()); +//}; + +USTRUCT() +struct FGAModifiedAttributeData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + TArray Mods; + UPROPERTY() + int32 ForceUpdate; + + FGAModifiedAttributeData() + : ForceUpdate(0) + {} +}; + +USTRUCT(BlueprintType) +struct FGAEffectUIData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "UI") + float RemainingTime; + + FGAEffectUIData() + : RemainingTime(0) + {}; +}; +struct FGAContextSetup +{ +public: + UGAAttributesBase* IntigatorAttributes; + UGAAttributesBase* TargetAttributes; + UAFAbilityComponent* InstigatorComp; + UAFAbilityComponent* TargetComp; + + FGAContextSetup() + {}; + FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, + UAFAbilityComponent* InstigatorCompIn, UAFAbilityComponent* TargetCompIn) + : IntigatorAttributes(IntigatorAttributesIn), + TargetAttributes(TargetAttributesIn), + InstigatorComp(InstigatorCompIn), + TargetComp(TargetCompIn) + {}; +}; +DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); +DECLARE_DELEGATE_TwoParams(FAFMontageGenericDelegate, const FGameplayTag&, const FName&); +/* TODO:: Implement fast serialization for structs. */ +/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ +/**/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASMontageRepData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + UAnimMontage* CurrentMontage; + + UPROPERTY() + FName SectionName; + + UPROPERTY() + uint8 ForceRep; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem +{ + GENERATED_BODY() + +public: + UPROPERTY() + UGAAbilityBase* Ability; + + void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); + void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); + void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); + + const bool operator==(const FGameplayTag& AbilityTag) const; + const bool operator==(UGAAbilityBase* OtherAbility) const + { + return Ability == OtherAbility; + } + const bool operator==(const FGASAbilityItem& OtherItem) const + { + return Ability == OtherItem.Ability; + } +}; +USTRUCT() +struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + + UPROPERTY() + TArray AbilitiesItems; + + TWeakObjectPtr AbilitiesComp; + TMap BlockedInput; + + + //Custom binding, for server side validation. + //ActionInput, AbilityTag + TMap ActionToAbility; + //AbilityTag, ActionInput + TMap> AbilityToAction; + //abilityTag, Ability Ptr + TMap AbilitiesInputs; + + TMap TagToAbility; + + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, + AActor* InAvatar); + void RemoveAbility(const FGameplayTag& AbilityIn); + + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InInputTag); + void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag); + + UGAAbilityBase* GetAbility(FGameplayTag TagIn); + + void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); + void HandleInputReleased(FGameplayTag ActionName); + + void TriggerAbylityByTag(FGameplayTag InTag); + bool AbilityExists(const FGameplayTag& AbilityTag) const + { + return AbilitiesInputs.Contains(AbilityTag); + } + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + + +USTRUCT() +struct FAFReplicatedAttributeItem : public FFastArraySerializerItem +{ + GENERATED_BODY() +public: + UPROPERTY() + FGameplayTag AttributeTag; + UPROPERTY() + UGAAttributesBase* Attributes; + + void PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer); + void PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer); + void PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer); +}; + +USTRUCT() +struct FAFReplicatedAttributeContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + UPROPERTY() + TArray Attributes; + + UPROPERTY() + TMap AttributeMap; + + + TMap AttributeReplicatedEvent; + + void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FSimpleDelegate& InDelegate) + { + if (!AttributeReplicatedEvent.Contains(InTag)) + return; + + AttributeReplicatedEvent.Add(InTag, InDelegate); + } + + void OnAttributeReplicated(const FGameplayTag& InTag) const + { + if (const FSimpleDelegate* Delegate = AttributeReplicatedEvent.Find(InTag)) + { + Delegate->Execute(); + //AttributeReplicatedEvent.Remove(InTag); + } + } + + UGAAttributesBase* Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter); + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(Attributes, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FAFReplicatedAttributeContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAbilityActionSet +{ + GENERATED_BODY() +public: + UPROPERTY() + FGameplayTag AbilityTag; + UPROPERTY() + TArray AbilityInputs; +}; + +UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) +class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface +{ + GENERATED_BODY() + /* Attributes handling */ +public: + //Only for base testing and prototyping cue application. + //will be removed when Cue Manager will be more functional. + + //FAFEffectTimerManager EffectTimerManager; + + UPROPERTY(EditAnywhere, Category = "Test") + FGameplayTag TagTest; + /* + Set attribute which will be considered for indicating whether or not actor is dead. + */ + UPROPERTY(EditAnywhere, Category = "Config") + FGAAttribute DeathAttribute; + + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray AbilityInputs; + + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DefaultTags; + + UPROPERTY() + FGACountedTagContainer AppliedTags; + + UPROPERTY() + FGACountedTagContainer ImmunityTags; + + UFUNCTION() + void OnRep_ActiveEffects(); + + UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) + FGameCueContainer ActiveCues; + UFUNCTION() + void OnRep_ActiveCues(); + /* + Could make it array. But realistically. How many times do you really need more, than one + attribute set for actor ? + + Of course array of attributes would allow to compose attributes from small discreete + attribute sets. On the other hand similiar funcionality can be achieved by using + inheritance. + + And I think that using inheritance in this case will be easier. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) + class UGAAttributesBase* DefaultAttributes; + + //probabaly replace FGameplayTag with FObjectKey + TMap AdditionalAttributes; + + UPROPERTY(Replicated) + FAFReplicatedAttributeContainer RepAttributes; + + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnAttributeModifed; + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnTargetAttributeModifed; + + + TMap AttributeChanged; + + + void BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData); + + virtual bool GetShouldTick() const override; + + UFUNCTION() + void OnRep_GameEffectContainer(); + + template + T* GetAttributes() + { + return CastChecked(DefaultAttributes); + } + + template + T* GetAttributeSet(FGameplayTag InOwner) + { + UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); + return Cast(AttributeSet); + } + UGAAttributesBase* AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) + { + if (!InAttributes) + return nullptr; + UGAAttributesBase* retVal = RepAttributes.Add(InOwner, InAttributes, this); + RepAttributes.MarkArrayDirty(); + + return retVal; + } + UFUNCTION(BlueprintCallable, Category = "Test") + void GetAttributeStructTest(FGAAttribute Name); + + /** UActorComponent Interface - Begin */ + virtual void BeginPlay() override; + virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; + virtual void DestroyComponent(bool bPromoteChildren = false) override; + virtual void InitializeComponent() override; + virtual void UninitializeComponent() override; + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + /* UActorComponent Interface - End **/ + +public: + ///////////////////////////////////////////////// + //////////// ATTRIBUTES HANDLING + + /* + Two functions, They will allow to apply any static numerical mods from player who + initiated attribute change, and from player who will be affected by change. + + Mods will be appiled by small objects, and changed against tags. + For example there might be physical armor mod, which will apply changes only + to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. + */ + + inline float GetFinalAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetFinalAttributeValue(Name); + } + inline float GetCurrentAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetCurrentAttributeValue(Name); + } + //////////// ATTRIBUTES HANDLING + ///////////////////////////////////////////////// + /* + Attribute replication. + */ + void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); + //Helper functions: +public: + /* + IGameplayTagAssetInterface Start + */ + /** + * Get any owned gameplay tags on the asset + * + * @param OutTags [OUT] Set of tags on the asset + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; + + /* + IGameplayTagAssetInterface End + */ + + // BEGIN IGameplayTaskOwnerInterface + virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + // END IGameplayTaskOwnerInterface + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; + + void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext); + FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; + float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + +private: + class IAFAbilityInterface* AttributeInterface; + +public: + UAFAbilityComponent(const FObjectInitializer& ObjectInitializer); + + UFUNCTION() + void OnRep_InstancedAbilities(); + UPROPERTY(Replicated) + FGASAbilityContainer AbilityContainer; + UPROPERTY() + TArray AbilitiesRefs; + + UPROPERTY() + APlayerController* PCOwner; + + /* Ability which is currently being executed. */ + UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") + class UGAAbilityBase* ExecutingAbility; + + + + /*UFUNCTION(NetMulticast, Reliable) + MulticastExecuteEffect()*/ + + + + + /* + True if player is currently casting/channeling/activating(?) + any ability. + */ + bool bIsAnyAbilityActive; + + //AbilityTag, Delegate + TMap OnAbilityReadyMap; + + void AddOnAbilityReadyDelegate(const FGameplayTag& InAbilityTag, FAFOnAbilityReady& InDelegate) + { + if(InDelegate.IsBound()) + OnAbilityReadyMap.Add(InAbilityTag, InDelegate); + } + + void NotifyOnAbilityReady(const FGameplayTag& InAbilityTag) + { + if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityTag)) + { + Ready->ExecuteIfBound(); + OnAbilityReadyMap.Remove(InAbilityTag); + } + } + + TMap OnAbilityInputReadyMap; + + void AddOnAbilityInputReadyDelegate(const FGameplayTag& InAbilityTag, const FAFOnAbilityReady& InDelegate) + { + if(InDelegate.IsBound()) + OnAbilityInputReadyMap.Add(InAbilityTag, InDelegate); + } + + void NotifyOnAbilityInputReady(const FGameplayTag& InAbilityTag) + { + if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityTag)) + { + Ready->ExecuteIfBound(); + OnAbilityInputReadyMap.Remove(InAbilityTag); + } + } + + TMap> OnPreAttributeModifiedMap; + void AddOnPreAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) + { + TArray& delegates = OnPreAttributeModifiedMap.FindOrAdd(InAttribute); + delegates.Add(InDelegate); + } + + void NotifyOnPreAttributeModified(const FGAAttribute& InAttribute) + { + if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) + { + for(const FAFGenericAttributeDelegate& delegate : *Ready) + delegate.ExecuteIfBound(); + } + } + + void RemoveOnPreAttributeModified(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& Delegate) + { + if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) + { + //Ready->RemoveSingle(Delegate); + if (Ready->Num() <= 0) + { + OnPreAttributeModifiedMap.Remove(InAttribute); + } + } + } + + TMap> OnPostAttributeModifiedMap; + void AddOnPostAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) + { + TArray& delegates = OnPostAttributeModifiedMap.FindOrAdd(InAttribute); + delegates.Add(InDelegate); + } + + void NotifyOnPostAttributeModified(const FGAAttribute& InAttribute) + { + if (TArray* Ready = OnPostAttributeModifiedMap.Find(InAttribute)) + { + for (const FAFGenericAttributeDelegate& delegate : *Ready) + delegate.ExecuteIfBound(); + } + } + + + + FAFOnAbilityReady OnAbilityReady; + + UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") + FAFOnAbilityAdded OnAbilityAdded; + + FAFMontageGenericDelegate OnAbilityNotifyBegin; + FAFMontageGenericDelegate OnAbilityNotifyTick; + FAFMontageGenericDelegate OnAbilityNotifyEnd; + +private: + + + UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) + FGASMontageRepData RepMontage; + UFUNCTION() + void OnRep_PlayMontage(); + +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + UFUNCTION(NetMulticast, Unreliable) + void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); +public: + inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) + { + return nullptr; + } + + TMap BlockedInput; + //TSharedPtr AbilityLoadedHandle; + void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar); + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); + void BindInputs(class UInputComponent* InputComponent); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") + void BP_BindAbilityToAction(FGameplayTag ActionName); + void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); + + //need to be called on both client and server. + //Change InInputTag To Array, clear previous binds on the same tag. + void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); + + FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const TArray& InInputTag); +public: + /* Called when ability action has been binded on server. */ + UFUNCTION(Client, Reliable) + void ClientNotifyAbilityInputReady(FGameplayTag AbilityTag); + void ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag); + + + void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); + UFUNCTION(Server, Reliable, WithValidation) + void ServerSetAbilitiesToActions(const TArray& InAbilitiesActions); + void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); + bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); + + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") + void BP_InputPressed(FGameplayTag ActionName); + + void NativeInputPressed(FGameplayTag ActionName); +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + + +public: + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") + void BP_InputReleased(FGameplayTag ActionName); + + void NativeInputReleased(FGameplayTag ActionName); +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputReleased(FGameplayTag ActionName); + virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); + virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); +public: + /* + Finds ability using asset registry and then gives it to component. + Only valid on server. + Does not check if component can or can't have given ability. + So it must be checked before this function is called. + */ + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability From Tag"), Category = "AbilityFramework|Abilities") + void BP_AddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, TArray InInputTag); + + void NativeAddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, const TArray& InInputTag); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeAddAbilityFromTag(FGameplayTag InAbilityTag, + AActor* InAvatar, const TArray& InInputTag); + + void ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, + AActor* InAvatar, const TArray& InInputTag); + + bool ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, + AActor* InAvatar, const TArray& InInputTag); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") + void BP_RemoveAbility(FGameplayTag TagIn); + + void NativeRemoveAbility(const FGameplayTag& InAbilityTag); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeRemoveAbility(const FGameplayTag& InAbilityTag); + + void ServerNativeRemoveAbility_Implementation(FGameplayTag InAbilityTag); + + bool ServerNativeRemoveAbility_Validate(FGameplayTag InAbilityTag); + + //TODO: Make it procted + + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") + UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); + + + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; + void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; + + void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); +protected: + void InitializeInstancedAbilities(); + UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, + AActor* InAvatar); + /* + Messagin implementation for applying effects from multiple threads (in case + at some beatyfull day UObject will be able to exist on any thread), and from single thread. + + Implementation is based on FMessageEndpoint. + */ + +}; + + + From b86cea25f37e64499e825483d5bde4670fa1a12a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Mon, 2 Apr 2018 23:25:28 +0200 Subject: [PATCH 096/187] remove simulated tasks, when ability that created them is removed --- .../AbilityFramework/AFAbilityComponent.cpp | 17 + .../AbilityFramework/AFAbilityComponent.h | 3 +- .../AFAbilityComponent.h | 693 ------------------ 3 files changed, 19 insertions(+), 694 deletions(-) delete mode 100644 enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 4c64f91..41ab779 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -3,6 +3,7 @@ #include "AbilityFramework.h" #include "Abilities/GAAbilityBase.h" +#include "Abilities/Tasks/GAAbilityTask.h" #include "IAbilityFramework.h" #include "Net/UnrealNetwork.h" @@ -127,6 +128,11 @@ void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickTyp } } +void UAFAbilityComponent::RemoveSimulatedTask(class UGAAbilityTask* Task) +{ + SimulatedTasks.Remove(Task); +} + void UAFAbilityComponent::BeginPlay() { Super::BeginPlay(); @@ -307,6 +313,8 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOfGetNetMode() == ENetMode::NM_Standalone || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) @@ -328,6 +336,15 @@ void FGASAbilityContainer::RemoveAbility(const FGameplayTag& AbilityIn) if (Index == INDEX_NONE) return; + + UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); + + for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) + { + AbilitiesComp->RemoveSimulatedTask(It->Value); + } + + TagToAbility.Remove(AbilityIn); MarkItemDirty(AbilitiesItems[Index]); RemoveAbilityFromAction(AbilityIn); AbilitiesItems.RemoveAt(Index); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 65adb79..0f83829 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -369,8 +369,9 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, virtual void InitializeComponent() override; virtual void UninitializeComponent() override; virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + /* UActorComponent Interface - End **/ - + void RemoveSimulatedTask(class UGAAbilityTask* Task); public: ///////////////////////////////////////////////// //////////// ATTRIBUTES HANDLING diff --git a/enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h b/enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h deleted file mode 100644 index 84b4f19..0000000 --- a/enc_temp_folder/757e284978f6b249eb3a6e68434e0d3/AFAbilityComponent.h +++ /dev/null @@ -1,693 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "GameplayTaskOwnerInterface.h" -#include "GameplayTaskTypes.h" -#include "GameplayTask.h" -#include "GameplayTasksComponent.h" -#include "GameplayTags.h" -#include "AFAbilityTypes.h" - -#include "Attributes/GAAttributeBase.h" -#include "Attributes/GAAttributesBase.h" -#include "Effects/GAEffectCueGlobals.h" - -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" - -#include "GameplayTagAssetInterface.h" - -#include "AssetRegistryModule.h" -#include "Engine/AssetManager.h" - -#include "AFAbilityComponent.generated.h" - -DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); -DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); -DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); - -DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); - - -DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); - -DECLARE_DELEGATE(FAFOnAbilityReady); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); -DECLARE_DELEGATE(FAFGenericAttributeDelegate); - - -//UAFAssetManager* GetAssetManager() -//{ -// return Cast(UAssetManager::GetIfValid()); -//}; - -USTRUCT() -struct FGAModifiedAttributeData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - TArray Mods; - UPROPERTY() - int32 ForceUpdate; - - FGAModifiedAttributeData() - : ForceUpdate(0) - {} -}; - -USTRUCT(BlueprintType) -struct FGAEffectUIData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(BlueprintReadOnly, Category = "UI") - float RemainingTime; - - FGAEffectUIData() - : RemainingTime(0) - {}; -}; -struct FGAContextSetup -{ -public: - UGAAttributesBase* IntigatorAttributes; - UGAAttributesBase* TargetAttributes; - UAFAbilityComponent* InstigatorComp; - UAFAbilityComponent* TargetComp; - - FGAContextSetup() - {}; - FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, - UAFAbilityComponent* InstigatorCompIn, UAFAbilityComponent* TargetCompIn) - : IntigatorAttributes(IntigatorAttributesIn), - TargetAttributes(TargetAttributesIn), - InstigatorComp(InstigatorCompIn), - TargetComp(TargetCompIn) - {}; -}; -DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); -DECLARE_DELEGATE_TwoParams(FAFMontageGenericDelegate, const FGameplayTag&, const FName&); -/* TODO:: Implement fast serialization for structs. */ -/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ -/**/ - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASMontageRepData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - UAnimMontage* CurrentMontage; - - UPROPERTY() - FName SectionName; - - UPROPERTY() - uint8 ForceRep; -}; - -USTRUCT() -struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem -{ - GENERATED_BODY() - -public: - UPROPERTY() - UGAAbilityBase* Ability; - - void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); - void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); - void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); - - const bool operator==(const FGameplayTag& AbilityTag) const; - const bool operator==(UGAAbilityBase* OtherAbility) const - { - return Ability == OtherAbility; - } - const bool operator==(const FGASAbilityItem& OtherItem) const - { - return Ability == OtherItem.Ability; - } -}; -USTRUCT() -struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - - UPROPERTY() - TArray AbilitiesItems; - - TWeakObjectPtr AbilitiesComp; - TMap BlockedInput; - - - //Custom binding, for server side validation. - //ActionInput, AbilityTag - TMap ActionToAbility; - //AbilityTag, ActionInput - TMap> AbilityToAction; - //abilityTag, Ability Ptr - TMap AbilitiesInputs; - - TMap TagToAbility; - - void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, - AActor* InAvatar); - void RemoveAbility(const FGameplayTag& AbilityIn); - - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InInputTag); - void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag); - - UGAAbilityBase* GetAbility(FGameplayTag TagIn); - - void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); - void HandleInputReleased(FGameplayTag ActionName); - - void TriggerAbylityByTag(FGameplayTag InTag); - bool AbilityExists(const FGameplayTag& AbilityTag) const - { - return AbilitiesInputs.Contains(AbilityTag); - } - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; - - -USTRUCT() -struct FAFReplicatedAttributeItem : public FFastArraySerializerItem -{ - GENERATED_BODY() -public: - UPROPERTY() - FGameplayTag AttributeTag; - UPROPERTY() - UGAAttributesBase* Attributes; - - void PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer); - void PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer); - void PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer); -}; - -USTRUCT() -struct FAFReplicatedAttributeContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - UPROPERTY() - TArray Attributes; - - UPROPERTY() - TMap AttributeMap; - - - TMap AttributeReplicatedEvent; - - void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FSimpleDelegate& InDelegate) - { - if (!AttributeReplicatedEvent.Contains(InTag)) - return; - - AttributeReplicatedEvent.Add(InTag, InDelegate); - } - - void OnAttributeReplicated(const FGameplayTag& InTag) const - { - if (const FSimpleDelegate* Delegate = AttributeReplicatedEvent.Find(InTag)) - { - Delegate->Execute(); - //AttributeReplicatedEvent.Remove(InTag); - } - } - - UGAAttributesBase* Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter); - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(Attributes, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FAFReplicatedAttributeContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; - - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFAbilityActionSet -{ - GENERATED_BODY() -public: - UPROPERTY() - FGameplayTag AbilityTag; - UPROPERTY() - TArray AbilityInputs; -}; - -UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) -class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface -{ - GENERATED_BODY() - /* Attributes handling */ -public: - //Only for base testing and prototyping cue application. - //will be removed when Cue Manager will be more functional. - - //FAFEffectTimerManager EffectTimerManager; - - UPROPERTY(EditAnywhere, Category = "Test") - FGameplayTag TagTest; - /* - Set attribute which will be considered for indicating whether or not actor is dead. - */ - UPROPERTY(EditAnywhere, Category = "Config") - FGAAttribute DeathAttribute; - - UPROPERTY(EditAnywhere, Category = "Input Config") - TArray AbilityInputs; - - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer DefaultTags; - - UPROPERTY() - FGACountedTagContainer AppliedTags; - - UPROPERTY() - FGACountedTagContainer ImmunityTags; - - UFUNCTION() - void OnRep_ActiveEffects(); - - UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) - FGameCueContainer ActiveCues; - UFUNCTION() - void OnRep_ActiveCues(); - /* - Could make it array. But realistically. How many times do you really need more, than one - attribute set for actor ? - - Of course array of attributes would allow to compose attributes from small discreete - attribute sets. On the other hand similiar funcionality can be achieved by using - inheritance. - - And I think that using inheritance in this case will be easier. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) - class UGAAttributesBase* DefaultAttributes; - - //probabaly replace FGameplayTag with FObjectKey - TMap AdditionalAttributes; - - UPROPERTY(Replicated) - FAFReplicatedAttributeContainer RepAttributes; - - UPROPERTY(BlueprintAssignable, Category = "Game Attributes") - FGAOnAttributeModifed OnAttributeModifed; - UPROPERTY(BlueprintAssignable, Category = "Game Attributes") - FGAOnAttributeModifed OnTargetAttributeModifed; - - - TMap AttributeChanged; - - - void BroadcastAttributeChange(const FGAAttribute& InAttribute, - const FAFAttributeChangedData& InData); - - virtual bool GetShouldTick() const override; - - UFUNCTION() - void OnRep_GameEffectContainer(); - - template - T* GetAttributes() - { - return CastChecked(DefaultAttributes); - } - - template - T* GetAttributeSet(FGameplayTag InOwner) - { - UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); - return Cast(AttributeSet); - } - UGAAttributesBase* AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) - { - if (!InAttributes) - return nullptr; - UGAAttributesBase* retVal = RepAttributes.Add(InOwner, InAttributes, this); - RepAttributes.MarkArrayDirty(); - - return retVal; - } - UFUNCTION(BlueprintCallable, Category = "Test") - void GetAttributeStructTest(FGAAttribute Name); - - /** UActorComponent Interface - Begin */ - virtual void BeginPlay() override; - virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; - virtual void DestroyComponent(bool bPromoteChildren = false) override; - virtual void InitializeComponent() override; - virtual void UninitializeComponent() override; - virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - /* UActorComponent Interface - End **/ - -public: - ///////////////////////////////////////////////// - //////////// ATTRIBUTES HANDLING - - /* - Two functions, They will allow to apply any static numerical mods from player who - initiated attribute change, and from player who will be affected by change. - - Mods will be appiled by small objects, and changed against tags. - For example there might be physical armor mod, which will apply changes only - to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. - */ - - inline float GetFinalAttributeValue(const FGAAttribute& Name) - { - return DefaultAttributes->GetFinalAttributeValue(Name); - } - inline float GetCurrentAttributeValue(const FGAAttribute& Name) - { - return DefaultAttributes->GetCurrentAttributeValue(Name); - } - //////////// ATTRIBUTES HANDLING - ///////////////////////////////////////////////// - /* - Attribute replication. - */ - void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); - //Helper functions: -public: - /* - IGameplayTagAssetInterface Start - */ - /** - * Get any owned gameplay tags on the asset - * - * @param OutTags [OUT] Set of tags on the asset - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; - - /* - IGameplayTagAssetInterface End - */ - - // BEGIN IGameplayTaskOwnerInterface - virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - // END IGameplayTaskOwnerInterface - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; - - void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; - void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, - const FGAEffectContext& InContext); - FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; - void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; - float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; - -private: - class IAFAbilityInterface* AttributeInterface; - -public: - UAFAbilityComponent(const FObjectInitializer& ObjectInitializer); - - UFUNCTION() - void OnRep_InstancedAbilities(); - UPROPERTY(Replicated) - FGASAbilityContainer AbilityContainer; - UPROPERTY() - TArray AbilitiesRefs; - - UPROPERTY() - APlayerController* PCOwner; - - /* Ability which is currently being executed. */ - UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") - class UGAAbilityBase* ExecutingAbility; - - - - /*UFUNCTION(NetMulticast, Reliable) - MulticastExecuteEffect()*/ - - - - - /* - True if player is currently casting/channeling/activating(?) - any ability. - */ - bool bIsAnyAbilityActive; - - //AbilityTag, Delegate - TMap OnAbilityReadyMap; - - void AddOnAbilityReadyDelegate(const FGameplayTag& InAbilityTag, FAFOnAbilityReady& InDelegate) - { - if(InDelegate.IsBound()) - OnAbilityReadyMap.Add(InAbilityTag, InDelegate); - } - - void NotifyOnAbilityReady(const FGameplayTag& InAbilityTag) - { - if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityTag)) - { - Ready->ExecuteIfBound(); - OnAbilityReadyMap.Remove(InAbilityTag); - } - } - - TMap OnAbilityInputReadyMap; - - void AddOnAbilityInputReadyDelegate(const FGameplayTag& InAbilityTag, const FAFOnAbilityReady& InDelegate) - { - if(InDelegate.IsBound()) - OnAbilityInputReadyMap.Add(InAbilityTag, InDelegate); - } - - void NotifyOnAbilityInputReady(const FGameplayTag& InAbilityTag) - { - if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityTag)) - { - Ready->ExecuteIfBound(); - OnAbilityInputReadyMap.Remove(InAbilityTag); - } - } - - TMap> OnPreAttributeModifiedMap; - void AddOnPreAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) - { - TArray& delegates = OnPreAttributeModifiedMap.FindOrAdd(InAttribute); - delegates.Add(InDelegate); - } - - void NotifyOnPreAttributeModified(const FGAAttribute& InAttribute) - { - if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) - { - for(const FAFGenericAttributeDelegate& delegate : *Ready) - delegate.ExecuteIfBound(); - } - } - - void RemoveOnPreAttributeModified(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& Delegate) - { - if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) - { - //Ready->RemoveSingle(Delegate); - if (Ready->Num() <= 0) - { - OnPreAttributeModifiedMap.Remove(InAttribute); - } - } - } - - TMap> OnPostAttributeModifiedMap; - void AddOnPostAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) - { - TArray& delegates = OnPostAttributeModifiedMap.FindOrAdd(InAttribute); - delegates.Add(InDelegate); - } - - void NotifyOnPostAttributeModified(const FGAAttribute& InAttribute) - { - if (TArray* Ready = OnPostAttributeModifiedMap.Find(InAttribute)) - { - for (const FAFGenericAttributeDelegate& delegate : *Ready) - delegate.ExecuteIfBound(); - } - } - - - - FAFOnAbilityReady OnAbilityReady; - - UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") - FAFOnAbilityAdded OnAbilityAdded; - - FAFMontageGenericDelegate OnAbilityNotifyBegin; - FAFMontageGenericDelegate OnAbilityNotifyTick; - FAFMontageGenericDelegate OnAbilityNotifyEnd; - -private: - - - UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) - FGASMontageRepData RepMontage; - UFUNCTION() - void OnRep_PlayMontage(); - -public: - UFUNCTION(BlueprintCallable, Category = "AbilityFramework") - void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); - UFUNCTION(NetMulticast, Unreliable) - void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); -public: - inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) - { - return nullptr; - } - - TMap BlockedInput; - //TSharedPtr AbilityLoadedHandle; - void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar); - void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - void BindInputs(class UInputComponent* InputComponent); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") - void BP_BindAbilityToAction(FGameplayTag ActionName); - void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); - - //need to be called on both client and server. - //Change InInputTag To Array, clear previous binds on the same tag. - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); - - FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const TArray& InInputTag); -public: - /* Called when ability action has been binded on server. */ - UFUNCTION(Client, Reliable) - void ClientNotifyAbilityInputReady(FGameplayTag AbilityTag); - void ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag); - - - void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); - UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilitiesToActions(const TArray& InAbilitiesActions); - void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); - bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); - - - UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") - void BP_InputPressed(FGameplayTag ActionName); - - void NativeInputPressed(FGameplayTag ActionName); -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - - -public: - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") - void BP_InputReleased(FGameplayTag ActionName); - - void NativeInputReleased(FGameplayTag ActionName); -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputReleased(FGameplayTag ActionName); - virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); - virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); -public: - /* - Finds ability using asset registry and then gives it to component. - Only valid on server. - Does not check if component can or can't have given ability. - So it must be checked before this function is called. - */ - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability From Tag"), Category = "AbilityFramework|Abilities") - void BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, TArray InInputTag); - - void NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); - - void ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); - - bool ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") - void BP_RemoveAbility(FGameplayTag TagIn); - - void NativeRemoveAbility(const FGameplayTag& InAbilityTag); - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeRemoveAbility(const FGameplayTag& InAbilityTag); - - void ServerNativeRemoveAbility_Implementation(FGameplayTag InAbilityTag); - - bool ServerNativeRemoveAbility_Validate(FGameplayTag InAbilityTag); - - //TODO: Make it procted - - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") - UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); - - - bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; - void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; - - void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); -protected: - void InitializeInstancedAbilities(); - UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, - AActor* InAvatar); - /* - Messagin implementation for applying effects from multiple threads (in case - at some beatyfull day UObject will be able to exist on any thread), and from single thread. - - Implementation is based on FMessageEndpoint. - */ - -}; - - - From d081d5435e754f3972842d6fa3415bbc6e93938b Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 21:03:58 +0200 Subject: [PATCH 097/187] add damage effect array for weapon ability, and BP function to apply it --- Config/DefaultGameplayTags.ini | 2 ++ .../Weapons/ARWeaponAbilityBase.cpp | 34 ++++++++++++++++++- .../Weapons/ARWeaponAbilityBase.h | 27 ++++++++++++++- 3 files changed, 61 insertions(+), 2 deletions(-) diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index cc5d7cc..3639b95 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -43,6 +43,8 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="AI.WoodCollected",DevComment="") +GameplayTagList=(Tag="Cue.Ability.Shoot",DevComment="") +GameplayTagList=(Tag="Damage",DevComment="") ++GameplayTagList=(Tag="Damage.Damage",DevComment="") ++GameplayTagList=(Tag="Damage.Fire",DevComment="") +GameplayTagList=(Tag="Effect.InstancedDuration",DevComment="") +GameplayTagList=(Tag="EffectEvent.Expired.InstancedDuration",DevComment="") +GameplayTagList=(Tag="Event.Executed.Damage.Fire",DevComment="") diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp index ed0b52a..b2503ee 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -1,10 +1,11 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARWeaponAbilityBase.h" - +#include "Effects/GABlueprintLibrary.h" void UARWeaponAbilityBase::OnAbilityInited() { + ResetDamageEffects(); } void UARWeaponAbilityBase::OnAvatarReady() @@ -12,4 +13,35 @@ void UARWeaponAbilityBase::OnAvatarReady() //AARWeaponBase* Weapon = Cast(AvatarActor); //Weapon->SetPawn(POwner); //Weapon->Equip(); +} + +void UARWeaponAbilityBase::ReplaceDamageEffects(const TArray& InEffects) +{ + +} + +void UARWeaponAbilityBase::AddDamageEffects(const TArray& InEffects) +{ + +} + +void UARWeaponAbilityBase::ResetDamageEffects() +{ + DamageEffects.Empty(); + DamageEffects.Append(DefaultDamageEffects); + AppliedEffectHandles.Empty(); + AppliedEffectHandles.AddZeroed(DamageEffects.Num()); +} + +void UARWeaponAbilityBase::ApplyDamageEffect(UObject* Target, FAFFunctionModifier Modifier) +{ + for (int32 Idx = 0; Idx < DamageEffects.Num(); Idx++) + { + UGABlueprintLibrary::ApplyEffectToObject(DamageEffects[Idx] + , AppliedEffectHandles[Idx] + , Target + , POwner + , this + , Modifier); + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h index 935c5b1..e291df8 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "Abilities/ARAbilityBase.h" +#include "Effects/GAGameEffect.h" #include "ARWeaponAbilityBase.generated.h" class AARWeaponAvatar; @@ -14,8 +15,32 @@ UCLASS() class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase { GENERATED_BODY() - +protected: + + /* + Default damage effects used, when no upgrades are present for this weapon ability. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Damage") + TArray DefaultDamageEffects; + + /* + Damage effects which are actually applied by this weapon. + */ + UPROPERTY(BlueprintReadOnly, Category = "Damage") + TArray DamageEffects; + + /* + Handles to currently applied effects. Their order matches effects from DamageEffects array. + */ + TArray AppliedEffectHandles; public: virtual void OnAbilityInited() override; virtual void OnAvatarReady() override; + + void ReplaceDamageEffects(const TArray& InEffects); + void AddDamageEffects(const TArray& InEffects); + void ResetDamageEffects(); + + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapon") + void ApplyDamageEffect(UObject* Target, FAFFunctionModifier Modifier); }; From 59831ec8425e3356541b5db0902464352d013d8c Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 21:27:19 +0200 Subject: [PATCH 098/187] added ability event called after ability has been bound to some input --- .../Source/AbilityFramework/AFAbilityComponent.cpp | 12 ++++++++++++ .../AbilityFramework/Abilities/GAAbilityBase.h | 6 ++++++ 2 files changed, 18 insertions(+) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 41ab779..8c9f22c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -396,6 +396,13 @@ void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, } if (!AbilitiesComp.IsValid()) return; + + UGAAbilityBase* Ability = TagToAbility.FindRef(InAbilityTag); + if (Ability) + { + Ability->OnAbilityInputReady(); + } + if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) { AbilitiesComp->ClientNotifyAbilityInputReady(InAbilityTag); @@ -578,6 +585,11 @@ bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const FGameplayTag& void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag) { NotifyOnAbilityInputReady(AbilityTag); + UGAAbilityBase* Ability = AbilityContainer.TagToAbility.FindRef(AbilityTag); + if (Ability) + { + Ability->OnAbilityInputReady(); + } } void UAFAbilityComponent::SetAbilitiesToActions(const TArray& InAbilitiesActions diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 7f0f4f7..ac6d716 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -282,6 +282,12 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask void OnAttributeSetReplicated(); //called on both server and client after InitAbility(); virtual void OnAbilityInited(); + + /* + Called on server and client, after ability has been bound to some input. + */ + virtual void OnAbilityInputReady() {}; + /* * @call Order: * Previous Function: FGASAbilityContainer::HandleInputPressed From 09a7a93d7594761b3f056eab7999e0580cf839c5 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 21:40:35 +0200 Subject: [PATCH 099/187] fixed ability not being added to ability map on clients --- .../Source/AbilityFramework/AFAbilityComponent.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 8c9f22c..c0132ce 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -250,6 +250,7 @@ void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InA FGameplayTag AbilityTag = Ability->AbilityTag; InArraySerializerC.RemoveAbilityFromAction(AbilityTag); InArraySerializerC.AbilitiesInputs.Remove(AbilityTag); + InArraySerializerC.TagToAbility.Remove(AbilityTag); } } void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) @@ -271,6 +272,7 @@ void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArr UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = attr; InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); + InArraySerializerC.TagToAbility.Add(Ability->AbilityTag, Ability); InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(Ability->AbilityTag); } } From b66f17a233bdcbf7ba0e538f9d40bc548ca6f2b5 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 21:43:19 +0200 Subject: [PATCH 100/187] cache weapon actor in weapon ability --- .../ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp | 13 ++++++++++++- Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h | 5 +++++ 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp index b2503ee..f75c137 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -2,12 +2,23 @@ #include "ARWeaponAbilityBase.h" #include "Effects/GABlueprintLibrary.h" +#include "ARCharacter.h" +#include "ARWeaponBase.h" void UARWeaponAbilityBase::OnAbilityInited() { ResetDamageEffects(); } - +void UARWeaponAbilityBase::OnAbilityInputReady() +{ + if (AARCharacter* Character = Cast(POwner)) + { + if (AARWeaponBase* Weapon = Cast(Character->GetEquipedMainWeapon()->GetChildActor())) + { + WeaponActor = Weapon; + } + } +} void UARWeaponAbilityBase::OnAvatarReady() { //AARWeaponBase* Weapon = Cast(AvatarActor); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h index e291df8..0d1c6b6 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -33,8 +33,13 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase Handles to currently applied effects. Their order matches effects from DamageEffects array. */ TArray AppliedEffectHandles; + + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon") + class AARWeaponBase* WeaponActor; + public: virtual void OnAbilityInited() override; + virtual void OnAbilityInputReady() override; virtual void OnAvatarReady() override; void ReplaceDamageEffects(const TArray& InEffects); From 7ef1824c403106d362bfb1a3734060fc7aa59030 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 23:23:41 +0200 Subject: [PATCH 101/187] ability attribute cost is now array> --- .../Abilities/GAAbilityBase.cpp | 39 +++++++++++-------- .../Abilities/GAAbilityBase.h | 4 +- 2 files changed, 25 insertions(+), 18 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 95a0b7b..0ff27ca 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -138,8 +138,11 @@ void UGAAbilityBase::InitAbility() ActivationEffect.InitializeIfNotInitialized(DefaultContext); CooldownEffect.InitializeIfNotInitialized(DefaultContext); AttributeCost.InitializeIfNotInitialized(DefaultContext); - AbilityAttributeCost.InitializeIfNotInitialized(DefaultContext); - + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + } + AbilityAttributeCostHandle.AddZeroed(AbilityAttributeCost.Num()); if (AbilityComponent) { World = AbilityComponent->GetWorld(); @@ -560,14 +563,16 @@ bool UGAAbilityBase::ApplyAbilityAttributeCost() if (CheckAbilityAttributeCost()) { - AbilityAttributeCostHandle = UGABlueprintLibrary::ApplyGameEffectToObject( - AbilityAttributeCost - , AbilityAttributeCostHandle - , this - , POwner - , this - , Modifier); - + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + AbilityAttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( + AbilityAttributeCost[Idx] + , AbilityAttributeCostHandle[Idx] + , this + , POwner + , this + , Modifier); + } return true; } return false; @@ -586,12 +591,14 @@ bool UGAAbilityBase::BP_CheckAbilityAttributeCost() } bool UGAAbilityBase::CheckAbilityAttributeCost() { - float ModValue = AbilityAttributeCost.GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AbilityAttributeCost.GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Attributes->GetFloatValue(Attribute); - if (ModValue > AttributeVal) - return false; - + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Attributes->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + } return true; } bool UGAAbilityBase::IsOnCooldown() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index ac6d716..dd6eda7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -192,8 +192,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask Attribute cost from ability own attributes */ UPROPERTY(EditAnywhere, Category = "Config") - FAFPropertytHandle AbilityAttributeCost; - FGAEffectHandle AbilityAttributeCostHandle; + TArray AbilityAttributeCost; + TArray AbilityAttributeCostHandle; UPROPERTY(AssetRegistrySearchable) FName AbilityTagSearch; From 95bb246324ebe41651c374c152dabc2b93f1a170 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 23:33:49 +0200 Subject: [PATCH 102/187] added support for attribute cost from owner --- .../Abilities/GAAbilityBase.cpp | 36 +++++++++++++++++-- .../Abilities/GAAbilityBase.h | 4 ++- 2 files changed, 37 insertions(+), 3 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 0ff27ca..2074baf 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -137,7 +137,12 @@ void UGAAbilityBase::InitAbility() DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); ActivationEffect.InitializeIfNotInitialized(DefaultContext); CooldownEffect.InitializeIfNotInitialized(DefaultContext); - AttributeCost.InitializeIfNotInitialized(DefaultContext); + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + AttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + } + AttributeCostHandle.AddZeroed(AttributeCost.Num()); + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) { AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); @@ -553,7 +558,22 @@ float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const bool UGAAbilityBase::ApplyAttributeCost() { - return true; + FAFFunctionModifier Modifier; + if (CheckAttributeCost()) + { + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + UGABlueprintLibrary::ApplyGameEffectToObject( + AttributeCost[Idx] + , AttributeCostHandle[Idx] + , this + , POwner + , this + , Modifier); + } + return true; + } + return false; } bool UGAAbilityBase::ApplyAbilityAttributeCost() { @@ -601,6 +621,18 @@ bool UGAAbilityBase::CheckAbilityAttributeCost() } return true; } +bool UGAAbilityBase::CheckAttributeCost() +{ + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Attributes->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + } + return true; +} bool UGAAbilityBase::IsOnCooldown() { bool bOnCooldown = false; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index dd6eda7..8edf6b6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -187,7 +187,8 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask Attribute cost from Ability Owner attributes */ UPROPERTY(EditAnywhere, Category = "Config") - FAFPropertytHandle AttributeCost; + TArray AttributeCost; + TArray AttributeCostHandle; /* Attribute cost from ability own attributes */ @@ -506,6 +507,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask bool ApplyAttributeCost(); bool ApplyAbilityAttributeCost(); bool CheckAbilityAttributeCost(); + bool CheckAttributeCost(); bool IsOnCooldown(); bool IsActivating(); From e18758ec91f7e6190016f8e5f13f5b22c4454eb2 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Tue, 3 Apr 2018 23:38:56 +0200 Subject: [PATCH 103/187] fixed target and annded BP check function --- .../Abilities/GAAbilityBase.cpp | 13 +- .../Abilities/GAAbilityBase.h | 3 + .../GAAbilityBase.cpp | 944 ++++++++++++++++++ .../GAAbilityBase.h | 630 ++++++++++++ 4 files changed, 1587 insertions(+), 3 deletions(-) create mode 100644 enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp create mode 100644 enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 2074baf..709b9c5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -563,10 +563,10 @@ bool UGAAbilityBase::ApplyAttributeCost() { for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) { - UGABlueprintLibrary::ApplyGameEffectToObject( + AttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( AttributeCost[Idx] , AttributeCostHandle[Idx] - , this + , POwner , POwner , this , Modifier); @@ -601,6 +601,11 @@ bool UGAAbilityBase::BP_ApplyAttributeCost() { return ApplyAttributeCost(); } +bool UGAAbilityBase::BP_CheckAttributeCost() +{ + return CheckAttributeCost(); +} + bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() { return ApplyAbilityAttributeCost(); @@ -623,11 +628,13 @@ bool UGAAbilityBase::CheckAbilityAttributeCost() } bool UGAAbilityBase::CheckAttributeCost() { + IAFAbilityInterface* Interface = Cast(POwner); + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) { float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Attributes->GetFloatValue(Attribute); + float AttributeVal = Interface->GetAttributes()->GetFloatValue(Attribute); if (ModValue > AttributeVal) return false; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 8edf6b6..61c9868 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -519,6 +519,9 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Attribute Cost"), Category = "AbilityFramework|Abilities") bool BP_ApplyAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_CheckAttributeCost(); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") bool BP_ApplyAbilityAttributeCost(); diff --git a/enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp b/enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp new file mode 100644 index 0000000..2074baf --- /dev/null +++ b/enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp @@ -0,0 +1,944 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + + +#include "../AbilityFramework.h" +#include "Tasks/GAAbilityTask.h" +#include "../Effects/GAGameEffect.h" +#include "../GAGlobalTypes.h" +#include "../Effects/GAEffectGlobalTypes.h" +#include "../AFAbilityComponent.h" +#include "AFEffectsComponent.h" + +#include "GameplayTagContainer.h" +#include "Net/UnrealNetwork.h" +#include "Animation/AnimMontage.h" +#include "../Effects/GABlueprintLibrary.h" +#include "Camera/CameraComponent.h" +#include "Kismet/KismetSystemLibrary.h" + +#include "GAAbilityBase.h" +FAFPredictionHandle UGAAbilityBase::GetPredictionHandle() { return PredictionHandle; } + +UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bReplicate = true; + bIsNameStable = false; +} + +void UGAAbilityBase::PostInitProperties() +{ + UpdateAssetRegistryInfo(); + Super::PostInitProperties(); +} + +void UGAAbilityBase::Serialize(FArchive& Ar) +{ + if (Ar.IsSaving()) + { + UpdateAssetRegistryInfo(); + } + + Super::Serialize(Ar); + + if (Ar.IsLoading()) + { + UpdateAssetRegistryInfo(); + } +} +#if WITH_EDITORONLY_DATA +void UGAAbilityBase::UpdateAssetBundleData() +{ + AssetBundleData.Reset(); + + // By default parse the metadata + if (UAssetManager::IsValid()) + { + UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); + } +} + +void UGAAbilityBase::PreSave(const class ITargetPlatform* TargetPlatform) +{ + Super::PreSave(TargetPlatform); + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid()) + { + // Bundles may have changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +} +#endif + +FPrimaryAssetId UGAAbilityBase::GetPrimaryAssetId() const +{ + //FName Name = GetFName(); + //FName clsNam = GetClass()->GetFName(); + FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); + //FName dupa2 = FPackageName::GetShortFName(GetFName()); + const UGAAbilityBase* A = this; + return FPrimaryAssetId(FPrimaryAssetType("Ability"), dupa1); + //if (HasAnyFlags(RF_ClassDefaultObject)) + { + UClass* SearchNativeClass = GetClass(); + + while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) + { + SearchNativeClass = SearchNativeClass->GetSuperClass(); + } + + if (SearchNativeClass && SearchNativeClass != GetClass()) + { + // If blueprint, return native class and asset name + + } + + // Native CDO, return nothing + return FPrimaryAssetId(); + } + + // Data assets use Class and ShortName by default, there's no inheritance so class works fine + //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); +} + +void UGAAbilityBase::PostLoad() +{ + Super::PostLoad(); + +#if WITH_EDITORONLY_DATA + FAssetBundleData OldData = AssetBundleData; + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid() && OldData != AssetBundleData) + { + // Bundles changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +#endif +} +#if WITH_EDITOR +void UGAAbilityBase::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) +{ + Super::PostEditChangeProperty(PropertyChangedEvent); +} +#endif // WITH_EDITOR + +void UGAAbilityBase::UpdateAssetRegistryInfo() +{ + AbilityTagSearch = AbilityTag.GetTagName(); +} + +void UGAAbilityBase::InitAbility() +{ + //still want to initialize, as Spec is used in multiple places. + DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); + ActivationEffect.InitializeIfNotInitialized(DefaultContext); + CooldownEffect.InitializeIfNotInitialized(DefaultContext); + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + AttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + } + AttributeCostHandle.AddZeroed(AttributeCost.Num()); + + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + } + AbilityAttributeCostHandle.AddZeroed(AbilityAttributeCost.Num()); + if (AbilityComponent) + { + World = AbilityComponent->GetWorld(); + } + + if (!AbilityComponent) + { + AbilityComponent = GetAbilityComp(); + } + if (Attributes) + { + Attributes->InitializeAttributes(GetAbilityComp()); + Attributes->InitializeAttributesFromTable(); + } + + ENetRole role = AbilityComponent->GetOwnerRole(); + ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); + + if (role < ENetRole::ROLE_Authority) + { + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); + AbilityComponent->RepAttributes.RegisterAttributeRepEvent(AbilityTag, Delegate); + } + + //AbilityComponent->RepAttributes.AttributeMap.Add(AbilityTag, Attributes); + if (role == ENetRole::ROLE_Authority || + mode == ENetMode::NM_Standalone) + { + if (AbilityComponent && Attributes) + { + UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes);; + Attributes = nullptr; + Attributes = NewAttributes; + } + } + + if (!OwnerCamera) + { + OwnerCamera = POwner->FindComponentByClass(); + } + + OnAbilityInited(); +} +void UGAAbilityBase::OnAttributeSetReplicated() +{ + UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); + Attributes = attributes; +} + +void UGAAbilityBase::OnAbilityInited() +{ + +} +void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) +{ + { + UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); + PredictionHandle = InPredictionHandle; + OnInputPressed(ActionName); + OnInputPressedDelegate.Broadcast(); + } +} + +void UGAAbilityBase::OnNativeInputReleased(FGameplayTag ActionName) +{ + { + UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputReleased in ability %s"), *GetName()); + OnInputReleased(ActionName); + OnInputReleasedDelegate.Broadcast(); + } +} + +void UGAAbilityBase::StartActivation(bool bApplyActivationEffect) +{ + if (!CanUseAbility()) + { + UE_LOG(AbilityFramework, Log, TEXT("Cannot use Ability: %s"), *GetName()); + return; + } + //AbilityComponent->ExecutingAbility = this; + AbilityState = EAFAbilityState::Activating; + NativeOnBeginAbilityActivation(bApplyActivationEffect); +} + +void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) +{ + UE_LOG(AbilityFramework, Log, TEXT("Begin Executing Ability: %s"), *GetName()); + + if (OnConfirmCastingEndedDelegate.IsBound()) + { + OnConfirmCastingEndedDelegate.Broadcast(); + } + //ActivationInfo.SetActivationInfo(); + ApplyActivationEffect(bApplyActivationEffect); + OnActivate(); + OnActivateBeginDelegate.Broadcast(); + AbilityComponent->AppliedTags.AddTagContainer(ActivationAddedTags); + //OnAbilityExecuted(); +} + +void UGAAbilityBase::OnCooldownEffectExpired() +{ + UE_LOG(AFAbilities, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); + + if (CooldownEffectHandle.IsValid()) + { + //CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); + } +} +/* Functions for activation effect delegates */ +void UGAAbilityBase::NativeOnAbilityActivationFinish(FGAEffectHandle InHandle) +{ + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); + OnActivationFinished(); + OnActivationFinishedDelegate.Broadcast(); +} +void UGAAbilityBase::NativeOnAbilityActivationCancel() +{ + //OnAbilityExecutedNative(); + //this works under assumption that current state == activation state. + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Removed In Ability: %s"), *GetName()); + //AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + + OnActivationCancel(); + //AbilityActivatedCounter++; +} +void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) +{ + UE_LOG(AFAbilities, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); + + OnPeriod(); +} +void UGAAbilityBase::FinishAbility() +{ + UE_LOG(AFAbilities, Log, TEXT("FinishExecution in ability %s"), *GetName()); + OnAbilityFinished(); + NativeFinishAbility(); + AbilityState = EAFAbilityState::Waiting; + GetEffectsComponent()->AppliedTags.RemoveTagContainer(ActivationAddedTags); +} +void UGAAbilityBase::NativeFinishAbility() +{ + UE_LOG(AFAbilities, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); + AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + if (!ActivationEffectHandle.IsValid()) + { + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + ActivationEffectHandle.Reset(); + } + //remove effect. +} +/* Functions for activation effect delegates */ +void UGAAbilityBase::CancelActivation() +{ + NativeCancelActivation(); +} +void UGAAbilityBase::NativeCancelActivation() +{ + if (!ActivationEffectHandle.IsValid()) + return; + + UAFAbilityComponent* AttrComp = DefaultContext.InstigatorComp.Get(); + AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + if (GetEffectsComponent()) + { + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + AbilityState = EAFAbilityState::Waiting; + ActivationEffectHandle.Reset(); + } + OnActivationCancel(); +} + +bool UGAAbilityBase::IsWaitingForConfirm() +{ + if (OnConfirmDelegate.IsBound()) + return true; + else + return false; +} +void UGAAbilityBase::ConfirmAbility() +{ + if (OnConfirmDelegate.IsBound()) + OnConfirmDelegate.Broadcast(); + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); +} + +bool UGAAbilityBase::ApplyCooldownEffect() +{ + if (!CooldownEffect.GetSpec()) + { + return false; + } + FAFFunctionModifier Modifier; + + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); + GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); + + CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + CooldownEffect + , CooldownEffectHandle + , this + , POwner + , this + , Modifier); + ENetMode nm = AbilityComponent->GetOwner()->GetNetMode(); + ENetRole role = AbilityComponent->GetOwnerRole(); + + if (role >= ENetRole::ROLE_Authority) + { + ClientSetCooldownHandle(CooldownEffectHandle); + } + OnCooldownStart(); + + //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); + return false; +} +void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) +{ + //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); + OnCooldownEnd(InHandle); + CooldownEffectHandle.Reset(); +} +void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) +{ + //CooldownEffectHandle = InCooldownHandle; +} +bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) +{ + if (!ActivationEffect.GetSpec()) + return false; + FHitResult Hit(ForceInit); + + UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); + float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); + float PeriodCheck = Spec->Period.GetFloatValue(DefaultContext); + if (DurationCheck > 0 || PeriodCheck > 0) + { + bApplyActivationEffect = true; + } + + if (bApplyActivationEffect) + { + FHitResult HitIn; + if (ActivationEffectHandle.IsValid()) + ActivationEffectHandle.Reset(); + + FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); + + FAFFunctionModifier Modifier; + ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + ActivationEffect + , ActivationEffectHandle + , this + , POwner + , this + , Modifier); + + //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) + // ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); + + + if (PeriodCheck > 0) + { + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); + //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) + // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); + } + } + else + { + NativeOnAbilityActivationFinish(FGAEffectHandle()); + } + return false; +} + +bool UGAAbilityBase::CanUseAbility() +{ + bool CanUse = true; + bool bIsOnCooldown = IsOnCooldown(); + bool bIsActivating = IsActivating(); + //if (!AbilityComponent->ExecutingAbility) + // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); + + CanUse = !bIsOnCooldown && !bIsActivating; + UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility Ability, Cooldown: %s, Activating: %s \n"), bIsOnCooldown ? TEXT("true") : TEXT("false"), bIsActivating ? TEXT("true") : TEXT("false") ); + //now Lets check tags + if (CanUse) + { + if (GetEffectsComponent()->HasAll(ActivationRequiredTags)) + { + CanUse = true; + } + //blocking takes precedence. + if (GetEffectsComponent()->HasAny(ActivationBlockedTags)) + { + CanUse = false; + } + } + + return CanUse; +} +bool UGAAbilityBase::BP_CanUseAbility() +{ + return CanUseAbility(); +} +bool UGAAbilityBase::CanReleaseAbility() +{ + bool bCanUse = true; + /*if (AbilityComponent->ExecutingAbility == this) + { + bCanUse = true; + }*/ + if (IsOnCooldown()) + { + bCanUse = false; + UE_LOG(AbilityFramework, Log, TEXT("CanReleaseAbility can't release ability is on cooldown")); + } + return bCanUse; +} + +void UGAAbilityBase::OnGameplayTaskInitialized(UGameplayTask& Task) +{ + if (UGAAbilityTask* task = Cast(&Task)) + { + task->Ability = this; + } +} +UGameplayTasksComponent* UGAAbilityBase::GetGameplayTasksComponent(const UGameplayTask& Task) const +{ + return AbilityComponent; +} +/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ +void UGAAbilityBase::OnGameplayTaskActivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Add(&Task); + //AbilityComponent->OnGameplayTaskActivated(Task); +} +/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ +void UGAAbilityBase::OnGameplayTaskDeactivated(UGameplayTask& Task) +{ + UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); + ActiveTasks.Remove(&Task); + //AbilityComponent->OnGameplayTaskDeactivated(Task); +} +AActor* UGAAbilityBase::GetGameplayTaskOwner(const UGameplayTask* Task) const +{ + return POwner; +} +AActor* UGAAbilityBase::GetGameplayTaskAvatar(const UGameplayTask* Task) const +{ + return AvatarActor; +} + +class UGAAttributesBase* UGAAbilityBase::GetAttributes() +{ + return Attributes; +} +UAFAbilityComponent* UGAAbilityBase::GetAbilityComp() +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->GetAbilityComp(); + } + return nullptr; +} + +UAFEffectsComponent* UGAAbilityBase::GetEffectsComponent() +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->GetEffectsComponent(); + } + return nullptr; +} +UAFEffectsComponent* UGAAbilityBase::NativeGetEffectsComponent() const +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->NativeGetEffectsComponent(); + } + return nullptr; +} +float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const +{ + return NativeGetAttributeValue(AttributeIn); +} +float UGAAbilityBase::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return Attributes->GetCurrentAttributeValue(AttributeIn); +} +float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const +{ + return Attributes->GetCurrentAttributeValue(AttributeIn); +} + +bool UGAAbilityBase::ApplyAttributeCost() +{ + FAFFunctionModifier Modifier; + if (CheckAttributeCost()) + { + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + UGABlueprintLibrary::ApplyGameEffectToObject( + AttributeCost[Idx] + , AttributeCostHandle[Idx] + , this + , POwner + , this + , Modifier); + } + return true; + } + return false; +} +bool UGAAbilityBase::ApplyAbilityAttributeCost() +{ + //add checking if attribute goes below zero + //maybe let game specific code handle it.. + FAFFunctionModifier Modifier; + + if (CheckAbilityAttributeCost()) + { + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + AbilityAttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( + AbilityAttributeCost[Idx] + , AbilityAttributeCostHandle[Idx] + , this + , POwner + , this + , Modifier); + } + return true; + } + return false; +} +bool UGAAbilityBase::BP_ApplyAttributeCost() +{ + return ApplyAttributeCost(); +} +bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() +{ + return ApplyAbilityAttributeCost(); +} +bool UGAAbilityBase::BP_CheckAbilityAttributeCost() +{ + return CheckAbilityAttributeCost(); +} +bool UGAAbilityBase::CheckAbilityAttributeCost() +{ + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Attributes->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + } + return true; +} +bool UGAAbilityBase::CheckAttributeCost() +{ + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Attributes->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + } + return true; +} +bool UGAAbilityBase::IsOnCooldown() +{ + bool bOnCooldown = false; + bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle); + if (bOnCooldown) + { + OnNotifyOnCooldown.Broadcast(); + } + return bOnCooldown; //temp +} +bool UGAAbilityBase::IsActivating() +{ + bool bAbilityActivating = false; + bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffect.GetHandle(this)); + bool bInActivatingState = AbilityState == EAFAbilityState::Activating; + UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); + bAbilityActivating = bHaveEffect || bInActivatingState; + + return bAbilityActivating; //temp +} +bool UGAAbilityBase::BP_IsOnCooldown() +{ + return IsOnCooldown(); +} +void UGAAbilityBase::BP_ApplyCooldown() +{ + ApplyCooldownEffect(); +} + +float UGAAbilityBase::GetCurrentActivationTime() +{ + if (ActivationEffectHandle.IsValid()) + { + if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) + { + FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); + if (Effect) + { + return Effect->GetCurrentDuration(); + } + } + //return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); + } + return 0; +} + +float UGAAbilityBase::CalculateAnimationSpeed(UAnimMontage* MontageIn) +{ + float ActivationTime = MontageIn->GetPlayLength(); + UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); + float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); + if (DurationCheck > 0) + { + ActivationTime = DurationCheck; + } + float Duration = MontageIn->GetPlayLength(); + + float PlaySpeed = Duration / ActivationTime; + return PlaySpeed; +} + + +bool UGAAbilityBase::IsNameStableForNetworking() const +{ + return bIsNameStable; +} + +void UGAAbilityBase::SetNetAddressable() +{ + bIsNameStable = true; +} + +class UWorld* UGAAbilityBase::GetWorld() const +{ + return World; +} +void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) +{ + AbilityComponent->PlayMontage(MontageIn, SectionName, Speed); +} + +//replication +void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly can be infered upon replication. + //does other players need info about this ? + DOREPLIFETIME(UGAAbilityBase, POwner); + DOREPLIFETIME(UGAAbilityBase, PCOwner); + DOREPLIFETIME(UGAAbilityBase, AICOwner); + DOREPLIFETIME(UGAAbilityBase, AvatarActor); + //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. + +} +int32 UGAAbilityBase::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) +{ + if (HasAnyFlags(RF_ClassDefaultObject)) + { + return FunctionCallspace::Local; + } + check(POwner != NULL); + return POwner->GetFunctionCallspace(Function, Parameters, Stack); +} +bool UGAAbilityBase::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) +{ + check(!HasAnyFlags(RF_ClassDefaultObject)); + check(POwner != NULL); + + + UNetDriver* NetDriver = POwner->GetNetDriver(); + if (NetDriver) + { + NetDriver->ProcessRemoteFunction(POwner, Function, Parameters, OutParms, Stack, this); + return true; + } + + return false; +} + +void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) +{ + AbilityComponent->NativeInputPressed(ActionName); +} +void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) +{ + AbilityComponent->NativeInputReleased(ActionName); +} + +bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) +{ + bool bHaveTag = false; + if (IAFAbilityInterface* Interface = Cast(Target)) + { + if (UAFEffectsComponent* Comp = GetEffectsComponent()) + { + if (Comp->HasTag(Tag)) + { + bHaveTag = true; + } + } + } + return bHaveTag; +} +bool UGAAbilityBase::HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag) +{ + bool bHaveTag = false; + if (IAFAbilityInterface* Interface = Cast(Target)) + { + if (UAFEffectsComponent* Comp = GetEffectsComponent()) + { + if (Comp->HasAny(Tag)) + { + bHaveTag = true; + } + } + } + return bHaveTag; +} +/* Tracing Helpers Start */ +bool UGAAbilityBase::LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit) +{ + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); + FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); + + bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); + return bHit; +} +bool UGAAbilityBase::LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + FVector Start = FVector::ZeroVector; + if (OwnerCamera) + { + Start = OwnerCamera->GetComponentLocation(); + } + else + { + FRotator UnusedRot; + POwner->GetActorEyesViewPoint(Start, UnusedRot); + } + FVector End = (POwner->GetBaseAimRotation().Vector() * Range) + Start; + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); + FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); + bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); +#if ENABLE_DRAW_DEBUG + if (DrawDebugType != EDrawDebugTrace::None) + { + bool bPersistent = DrawDebugType == EDrawDebugTrace::Persistent; + float LifeTime = (DrawDebugType == EDrawDebugTrace::ForDuration) ? DrawTime : 0.f; + + // @fixme, draw line with thickness = 2.f? + if (bHit && OutHit.bBlockingHit) + { + // Red up to the blocking hit, green thereafter + ::DrawDebugLine(World, Start, OutHit.ImpactPoint, TraceColor.ToFColor(true), bPersistent, LifeTime); + ::DrawDebugLine(World, OutHit.ImpactPoint, End, TraceHitColor.ToFColor(true), bPersistent, LifeTime); + ::DrawDebugPoint(World, OutHit.ImpactPoint, 16, TraceColor.ToFColor(true), bPersistent, LifeTime); + } + else + { + // no hit means all red + ::DrawDebugLine(World, Start, End, TraceColor.ToFColor(true), bPersistent, LifeTime); + } + } +#endif + return bHit; +} +bool UGAAbilityBase::LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + return false; +} +bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + return false; +} +/* Tracing Helpers End */ + +//Helpers +float UGAAbilityBase::GetActivationRemainingTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationRemainingTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationCurrentTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationCurrentTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationEndTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle); +} +float UGAAbilityBase::BP_GetActivationRemainingTime() +{ + return GetActivationRemainingTime(); +} +float UGAAbilityBase::BP_GetActivationRemainingTimeNormalized() +{ + return GetActivationRemainingTimeNormalized(); +} +float UGAAbilityBase::BP_GetActivationCurrentTime() +{ + return GetActivationCurrentTime(); +} +float UGAAbilityBase::BP_GetActivationCurrentTimeNormalized() +{ + return GetActivationCurrentTimeNormalized(); +} +float UGAAbilityBase::BP_GetActivationEndTime() +{ + return GetActivationEndTime(); +} + + +float UGAAbilityBase::GetCooldownRemainingTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownCurrentTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownEndTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle); +} +float UGAAbilityBase::BP_GetCooldownRemainingTime() +{ + return GetCooldownRemainingTime(); +} +float UGAAbilityBase::BP_GetCooldownRemainingTimeNormalized() +{ + return GetCooldownRemainingTimeNormalized(); +} +float UGAAbilityBase::BP_GetCooldownCurrentTime() +{ + return GetCooldownCurrentTime(); +} +float UGAAbilityBase::BP_GetCooldownCurrentTimeNormalized() +{ + return GetCooldownCurrentTimeNormalized(); +} +float UGAAbilityBase::BP_GetCooldownEndTime() +{ + return GetCooldownEndTime(); +} + +AActor* UGAAbilityBase::BP_GetAvatar() +{ + return AvatarActor; +} \ No newline at end of file diff --git a/enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h b/enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h new file mode 100644 index 0000000..8edf6b6 --- /dev/null +++ b/enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h @@ -0,0 +1,630 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "../Effects/GAGameEffect.h" +#include "GameplayTasksComponent.h" +#include "GameplayTask.h" +#include "GameplayTaskOwnerInterface.h" +#include "../Attributes/GAAttributesBase.h" +#include "AFAbilityInterface.h" +#include "AFAbilityActivationSpec.h" +#include "AssetBundleData.h" +#include "SubclassOf.h" +#include "GAAbilityBase.generated.h" + +/* + TODO:: + 1. Add virtual functions, for default behaviours inside ability. + And figure out some clever names for them. Functions like: + ExecuteAbility() + Possibly default input functions. + The interface for it, is not yet fully determined. + It would be best if the functions and names of them, made sense.. For both AI and player + pawns. + 2. Add linked abilities. I'm not 100% sure if it really should be default functionality, + but the idea is that after first ability is executed, it will automatically set next, ability + for execution in chain, and so on, until last ability. Last ability will, simply back to first. + This can be implement as very simple linked list (though I'm not sure about nice BP workflow), + at ability level, OR it can be implemented at component level as queue. + But, from game design perspective implementation on ability level makes more sense. + + Moar TODO: (idk, if the above is still relevelant). + 1. Add simple tracing directly inside ability. Aside from targeting tasks. + + 2. Add caching for effects, so we don;'t create new ones every time, just reference handle. +*/ +/* + Base class for abilities. It will only implement few generic virtual functions, needed by all + abilities. + + Ability is what actor can do, not nessesarly, how actor will go about doing it. + For example we can have jump ability, which is nothing else, than object encapsulating, + access jump function inside Movement Component. + + This way you can give actors, certain abilities, which they can then used based on + some critera (for example defined in Blackboard and Behaviour tree), and if it is + possible for actor to perform ability, he will do it (though, one must be careful to + give abilities, which can be performed by actors, an ordinary actor, can't jump). + + More complicated abilities, can be actions in their own right. Like spells. + + Abilities are using state machine, combined with effects, to perform actions, like + casting, channeling etc. + It needs to be better explained on how each state makes use of effect parameters (Duration, Period). +*/ +DECLARE_MULTICAST_DELEGATE(FGASSimpleAbilityDynamicDelegate); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASGenericAbilityDelegate); + +USTRUCT() +struct FGAActiationInfo +{ + GENERATED_USTRUCT_BODY(); + + UPROPERTY() + float TimeStamp; + UPROPERTY() + float Duration; + UPROPERTY() + float Period; + UPROPERTY() + bool bApplyActivationEffect; + + inline void SetActivationInfo(float TimeStampIn, float DurationIn, float PeriodIn, + bool bApplyActivationEffectIn) + { + TimeStamp = TimeStampIn; + Duration = DurationIn; + Period = PeriodIn; + bApplyActivationEffect = bApplyActivationEffectIn; + //always increment to make sure it is replicated. + ForceReplication++; + } + + UPROPERTY() + int8 ForceReplication; +}; + +enum EAFAbilityState +{ + Waiting, + Activating +}; + +UCLASS(BlueprintType, Blueprintable) +class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTaskOwnerInterface, public IAFAbilityInterface +{ + GENERATED_BODY() +public: + + /* + Since each ability is instanced per owner, and cannot be activated multiple times (ie, to run in background), + we can assume that PredictionHandle will always be unique per activation. + */ + FAFPredictionHandle PredictionHandle; + /* By default all abilities are considered to be replicated. */ + UPROPERTY(EditAnywhere, Category = "Replication") + bool bReplicate; + + bool bIsNameStable; + + //possibly map TMap ? + UPROPERTY() + TSet ActiveTasks; + /* List of tasks, this ability have. */ + UPROPERTY() + TMap AbilityTasks; + + /* + Delegate is used to confirm ability execution. + After confirming ability will proceed to activation state and either casts instatly or start + casting effect. + */ + FGASSimpleAbilityDynamicDelegate OnConfirmDelegate; + /* + Delegate which is called after ability is confirmed and then cast time ended. + */ + FGASSimpleAbilityDynamicDelegate OnConfirmCastingEndedDelegate; + FSimpleDelegate ConfirmDelegate; + + /* Attributes specific to ability. */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "AbilityFramework|Abilities") + UGAAttributesBase* Attributes; + + UPROPERTY() + class UWorld* World; + /* + Replicated to everyone because we will need it, to determine cosmetic stuff on clients. + */ + /* + */ + UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") + APawn* POwner; + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + APlayerController* PCOwner; + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + class AAIController* AICOwner; + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + class UAFAbilityComponent* AbilityComponent; + + /* + Physical reprsentation of ability in game world. It might be sword, gun, or character. + What differs it from pawn or controller is that Avatar is actually used by ability to perform actions. + + It will need some common interfaces for getting data out. + */ + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + class AActor* AvatarActor; + + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UCameraComponent* OwnerCamera; + + FGAEffectContext DefaultContext; + + /* + Tags applied to instigator of this ability, for duration of cooldown. + Duration of this effect equals cooldown of ability. + */ + UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") + FAFPropertytHandle CooldownEffect; + FGAEffectHandle CooldownEffectHandle; + /* + Tags applied to the time of activation ability. + Only applies to abilities, which are not instant (for now). + Though even instant abilities have animation time, + they probabaly never apply activation tags, since + main usecase for those tags is to make other abilities + being able to interrupt them. + All abilities with casting/channeling time use it. + + Add Periodic Effect ? (For abilities with period). + */ + UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") + FAFPropertytHandle ActivationEffect; + FGAEffectHandle ActivationEffectHandle; + + /* + These attributes will be reduced by specified amount when ability is activated. + Attribute cost from Ability Owner attributes + */ + UPROPERTY(EditAnywhere, Category = "Config") + TArray AttributeCost; + TArray AttributeCostHandle; + /* + Attribute cost from ability own attributes + */ + UPROPERTY(EditAnywhere, Category = "Config") + TArray AbilityAttributeCost; + TArray AbilityAttributeCostHandle; + + UPROPERTY(AssetRegistrySearchable) + FName AbilityTagSearch; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTag AbilityTag; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer OwnedTags; + /* + These tags are added to owner while ability is activating (or channeled). + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationAddedTags; + /* + These tags must be present on onwer to activate this ability. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationRequiredTags; + /* + If any of these tags is present ability activation is blocked. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationBlockedTags; + +public: //because I'm to lazy to write all those friend states.. + UFUNCTION() + void OnActivationEffectPeriod(FGAEffectHandle InHandle); + + /* Replication counters for above events. */ + + + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnInputPressedDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnInputReleasedDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnActivateBeginDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnActivationFinishedDelegate; + + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnNotifyOnCooldown; + + /* Stub, I think replicating montage directly from ability will be better, as abilities are replicated regardless. */ + UPROPERTY() + UAnimMontage* RepMontage; +protected: + EAFAbilityState AbilityState; + +public: + UGAAbilityBase(const FObjectInitializer& ObjectInitializer); + + virtual void PostInitProperties() override; + + virtual void Serialize(FArchive& Ar) override; + // UObject interface + virtual FPrimaryAssetId GetPrimaryAssetId() const override; + virtual void PostLoad() override; + +#if WITH_EDITORONLY_DATA + /** This scans the class for AssetBundles metadata on asset properties and initializes the AssetBundleData with InitializeAssetBundlesFromMetadata */ + virtual void UpdateAssetBundleData(); + + /** Updates AssetBundleData */ + virtual void PreSave(const class ITargetPlatform* TargetPlatform) override; + +protected: + /** Asset Bundle data computed at save time. In cooked builds this is accessible from AssetRegistry */ + UPROPERTY() + FAssetBundleData AssetBundleData; +#endif +public: +#if WITH_EDITOR + virtual void PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) override; +#endif // WITH_EDITOR + + void UpdateAssetRegistryInfo(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + + void InitAbility(); +public: + UFUNCTION() + void OnAttributeSetReplicated(); + //called on both server and client after InitAbility(); + virtual void OnAbilityInited(); + + /* + Called on server and client, after ability has been bound to some input. + */ + virtual void OnAbilityInputReady() {}; + + /* + * @call Order: + * Previous Function: FGASAbilityContainer::HandleInputPressed + * Next Function: UGAAbilityBase::OnInputPressed + * + * Called on both Client and Server. + * + * @param ActionName - Name of action which tirggered this ability + * @param InPredictionHandle - Prediction Handle Generate By Client + */ + void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); + /* + * @call Order: + * Previous Function: UGAAbilityBase::OnNativeInputPressed + * Next Function: Multiple Choices. Next function is usually called from within Ability Blueprint + * Default Choices: + * UGAAbilityBase::StartActivation + * UGAAbilityBase::CanUseAbility + * Custom Function + * + * Called on both Client and Server. + * + * @param ActionName - Name of action which tirggered this ability + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnInputPressed(FGameplayTag ActionName); + + void OnNativeInputReleased(FGameplayTag ActionName); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnInputReleased(FGameplayTag ActionName); + + + + + void NativeOnAbilityConfirmed(); + + + + /* + * @call Order: + * Previous Function: UGAAbilityBase::StartActivation + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility + * + * Called on both Client and Server to indicate that ability is finished. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivationFinished(); + + /* + * @call Order: + * Previous Function: (Blueprint) UGAAbilityBase::OnInputPressed + * Next Function: UGAAbilityBase::NativeOnBeginAbilityActivation + * + * Called on both Client and Server. + * + * @param bApplyActivationEffect - Should apply activation effect to Owner. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void StartActivation(bool bApplyActivationEffect); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::StartActivation + * Next Function: UGAAbilityBase::ApplyActivationEffect + * Next Function: (Blueprint) UGAAbilityBase::OnActivate + * + * Called on both Client and Server. + * + * @param bApplyActivationEffect - Should apply activation effect to Owner. + */ + virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called on both Client and Server. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivate(); + + /* Event called when ability activation has been canceled. */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivationCancel(); + /* + * @call Order: + * Previous Function: Called if Periodic effect has been applied and is active. Otherwise inactive. + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * + * Called on both Client and Server. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnPeriod(); + + + + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnCooldownStart(); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnCooldownEnd(FGAEffectHandle InHandle); + + void NativeOnCooldownEnd(FGAEffectHandle InHandle); + + UFUNCTION() + void OnCooldownEffectExpired(); + UFUNCTION() + void NativeOnAbilityActivationFinish(FGAEffectHandle InHandle); + UFUNCTION() + void NativeOnAbilityActivationCancel(); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called to finish ability and start clean up. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void FinishAbility(); + /* + * @call Order: + * Previous Function: UGAAbilityBase::FinishAbility + * Next Function: (Blueprint) UGAAbilityBase::OnAbilityFinished + * + * Called to finish ability and start clean up. + */ + void NativeFinishAbility(); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeFinishAbility + * Next Function: (Blueprint) Custom Functions + * + * Called when ability is finished. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnAbilityFinished(); + /* + Stop effect activation and remove activation effect. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void CancelActivation(); + void NativeCancelActivation(); + + bool IsWaitingForConfirm(); + void ConfirmAbility(); + + bool CanUseAbility(); + bool CanReleaseAbility(); + + UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") + bool BP_CanUseAbility(); + + /** GameplayTaskOwnerInterface - Begin */ + virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; + /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ + /** Get owner of a task or default one when task is null */ + virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; + + /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ + virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; + + /** Get default priority for running a task */ + virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; + + /** Notify called after GameplayTask finishes initialization (not active yet) */ + virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; + + /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ + virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; + + /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ + virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; + /** GameplayTaskOwnerInterface - end */ + + /** IAFAbilityInterface Begin */ + virtual class UGAAttributesBase* GetAttributes() override; + virtual class UAFAbilityComponent* GetAbilityComp() override; + virtual class UAFEffectsComponent* GetEffectsComponent() override; + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty) override + { + if (!Attributes) + { + UE_LOG(AFAbilities, Log, TEXT("ModifyAttribute Ability Attributes INVALID")); + return; + } + Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); + }; + virtual FAFPredictionHandle GetPredictionHandle() override; + /* IAFAbilityInterface End **/ + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") + virtual float GetAttributeVal(FGAAttribute AttributeIn) const; + +public: //protected ? + bool ApplyCooldownEffect(); + UFUNCTION(Client, Reliable) + void ClientSetCooldownHandle(FGAEffectHandle InCooldownHandle); + void ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle); + + bool ApplyActivationEffect(bool bApplyActivationEffect); + bool ApplyAttributeCost(); + bool ApplyAbilityAttributeCost(); + bool CheckAbilityAttributeCost(); + bool CheckAttributeCost(); + bool IsOnCooldown(); + bool IsActivating(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Is On Cooldown"), Category = "AbilityFramework|Abilities") + bool BP_IsOnCooldown(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Cooldown"), Category = "AbilityFramework|Abilities") + void BP_ApplyCooldown(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_ApplyAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_ApplyAbilityAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Ability Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_CheckAbilityAttributeCost(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + float GetCurrentActivationTime(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + float CalculateAnimationSpeed(UAnimMontage* MontageIn); + + /* Replication */ + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return bReplicate; + } + void SetNetAddressable(); + +public: + int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; + virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); + + virtual class UWorld* GetWorld() const override; + + inline void AddAbilityTask(FName InName, class UGAAbilityTask* InTask) + { + if (!AbilityTasks.Contains(InName)) + { + AbilityTasks.Add(InName, InTask); + } + } + inline class UGAAbilityTask* GetAbilityTask(const FName& InName) + { + return AbilityTasks.FindRef(InName); + } + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") + bool HaveGameplayTag(AActor* Target, const FGameplayTag& Tag); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") + bool HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag); + + /* Tracing Helpers Start */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit); + /* Traces location from owner camera position if no camera available traces from eyes */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Traces from ability avatar socket. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Make first trace from camera location and then second trace from avatar socket in direction of first trace. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Tracing Helpers End */ + + + //Helpers + float GetActivationRemainingTime() const; + float GetActivationRemainingTimeNormalized() const; + float GetActivationCurrentTime() const; + float GetActivationCurrentTimeNormalized() const; + float GetActivationEndTime() const; + + UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationRemainingTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationCurrentTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationEndTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationEndTime(); + + + float GetCooldownRemainingTime() const; + float GetCooldownRemainingTimeNormalized() const; + float GetCooldownCurrentTime() const; + float GetCooldownCurrentTimeNormalized() const; + float GetCooldownEndTime() const; + + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownRemainingTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownCurrentTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownEndTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownEndTime(); + + UFUNCTION(BlueprintCallable, DisplayName = "Get Avatar", Category = "AbilityFramework|Abilities|Helpers") + AActor* BP_GetAvatar(); + + virtual void OnAvatarReady() {}; +}; From e3f07e214dcc411ca5cd650b677e80037905040a Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Thu, 5 Apr 2018 23:54:08 +0200 Subject: [PATCH 104/187] ARG-29 removing dependency on GameplayTasks module, as it's functionality is not really needed for async actions in Abilities/Effects --- ActionRPGGame.uproject | 4 - Config/DefaultGameplayTags.ini | 7 - .../AbilityFramework/AFAbilityComponent.cpp | 27 +- .../AbilityFramework/AFAbilityComponent.h | 27 +- .../Abilities/GAAbilityBase.cpp | 62 +- .../Abilities/GAAbilityBase.h | 44 +- .../Abilities/Tasks/GAAbilityTask.cpp | 51 - .../Abilities/Tasks/GAAbilityTask.h | 62 +- .../GAAbilityTask_TargetDataLineTrace.cpp | 1 - .../Tasks/GAAbilityTask_WaitForConfirm.cpp | 2 +- .../Tasks/GAAbilityTask_WaitTargetData.cpp | 13 +- .../Tasks/GAAbilityTask_WaitTargetData.h | 15 +- .../AbilityFramework.Build.cs | 1 + .../LatentActions/GALatentFunctionBase.cpp | 39 +- .../LatentActions/GALatentFunctionBase.h | 62 +- .../LatentActions/GAWaitAction.cpp | 6 +- .../LatentActions/GAWaitAction.h | 2 +- .../GAEK2Node_LatentAbilityTaskCall.cpp | 6 - .../GAEK2Node_LatentAbilityTaskCall.h | 4 +- .../GAEK2Node_LatentAction.cpp | 2 +- Source/ActionRPGGame/ARCharacter.cpp | 4 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 10 +- .../GAAbilityBase.cpp | 944 ------------------ .../GAAbilityBase.h | 630 ------------ 24 files changed, 168 insertions(+), 1857 deletions(-) delete mode 100644 enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp delete mode 100644 enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 7f03574..e57bfe7 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -194,10 +194,6 @@ "Enabled": true, "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" }, - { - "Name": "GameLiftServerSDK", - "Enabled": true - }, { "Name": "LiveLink", "Enabled": true diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 3639b95..900a43d 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -29,13 +29,6 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Shotgun",DevComment="") +GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Base",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Base.Activation",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Charged",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Charged.Activate",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Periodic.Cue",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Periodic.Period",DevComment="") -+GameplayTagList=(Tag="AFD.Ability.Periodic.Removed",DevComment="") +GameplayTagList=(Tag="AI.HaveAxe",DevComment="") +GameplayTagList=(Tag="AI.HaveOre",DevComment="") +GameplayTagList=(Tag="AI.HavePick",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index c0132ce..557e7ac 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -82,11 +82,6 @@ void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribu } } -bool UAFAbilityComponent::GetShouldTick() const -{ - return true; -} - void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn ,FGAEffectProperty& InProperty) { @@ -128,11 +123,6 @@ void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickTyp } } -void UAFAbilityComponent::RemoveSimulatedTask(class UGAAbilityTask* Task) -{ - SimulatedTasks.Remove(Task); -} - void UAFAbilityComponent::BeginPlay() { Super::BeginPlay(); @@ -219,22 +209,7 @@ void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContain TagContainer = ABInterface->NativeGetEffectsComponent()->AppliedTags.AllTags; } } -void UAFAbilityComponent::OnGameplayTaskActivated(UGameplayTask& Task) -{ - Super::OnGameplayTaskActivated(Task); - if (UGAAbilityTask* ABTask = Cast(&Task)) - { - if (ABTask->IsReplicated()) - { - if (SimulatedTasks.Contains(&Task) == false) - { - SimulatedTasks.Add(&Task); - bIsNetDirty = true; - } - } - } -} const bool FGASAbilityItem::operator==(const FGameplayTag& AbilityTag) const { return Ability->AbilityTag == AbilityTag; @@ -343,7 +318,7 @@ void FGASAbilityContainer::RemoveAbility(const FGameplayTag& AbilityIn) for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) { - AbilitiesComp->RemoveSimulatedTask(It->Value); + AbilitiesComp->ReplicatedTasks.Remove(It->Value); } TagToAbility.Remove(AbilityIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 0f83829..fa1d6ea 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -265,7 +265,7 @@ struct ABILITYFRAMEWORK_API FAFAbilityActionSet }; UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) -class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, public IGameplayTagAssetInterface +class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, /*UGameplayTasksComponent,*/ public IGameplayTagAssetInterface { GENERATED_BODY() /* Attributes handling */ @@ -333,8 +333,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void BroadcastAttributeChange(const FGAAttribute& InAttribute, const FAFAttributeChangedData& InData); - virtual bool GetShouldTick() const override; - UFUNCTION() void OnRep_GameEffectContainer(); @@ -371,7 +369,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; /* UActorComponent Interface - End **/ - void RemoveSimulatedTask(class UGAAbilityTask* Task); public: ///////////////////////////////////////////////// //////////// ATTRIBUTES HANDLING @@ -416,18 +413,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, IGameplayTagAssetInterface End */ - // BEGIN IGameplayTaskOwnerInterface - /* - Overrided because I'm not using GameplayTasks as they were meant to. - Create tasks, hold for it for a while and then destroy it (even for replicated tasks). - Instead I cache tasks off, and reuse them, which mean I don't want to fail at check if tasks is already simulated (because it is). - Instead if tasks is already simulating I simply skip adding it. - - I also want to manually remove tasks, when they ability that owns them is removed. - */ - virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - // END IGameplayTaskOwnerInterface - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; @@ -689,13 +674,15 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UGameplayTasksComponent, void InitializeInstancedAbilities(); UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, AActor* InAvatar); - /* - Messagin implementation for applying effects from multiple threads (in case - at some beatyfull day UObject will be able to exist on any thread), and from single thread. - Implementation is based on FMessageEndpoint. + +public: + /* + Latent Tasks Handling */ + UPROPERTY(Replicated) + TArray ReplicatedTasks; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 709b9c5..42198bc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -477,40 +477,6 @@ bool UGAAbilityBase::CanReleaseAbility() return bCanUse; } -void UGAAbilityBase::OnGameplayTaskInitialized(UGameplayTask& Task) -{ - if (UGAAbilityTask* task = Cast(&Task)) - { - task->Ability = this; - } -} -UGameplayTasksComponent* UGAAbilityBase::GetGameplayTasksComponent(const UGameplayTask& Task) const -{ - return AbilityComponent; -} -/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ -void UGAAbilityBase::OnGameplayTaskActivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Add(&Task); - //AbilityComponent->OnGameplayTaskActivated(Task); -} -/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ -void UGAAbilityBase::OnGameplayTaskDeactivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Remove(&Task); - //AbilityComponent->OnGameplayTaskDeactivated(Task); -} -AActor* UGAAbilityBase::GetGameplayTaskOwner(const UGameplayTask* Task) const -{ - return POwner; -} -AActor* UGAAbilityBase::GetGameplayTaskAvatar(const UGameplayTask* Task) const -{ - return AvatarActor; -} - class UGAAttributesBase* UGAAbilityBase::GetAttributes() { return Attributes; @@ -948,4 +914,32 @@ float UGAAbilityBase::BP_GetCooldownEndTime() AActor* UGAAbilityBase::BP_GetAvatar() { return AvatarActor; +} + + +void UGAAbilityBase::OnLatentTaskAdded(FName InstanceName, class UGALatentFunctionBase* TaskIn) +{ + if (!InstanceName.IsNone()) + { + AbilityTasks.Add(InstanceName, Cast(TaskIn)); + } +}; +void UGAAbilityBase::AddReplicatedTask(class UGALatentFunctionBase* TaskIn) +{ + AbilityComponent->ReplicatedTasks.Add(TaskIn); +} +void UGAAbilityBase::OnLatentTaskRemoved(class UGALatentFunctionBase* TaskIn) +{ +}; + +void UGAAbilityBase::OnLatentTaskActivated(class UGALatentFunctionBase* TaskIn) +{ +}; +void UGAAbilityBase::OnLatentTaskDeactivated(class UGALatentFunctionBase* TaskIn) +{ +}; + +class UGALatentFunctionBase* UGAAbilityBase::GetCachedLatentAction(FName TaskName) +{ + return AbilityTasks.FindRef(TaskName); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 61c9868..49f9e79 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -1,14 +1,16 @@ #pragma once -#include "../GAGlobalTypes.h" -#include "../Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" #include "GameplayTasksComponent.h" #include "GameplayTask.h" #include "GameplayTaskOwnerInterface.h" -#include "../Attributes/GAAttributesBase.h" +#include "Attributes/GAAttributesBase.h" #include "AFAbilityInterface.h" #include "AFAbilityActivationSpec.h" #include "AssetBundleData.h" #include "SubclassOf.h" +#include "LatentActions/AFLatentInterface.h" + #include "GAAbilityBase.generated.h" /* @@ -91,7 +93,7 @@ enum EAFAbilityState }; UCLASS(BlueprintType, Blueprintable) -class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTaskOwnerInterface, public IAFAbilityInterface +class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInterface, public IAFLatentInterface { GENERATED_BODY() public: @@ -449,28 +451,6 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") bool BP_CanUseAbility(); - - /** GameplayTaskOwnerInterface - Begin */ - virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; - /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ - /** Get owner of a task or default one when task is null */ - virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; - - /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ - virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; - - /** Get default priority for running a task */ - virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; - - /** Notify called after GameplayTask finishes initialization (not active yet) */ - virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; - - /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ - virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - - /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ - virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; - /** GameplayTaskOwnerInterface - end */ /** IAFAbilityInterface Begin */ virtual class UGAAttributesBase* GetAttributes() override; @@ -630,4 +610,16 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTask AActor* BP_GetAvatar(); virtual void OnAvatarReady() {}; + + + /* IAFLatentInterface */ + virtual void OnLatentTaskAdded(FName InstanceName, class UGALatentFunctionBase* TaskIn); + virtual void AddReplicatedTask(class UGALatentFunctionBase* TaskIn); + virtual void OnLatentTaskRemoved(class UGALatentFunctionBase* TaskIn); + + virtual void OnLatentTaskActivated(class UGALatentFunctionBase* TaskIn); + virtual void OnLatentTaskDeactivated(class UGALatentFunctionBase* TaskIn); + + virtual class UGALatentFunctionBase* GetCachedLatentAction(FName TaskName); + /* IAFLatentInterface */ }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp index fd3b10c..190da1a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp @@ -8,56 +8,5 @@ UGAAbilityTask::UGAAbilityTask(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { bIsReplicated = false; - bTickingTask = false; - bSimulatedTask = false; - bIsSimulating = false; - bOwnedByTasksComponent = false; - bClaimRequiredResources = true; - TaskState = EGameplayTaskState::Uninitialized; - ResourceOverlapPolicy = ETaskResourceOverlapPolicy::StartOnTop; - Priority = FGameplayTasks::DefaultPriority; - SetFlags(RF_StrongRefOnFrame); } - -//UWorld* UGAAbilityTask::GetWorld() const -//{ -// return GetOuterUGAAbilityBase()->GetWorld(); -//} - -void UGAAbilityTask::Initialize() -{ - -} - - - -void UGAAbilityTask::EndAbilityTask() -{ - -} - -//int32 UGAAbilityTask::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) -//{ -// if (HasAnyFlags(RF_ClassDefaultObject)) -// { -// return FunctionCallspace::Local; -// } -// check(AbilityComponent.IsValid()); -// return AbilityComponent->GetFunctionCallspace(Function, Parameters, Stack); -//} -//bool UGAAbilityTask::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) -//{ -// check(!HasAnyFlags(RF_ClassDefaultObject)); -// check(AbilityComponent.IsValid()); -// -// -// UNetDriver* NetDriver = AbilityComponent->GetOwner()->GetNetDriver(); -// if (NetDriver) -// { -// NetDriver->ProcessRemoteFunction(AbilityComponent->GetOwner(), Function, Parameters, OutParms, Stack, this); -// return true; -// } -// -// return false; -//} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 62fbd0d..f451049 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -1,11 +1,9 @@ #pragma once #include "GameplayTask.h" -#include "../GAAbilityBase.h" -#include "../../AFAbilityComponent.h" +#include "GAAbilityBase.h" +#include "AFAbilityComponent.h" -//#include "Messaging.h" -#include "MessageEndpoint.h" -#include "MessageEndpointBuilder.h" +#include "LatentActions/GALatentFunctionBase.h" #include "GAAbilityTask.generated.h" /* @@ -20,9 +18,9 @@ */ UCLASS(BlueprintType, Blueprintable, Within=GAAbilityBase) -class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask +class ABILITYFRAMEWORK_API UGAAbilityTask : public UGALatentFunctionBase { - GENERATED_UCLASS_BODY() + GENERATED_BODY() friend struct FAFAbilityTaskMessageTick; public: uint8 bIsReplicated : 1; @@ -31,11 +29,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask /* Ability owning this task */ TWeakObjectPtr AbilityComponent; public: - //virtual UWorld* GetWorld() const override; - //virtual void Tick(float DeltaSecondsIn); - - virtual void Initialize(); template static T* NewAbilityTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) { @@ -43,60 +37,20 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UGameplayTask T* MyObj = nullptr; UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); - if (UGAAbilityTask* CachedTask = ThisAbility->GetAbilityTask(InTaskName)) - { - MyObj = Cast(CachedTask); - } - else - { - MyObj = NewObject(WorldContextObject); - ThisAbility->AddAbilityTask(InTaskName, MyObj); - } + MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); + MyObj->Ability = ThisAbility; MyObj->AbilityComponent = ThisAbility->AbilityComponent; - MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); - MyObj->InstanceName = InstanceName; return MyObj; } - - template - static bool DelayedFalse() - { - return false; - } - - // this function has been added to make sure AbilityTasks don't use this method - template - FORCEINLINE static T* NewTask(UObject* WorldContextObject, FName InstanceName = FName()) - { - static_assert(DelayedFalse(), "UAbilityTask::NewTask should never be used. Use NewAbilityTask instead"); - } - + UGAAbilityTask(const FObjectInitializer& ObjectInitializer); bool IsReplicated() { return bIsReplicated; } - //network overrides: - //int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; - //virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; protected: - void EndAbilityTask(); - - void OnDestroy(bool bInOwnerFinished) override - { - ensure(TaskState != EGameplayTaskState::Finished && !IsPendingKill()); - TaskState = EGameplayTaskState::Finished; - - if (TasksComponent.IsValid()) - { - TasksComponent->OnGameplayTaskDeactivated(*this); - } - - //MarkPendingKill(); - } - bool IsClient() { APawn* POwner = Ability->POwner; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp index 7dd4c9e..5a66e3b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp @@ -31,7 +31,6 @@ UGAAbilityTask_TargetDataLineTrace* UGAAbilityTask_TargetDataLineTrace::CreateTa UGAAbilityTask_TargetDataLineTrace::UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - bSimulatedTask = false; bIsReplicated = true; } void UGAAbilityTask_TargetDataLineTrace::Activate() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp index 6114296..b84c262 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp @@ -29,5 +29,5 @@ void UGAAbilityTask_WaitForConfirm::OnConfirm() { Ability->OnConfirmDelegate.Clear(); OnConfirmed.Broadcast(); - EndAbilityTask(); + EndTask(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp index 71fefb5..38f2151 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp @@ -7,7 +7,6 @@ UGAAbilityTask_WaitTargetData::UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - bTickingTask = true; } @@ -59,7 +58,7 @@ void UGAAbilityTask_WaitTargetData::Activate() // ReadyForActivation(); // UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); //} -void UGAAbilityTask_WaitTargetData::TickTask(float DeltaTime) +void UGAAbilityTask_WaitTargetData::TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) { //if (TargetActor && Ability.IsValid()) //{ @@ -76,15 +75,7 @@ void UGAAbilityTask_WaitTargetData::TickTask(float DeltaTime) // } //} } -void UGAAbilityTask_WaitTargetData::OnDestroy(bool bInOwnerFinished) -{ - Super::OnDestroy(bInOwnerFinished); - //if (TargetActor) - //{ - // TargetActor->SetActorHiddenInGame(true); - // TargetActor->Destroy(); - //} -} + void UGAAbilityTask_WaitTargetData::OnConfirm() { Ability->OnConfirmDelegate.Clear(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h index 683affa..d50f96e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h @@ -20,24 +20,11 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_WaitTargetData : public UGAAbilityTask UPROPERTY() float Range; ETraceTypeQuery TraceChannel; - //UPROPERTY() - // class AGATargetingActor* TargetActor; - - //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - // static UGAAbilityTask_WaitTargetData* WaitTargetData(UObject* WorldContextObject, - // FName InTaskName, TSubclassOf Class, float InRange, ETraceTypeQuery InTraceChannel); - - //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - // bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class AGATargetingActor*& SpawnedActor); - - //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - // void FinishSpawningActor(UObject* WorldContextObject, class AGATargetingActor* SpawnedActor); virtual void Activate() override; - virtual void TickTask(float DeltaTime) override; + virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; - virtual void OnDestroy(bool bInOwnerFinished) override; UFUNCTION() void OnConfirm(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index cc2a4ed..292e707 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -25,6 +25,7 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) "AbilityFramework/Abilities", "AbilityFramework/Attributes", "AbilityFramework/Effects", + "AbilityFramework/LatentActions", "AbilityFramework/Private", // ... add other private include paths required here ... } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp index 097463e..1accfd5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp @@ -1,6 +1,8 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" +#include "AbilityFramework.h" +#include "AFLatentInterface.h" + #include "GALatentFunctionBase.h" void FGALatentFunctionTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) @@ -8,7 +10,7 @@ void FGALatentFunctionTick::ExecuteTick(float DeltaTime, ELevelTick TickType, EN if (Target && !Target->IsPendingKillOrUnreachable()) { FScopeCycleCounterUObject ActorScope(Target); - Target->TickAction(DeltaTime, TickType, *this); + Target->TickTask(DeltaTime, TickType, *this); } } @@ -29,6 +31,7 @@ UGALatentFunctionBase::UGALatentFunctionBase(const FObjectInitializer& ObjectIni TickFunction.SetTickFunctionEnable(true); SetFlags(RF_StrongRefOnFrame); + TaskState = EState::Waiting; } void UGALatentFunctionBase::Initialize() @@ -43,6 +46,25 @@ void UGALatentFunctionBase::Initialize() } } } + +void UGALatentFunctionBase::ReadyForActivation() +{ + if (TaskOwner) + { + if (TaskState != EState::Active) + { + TaskState = EState::Active; + Activate(); + Cast(TaskOwner)->OnLatentTaskActivated(this); + } + + } + else + { + EndTask(); + } +} + void UGALatentFunctionBase::EndTask() { if (TickFunction.bCanEverTick && TickFunction.IsTickFunctionRegistered()) @@ -50,12 +72,23 @@ void UGALatentFunctionBase::EndTask() TickFunction.UnRegisterTickFunction(); TickFunction.SetTickFunctionEnable(false); } - MarkPendingKill(); + Cast(TaskOwner)->OnLatentTaskDeactivated(this); + TaskState = EState::Finished; + //MarkPendingKill(); } void UGALatentFunctionBase::BeginDestroy() { Super::BeginDestroy(); } + +bool UGALatentFunctionBase::IsNameStableForNetworking() const +{ + return false; +} +void UGALatentFunctionBase::SetNetAddressable() +{ + +} UWorld* UGALatentFunctionBase::GetWorld() const { if (TaskOwner) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h index 5e94d4d..ae3fd97 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h @@ -1,7 +1,8 @@ #pragma once #include "CoreMinimal.h" #include "Engine/EngineBaseTypes.h" -//#include "Messaging.h" +#include "AFLatentInterface.h" + #include "GALatentFunctionBase.generated.h" struct FGALatentFunctionTick: public FTickFunction @@ -27,6 +28,16 @@ class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject GENERATED_BODY() //never access internals of these classes directly. Use messages instead. protected: + enum class EState : uint8 + { + Waiting, + Active, + Finished + }; + + EState TaskState; + bool bReplicated; + UPROPERTY() UObject* TaskOwner; friend struct FGALatentFunctionTick; @@ -36,19 +47,56 @@ class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject virtual UWorld* GetWorld() const override; //virtual void Tick(float DeltaSecondsIn); - virtual void TickAction(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) {}; + virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) {}; virtual void Initialize(); - virtual void ReadyForActivation() {}; +public: + UFUNCTION(BlueprintCallable, meta = (BlueprintInternalUseOnly = "true"), Category = "Latent Action") + virtual void ReadyForActivation(); +protected: virtual void Activate() {}; virtual void EndTask(); virtual void BeginDestroy() override; +public: + /* Replication */ + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return bReplicated; + } + void SetNetAddressable(); + +protected: template - FORCEINLINE static T* NewTask(UObject* WorldContextObject, UObject* InTaskOwner, FName InstanceName = FName()) + static T* NewTask(UObject* WorldContextObject, UObject* InTaskOwner, FName InstanceName = FName()) { - T* MyObj = NewObject(WorldContextObject); - MyObj->TaskOwner = InTaskOwner; - MyObj->Initialize(); + T* MyObj = nullptr; + if (IAFLatentInterface* Interface = Cast(InTaskOwner)) + { + if (!InstanceName.IsNone()) + { + MyObj = Cast(Interface->GetCachedLatentAction(InstanceName)); + if (!MyObj) + { + MyObj = NewObject(WorldContextObject); + + Interface->OnLatentTaskAdded(InstanceName, MyObj); + } + } + else + { + MyObj = NewObject(WorldContextObject); + + Interface->OnLatentTaskAdded(InstanceName, MyObj); + } + if (MyObj->bReplicated) + { + Interface->AddReplicatedTask(MyObj); + } + MyObj->TaskOwner = InTaskOwner; + } + return MyObj; } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp index b3e128d..8199eab 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp @@ -19,10 +19,6 @@ UGAWaitAction* UGAWaitAction::NewGAWaitAction(UObject* InTaskOwner, float Time) if (MyTask) { MyTask->Time = Time; - //MyTask->TaskOwner = InTaskOwner; - //MyTask->Initialize(); - MyTask->Activate(); - } return MyTask; } @@ -44,7 +40,7 @@ void UGAWaitAction::Activate() World->GetTimerManager().SetTimer(TimerHandle, this, &UGAWaitAction::OnTimeFinish, Time, false); } } -void UGAWaitAction::TickAction(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) +void UGAWaitAction::TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) { OnTick.Broadcast(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h index 0c4b147..fe34b7f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h @@ -33,7 +33,7 @@ class ABILITYFRAMEWORK_API UGAWaitAction : public UGALatentFunctionBase //virtual void Tick(float DeltaSecondsIn); virtual void Activate() override; - virtual void TickAction(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; + virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; UFUNCTION(BlueprintCallable, Category = "Latent Actions", meta = (AdvancedDisplay = "InTaskOwner, Priority", DefaultToSelf = "InTaskOwner", BlueprintInternalUseOnly = "TRUE")) static UGAWaitAction* NewGAWaitAction(UObject* InTaskOwner, float Time); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp index 73b1eb0..3305cab 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -24,12 +24,6 @@ UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObject } } -bool UGAEK2Node_LatentAbilityTaskCall::IsHandling(TSubclassOf TaskClass) const -{ - bool isChilldOf = TaskClass && TaskClass->IsChildOf(UGAAbilityTask::StaticClass()); - return isChilldOf; -} - bool UGAEK2Node_LatentAbilityTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const { bool bIsCompatible = false; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h index f8ba9c0..0dcbec4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h @@ -7,7 +7,7 @@ #include "GAEK2Node_LatentAbilityTaskCall.generated.h" UCLASS() -class UGAEK2Node_LatentAbilityTaskCall : public UK2Node_LatentGameplayTaskCall +class UGAEK2Node_LatentAbilityTaskCall : public UK2Node_BaseAsyncTask//UK2Node_LatentGameplayTaskCall { GENERATED_BODY() @@ -18,6 +18,4 @@ class UGAEK2Node_LatentAbilityTaskCall : public UK2Node_LatentGameplayTaskCall virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; // End of UEdGraphNode interface -protected: - virtual bool IsHandling(TSubclassOf TaskClass) const override; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp index 0a4dd85..34bc73b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp @@ -14,7 +14,7 @@ UGAEK2Node_LatentAction::UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - //ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentActionBase, ReadyForActivation); + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentFunctionBase, ReadyForActivation); } bool UGAEK2Node_LatentAction::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 81bedcb..7ad6fac 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -53,9 +53,7 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) GetCharacterMovement()->MaxWalkSpeed = 270.0f; GetCharacterMovement()->MaxWalkSpeedCrouched = 150.0f; GetCharacterMovement()->BrakingDecelerationWalking = 150.0f; - - GetArrowComponent()->bIsEditorOnly = true; - + // Create a camera boom (pulls in towards the player if there is a collision) CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); //CameraBoom->SetupAttachment(GetMesh()); diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 8deb862..5646e5f 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -31,7 +31,7 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AbilityFramework", "OrionAnimation", "OrionAnimation/Private", - "OrionAnimation/Public", + "OrionAnimation/Public", "AbilityFramework/Abilities", "AbilityFramework/Attributes", "AbilityFramework/Effects", @@ -68,9 +68,9 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); } - if (Target.Type == TargetRules.TargetType.Server) - { - PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); - } + //if (Target.Type == TargetRules.TargetType.Server) + //{ + // PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); + //} } } diff --git a/enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp b/enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp deleted file mode 100644 index 2074baf..0000000 --- a/enc_temp_folder/a32c694022ff7e128780c9b4bfd310/GAAbilityBase.cpp +++ /dev/null @@ -1,944 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - - -#include "../AbilityFramework.h" -#include "Tasks/GAAbilityTask.h" -#include "../Effects/GAGameEffect.h" -#include "../GAGlobalTypes.h" -#include "../Effects/GAEffectGlobalTypes.h" -#include "../AFAbilityComponent.h" -#include "AFEffectsComponent.h" - -#include "GameplayTagContainer.h" -#include "Net/UnrealNetwork.h" -#include "Animation/AnimMontage.h" -#include "../Effects/GABlueprintLibrary.h" -#include "Camera/CameraComponent.h" -#include "Kismet/KismetSystemLibrary.h" - -#include "GAAbilityBase.h" -FAFPredictionHandle UGAAbilityBase::GetPredictionHandle() { return PredictionHandle; } - -UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bReplicate = true; - bIsNameStable = false; -} - -void UGAAbilityBase::PostInitProperties() -{ - UpdateAssetRegistryInfo(); - Super::PostInitProperties(); -} - -void UGAAbilityBase::Serialize(FArchive& Ar) -{ - if (Ar.IsSaving()) - { - UpdateAssetRegistryInfo(); - } - - Super::Serialize(Ar); - - if (Ar.IsLoading()) - { - UpdateAssetRegistryInfo(); - } -} -#if WITH_EDITORONLY_DATA -void UGAAbilityBase::UpdateAssetBundleData() -{ - AssetBundleData.Reset(); - - // By default parse the metadata - if (UAssetManager::IsValid()) - { - UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); - } -} - -void UGAAbilityBase::PreSave(const class ITargetPlatform* TargetPlatform) -{ - Super::PreSave(TargetPlatform); - - UpdateAssetBundleData(); - - if (UAssetManager::IsValid()) - { - // Bundles may have changed, refresh - UAssetManager::Get().RefreshAssetData(this); - } -} -#endif - -FPrimaryAssetId UGAAbilityBase::GetPrimaryAssetId() const -{ - //FName Name = GetFName(); - //FName clsNam = GetClass()->GetFName(); - FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); - //FName dupa2 = FPackageName::GetShortFName(GetFName()); - const UGAAbilityBase* A = this; - return FPrimaryAssetId(FPrimaryAssetType("Ability"), dupa1); - //if (HasAnyFlags(RF_ClassDefaultObject)) - { - UClass* SearchNativeClass = GetClass(); - - while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) - { - SearchNativeClass = SearchNativeClass->GetSuperClass(); - } - - if (SearchNativeClass && SearchNativeClass != GetClass()) - { - // If blueprint, return native class and asset name - - } - - // Native CDO, return nothing - return FPrimaryAssetId(); - } - - // Data assets use Class and ShortName by default, there's no inheritance so class works fine - //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); -} - -void UGAAbilityBase::PostLoad() -{ - Super::PostLoad(); - -#if WITH_EDITORONLY_DATA - FAssetBundleData OldData = AssetBundleData; - - UpdateAssetBundleData(); - - if (UAssetManager::IsValid() && OldData != AssetBundleData) - { - // Bundles changed, refresh - UAssetManager::Get().RefreshAssetData(this); - } -#endif -} -#if WITH_EDITOR -void UGAAbilityBase::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) -{ - Super::PostEditChangeProperty(PropertyChangedEvent); -} -#endif // WITH_EDITOR - -void UGAAbilityBase::UpdateAssetRegistryInfo() -{ - AbilityTagSearch = AbilityTag.GetTagName(); -} - -void UGAAbilityBase::InitAbility() -{ - //still want to initialize, as Spec is used in multiple places. - DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); - ActivationEffect.InitializeIfNotInitialized(DefaultContext); - CooldownEffect.InitializeIfNotInitialized(DefaultContext); - for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) - { - AttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); - } - AttributeCostHandle.AddZeroed(AttributeCost.Num()); - - for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) - { - AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); - } - AbilityAttributeCostHandle.AddZeroed(AbilityAttributeCost.Num()); - if (AbilityComponent) - { - World = AbilityComponent->GetWorld(); - } - - if (!AbilityComponent) - { - AbilityComponent = GetAbilityComp(); - } - if (Attributes) - { - Attributes->InitializeAttributes(GetAbilityComp()); - Attributes->InitializeAttributesFromTable(); - } - - ENetRole role = AbilityComponent->GetOwnerRole(); - ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); - - if (role < ENetRole::ROLE_Authority) - { - FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); - AbilityComponent->RepAttributes.RegisterAttributeRepEvent(AbilityTag, Delegate); - } - - //AbilityComponent->RepAttributes.AttributeMap.Add(AbilityTag, Attributes); - if (role == ENetRole::ROLE_Authority || - mode == ENetMode::NM_Standalone) - { - if (AbilityComponent && Attributes) - { - UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes);; - Attributes = nullptr; - Attributes = NewAttributes; - } - } - - if (!OwnerCamera) - { - OwnerCamera = POwner->FindComponentByClass(); - } - - OnAbilityInited(); -} -void UGAAbilityBase::OnAttributeSetReplicated() -{ - UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); - Attributes = attributes; -} - -void UGAAbilityBase::OnAbilityInited() -{ - -} -void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) -{ - { - UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); - PredictionHandle = InPredictionHandle; - OnInputPressed(ActionName); - OnInputPressedDelegate.Broadcast(); - } -} - -void UGAAbilityBase::OnNativeInputReleased(FGameplayTag ActionName) -{ - { - UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputReleased in ability %s"), *GetName()); - OnInputReleased(ActionName); - OnInputReleasedDelegate.Broadcast(); - } -} - -void UGAAbilityBase::StartActivation(bool bApplyActivationEffect) -{ - if (!CanUseAbility()) - { - UE_LOG(AbilityFramework, Log, TEXT("Cannot use Ability: %s"), *GetName()); - return; - } - //AbilityComponent->ExecutingAbility = this; - AbilityState = EAFAbilityState::Activating; - NativeOnBeginAbilityActivation(bApplyActivationEffect); -} - -void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) -{ - UE_LOG(AbilityFramework, Log, TEXT("Begin Executing Ability: %s"), *GetName()); - - if (OnConfirmCastingEndedDelegate.IsBound()) - { - OnConfirmCastingEndedDelegate.Broadcast(); - } - //ActivationInfo.SetActivationInfo(); - ApplyActivationEffect(bApplyActivationEffect); - OnActivate(); - OnActivateBeginDelegate.Broadcast(); - AbilityComponent->AppliedTags.AddTagContainer(ActivationAddedTags); - //OnAbilityExecuted(); -} - -void UGAAbilityBase::OnCooldownEffectExpired() -{ - UE_LOG(AFAbilities, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); - - if (CooldownEffectHandle.IsValid()) - { - //CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); - } -} -/* Functions for activation effect delegates */ -void UGAAbilityBase::NativeOnAbilityActivationFinish(FGAEffectHandle InHandle) -{ - UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); - OnActivationFinished(); - OnActivationFinishedDelegate.Broadcast(); -} -void UGAAbilityBase::NativeOnAbilityActivationCancel() -{ - //OnAbilityExecutedNative(); - //this works under assumption that current state == activation state. - UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Removed In Ability: %s"), *GetName()); - //AbilityComponent->ExecutingAbility = nullptr; - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); - - OnActivationCancel(); - //AbilityActivatedCounter++; -} -void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) -{ - UE_LOG(AFAbilities, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); - - OnPeriod(); -} -void UGAAbilityBase::FinishAbility() -{ - UE_LOG(AFAbilities, Log, TEXT("FinishExecution in ability %s"), *GetName()); - OnAbilityFinished(); - NativeFinishAbility(); - AbilityState = EAFAbilityState::Waiting; - GetEffectsComponent()->AppliedTags.RemoveTagContainer(ActivationAddedTags); -} -void UGAAbilityBase::NativeFinishAbility() -{ - UE_LOG(AFAbilities, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); - AbilityComponent->ExecutingAbility = nullptr; - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); - if (!ActivationEffectHandle.IsValid()) - { - GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); - ActivationEffectHandle.Reset(); - } - //remove effect. -} -/* Functions for activation effect delegates */ -void UGAAbilityBase::CancelActivation() -{ - NativeCancelActivation(); -} -void UGAAbilityBase::NativeCancelActivation() -{ - if (!ActivationEffectHandle.IsValid()) - return; - - UAFAbilityComponent* AttrComp = DefaultContext.InstigatorComp.Get(); - AbilityComponent->ExecutingAbility = nullptr; - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); - if (GetEffectsComponent()) - { - GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); - AbilityState = EAFAbilityState::Waiting; - ActivationEffectHandle.Reset(); - } - OnActivationCancel(); -} - -bool UGAAbilityBase::IsWaitingForConfirm() -{ - if (OnConfirmDelegate.IsBound()) - return true; - else - return false; -} -void UGAAbilityBase::ConfirmAbility() -{ - if (OnConfirmDelegate.IsBound()) - OnConfirmDelegate.Broadcast(); - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); -} - -bool UGAAbilityBase::ApplyCooldownEffect() -{ - if (!CooldownEffect.GetSpec()) - { - return false; - } - FAFFunctionModifier Modifier; - - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); - GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); - - CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( - CooldownEffect - , CooldownEffectHandle - , this - , POwner - , this - , Modifier); - ENetMode nm = AbilityComponent->GetOwner()->GetNetMode(); - ENetRole role = AbilityComponent->GetOwnerRole(); - - if (role >= ENetRole::ROLE_Authority) - { - ClientSetCooldownHandle(CooldownEffectHandle); - } - OnCooldownStart(); - - //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); - return false; -} -void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) -{ - //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); - OnCooldownEnd(InHandle); - CooldownEffectHandle.Reset(); -} -void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) -{ - //CooldownEffectHandle = InCooldownHandle; -} -bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) -{ - if (!ActivationEffect.GetSpec()) - return false; - FHitResult Hit(ForceInit); - - UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); - float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); - float PeriodCheck = Spec->Period.GetFloatValue(DefaultContext); - if (DurationCheck > 0 || PeriodCheck > 0) - { - bApplyActivationEffect = true; - } - - if (bApplyActivationEffect) - { - FHitResult HitIn; - if (ActivationEffectHandle.IsValid()) - ActivationEffectHandle.Reset(); - - FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); - GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); - - FAFFunctionModifier Modifier; - ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( - ActivationEffect - , ActivationEffectHandle - , this - , POwner - , this - , Modifier); - - //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) - // ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); - - - if (PeriodCheck > 0) - { - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); - GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); - //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) - // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); - } - } - else - { - NativeOnAbilityActivationFinish(FGAEffectHandle()); - } - return false; -} - -bool UGAAbilityBase::CanUseAbility() -{ - bool CanUse = true; - bool bIsOnCooldown = IsOnCooldown(); - bool bIsActivating = IsActivating(); - //if (!AbilityComponent->ExecutingAbility) - // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); - - CanUse = !bIsOnCooldown && !bIsActivating; - UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility Ability, Cooldown: %s, Activating: %s \n"), bIsOnCooldown ? TEXT("true") : TEXT("false"), bIsActivating ? TEXT("true") : TEXT("false") ); - //now Lets check tags - if (CanUse) - { - if (GetEffectsComponent()->HasAll(ActivationRequiredTags)) - { - CanUse = true; - } - //blocking takes precedence. - if (GetEffectsComponent()->HasAny(ActivationBlockedTags)) - { - CanUse = false; - } - } - - return CanUse; -} -bool UGAAbilityBase::BP_CanUseAbility() -{ - return CanUseAbility(); -} -bool UGAAbilityBase::CanReleaseAbility() -{ - bool bCanUse = true; - /*if (AbilityComponent->ExecutingAbility == this) - { - bCanUse = true; - }*/ - if (IsOnCooldown()) - { - bCanUse = false; - UE_LOG(AbilityFramework, Log, TEXT("CanReleaseAbility can't release ability is on cooldown")); - } - return bCanUse; -} - -void UGAAbilityBase::OnGameplayTaskInitialized(UGameplayTask& Task) -{ - if (UGAAbilityTask* task = Cast(&Task)) - { - task->Ability = this; - } -} -UGameplayTasksComponent* UGAAbilityBase::GetGameplayTasksComponent(const UGameplayTask& Task) const -{ - return AbilityComponent; -} -/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ -void UGAAbilityBase::OnGameplayTaskActivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Add(&Task); - //AbilityComponent->OnGameplayTaskActivated(Task); -} -/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ -void UGAAbilityBase::OnGameplayTaskDeactivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Remove(&Task); - //AbilityComponent->OnGameplayTaskDeactivated(Task); -} -AActor* UGAAbilityBase::GetGameplayTaskOwner(const UGameplayTask* Task) const -{ - return POwner; -} -AActor* UGAAbilityBase::GetGameplayTaskAvatar(const UGameplayTask* Task) const -{ - return AvatarActor; -} - -class UGAAttributesBase* UGAAbilityBase::GetAttributes() -{ - return Attributes; -} -UAFAbilityComponent* UGAAbilityBase::GetAbilityComp() -{ - IAFAbilityInterface* OwnerAttributes = Cast(POwner); - if (OwnerAttributes) - { - return OwnerAttributes->GetAbilityComp(); - } - return nullptr; -} - -UAFEffectsComponent* UGAAbilityBase::GetEffectsComponent() -{ - IAFAbilityInterface* OwnerAttributes = Cast(POwner); - if (OwnerAttributes) - { - return OwnerAttributes->GetEffectsComponent(); - } - return nullptr; -} -UAFEffectsComponent* UGAAbilityBase::NativeGetEffectsComponent() const -{ - IAFAbilityInterface* OwnerAttributes = Cast(POwner); - if (OwnerAttributes) - { - return OwnerAttributes->NativeGetEffectsComponent(); - } - return nullptr; -} -float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const -{ - return NativeGetAttributeValue(AttributeIn); -} -float UGAAbilityBase::NativeGetAttributeValue(const FGAAttribute AttributeIn) const -{ - return Attributes->GetCurrentAttributeValue(AttributeIn); -} -float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const -{ - return Attributes->GetCurrentAttributeValue(AttributeIn); -} - -bool UGAAbilityBase::ApplyAttributeCost() -{ - FAFFunctionModifier Modifier; - if (CheckAttributeCost()) - { - for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) - { - UGABlueprintLibrary::ApplyGameEffectToObject( - AttributeCost[Idx] - , AttributeCostHandle[Idx] - , this - , POwner - , this - , Modifier); - } - return true; - } - return false; -} -bool UGAAbilityBase::ApplyAbilityAttributeCost() -{ - //add checking if attribute goes below zero - //maybe let game specific code handle it.. - FAFFunctionModifier Modifier; - - if (CheckAbilityAttributeCost()) - { - for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) - { - AbilityAttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( - AbilityAttributeCost[Idx] - , AbilityAttributeCostHandle[Idx] - , this - , POwner - , this - , Modifier); - } - return true; - } - return false; -} -bool UGAAbilityBase::BP_ApplyAttributeCost() -{ - return ApplyAttributeCost(); -} -bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() -{ - return ApplyAbilityAttributeCost(); -} -bool UGAAbilityBase::BP_CheckAbilityAttributeCost() -{ - return CheckAbilityAttributeCost(); -} -bool UGAAbilityBase::CheckAbilityAttributeCost() -{ - for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) - { - float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Attributes->GetFloatValue(Attribute); - if (ModValue > AttributeVal) - return false; - } - return true; -} -bool UGAAbilityBase::CheckAttributeCost() -{ - for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) - { - float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Attributes->GetFloatValue(Attribute); - if (ModValue > AttributeVal) - return false; - } - return true; -} -bool UGAAbilityBase::IsOnCooldown() -{ - bool bOnCooldown = false; - bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle); - if (bOnCooldown) - { - OnNotifyOnCooldown.Broadcast(); - } - return bOnCooldown; //temp -} -bool UGAAbilityBase::IsActivating() -{ - bool bAbilityActivating = false; - bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffect.GetHandle(this)); - bool bInActivatingState = AbilityState == EAFAbilityState::Activating; - UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); - bAbilityActivating = bHaveEffect || bInActivatingState; - - return bAbilityActivating; //temp -} -bool UGAAbilityBase::BP_IsOnCooldown() -{ - return IsOnCooldown(); -} -void UGAAbilityBase::BP_ApplyCooldown() -{ - ApplyCooldownEffect(); -} - -float UGAAbilityBase::GetCurrentActivationTime() -{ - if (ActivationEffectHandle.IsValid()) - { - if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) - { - FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); - if (Effect) - { - return Effect->GetCurrentDuration(); - } - } - //return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); - } - return 0; -} - -float UGAAbilityBase::CalculateAnimationSpeed(UAnimMontage* MontageIn) -{ - float ActivationTime = MontageIn->GetPlayLength(); - UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); - float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); - if (DurationCheck > 0) - { - ActivationTime = DurationCheck; - } - float Duration = MontageIn->GetPlayLength(); - - float PlaySpeed = Duration / ActivationTime; - return PlaySpeed; -} - - -bool UGAAbilityBase::IsNameStableForNetworking() const -{ - return bIsNameStable; -} - -void UGAAbilityBase::SetNetAddressable() -{ - bIsNameStable = true; -} - -class UWorld* UGAAbilityBase::GetWorld() const -{ - return World; -} -void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) -{ - AbilityComponent->PlayMontage(MontageIn, SectionName, Speed); -} - -//replication -void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly can be infered upon replication. - //does other players need info about this ? - DOREPLIFETIME(UGAAbilityBase, POwner); - DOREPLIFETIME(UGAAbilityBase, PCOwner); - DOREPLIFETIME(UGAAbilityBase, AICOwner); - DOREPLIFETIME(UGAAbilityBase, AvatarActor); - //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. - -} -int32 UGAAbilityBase::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) -{ - if (HasAnyFlags(RF_ClassDefaultObject)) - { - return FunctionCallspace::Local; - } - check(POwner != NULL); - return POwner->GetFunctionCallspace(Function, Parameters, Stack); -} -bool UGAAbilityBase::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) -{ - check(!HasAnyFlags(RF_ClassDefaultObject)); - check(POwner != NULL); - - - UNetDriver* NetDriver = POwner->GetNetDriver(); - if (NetDriver) - { - NetDriver->ProcessRemoteFunction(POwner, Function, Parameters, OutParms, Stack, this); - return true; - } - - return false; -} - -void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) -{ - AbilityComponent->NativeInputPressed(ActionName); -} -void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) -{ - AbilityComponent->NativeInputReleased(ActionName); -} - -bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) -{ - bool bHaveTag = false; - if (IAFAbilityInterface* Interface = Cast(Target)) - { - if (UAFEffectsComponent* Comp = GetEffectsComponent()) - { - if (Comp->HasTag(Tag)) - { - bHaveTag = true; - } - } - } - return bHaveTag; -} -bool UGAAbilityBase::HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag) -{ - bool bHaveTag = false; - if (IAFAbilityInterface* Interface = Cast(Target)) - { - if (UAFEffectsComponent* Comp = GetEffectsComponent()) - { - if (Comp->HasAny(Tag)) - { - bHaveTag = true; - } - } - } - return bHaveTag; -} -/* Tracing Helpers Start */ -bool UGAAbilityBase::LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit) -{ - ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); - static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); - FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); - - bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); - return bHit; -} -bool UGAAbilityBase::LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) -{ - FVector Start = FVector::ZeroVector; - if (OwnerCamera) - { - Start = OwnerCamera->GetComponentLocation(); - } - else - { - FRotator UnusedRot; - POwner->GetActorEyesViewPoint(Start, UnusedRot); - } - FVector End = (POwner->GetBaseAimRotation().Vector() * Range) + Start; - ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); - static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); - FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); - bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); -#if ENABLE_DRAW_DEBUG - if (DrawDebugType != EDrawDebugTrace::None) - { - bool bPersistent = DrawDebugType == EDrawDebugTrace::Persistent; - float LifeTime = (DrawDebugType == EDrawDebugTrace::ForDuration) ? DrawTime : 0.f; - - // @fixme, draw line with thickness = 2.f? - if (bHit && OutHit.bBlockingHit) - { - // Red up to the blocking hit, green thereafter - ::DrawDebugLine(World, Start, OutHit.ImpactPoint, TraceColor.ToFColor(true), bPersistent, LifeTime); - ::DrawDebugLine(World, OutHit.ImpactPoint, End, TraceHitColor.ToFColor(true), bPersistent, LifeTime); - ::DrawDebugPoint(World, OutHit.ImpactPoint, 16, TraceColor.ToFColor(true), bPersistent, LifeTime); - } - else - { - // no hit means all red - ::DrawDebugLine(World, Start, End, TraceColor.ToFColor(true), bPersistent, LifeTime); - } - } -#endif - return bHit; -} -bool UGAAbilityBase::LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) -{ - return false; -} -bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) -{ - return false; -} -/* Tracing Helpers End */ - -//Helpers -float UGAAbilityBase::GetActivationRemainingTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationRemainingTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationCurrentTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationCurrentTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationEndTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle); -} -float UGAAbilityBase::BP_GetActivationRemainingTime() -{ - return GetActivationRemainingTime(); -} -float UGAAbilityBase::BP_GetActivationRemainingTimeNormalized() -{ - return GetActivationRemainingTimeNormalized(); -} -float UGAAbilityBase::BP_GetActivationCurrentTime() -{ - return GetActivationCurrentTime(); -} -float UGAAbilityBase::BP_GetActivationCurrentTimeNormalized() -{ - return GetActivationCurrentTimeNormalized(); -} -float UGAAbilityBase::BP_GetActivationEndTime() -{ - return GetActivationEndTime(); -} - - -float UGAAbilityBase::GetCooldownRemainingTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownCurrentTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownEndTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle); -} -float UGAAbilityBase::BP_GetCooldownRemainingTime() -{ - return GetCooldownRemainingTime(); -} -float UGAAbilityBase::BP_GetCooldownRemainingTimeNormalized() -{ - return GetCooldownRemainingTimeNormalized(); -} -float UGAAbilityBase::BP_GetCooldownCurrentTime() -{ - return GetCooldownCurrentTime(); -} -float UGAAbilityBase::BP_GetCooldownCurrentTimeNormalized() -{ - return GetCooldownCurrentTimeNormalized(); -} -float UGAAbilityBase::BP_GetCooldownEndTime() -{ - return GetCooldownEndTime(); -} - -AActor* UGAAbilityBase::BP_GetAvatar() -{ - return AvatarActor; -} \ No newline at end of file diff --git a/enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h b/enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h deleted file mode 100644 index 8edf6b6..0000000 --- a/enc_temp_folder/e0d02e45ea9665fde0a7acf0836a1a/GAAbilityBase.h +++ /dev/null @@ -1,630 +0,0 @@ -#pragma once -#include "../GAGlobalTypes.h" -#include "../Effects/GAGameEffect.h" -#include "GameplayTasksComponent.h" -#include "GameplayTask.h" -#include "GameplayTaskOwnerInterface.h" -#include "../Attributes/GAAttributesBase.h" -#include "AFAbilityInterface.h" -#include "AFAbilityActivationSpec.h" -#include "AssetBundleData.h" -#include "SubclassOf.h" -#include "GAAbilityBase.generated.h" - -/* - TODO:: - 1. Add virtual functions, for default behaviours inside ability. - And figure out some clever names for them. Functions like: - ExecuteAbility() - Possibly default input functions. - The interface for it, is not yet fully determined. - It would be best if the functions and names of them, made sense.. For both AI and player - pawns. - 2. Add linked abilities. I'm not 100% sure if it really should be default functionality, - but the idea is that after first ability is executed, it will automatically set next, ability - for execution in chain, and so on, until last ability. Last ability will, simply back to first. - This can be implement as very simple linked list (though I'm not sure about nice BP workflow), - at ability level, OR it can be implemented at component level as queue. - But, from game design perspective implementation on ability level makes more sense. - - Moar TODO: (idk, if the above is still relevelant). - 1. Add simple tracing directly inside ability. Aside from targeting tasks. - - 2. Add caching for effects, so we don;'t create new ones every time, just reference handle. -*/ -/* - Base class for abilities. It will only implement few generic virtual functions, needed by all - abilities. - - Ability is what actor can do, not nessesarly, how actor will go about doing it. - For example we can have jump ability, which is nothing else, than object encapsulating, - access jump function inside Movement Component. - - This way you can give actors, certain abilities, which they can then used based on - some critera (for example defined in Blackboard and Behaviour tree), and if it is - possible for actor to perform ability, he will do it (though, one must be careful to - give abilities, which can be performed by actors, an ordinary actor, can't jump). - - More complicated abilities, can be actions in their own right. Like spells. - - Abilities are using state machine, combined with effects, to perform actions, like - casting, channeling etc. - It needs to be better explained on how each state makes use of effect parameters (Duration, Period). -*/ -DECLARE_MULTICAST_DELEGATE(FGASSimpleAbilityDynamicDelegate); - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASGenericAbilityDelegate); - -USTRUCT() -struct FGAActiationInfo -{ - GENERATED_USTRUCT_BODY(); - - UPROPERTY() - float TimeStamp; - UPROPERTY() - float Duration; - UPROPERTY() - float Period; - UPROPERTY() - bool bApplyActivationEffect; - - inline void SetActivationInfo(float TimeStampIn, float DurationIn, float PeriodIn, - bool bApplyActivationEffectIn) - { - TimeStamp = TimeStampIn; - Duration = DurationIn; - Period = PeriodIn; - bApplyActivationEffect = bApplyActivationEffectIn; - //always increment to make sure it is replicated. - ForceReplication++; - } - - UPROPERTY() - int8 ForceReplication; -}; - -enum EAFAbilityState -{ - Waiting, - Activating -}; - -UCLASS(BlueprintType, Blueprintable) -class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IGameplayTaskOwnerInterface, public IAFAbilityInterface -{ - GENERATED_BODY() -public: - - /* - Since each ability is instanced per owner, and cannot be activated multiple times (ie, to run in background), - we can assume that PredictionHandle will always be unique per activation. - */ - FAFPredictionHandle PredictionHandle; - /* By default all abilities are considered to be replicated. */ - UPROPERTY(EditAnywhere, Category = "Replication") - bool bReplicate; - - bool bIsNameStable; - - //possibly map TMap ? - UPROPERTY() - TSet ActiveTasks; - /* List of tasks, this ability have. */ - UPROPERTY() - TMap AbilityTasks; - - /* - Delegate is used to confirm ability execution. - After confirming ability will proceed to activation state and either casts instatly or start - casting effect. - */ - FGASSimpleAbilityDynamicDelegate OnConfirmDelegate; - /* - Delegate which is called after ability is confirmed and then cast time ended. - */ - FGASSimpleAbilityDynamicDelegate OnConfirmCastingEndedDelegate; - FSimpleDelegate ConfirmDelegate; - - /* Attributes specific to ability. */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "AbilityFramework|Abilities") - UGAAttributesBase* Attributes; - - UPROPERTY() - class UWorld* World; - /* - Replicated to everyone because we will need it, to determine cosmetic stuff on clients. - */ - /* - */ - UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") - APawn* POwner; - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") - APlayerController* PCOwner; - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") - class AAIController* AICOwner; - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") - class UAFAbilityComponent* AbilityComponent; - - /* - Physical reprsentation of ability in game world. It might be sword, gun, or character. - What differs it from pawn or controller is that Avatar is actually used by ability to perform actions. - - It will need some common interfaces for getting data out. - */ - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") - class AActor* AvatarActor; - - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") - UCameraComponent* OwnerCamera; - - FGAEffectContext DefaultContext; - - /* - Tags applied to instigator of this ability, for duration of cooldown. - Duration of this effect equals cooldown of ability. - */ - UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") - FAFPropertytHandle CooldownEffect; - FGAEffectHandle CooldownEffectHandle; - /* - Tags applied to the time of activation ability. - Only applies to abilities, which are not instant (for now). - Though even instant abilities have animation time, - they probabaly never apply activation tags, since - main usecase for those tags is to make other abilities - being able to interrupt them. - All abilities with casting/channeling time use it. - - Add Periodic Effect ? (For abilities with period). - */ - UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") - FAFPropertytHandle ActivationEffect; - FGAEffectHandle ActivationEffectHandle; - - /* - These attributes will be reduced by specified amount when ability is activated. - Attribute cost from Ability Owner attributes - */ - UPROPERTY(EditAnywhere, Category = "Config") - TArray AttributeCost; - TArray AttributeCostHandle; - /* - Attribute cost from ability own attributes - */ - UPROPERTY(EditAnywhere, Category = "Config") - TArray AbilityAttributeCost; - TArray AbilityAttributeCostHandle; - - UPROPERTY(AssetRegistrySearchable) - FName AbilityTagSearch; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTag AbilityTag; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer OwnedTags; - /* - These tags are added to owner while ability is activating (or channeled). - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer ActivationAddedTags; - /* - These tags must be present on onwer to activate this ability. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer ActivationRequiredTags; - /* - If any of these tags is present ability activation is blocked. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer ActivationBlockedTags; - -public: //because I'm to lazy to write all those friend states.. - UFUNCTION() - void OnActivationEffectPeriod(FGAEffectHandle InHandle); - - /* Replication counters for above events. */ - - - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnInputPressedDelegate; - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnInputReleasedDelegate; - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnActivateBeginDelegate; - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnActivationFinishedDelegate; - - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnNotifyOnCooldown; - - /* Stub, I think replicating montage directly from ability will be better, as abilities are replicated regardless. */ - UPROPERTY() - UAnimMontage* RepMontage; -protected: - EAFAbilityState AbilityState; - -public: - UGAAbilityBase(const FObjectInitializer& ObjectInitializer); - - virtual void PostInitProperties() override; - - virtual void Serialize(FArchive& Ar) override; - // UObject interface - virtual FPrimaryAssetId GetPrimaryAssetId() const override; - virtual void PostLoad() override; - -#if WITH_EDITORONLY_DATA - /** This scans the class for AssetBundles metadata on asset properties and initializes the AssetBundleData with InitializeAssetBundlesFromMetadata */ - virtual void UpdateAssetBundleData(); - - /** Updates AssetBundleData */ - virtual void PreSave(const class ITargetPlatform* TargetPlatform) override; - -protected: - /** Asset Bundle data computed at save time. In cooked builds this is accessible from AssetRegistry */ - UPROPERTY() - FAssetBundleData AssetBundleData; -#endif -public: -#if WITH_EDITOR - virtual void PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) override; -#endif // WITH_EDITOR - - void UpdateAssetRegistryInfo(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); - - void InitAbility(); -public: - UFUNCTION() - void OnAttributeSetReplicated(); - //called on both server and client after InitAbility(); - virtual void OnAbilityInited(); - - /* - Called on server and client, after ability has been bound to some input. - */ - virtual void OnAbilityInputReady() {}; - - /* - * @call Order: - * Previous Function: FGASAbilityContainer::HandleInputPressed - * Next Function: UGAAbilityBase::OnInputPressed - * - * Called on both Client and Server. - * - * @param ActionName - Name of action which tirggered this ability - * @param InPredictionHandle - Prediction Handle Generate By Client - */ - void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); - /* - * @call Order: - * Previous Function: UGAAbilityBase::OnNativeInputPressed - * Next Function: Multiple Choices. Next function is usually called from within Ability Blueprint - * Default Choices: - * UGAAbilityBase::StartActivation - * UGAAbilityBase::CanUseAbility - * Custom Function - * - * Called on both Client and Server. - * - * @param ActionName - Name of action which tirggered this ability - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnInputPressed(FGameplayTag ActionName); - - void OnNativeInputReleased(FGameplayTag ActionName); - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnInputReleased(FGameplayTag ActionName); - - - - - void NativeOnAbilityConfirmed(); - - - - /* - * @call Order: - * Previous Function: UGAAbilityBase::StartActivation - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - * - * Called on both Client and Server to indicate that ability is finished. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivationFinished(); - - /* - * @call Order: - * Previous Function: (Blueprint) UGAAbilityBase::OnInputPressed - * Next Function: UGAAbilityBase::NativeOnBeginAbilityActivation - * - * Called on both Client and Server. - * - * @param bApplyActivationEffect - Should apply activation effect to Owner. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void StartActivation(bool bApplyActivationEffect); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::StartActivation - * Next Function: UGAAbilityBase::ApplyActivationEffect - * Next Function: (Blueprint) UGAAbilityBase::OnActivate - * - * Called on both Client and Server. - * - * @param bApplyActivationEffect - Should apply activation effect to Owner. - */ - virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - - * called when activation effect finishes (or immedietly, if there was no activation effect applied). - * Next Function: (Blueprint) Custom Functions - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point - * finish ability. - * - * Called on both Client and Server. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivate(); - - /* Event called when ability activation has been canceled. */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivationCancel(); - /* - * @call Order: - * Previous Function: Called if Periodic effect has been applied and is active. Otherwise inactive. - * called when activation effect finishes (or immedietly, if there was no activation effect applied). - * Next Function: (Blueprint) Custom Functions - * - * Called on both Client and Server. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnPeriod(); - - - - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnCooldownStart(); - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnCooldownEnd(FGAEffectHandle InHandle); - - void NativeOnCooldownEnd(FGAEffectHandle InHandle); - - UFUNCTION() - void OnCooldownEffectExpired(); - UFUNCTION() - void NativeOnAbilityActivationFinish(FGAEffectHandle InHandle); - UFUNCTION() - void NativeOnAbilityActivationCancel(); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - - * called when activation effect finishes (or immedietly, if there was no activation effect applied). - * Next Function: (Blueprint) Custom Functions - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point - * finish ability. - * - * Called to finish ability and start clean up. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void FinishAbility(); - /* - * @call Order: - * Previous Function: UGAAbilityBase::FinishAbility - * Next Function: (Blueprint) UGAAbilityBase::OnAbilityFinished - * - * Called to finish ability and start clean up. - */ - void NativeFinishAbility(); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::NativeFinishAbility - * Next Function: (Blueprint) Custom Functions - * - * Called when ability is finished. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnAbilityFinished(); - /* - Stop effect activation and remove activation effect. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void CancelActivation(); - void NativeCancelActivation(); - - bool IsWaitingForConfirm(); - void ConfirmAbility(); - - bool CanUseAbility(); - bool CanReleaseAbility(); - - UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") - bool BP_CanUseAbility(); - - /** GameplayTaskOwnerInterface - Begin */ - virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; - /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ - /** Get owner of a task or default one when task is null */ - virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; - - /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ - virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; - - /** Get default priority for running a task */ - virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; - - /** Notify called after GameplayTask finishes initialization (not active yet) */ - virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; - - /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ - virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - - /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ - virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; - /** GameplayTaskOwnerInterface - end */ - - /** IAFAbilityInterface Begin */ - virtual class UGAAttributesBase* GetAttributes() override; - virtual class UAFAbilityComponent* GetAbilityComp() override; - virtual class UAFEffectsComponent* GetEffectsComponent() override; - virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") - virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; - virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; - virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; - virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - , FGAEffectProperty& InProperty) override - { - if (!Attributes) - { - UE_LOG(AFAbilities, Log, TEXT("ModifyAttribute Ability Attributes INVALID")); - return; - } - Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); - }; - virtual FAFPredictionHandle GetPredictionHandle() override; - /* IAFAbilityInterface End **/ - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") - virtual float GetAttributeVal(FGAAttribute AttributeIn) const; - -public: //protected ? - bool ApplyCooldownEffect(); - UFUNCTION(Client, Reliable) - void ClientSetCooldownHandle(FGAEffectHandle InCooldownHandle); - void ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle); - - bool ApplyActivationEffect(bool bApplyActivationEffect); - bool ApplyAttributeCost(); - bool ApplyAbilityAttributeCost(); - bool CheckAbilityAttributeCost(); - bool CheckAttributeCost(); - bool IsOnCooldown(); - bool IsActivating(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Is On Cooldown"), Category = "AbilityFramework|Abilities") - bool BP_IsOnCooldown(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Cooldown"), Category = "AbilityFramework|Abilities") - void BP_ApplyCooldown(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_ApplyAttributeCost(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_ApplyAbilityAttributeCost(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Ability Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_CheckAbilityAttributeCost(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - float GetCurrentActivationTime(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - float CalculateAnimationSpeed(UAnimMontage* MontageIn); - - /* Replication */ - bool IsNameStableForNetworking() const override; - - bool IsSupportedForNetworking() const override - { - return bReplicate; - } - void SetNetAddressable(); - -public: - int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; - virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); - - virtual class UWorld* GetWorld() const override; - - inline void AddAbilityTask(FName InName, class UGAAbilityTask* InTask) - { - if (!AbilityTasks.Contains(InName)) - { - AbilityTasks.Add(InName, InTask); - } - } - inline class UGAAbilityTask* GetAbilityTask(const FName& InName) - { - return AbilityTasks.FindRef(InName); - } - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") - bool HaveGameplayTag(AActor* Target, const FGameplayTag& Tag); - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") - bool HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag); - - /* Tracing Helpers Start */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit); - /* Traces location from owner camera position if no camera available traces from eyes */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); - /* Traces from ability avatar socket. */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); - /* Make first trace from camera location and then second trace from avatar socket in direction of first trace. */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); - /* Tracing Helpers End */ - - - //Helpers - float GetActivationRemainingTime() const; - float GetActivationRemainingTimeNormalized() const; - float GetActivationCurrentTime() const; - float GetActivationCurrentTimeNormalized() const; - float GetActivationEndTime() const; - - UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationRemainingTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationCurrentTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationEndTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationEndTime(); - - - float GetCooldownRemainingTime() const; - float GetCooldownRemainingTimeNormalized() const; - float GetCooldownCurrentTime() const; - float GetCooldownCurrentTimeNormalized() const; - float GetCooldownEndTime() const; - - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownRemainingTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownCurrentTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownEndTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownEndTime(); - - UFUNCTION(BlueprintCallable, DisplayName = "Get Avatar", Category = "AbilityFramework|Abilities|Helpers") - AActor* BP_GetAvatar(); - - virtual void OnAvatarReady() {}; -}; From a7cfe657108dcac7541cd3a21c79a373316a931f Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 6 Apr 2018 23:31:05 +0200 Subject: [PATCH 105/187] ARG-29 removing more GameplayTasks module dependencies --- ActionRPGGame.uproject | 2 +- .../AbilityFramework/AFAbilityComponent.h | 6 +--- .../AbilityFramework/AFEffectsComponent.h | 3 +- .../Abilities/GAAbilityBase.h | 2 +- .../AbilityFramework.Build.cs | 1 - .../Effects/EffectTasks/AFEffectTask.h | 34 ++---------------- .../AFEffectTask_AppliedEffectEvent.cpp | 13 +------ .../AFEffectTask_AppliedEffectEvent.h | 2 -- .../AFEffectTask_AttributeChange.cpp | 15 +------- .../AFEffectTask_AttributeChange.h | 4 +-- .../AFEffectTask_EffectAppliedToSelf.cpp | 13 +------ .../AFEffectTask_EffectAppliedToSelf.h | 4 +-- .../AFEffectTask_EffectAppliedToTarget.cpp | 11 ------ .../AFEffectTask_EffectAppliedToTarget.h | 4 +-- .../EffectTasks/AFEffectTask_EffectEvent.cpp | 13 +------ .../EffectTasks/AFEffectTask_EffectEvent.h | 2 -- .../AFEffectTask_ExecutedEffectEvent.cpp | 13 +------ .../AFEffectTask_ExecutedEffectEvent.h | 2 -- .../Effects/GAEffectExtension.cpp | 35 ------------------- .../Effects/GAEffectExtension.h | 26 ++------------ .../AFEK2Node_AsyncEffectTaskCall.cpp | 13 ++----- .../AFEK2Node_AsyncEffectTaskCall.h | 5 +-- .../AbilityFrameworkEditor.Build.cs | 2 -- .../GAEK2Node_LatentAbilityTaskCall.cpp | 6 +--- .../GAEK2Node_LatentAbilityTaskCall.h | 1 - 25 files changed, 21 insertions(+), 211 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index e57bfe7..3fe96b4 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -1,6 +1,6 @@ { "FileVersion": 3, - "EngineAssociation": "{A36EBF10-476D-8159-343E-8FA796F9AC8F}", + "EngineAssociation": "{AB02FCC6-45E0-8362-E7EB-B98E6E6B9DF2}", "Category": "", "Description": "", "Modules": [ diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index fa1d6ea..49c9e62 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -1,9 +1,5 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #pragma once -#include "GameplayTaskOwnerInterface.h" -#include "GameplayTaskTypes.h" -#include "GameplayTask.h" -#include "GameplayTasksComponent.h" #include "GameplayTags.h" #include "AFAbilityTypes.h" @@ -265,7 +261,7 @@ struct ABILITYFRAMEWORK_API FAFAbilityActionSet }; UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) -class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, /*UGameplayTasksComponent,*/ public IGameplayTagAssetInterface +class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public IGameplayTagAssetInterface { GENERATED_BODY() /* Attributes handling */ diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index 057be33..76574f2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -4,7 +4,6 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" -#include "GameplayTasksComponent.h" #include "GameplayTags.h" #include "GameplayTagAssetInterface.h" @@ -22,7 +21,7 @@ DECLARE_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); DECLARE_MULTICAST_DELEGATE_ThreeParams(FAFApplicationDelegate, FAFContextHandle, FAFPropertytHandle, FAFEffectSpecHandle); UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ABILITYFRAMEWORK_API UAFEffectsComponent : public UGameplayTasksComponent//public UActorComponent +class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent { GENERATED_BODY() private: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 49f9e79..691b809 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -111,7 +111,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt //possibly map TMap ? UPROPERTY() - TSet ActiveTasks; + TSet ActiveTasks; /* List of tasks, this ability have. */ UPROPERTY() TMap AbilityTasks; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index 292e707..d76f8a6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -42,7 +42,6 @@ public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) "UMG", "Slate", "SlateCore", - "GameplayTasks", "AIModule", "MovieScene", "MovieSceneTracks", diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index 0330719..edd23e9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -2,7 +2,7 @@ #pragma once -#include "GameplayTask.h" +#include "LatentActions/GALatentFunctionBase.h" #include "../GAEffectExtension.h" #include "../../GAGlobalTypes.h" #include "../../AFAbilityComponent.h" @@ -12,7 +12,7 @@ * */ UCLASS(BlueprintType, meta = (ExposedAsyncProxy = "true") ) -class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask +class ABILITYFRAMEWORK_API UAFEffectTask : public UGALatentFunctionBase { GENERATED_BODY() public: @@ -25,34 +25,6 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UGameplayTask template static T* NewEffectTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) { - check(WorldContextObject); - - T* MyObj = NewObject(WorldContextObject); - UGAEffectExtension* ThisAbility = CastChecked(WorldContextObject); - if (UAFEffectTask** CachedTask = ThisAbility->Tasks.Find(InTaskName)) - { - return Cast(*CachedTask); - } - //MyObj->Effect = ThisAbility; - MyObj->EffectsComponent = ThisAbility->OwningComponent; - MyObj->InitTask(*ThisAbility, ThisAbility->GetGameplayTaskDefaultPriority()); - MyObj->InstanceName = InstanceName; - //ThisAbility->AddAbilityTask(InTaskName, MyObj); - ThisAbility->Tasks.Add(InTaskName, MyObj); - //ThisAbility->Dupa.Add(MyObj); - return MyObj; - } - - template - static bool DelayedFalse() - { - return false; - } - - // this function has been added to make sure AbilityTasks don't use this method - template - FORCEINLINE static T* NewTask(UObject* WorldContextObject, FName InstanceName = FName()) - { - static_assert(DelayedFalse(), "UAbilityTask::NewTask should never be used. Use NewAbilityTask instead"); + return nullptr; } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp index 1df2db9..de64ad2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp @@ -72,15 +72,4 @@ UAFEffectsComponent* UAFEffectTask_AppliedEffectEvent::GetTargetASC() } return EffectsComponent; -} - -void UAFEffectTask_AppliedEffectEvent::OnDestroy(bool AbilityEnding) -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC && MyHandle.IsValid()) - { - ASC->RemoveAppliedEvent(Tag, MyHandle); - } - - Super::OnDestroy(AbilityEnding); -} +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h index 996ed71..86b21f4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h @@ -34,8 +34,6 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTa virtual void GameplayEventCallback(FAFEventData Payload); - void OnDestroy(bool AbilityEnding) override; - FGameplayTag Tag; UPROPERTY() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp index 7a428eb..81c77fe 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp @@ -67,17 +67,4 @@ UAFEffectsComponent* UAFEffectTask_AttributeChange::GetTargetASC() } return EffectsComponent; -} - -void UAFEffectTask_AttributeChange::OnDestroy(bool AbilityEnding) -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC && MyHandle.IsValid()) - { - // ASC->AttributeChanged.FindOrAdd(Attribute).Remove(MyHandle); - } - - Super::OnDestroy(AbilityEnding); -} - - +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h index fc5b661..628c03f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h @@ -33,9 +33,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask virtual void Activate() override; void AttributeChangedCallback(FAFAttributeChangedData Payload); - - void OnDestroy(bool AbilityEnding) override; - + FGAAttribute Attribute; UPROPERTY() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp index 0288262..02df3ce 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp @@ -70,15 +70,4 @@ UAFEffectsComponent* UAFEffectTask_EffectAppliedToSelf::GetTargetASC() } return EffectsComponent; -} - -void UAFEffectTask_EffectAppliedToSelf::OnDestroy(bool AbilityEnding) -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC && MyHandle.IsValid()) - { - ASC->OnAppliedToSelf.Remove(MyHandle); - } - - Super::OnDestroy(AbilityEnding); -} +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h index bc7cbd3..1836994 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h @@ -36,9 +36,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectT virtual void GameplayEventCallback(FAFContextHandle Context , FAFPropertytHandle Property , FAFEffectSpecHandle Spec); - - void OnDestroy(bool AbilityEnding) override; - + UPROPERTY() UAFEffectsComponent* OptionalExternalTarget; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp index 741e4f6..2ee8650 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp @@ -74,14 +74,3 @@ UAFEffectsComponent* UAFEffectTask_EffectAppliedToTarget::GetTargetASC() return EffectsComponent; } - -void UAFEffectTask_EffectAppliedToTarget::OnDestroy(bool AbilityEnding) -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC && MyHandle.IsValid()) - { - ASC->OnAppliedToTarget.Remove(MyHandle); - } - - Super::OnDestroy(AbilityEnding); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h index e231316..289d195 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h @@ -36,9 +36,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffec virtual void GameplayEventCallback(FAFContextHandle Context , FAFPropertytHandle Property , FAFEffectSpecHandle Spec); - - void OnDestroy(bool AbilityEnding) override; - + UPROPERTY() UAFEffectsComponent* OptionalExternalTarget; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp index d386bdc..a7817ad 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -72,15 +72,4 @@ UAFEffectsComponent* UAFEffectTask_EffectEvent::GetTargetASC() } return EffectsComponent; -} - -void UAFEffectTask_EffectEvent::OnDestroy(bool AbilityEnding) -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC && MyHandle.IsValid()) - { - ASC->RemoveEvent(Tag, MyHandle); - } - - Super::OnDestroy(AbilityEnding); -} +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h index 1a7cea5..39fb5c2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -33,8 +33,6 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask virtual void GameplayEventCallback(FAFEventData Payload); - void OnDestroy(bool AbilityEnding) override; - FGameplayTag Tag; UPROPERTY() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp index 6aec49b..25dae2c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp @@ -72,15 +72,4 @@ UAFEffectsComponent* UAFEffectTask_ExecutedEffectEvent::GetTargetASC() } return EffectsComponent; -} - -void UAFEffectTask_ExecutedEffectEvent::OnDestroy(bool AbilityEnding) -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC && MyHandle.IsValid()) - { - ASC->RemoveExecuteEvent(Tag, MyHandle); - } - - Super::OnDestroy(AbilityEnding); -} +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h index e437d45..59e18ff 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h @@ -34,8 +34,6 @@ class ABILITYFRAMEWORK_API UAFEffectTask_ExecutedEffectEvent : public UAFEffectT virtual void GameplayEventCallback(FAFEventData Payload); - void OnDestroy(bool AbilityEnding) override; - FGameplayTag Tag; UPROPERTY() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp index 08ea366..aefe50f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp @@ -33,41 +33,6 @@ void UGAEffectExtension::NativeOnEffectRemoved() { OnEffectRemoved(); } -/** GameplayTaskOwnerInterface - Begin */ -void UGAEffectExtension::OnGameplayTaskInitialized(UGameplayTask& Task) -{ - if (UAFEffectTask* task = Cast(&Task)) - { - task->Effect = this; - } -} -UGameplayTasksComponent* UGAEffectExtension::GetGameplayTasksComponent(const UGameplayTask& Task) const -{ - return OwningComponent; -} -/** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ -void UGAEffectExtension::OnGameplayTaskActivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Started; %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Add(&Task); - //AbilityComponent->OnGameplayTaskActivated(Task); -} -/** this gets called both when task finished and when task gets paused. Check Task.GetStatus() if you want to differenciate */ -void UGAEffectExtension::OnGameplayTaskDeactivated(UGameplayTask& Task) -{ - UE_LOG(AbilityFramework, Log, TEXT("Task Removed: %s in ability: %s"), *Task.GetName(), *GetName()); - ActiveTasks.Remove(&Task); - //AbilityComponent->OnGameplayTaskDeactivated(Task); -} -AActor* UGAEffectExtension::GetGameplayTaskOwner(const UGameplayTask* Task) const -{ - return OwningComponent->GetOwner(); -} -AActor* UGAEffectExtension::GetGameplayTaskAvatar(const UGameplayTask* Task) const -{ - return OwningComponent->GetOwner(); -} -/** GameplayTaskOwnerInterface - end */ UWorld* UGAEffectExtension::GetWorld() const { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h index 4640cc3..2762259 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h @@ -19,7 +19,7 @@ Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). */ UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplayTaskOwnerInterface +class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject { GENERATED_BODY() public: @@ -31,7 +31,7 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplay class AActor* Avatar; UPROPERTY() - TSet ActiveTasks; + TSet ActiveTasks; UPROPERTY() TMap Tasks; @@ -64,27 +64,5 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IGameplay void NativeOnEffectExpired(); void NativeOnEffectRemoved(); - /** GameplayTaskOwnerInterface - Begin */ - virtual UGameplayTasksComponent* GetGameplayTasksComponent(const UGameplayTask& Task) const override; - /** this gets called both when task starts and when task gets resumed. Check Task.GetStatus() if you want to differenciate */ - /** Get owner of a task or default one when task is null */ - virtual AActor* GetGameplayTaskOwner(const UGameplayTask* Task) const override; - - /** Get "body" of task's owner / default, having location in world (e.g. Owner = AIController, Avatar = Pawn) */ - virtual AActor* GetGameplayTaskAvatar(const UGameplayTask* Task) const override; - - /** Get default priority for running a task */ - virtual uint8 GetGameplayTaskDefaultPriority() const { return 1; }; - - /** Notify called after GameplayTask finishes initialization (not active yet) */ - virtual void OnGameplayTaskInitialized(UGameplayTask& Task) override; - - /** Notify called after GameplayTask changes state to Active (initial activation or resuming) */ - virtual void OnGameplayTaskActivated(UGameplayTask& Task) override; - - /** Notify called after GameplayTask changes state from Active (finishing or pausing) */ - virtual void OnGameplayTaskDeactivated(UGameplayTask& Task) override; - /** GameplayTaskOwnerInterface - end */ - virtual UWorld* GetWorld() const override; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp index 61b6b5f..1d424f5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp @@ -2,7 +2,7 @@ #include "AbilityFrameworkEditor.h" #include "Kismet/KismetMathLibrary.h" #include "Kismet/KismetArrayLibrary.h" -#include "GameplayTask.h" +#include "LatentActions/GALatentFunctionBase.h" #include "Effects/EffectTasks/AFEffectTask.h" #include "Effects/GAEffectExtension.h" #include "KismetCompiler.h" @@ -17,16 +17,7 @@ UAFEK2Node_AsyncEffectTaskCall::UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - if (HasAnyFlags(RF_ClassDefaultObject) == true) - { - UK2Node_LatentGameplayTaskCall::RegisterSpecializedTaskNodeClass(GetClass()); - } -} - -bool UAFEK2Node_AsyncEffectTaskCall::IsHandling(TSubclassOf TaskClass) const -{ - bool isChilldOf = TaskClass && TaskClass->IsChildOf(UAFEffectTask::StaticClass()); - return isChilldOf; + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentFunctionBase, ReadyForActivation); } bool UAFEK2Node_AsyncEffectTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h index 0762b9c..d9c7d0f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h @@ -3,11 +3,10 @@ #include "EdGraph/EdGraphPin.h" #include "EdGraphSchema_K2.h" #include "K2Node_BaseAsyncTask.h" -#include "K2Node_LatentGameplayTaskCall.h" #include "AFEK2Node_AsyncEffectTaskCall.generated.h" UCLASS() -class UAFEK2Node_AsyncEffectTaskCall : public UK2Node_LatentGameplayTaskCall +class UAFEK2Node_AsyncEffectTaskCall : public UK2Node_BaseAsyncTask { GENERATED_BODY() @@ -18,6 +17,4 @@ class UAFEK2Node_AsyncEffectTaskCall : public UK2Node_LatentGameplayTaskCall virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; // End of UEdGraphNode interface -protected: - virtual bool IsHandling(TSubclassOf TaskClass) const override; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs index 27d4dfe..5df26d0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs @@ -64,8 +64,6 @@ public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) "AssetTools", "MainFrame", "InputCore", - "GameplayTasks", - "GameplayTasksEditor", "AbilityFramework", "MovieScene", "MovieSceneTools", diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp index 3305cab..b4e7672 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -17,11 +17,7 @@ UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGameplayTask, ReadyForActivation); - if (HasAnyFlags(RF_ClassDefaultObject) == true) - { - UK2Node_LatentGameplayTaskCall::RegisterSpecializedTaskNodeClass(GetClass()); - } + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentFunctionBase, ReadyForActivation); } bool UGAEK2Node_LatentAbilityTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h index 0dcbec4..e81d718 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h @@ -3,7 +3,6 @@ #include "EdGraph/EdGraphPin.h" #include "EdGraphSchema_K2.h" #include "K2Node_BaseAsyncTask.h" -#include "K2Node_LatentGameplayTaskCall.h" #include "GAEK2Node_LatentAbilityTaskCall.generated.h" UCLASS() From 46f4ba4e9c48a79fb8e57b89ecfe6465b0f6dd19 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 7 Apr 2018 14:20:42 +0200 Subject: [PATCH 106/187] changed GALatentFunctionBase to AFTaskBAse to better reflect intended functionality --- .../AbilityFramework/AFAbilityComponent.h | 2 +- .../Abilities/GAAbilityBase.cpp | 12 +++--- .../Abilities/GAAbilityBase.h | 12 +++--- .../Abilities/Tasks/GAAbilityTask.h | 4 +- .../Effects/EffectTasks/AFEffectTask.h | 10 ++--- .../LatentActions/AFLatentInterface.cpp | 8 ++++ .../LatentActions/AFLatentInterface.h | 25 +++++++++++ ...ALatentFunctionBase.cpp => AFTaskBase.cpp} | 18 ++++---- .../{GALatentFunctionBase.h => AFTaskBase.h} | 42 +++++++++++++++++-- .../LatentActions/AFTaskManager.cpp | 10 +++++ .../LatentActions/AFTaskManager.h | 13 ++++++ .../LatentActions/GAWaitAction.h | 4 +- .../AFEK2Node_AsyncEffectTaskCall.cpp | 4 +- .../GAEK2Node_LatentAbilityTaskCall.cpp | 2 +- .../GAEK2Node_LatentAction.cpp | 6 +-- 15 files changed, 131 insertions(+), 41 deletions(-) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h rename Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/{GALatentFunctionBase.cpp => AFTaskBase.cpp} (80%) rename Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/{GALatentFunctionBase.h => AFTaskBase.h} (72%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 49c9e62..7bf4d6c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -678,7 +678,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public */ UPROPERTY(Replicated) - TArray ReplicatedTasks; + TArray ReplicatedTasks; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 42198bc..3dd65cc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -917,29 +917,29 @@ AActor* UGAAbilityBase::BP_GetAvatar() } -void UGAAbilityBase::OnLatentTaskAdded(FName InstanceName, class UGALatentFunctionBase* TaskIn) +void UGAAbilityBase::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) { if (!InstanceName.IsNone()) { AbilityTasks.Add(InstanceName, Cast(TaskIn)); } }; -void UGAAbilityBase::AddReplicatedTask(class UGALatentFunctionBase* TaskIn) +void UGAAbilityBase::AddReplicatedTask(class UAFTaskBase* TaskIn) { AbilityComponent->ReplicatedTasks.Add(TaskIn); } -void UGAAbilityBase::OnLatentTaskRemoved(class UGALatentFunctionBase* TaskIn) +void UGAAbilityBase::OnLatentTaskRemoved(class UAFTaskBase* TaskIn) { }; -void UGAAbilityBase::OnLatentTaskActivated(class UGALatentFunctionBase* TaskIn) +void UGAAbilityBase::OnLatentTaskActivated(class UAFTaskBase* TaskIn) { }; -void UGAAbilityBase::OnLatentTaskDeactivated(class UGALatentFunctionBase* TaskIn) +void UGAAbilityBase::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) { }; -class UGALatentFunctionBase* UGAAbilityBase::GetCachedLatentAction(FName TaskName) +class UAFTaskBase* UGAAbilityBase::GetCachedLatentAction(FName TaskName) { return AbilityTasks.FindRef(TaskName); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 691b809..3a76d42 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -613,13 +613,13 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt /* IAFLatentInterface */ - virtual void OnLatentTaskAdded(FName InstanceName, class UGALatentFunctionBase* TaskIn); - virtual void AddReplicatedTask(class UGALatentFunctionBase* TaskIn); - virtual void OnLatentTaskRemoved(class UGALatentFunctionBase* TaskIn); + virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn); + virtual void AddReplicatedTask(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn); - virtual void OnLatentTaskActivated(class UGALatentFunctionBase* TaskIn); - virtual void OnLatentTaskDeactivated(class UGALatentFunctionBase* TaskIn); + virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn); - virtual class UGALatentFunctionBase* GetCachedLatentAction(FName TaskName); + virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); /* IAFLatentInterface */ }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index f451049..55cdfe9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -3,7 +3,7 @@ #include "GAAbilityBase.h" #include "AFAbilityComponent.h" -#include "LatentActions/GALatentFunctionBase.h" +#include "LatentActions/AFTaskBase.h" #include "GAAbilityTask.generated.h" /* @@ -18,7 +18,7 @@ */ UCLASS(BlueprintType, Blueprintable, Within=GAAbilityBase) -class ABILITYFRAMEWORK_API UGAAbilityTask : public UGALatentFunctionBase +class ABILITYFRAMEWORK_API UGAAbilityTask : public UAFTaskBase { GENERATED_BODY() friend struct FAFAbilityTaskMessageTick; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index edd23e9..e0746dc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -2,17 +2,17 @@ #pragma once -#include "LatentActions/GALatentFunctionBase.h" -#include "../GAEffectExtension.h" -#include "../../GAGlobalTypes.h" -#include "../../AFAbilityComponent.h" +#include "LatentActions/AFTaskBase.h" +#include "GAEffectExtension.h" +#include "GAGlobalTypes.h" +#include "AFAbilityComponent.h" #include "AFEffectTask.generated.h" /** * */ UCLASS(BlueprintType, meta = (ExposedAsyncProxy = "true") ) -class ABILITYFRAMEWORK_API UAFEffectTask : public UGALatentFunctionBase +class ABILITYFRAMEWORK_API UAFEffectTask : public UAFTaskBase { GENERATED_BODY() public: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp new file mode 100644 index 0000000..abdf620 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp @@ -0,0 +1,8 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFLatentInterface.h" +UAFLatentInterface::UAFLatentInterface(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h new file mode 100644 index 0000000..0ce54c8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h @@ -0,0 +1,25 @@ +#pragma once +#include "AFLatentInterface.generated.h" + + +struct FAFAttributeBase; +struct FGAEffectHandle; +UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) +class ABILITYFRAMEWORK_API UAFLatentInterface : public UInterface +{ + GENERATED_UINTERFACE_BODY() +}; + +class IAFLatentInterface +{ + GENERATED_IINTERFACE_BODY() +public: + virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) = 0; + virtual void AddReplicatedTask(class UAFTaskBase* TaskIn) = 0; + virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn) = 0; + + virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn) = 0; + virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) = 0; + + virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName) = 0; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp similarity index 80% rename from Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp rename to Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp index 1accfd5..20e39df 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp @@ -3,7 +3,7 @@ #include "AbilityFramework.h" #include "AFLatentInterface.h" -#include "GALatentFunctionBase.h" +#include "AFTaskBase.h" void FGALatentFunctionTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) { @@ -19,7 +19,7 @@ FString FGALatentFunctionTick::DiagnosticMessage() return Target->GetFullName() + TEXT("[TickAction]"); } -UGALatentFunctionBase::UGALatentFunctionBase(const FObjectInitializer& ObjectInitializer) +UAFTaskBase::UAFTaskBase(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { TickFunction.TickGroup = TG_PrePhysics; @@ -34,7 +34,7 @@ UGALatentFunctionBase::UGALatentFunctionBase(const FObjectInitializer& ObjectIni TaskState = EState::Waiting; } -void UGALatentFunctionBase::Initialize() +void UAFTaskBase::Initialize() { if (GetWorld()) { @@ -47,7 +47,7 @@ void UGALatentFunctionBase::Initialize() } } -void UGALatentFunctionBase::ReadyForActivation() +void UAFTaskBase::ReadyForActivation() { if (TaskOwner) { @@ -65,7 +65,7 @@ void UGALatentFunctionBase::ReadyForActivation() } } -void UGALatentFunctionBase::EndTask() +void UAFTaskBase::EndTask() { if (TickFunction.bCanEverTick && TickFunction.IsTickFunctionRegistered()) { @@ -76,20 +76,20 @@ void UGALatentFunctionBase::EndTask() TaskState = EState::Finished; //MarkPendingKill(); } -void UGALatentFunctionBase::BeginDestroy() +void UAFTaskBase::BeginDestroy() { Super::BeginDestroy(); } -bool UGALatentFunctionBase::IsNameStableForNetworking() const +bool UAFTaskBase::IsNameStableForNetworking() const { return false; } -void UGALatentFunctionBase::SetNetAddressable() +void UAFTaskBase::SetNetAddressable() { } -UWorld* UGALatentFunctionBase::GetWorld() const +UWorld* UAFTaskBase::GetWorld() const { if (TaskOwner) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h similarity index 72% rename from Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h rename to Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h index ae3fd97..7a13f51 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GALatentFunctionBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h @@ -3,12 +3,12 @@ #include "Engine/EngineBaseTypes.h" #include "AFLatentInterface.h" -#include "GALatentFunctionBase.generated.h" +#include "AFTaskBase.generated.h" struct FGALatentFunctionTick: public FTickFunction { /** AActor that is the target of this tick **/ - class UGALatentFunctionBase* Target; + class UAFTaskBase* Target; /** * Abstract function actually execute the tick. @@ -23,7 +23,7 @@ struct FGALatentFunctionTick: public FTickFunction }; UCLASS(meta = (ExposedAsyncProxy = "true")) -class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject +class ABILITYFRAMEWORK_API UAFTaskBase : public UObject { GENERATED_BODY() //never access internals of these classes directly. Use messages instead. @@ -43,7 +43,7 @@ class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject friend struct FGALatentFunctionTick; FGALatentFunctionTick TickFunction; - UGALatentFunctionBase(const FObjectInitializer& ObjectInitializer); + UAFTaskBase(const FObjectInitializer& ObjectInitializer); virtual UWorld* GetWorld() const override; //virtual void Tick(float DeltaSecondsIn); @@ -68,6 +68,40 @@ class ABILITYFRAMEWORK_API UGALatentFunctionBase : public UObject void SetNetAddressable(); protected: + + //use template to avoid using interface + template + static TaskType* NewTask2(UObject* WorldContextObject, OwnerType* InTaskOwner, FName InstanceName = FName()) + { + TaskType* MyObj = nullptr; + //if (IAFLatentInterface* Interface = Cast(InTaskOwner)) + { + if (!InstanceName.IsNone()) + { + MyObj = Cast(InTaskOwner->GetCachedLatentAction(InstanceName)); + if (!MyObj) + { + MyObj = NewObject(WorldContextObject); + + InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); + } + } + else + { + MyObj = NewObject(WorldContextObject); + + InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); + } + if (MyObj->bReplicated) + { + InTaskOwner->AddReplicatedTask(MyObj); + } + MyObj->TaskOwner = InTaskOwner; + } + + return MyObj; + } + template static T* NewTask(UObject* WorldContextObject, UObject* InTaskOwner, FName InstanceName = FName()) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp new file mode 100644 index 0000000..defc5fe --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp @@ -0,0 +1,10 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFTaskManager.h" + + +UAFTaskManager::UAFTaskManager(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h new file mode 100644 index 0000000..6ae8999 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h @@ -0,0 +1,13 @@ +#pragma once +#include "CoreMinimal.h" +#include "Engine/EngineBaseTypes.h" + +#include "AFTaskManager.generated.h" + +UCLASS() +class ABILITYFRAMEWORK_API UAFTaskManager : public UObject +{ + GENERATED_BODY() +public: + UAFTaskManager(const FObjectInitializer& ObjectInitializer); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h index fe34b7f..af68fc7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h @@ -1,5 +1,5 @@ #pragma once -#include "GALatentFunctionBase.h" +#include "AFTaskBase.h" #include "GAWaitAction.generated.h" /* AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and @@ -12,7 +12,7 @@ or should designer in blueprint decide when to launch actions ?). */ UCLASS(meta = (ExposedAsyncProxy = "true") ) -class ABILITYFRAMEWORK_API UGAWaitAction : public UGALatentFunctionBase +class ABILITYFRAMEWORK_API UGAWaitAction : public UAFTaskBase { GENERATED_BODY() diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp index 1d424f5..f0898d5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp @@ -2,7 +2,7 @@ #include "AbilityFrameworkEditor.h" #include "Kismet/KismetMathLibrary.h" #include "Kismet/KismetArrayLibrary.h" -#include "LatentActions/GALatentFunctionBase.h" +#include "LatentActions/AFTaskBase.h" #include "Effects/EffectTasks/AFEffectTask.h" #include "Effects/GAEffectExtension.h" #include "KismetCompiler.h" @@ -17,7 +17,7 @@ UAFEK2Node_AsyncEffectTaskCall::UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentFunctionBase, ReadyForActivation); + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); } bool UAFEK2Node_AsyncEffectTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp index b4e7672..1784ae6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp @@ -17,7 +17,7 @@ UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentFunctionBase, ReadyForActivation); + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); } bool UGAEK2Node_LatentAbilityTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp index 34bc73b..a5c474a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp @@ -8,13 +8,13 @@ #include "K2Node_EnumLiteral.h" #include "BlueprintFunctionNodeSpawner.h" #include "BlueprintActionDatabaseRegistrar.h" -#include "LatentActions/GALatentFunctionBase.h" +#include "LatentActions/AFTaskBase.h" #define LOCTEXT_NAMESPACE "K2Node" UGAEK2Node_LatentAction::UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UGALatentFunctionBase, ReadyForActivation); + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); } bool UGAEK2Node_LatentAction::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const @@ -61,7 +61,7 @@ void UGAEK2Node_LatentAction::GetMenuActions(FBlueprintActionDatabaseRegistrar& UClass* NodeClass = GetClass(); //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); - ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* { UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); check(NodeSpawner != nullptr); From c9fd4e81fa3055cd78a11c9fad656b4abb3b824a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 7 Apr 2018 14:56:22 +0200 Subject: [PATCH 107/187] ability tasks are now using template to instance instead of interface --- .../Tasks/AFAbilityTask_SpawnProjectile.cpp | 2 +- .../Tasks/AFAbilityTask_SpawnProjectile.h | 2 +- .../Abilities/Tasks/GAAbilityTask.h | 4 ++-- .../Tasks/GAAbilityTask_CreateObject.cpp | 6 +++--- .../Abilities/Tasks/GAAbilityTask_CreateObject.h | 6 +++--- .../Abilities/Tasks/GAAbilityTask_PlayMontage.cpp | 2 +- .../Abilities/Tasks/GAAbilityTask_PlayMontage.h | 2 +- .../Abilities/Tasks/GAAbilityTask_Repeat.cpp | 2 +- .../Abilities/Tasks/GAAbilityTask_Repeat.h | 2 +- .../Abilities/Tasks/GAAbilityTask_SpawnActor.cpp | 6 +++--- .../Abilities/Tasks/GAAbilityTask_SpawnActor.h | 6 +++--- .../Abilities/Tasks/GAAbilityTask_TargetData.cpp | 2 +- .../Abilities/Tasks/GAAbilityTask_TargetData.h | 2 +- .../Tasks/GAAbilityTask_TargetDataCircle.cpp | 2 +- .../Tasks/GAAbilityTask_TargetDataCircle.h | 2 +- .../Tasks/GAAbilityTask_TargetDataLineTrace.cpp | 2 +- .../Tasks/GAAbilityTask_TargetDataLineTrace.h | 2 +- .../Tasks/GAAbilityTask_WaitForConfirm.cpp | 2 +- .../Tasks/GAAbilityTask_WaitForConfirm.h | 2 +- .../LatentActions/AFTaskManager.cpp | 15 +++++++++++++++ .../LatentActions/AFTaskManager.h | 4 ++++ 21 files changed, 47 insertions(+), 28 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp index c7db9d7..dee0062 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp @@ -6,7 +6,7 @@ -UAFAbilityTask_SpawnProjectile* UAFAbilityTask_SpawnProjectile::Ability_SpawnProjectile(UObject* WorldContextObject, +UAFAbilityTask_SpawnProjectile* UAFAbilityTask_SpawnProjectile::Ability_SpawnProjectile(UGAAbilityBase* WorldContextObject, FName InTaskName, FVector InStartLocation, FVector InEndLocation, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h index fd47dd4..5d3e7ae 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h @@ -44,7 +44,7 @@ class ABILITYFRAMEWORK_API UAFAbilityTask_SpawnProjectile : public UGAAbilityTas UPROPERTY(BlueprintAssignable) FAFOnPRojectileSpawned Played; public: - static UAFAbilityTask_SpawnProjectile* Ability_SpawnProjectile(UObject* WorldContextObject, + static UAFAbilityTask_SpawnProjectile* Ability_SpawnProjectile(UGAAbilityBase* WorldContextObject, FName InTaskName, FVector InStartLocation, FVector InEndLocation, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 55cdfe9..32abc3d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -31,13 +31,13 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UAFTaskBase public: template - static T* NewAbilityTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) + static T* NewAbilityTask(UGAAbilityBase* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) { check(WorldContextObject); T* MyObj = nullptr; UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); - MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); + MyObj = NewTask2(WorldContextObject, WorldContextObject, InTaskName); MyObj->Ability = ThisAbility; MyObj->AbilityComponent = ThisAbility->AbilityComponent; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp index ff4e38b..c82011a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp @@ -3,7 +3,7 @@ #include "../../AbilityFramework.h" #include "GAAbilityTask_CreateObject.h" -UGAAbilityTask_CreateObject* UGAAbilityTask_CreateObject::CreateObject(UObject* WorldContextObject, +UGAAbilityTask_CreateObject* UGAAbilityTask_CreateObject::CreateObject(UGAAbilityBase* WorldContextObject, FName InTaskName, TSubclassOf Class, UObject* Outer) { auto MyObj = NewAbilityTask(WorldContextObject); @@ -15,7 +15,7 @@ UGAAbilityTask_CreateObject* UGAAbilityTask_CreateObject::CreateObject(UObject* // --------------------------------------------------------------------------------------- -bool UGAAbilityTask_CreateObject::BeginSpawningActor(UObject* WorldContextObject, +bool UGAAbilityTask_CreateObject::BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, UObject*& SpawnedActor) { //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) @@ -36,7 +36,7 @@ bool UGAAbilityTask_CreateObject::BeginSpawningActor(UObject* WorldContextObject return true; } -void UGAAbilityTask_CreateObject::FinishSpawningActor(UObject* WorldContextObject, UObject* SpawnedActor) +void UGAAbilityTask_CreateObject::FinishSpawningActor(UGAAbilityBase* WorldContextObject, UObject* SpawnedActor) { if (SpawnedActor) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h index 6aa3bed..3fbdd2c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h @@ -21,12 +21,12 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_CreateObject : public UGAAbilityTask FGASSpawnObjectDelegate Failure; UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_CreateObject* CreateObject(UObject* WorldContextObject, + static UGAAbilityTask_CreateObject* CreateObject(UGAAbilityBase* WorldContextObject, FName InTaskName, TSubclassOf Class, UObject* Outer); UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, class UObject*& SpawnedActor); + bool BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, class UObject*& SpawnedActor); UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - void FinishSpawningActor(UObject* WorldContextObject, class UObject* SpawnedActor); + void FinishSpawningActor(UGAAbilityBase* WorldContextObject, class UObject* SpawnedActor); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp index afdbd32..3ab4e2e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp @@ -4,7 +4,7 @@ #include "../../AFAbilityComponent.h" #include "GAAbilityTask_PlayMontage.h" -UGAAbilityTask_PlayMontage* UGAAbilityTask_PlayMontage::AbilityPlayMontage(UObject* WorldContextObject, +UGAAbilityTask_PlayMontage* UGAAbilityTask_PlayMontage::AbilityPlayMontage(UGAAbilityBase* WorldContextObject, FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, bool bInUseActivationTime) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h index 2a2b708..1c33398 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h @@ -33,7 +33,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_PlayMontage : public UGAAbilityTask FGASGenericMontageDelegate NotifyEnd; UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_PlayMontage* AbilityPlayMontage(UObject* WorldContextObject, + static UGAAbilityTask_PlayMontage* AbilityPlayMontage(UGAAbilityBase* WorldContextObject, FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, bool bInUseActivationTime); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp index 214da95..1ee4cbb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp @@ -6,7 +6,7 @@ -UGAAbilityTask_Repeat* UGAAbilityTask_Repeat::CreateRepeatTask(UObject* WorldContextObject, +UGAAbilityTask_Repeat* UGAAbilityTask_Repeat::CreateRepeatTask(UGAAbilityBase* WorldContextObject, FName InTaskName) { auto MyObj = NewAbilityTask(WorldContextObject); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h index 338343e..914bf6a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h @@ -19,6 +19,6 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_Repeat : public UGAAbilityTask FGASOnTaskRepeated OnTaskRepeated; UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_Repeat* CreateRepeatTask(UObject* WorldContextObject, + static UGAAbilityTask_Repeat* CreateRepeatTask(UGAAbilityBase* WorldContextObject, FName InTaskName); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp index 370a513..a075365 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp @@ -7,7 +7,7 @@ -UGAAbilityTask_SpawnActor* UGAAbilityTask_SpawnActor::SpawnActor(UObject* WorldContextObject, +UGAAbilityTask_SpawnActor* UGAAbilityTask_SpawnActor::SpawnActor(UGAAbilityBase* WorldContextObject, FName InTaskName, TSubclassOf InClass) { auto MyObj = NewAbilityTask(WorldContextObject); @@ -22,7 +22,7 @@ void UGAAbilityTask_SpawnActor::Activate() //EndTask(); } -bool UGAAbilityTask_SpawnActor::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf InClass, AActor*& SpawnedActor) +bool UGAAbilityTask_SpawnActor::BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf InClass, AActor*& SpawnedActor) { //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) //{ @@ -42,7 +42,7 @@ bool UGAAbilityTask_SpawnActor::BeginSpawningActor(UObject* WorldContextObject, return true; } -void UGAAbilityTask_SpawnActor::FinishSpawningActor(UObject* WorldContextObject, AActor* SpawnedActor) +void UGAAbilityTask_SpawnActor::FinishSpawningActor(UGAAbilityBase* WorldContextObject, AActor* SpawnedActor) { if (SpawnedActor) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h index 162fb88..af30e2f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h @@ -21,14 +21,14 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_SpawnActor : public UGAAbilityTask FGASSpawnActorDelegate Failure; UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_SpawnActor* SpawnActor(UObject* WorldContextObject, + static UGAAbilityTask_SpawnActor* SpawnActor(UGAAbilityBase* WorldContextObject, FName InTaskName, TSubclassOf Class); UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - bool BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AActor*& SpawnedActor); + bool BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, AActor*& SpawnedActor); UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - void FinishSpawningActor(UObject* WorldContextObject, AActor* SpawnedActor); + void FinishSpawningActor(UGAAbilityBase* WorldContextObject, AActor* SpawnedActor); virtual void Activate() override; }; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp index ce4a128..9221e99 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp @@ -5,7 +5,7 @@ #include "GAAbilityTask_TargetData.h" -UGAAbilityTask_TargetData* UGAAbilityTask_TargetData::CreateTargetDataTask(UObject* WorldContextObject, +UGAAbilityTask_TargetData* UGAAbilityTask_TargetData::CreateTargetDataTask(UGAAbilityBase* WorldContextObject, FName InTaskName, bool bDrawDebug, bool bDrawCorrectedDebug, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h index 859b250..2ce9ab4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h @@ -37,7 +37,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetData : public UGAAbilityTask, pu bool bUseCorrectedTrace; public: UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_TargetData* CreateTargetDataTask(UObject* WorldContextObject, + static UGAAbilityTask_TargetData* CreateTargetDataTask(UGAAbilityBase* WorldContextObject, FName InTaskName, bool bDrawDebug, bool bDrawCorrectedDebug, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp index 6a2b50a..1d539b4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp @@ -5,7 +5,7 @@ #include "GAAbilityTask_TargetDataCircle.h" -UGAAbilityTask_TargetDataCircle* UGAAbilityTask_TargetDataCircle::TargetCircleDataTask(UObject* WorldContextObject, +UGAAbilityTask_TargetDataCircle* UGAAbilityTask_TargetDataCircle::TargetCircleDataTask(UGAAbilityBase* WorldContextObject, FName InTaskName, EGASConfirmType ConfirmTypeIn) { auto MyObj = NewAbilityTask(WorldContextObject); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h index fdb89b0..ea39110 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h @@ -23,7 +23,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataCircle : public UGAAbilityTa public: UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_TargetDataCircle* TargetCircleDataTask(UObject* WorldContextObject, + static UGAAbilityTask_TargetDataCircle* TargetCircleDataTask(UGAAbilityBase* WorldContextObject, FName InTaskName, EGASConfirmType ConfirmTypeIn); virtual void Activate() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp index 5a66e3b..38115e5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp @@ -5,7 +5,7 @@ #include "GAAbilityTask_TargetDataLineTrace.h" -UGAAbilityTask_TargetDataLineTrace* UGAAbilityTask_TargetDataLineTrace::CreateTargetDataLineTrace(UObject* WorldContextObject +UGAAbilityTask_TargetDataLineTrace* UGAAbilityTask_TargetDataLineTrace::CreateTargetDataLineTrace(UGAAbilityBase* WorldContextObject , FName InTaskName , ETraceTypeQuery InTraceChannel , USkeletalMeshComponent* InSocketComponent diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h index c8beb76..bf137c2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h @@ -68,7 +68,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataLineTrace : public UGAAbilit FHitResult LocalHitResult; public: UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_TargetDataLineTrace* CreateTargetDataLineTrace(UObject* WorldContextObject + static UGAAbilityTask_TargetDataLineTrace* CreateTargetDataLineTrace(UGAAbilityBase* WorldContextObject , FName InTaskName , ETraceTypeQuery InTraceChannel , USkeletalMeshComponent* InSocketComponent diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp index b84c262..58e48ce 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp @@ -7,7 +7,7 @@ -UGAAbilityTask_WaitForConfirm* UGAAbilityTask_WaitForConfirm::CreateWaitConfirmTask(UObject* WorldContextObject, +UGAAbilityTask_WaitForConfirm* UGAAbilityTask_WaitForConfirm::CreateWaitConfirmTask(UGAAbilityBase* WorldContextObject, FName InTaskName) { auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h index 39c8203..e81c18a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h @@ -19,7 +19,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_WaitForConfirm : public UGAAbilityTask FGASOnConfirmed OnConfirmed; UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_WaitForConfirm* CreateWaitConfirmTask(UObject* WorldContextObject, + static UGAAbilityTask_WaitForConfirm* CreateWaitConfirmTask(UGAAbilityBase* WorldContextObject, FName InTaskName); virtual void Activate() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp index defc5fe..10382b4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp @@ -3,8 +3,23 @@ #include "AbilityFramework.h" #include "AFTaskManager.h" +UAFTaskManager* UAFTaskManager::Instance = nullptr; UAFTaskManager::UAFTaskManager(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { } + +UAFTaskManager* UAFTaskManager::Get() +{ + if (Instance) + { + return Instance; + } + else + { + Instance = NewObject(); + Instance->AddToRoot(); + return Instance; + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h index 6ae8999..8a39299 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h @@ -8,6 +8,10 @@ UCLASS() class ABILITYFRAMEWORK_API UAFTaskManager : public UObject { GENERATED_BODY() + + static UAFTaskManager* Instance; + public: UAFTaskManager(const FObjectInitializer& ObjectInitializer); + static UAFTaskManager* Get(); }; From 1538658be6a98743a07ef08a4382b6b6e5d3b2c6 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 7 Apr 2018 14:57:46 +0200 Subject: [PATCH 108/187] formatting --- .../LatentActions/AFTaskBase.h | 32 +++++++++---------- 1 file changed, 15 insertions(+), 17 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h index 7a13f51..dc4b96d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h @@ -74,31 +74,29 @@ class ABILITYFRAMEWORK_API UAFTaskBase : public UObject static TaskType* NewTask2(UObject* WorldContextObject, OwnerType* InTaskOwner, FName InstanceName = FName()) { TaskType* MyObj = nullptr; - //if (IAFLatentInterface* Interface = Cast(InTaskOwner)) + + if (!InstanceName.IsNone()) { - if (!InstanceName.IsNone()) - { - MyObj = Cast(InTaskOwner->GetCachedLatentAction(InstanceName)); - if (!MyObj) - { - MyObj = NewObject(WorldContextObject); - - InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); - } - } - else + MyObj = Cast(InTaskOwner->GetCachedLatentAction(InstanceName)); + if (!MyObj) { MyObj = NewObject(WorldContextObject); InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); } - if (MyObj->bReplicated) - { - InTaskOwner->AddReplicatedTask(MyObj); - } - MyObj->TaskOwner = InTaskOwner; } + else + { + MyObj = NewObject(WorldContextObject); + InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); + } + if (MyObj->bReplicated) + { + InTaskOwner->AddReplicatedTask(MyObj); + } + MyObj->TaskOwner = InTaskOwner; + return MyObj; } From 696e320a50043bb9f586baa86796ef829745eabd Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 7 Apr 2018 18:24:11 +0200 Subject: [PATCH 109/187] removed old task creation functions, and refactored Effect Tasks for new system --- Config/DefaultEngine.ini | 2 +- .../Abilities/Tasks/GAAbilityTask.h | 2 +- .../Effects/EffectTasks/AFEffectTask.h | 2 +- .../AFEffectTask_AppliedEffectEvent.cpp | 2 +- .../AFEffectTask_AppliedEffectEvent.h | 2 +- .../AFEffectTask_AttributeChange.cpp | 2 +- .../AFEffectTask_AttributeChange.h | 2 +- .../AFEffectTask_EffectAppliedToSelf.cpp | 2 +- .../AFEffectTask_EffectAppliedToSelf.h | 2 +- .../AFEffectTask_EffectAppliedToTarget.cpp | 2 +- .../AFEffectTask_EffectAppliedToTarget.h | 2 +- .../EffectTasks/AFEffectTask_EffectEvent.cpp | 2 +- .../EffectTasks/AFEffectTask_EffectEvent.h | 2 +- .../AFEffectTask_ExecutedEffectEvent.cpp | 2 +- .../AFEffectTask_ExecutedEffectEvent.h | 2 +- .../LatentActions/AFTaskBase.h | 34 +------------------ .../LatentActions/GAWaitAction.cpp | 4 +-- 17 files changed, 18 insertions(+), 50 deletions(-) diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index f67c99c..ddd73ef 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -26,6 +26,7 @@ r.GenerateLandscapeGIData=True r.TemporalAA.Upsampling=False bDefaultParticleCutouts=True r.SupportMaterialLayers=True +r.GBufferFormat=3 [/Script/Engine.StreamingSettings] s.AsyncLoadingThreadEnabled=True @@ -176,4 +177,3 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h index 32abc3d..b989524 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h @@ -37,7 +37,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask : public UAFTaskBase T* MyObj = nullptr; UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); - MyObj = NewTask2(WorldContextObject, WorldContextObject, InTaskName); + MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); MyObj->Ability = ThisAbility; MyObj->AbilityComponent = ThisAbility->AbilityComponent; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index e0746dc..b87e0a8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -23,7 +23,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UAFTaskBase public: template - static T* NewEffectTask(UObject* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) + static T* NewEffectTask(UGAEffectExtension* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) { return nullptr; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp index de64ad2..5309e9e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp @@ -14,7 +14,7 @@ UAFEffectTask_AppliedEffectEvent::UAFEffectTask_AppliedEffectEvent(const FObject } -UAFEffectTask_AppliedEffectEvent* UAFEffectTask_AppliedEffectEvent::ListenAppliedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +UAFEffectTask_AppliedEffectEvent* UAFEffectTask_AppliedEffectEvent::ListenAppliedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) { auto MyObj = NewEffectTask(OwningExtension, TaskName); MyObj->Tag = Tag; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h index 86b21f4..52e0849 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h @@ -22,7 +22,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTa FAFEffectEventDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_AppliedEffectEvent* ListenAppliedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + static UAFEffectTask_AppliedEffectEvent* ListenAppliedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp index 81c77fe..1e91f68 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp @@ -10,7 +10,7 @@ UAFEffectTask_AttributeChange::UAFEffectTask_AttributeChange(const FObjectInitia } -UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeChanged(UObject* OwningExtension, +UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeChanged(UGAEffectExtension* OwningExtension, FGAAttribute InAttribute, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h index 628c03f..1952d19 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h @@ -19,7 +19,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask FAFTaskAttributeChangedDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_AttributeChange* ListenAttributeChanged(UObject* OwningExtension, + static UAFEffectTask_AttributeChange* ListenAttributeChanged(UGAEffectExtension* OwningExtension, FGAAttribute InAttribute, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp index 02df3ce..c4ab076 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp @@ -14,7 +14,7 @@ UAFEffectTask_EffectAppliedToSelf::UAFEffectTask_EffectAppliedToSelf(const FObje } -UAFEffectTask_EffectAppliedToSelf* UAFEffectTask_EffectAppliedToSelf::ListenEffectAppliedToSelf(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +UAFEffectTask_EffectAppliedToSelf* UAFEffectTask_EffectAppliedToSelf::ListenEffectAppliedToSelf(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) { auto MyObj = NewEffectTask(OwningExtension, TaskName); MyObj->SetExternalTarget(OptionalExternalTarget); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h index 1836994..3d2e8b5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h @@ -23,7 +23,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectT FAFEffectEventDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectAppliedToSelf* ListenEffectAppliedToSelf(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + static UAFEffectTask_EffectAppliedToSelf* ListenEffectAppliedToSelf(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp index 2ee8650..d2fdf90 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp @@ -14,7 +14,7 @@ UAFEffectTask_EffectAppliedToTarget::UAFEffectTask_EffectAppliedToTarget(const F } -UAFEffectTask_EffectAppliedToTarget* UAFEffectTask_EffectAppliedToTarget::ListenEffectAppliedToTarget(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +UAFEffectTask_EffectAppliedToTarget* UAFEffectTask_EffectAppliedToTarget::ListenEffectAppliedToTarget(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) { auto MyObj = NewEffectTask(OwningExtension, TaskName); MyObj->SetExternalTarget(OptionalExternalTarget); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h index 289d195..eec8f41 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h @@ -23,7 +23,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffec FAFEffectEventDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectAppliedToTarget* ListenEffectAppliedToTarget(UObject* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + static UAFEffectTask_EffectAppliedToTarget* ListenEffectAppliedToTarget(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp index a7817ad..c8fefff 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -14,7 +14,7 @@ UAFEffectTask_EffectEvent::UAFEffectTask_EffectEvent(const FObjectInitializer& O } -UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) { auto MyObj = NewEffectTask(OwningExtension, TaskName); MyObj->Tag = Tag; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h index 39fb5c2..fe4518f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -21,7 +21,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask FAFEffectEventDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectEvent* ListenEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + static UAFEffectTask_EffectEvent* ListenEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp index 25dae2c..512551c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp @@ -14,7 +14,7 @@ UAFEffectTask_ExecutedEffectEvent::UAFEffectTask_ExecutedEffectEvent(const FObje } -UAFEffectTask_ExecutedEffectEvent* UAFEffectTask_ExecutedEffectEvent::ListenExecutedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +UAFEffectTask_ExecutedEffectEvent* UAFEffectTask_ExecutedEffectEvent::ListenExecutedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) { auto MyObj = NewEffectTask(OwningExtension, TaskName); MyObj->Tag = Tag; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h index 59e18ff..22f848f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h @@ -22,7 +22,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_ExecutedEffectEvent : public UAFEffectT FAFEffectEventDelegate OnEvent; UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_ExecutedEffectEvent* ListenExecutedEffectEvent(UObject* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + static UAFEffectTask_ExecutedEffectEvent* ListenExecutedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h index dc4b96d..55630d6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h @@ -71,7 +71,7 @@ class ABILITYFRAMEWORK_API UAFTaskBase : public UObject //use template to avoid using interface template - static TaskType* NewTask2(UObject* WorldContextObject, OwnerType* InTaskOwner, FName InstanceName = FName()) + static TaskType* NewTask(UObject* WorldContextObject, OwnerType* InTaskOwner, FName InstanceName = FName()) { TaskType* MyObj = nullptr; @@ -99,36 +99,4 @@ class ABILITYFRAMEWORK_API UAFTaskBase : public UObject return MyObj; } - - template - static T* NewTask(UObject* WorldContextObject, UObject* InTaskOwner, FName InstanceName = FName()) - { - T* MyObj = nullptr; - if (IAFLatentInterface* Interface = Cast(InTaskOwner)) - { - if (!InstanceName.IsNone()) - { - MyObj = Cast(Interface->GetCachedLatentAction(InstanceName)); - if (!MyObj) - { - MyObj = NewObject(WorldContextObject); - - Interface->OnLatentTaskAdded(InstanceName, MyObj); - } - } - else - { - MyObj = NewObject(WorldContextObject); - - Interface->OnLatentTaskAdded(InstanceName, MyObj); - } - if (MyObj->bReplicated) - { - Interface->AddReplicatedTask(MyObj); - } - MyObj->TaskOwner = InTaskOwner; - } - - return MyObj; - } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp index 8199eab..be34c49 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp @@ -15,11 +15,11 @@ UGAWaitAction::UGAWaitAction(const FObjectInitializer& ObjectInitializer) UGAWaitAction* UGAWaitAction::NewGAWaitAction(UObject* InTaskOwner, float Time) { - UGAWaitAction* MyTask = NewTask(InTaskOwner, InTaskOwner); + UGAWaitAction* MyTask = nullptr;/*NewTask(InTaskOwner, InTaskOwner); if (MyTask) { MyTask->Time = Time; - } + }*/ return MyTask; } From e8f7e60a786ffaf6e40f222c6f784599c9cc208c Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 7 Apr 2018 21:39:53 +0200 Subject: [PATCH 110/187] working on ability/effects tasks --- .../Abilities/GAAbilityBase.cpp | 21 +++++++++------ .../Abilities/GAAbilityBase.h | 11 +++----- .../Effects/EffectTasks/AFEffectTask.h | 9 ++++++- .../AFEffectTask_AppliedEffectEvent.cpp | 9 ++++++- .../AFEffectTask_AppliedEffectEvent.h | 2 ++ .../Effects/GAEffectExtension.cpp | 27 +++++++++++++++++++ .../Effects/GAEffectExtension.h | 17 +++++++++--- .../LatentActions/AFTaskBase.cpp | 1 + .../LatentActions/AFTaskBase.h | 2 +- 9 files changed, 78 insertions(+), 21 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp index 3dd65cc..9b5a023 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp @@ -1,18 +1,18 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" +#include "AbilityFramework.h" #include "Tasks/GAAbilityTask.h" -#include "../Effects/GAGameEffect.h" -#include "../GAGlobalTypes.h" -#include "../Effects/GAEffectGlobalTypes.h" -#include "../AFAbilityComponent.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Effects/GAEffectGlobalTypes.h" +#include "AFAbilityComponent.h" #include "AFEffectsComponent.h" #include "GameplayTagContainer.h" #include "Net/UnrealNetwork.h" #include "Animation/AnimMontage.h" -#include "../Effects/GABlueprintLibrary.h" +#include "Effects/GABlueprintLibrary.h" #include "Camera/CameraComponent.h" #include "Kismet/KismetSystemLibrary.h" @@ -921,7 +921,7 @@ void UGAAbilityBase::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* Ta { if (!InstanceName.IsNone()) { - AbilityTasks.Add(InstanceName, Cast(TaskIn)); + AbilityTasks.Add(InstanceName, TaskIn); } }; void UGAAbilityBase::AddReplicatedTask(class UAFTaskBase* TaskIn) @@ -942,4 +942,9 @@ void UGAAbilityBase::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) class UAFTaskBase* UGAAbilityBase::GetCachedLatentAction(FName TaskName) { return AbilityTasks.FindRef(TaskName); -} \ No newline at end of file +} +class UGAAbilityTask* UGAAbilityBase::GetAbilityTask(const FName& InName) +{ + UAFTaskBase* result = AbilityTasks.FindRef(InName); + return Cast(result); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h index 3a76d42..91519ad 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h @@ -111,10 +111,10 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt //possibly map TMap ? UPROPERTY() - TSet ActiveTasks; + TSet ActiveTasks; /* List of tasks, this ability have. */ UPROPERTY() - TMap AbilityTasks; + TMap AbilityTasks; /* Delegate is used to confirm ability execution. @@ -535,17 +535,14 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt virtual class UWorld* GetWorld() const override; - inline void AddAbilityTask(FName InName, class UGAAbilityTask* InTask) + inline void AddAbilityTask(FName InName, class UAFTaskBase* InTask) { if (!AbilityTasks.Contains(InName)) { AbilityTasks.Add(InName, InTask); } } - inline class UGAAbilityTask* GetAbilityTask(const FName& InName) - { - return AbilityTasks.FindRef(InName); - } + class UGAAbilityTask* GetAbilityTask(const FName& InName); UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") bool HaveGameplayTag(AActor* Target, const FGameplayTag& Tag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h index b87e0a8..67a5429 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h @@ -25,6 +25,13 @@ class ABILITYFRAMEWORK_API UAFEffectTask : public UAFTaskBase template static T* NewEffectTask(UGAEffectExtension* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) { - return nullptr; + T* MyObj = nullptr; + UGAEffectExtension* EffectExtension = WorldContextObject; + MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); + + MyObj->Effect = EffectExtension; + MyObj->EffectsComponent = EffectExtension->OwningComponent; + + return MyObj; } }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp index 5309e9e..df86500 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp @@ -49,7 +49,14 @@ void UAFEffectTask_AppliedEffectEvent::GameplayEventCallback(FAFEventData Payloa EndTask(); } } - +void UAFEffectTask_AppliedEffectEvent::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->RemoveAppliedEvent(Tag, MyHandle); + } +} void UAFEffectTask_AppliedEffectEvent::SetExternalTarget(AActor* Actor) { if (Actor) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h index 52e0849..72d7cef 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h @@ -33,6 +33,8 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTa virtual void Activate() override; virtual void GameplayEventCallback(FAFEventData Payload); + + virtual void OnTaskEnded(); FGameplayTag Tag; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp index aefe50f..8bd4fac 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp @@ -40,4 +40,31 @@ UWorld* UGAEffectExtension::GetWorld() const return Context.Target->GetWorld(); return nullptr; +} + +void UGAEffectExtension::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) +{ + if (!InstanceName.IsNone()) + { + Tasks.Add(InstanceName, TaskIn); + } +}; +void UGAEffectExtension::AddReplicatedTask(class UAFTaskBase* TaskIn) +{ + //AbilityComponent->ReplicatedTasks.Add(TaskIn); +} +void UGAEffectExtension::OnLatentTaskRemoved(class UAFTaskBase* TaskIn) +{ +}; + +void UGAEffectExtension::OnLatentTaskActivated(class UAFTaskBase* TaskIn) +{ +}; +void UGAEffectExtension::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) +{ +}; + +class UAFTaskBase* UGAEffectExtension::GetCachedLatentAction(FName TaskName) +{ + return Tasks.FindRef(TaskName); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h index 2762259..342e234 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h @@ -19,7 +19,7 @@ Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). */ UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject +class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatentInterface //this interface is not needed, but NewTask is expting those functions. { GENERATED_BODY() public: @@ -31,10 +31,10 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject class AActor* Avatar; UPROPERTY() - TSet ActiveTasks; + TSet ActiveTasks; UPROPERTY() - TMap Tasks; + TMap Tasks; public: UGAEffectExtension(const FObjectInitializer& ObjectInitializer); @@ -65,4 +65,15 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject void NativeOnEffectRemoved(); virtual UWorld* GetWorld() const override; + + /* IAFLatentInterface */ + virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn); + virtual void AddReplicatedTask(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn); + + virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn); + + virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); + /* IAFLatentInterface */ }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp index 20e39df..7b0fce9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp @@ -72,6 +72,7 @@ void UAFTaskBase::EndTask() TickFunction.UnRegisterTickFunction(); TickFunction.SetTickFunctionEnable(false); } + OnTaskEnded(); Cast(TaskOwner)->OnLatentTaskDeactivated(this); TaskState = EState::Finished; //MarkPendingKill(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h index 55630d6..2db8241 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h @@ -56,7 +56,7 @@ class ABILITYFRAMEWORK_API UAFTaskBase : public UObject virtual void Activate() {}; virtual void EndTask(); virtual void BeginDestroy() override; - + virtual void OnTaskEnded() {}; public: /* Replication */ bool IsNameStableForNetworking() const override; From 34ec8dfa2ea9ddbd949c282f8a93bffc4c213a9b Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 8 Apr 2018 00:05:38 +0200 Subject: [PATCH 111/187] unregistering delegates from effect tasks --- .../EffectTasks/AFEffectTask_AppliedEffectEvent.h | 2 +- .../EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp | 9 ++++++++- .../EffectTasks/AFEffectTask_EffectAppliedToSelf.h | 4 +++- .../EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp | 9 +++++++++ .../EffectTasks/AFEffectTask_EffectAppliedToTarget.h | 4 +++- .../Effects/EffectTasks/AFEffectTask_EffectEvent.cpp | 9 +++++++++ .../Effects/EffectTasks/AFEffectTask_EffectEvent.h | 2 ++ .../EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp | 9 +++++++++ .../EffectTasks/AFEffectTask_ExecutedEffectEvent.h | 2 ++ 9 files changed, 46 insertions(+), 4 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h index 72d7cef..3393112 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h @@ -34,7 +34,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTa virtual void GameplayEventCallback(FAFEventData Payload); - virtual void OnTaskEnded(); + virtual void OnTaskEnded() override; FGameplayTag Tag; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp index c4ab076..584eaed 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp @@ -47,7 +47,14 @@ void UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback(FAFContextHandle C EndTask(); } } - +void UAFEffectTask_EffectAppliedToSelf::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->OnAppliedToSelf.Remove(MyHandle); + } +} void UAFEffectTask_EffectAppliedToSelf::SetExternalTarget(AActor* Actor) { if (Actor) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h index 3d2e8b5..81ac081 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h @@ -36,7 +36,9 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectT virtual void GameplayEventCallback(FAFContextHandle Context , FAFPropertytHandle Property , FAFEffectSpecHandle Spec); - + + virtual void OnTaskEnded() override; + UPROPERTY() UAFEffectsComponent* OptionalExternalTarget; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp index d2fdf90..9c8b566 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp @@ -51,6 +51,15 @@ void UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback(FAFContextHandle } } +void UAFEffectTask_EffectAppliedToTarget::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->OnAppliedToTarget.Remove(MyHandle); + } +} + void UAFEffectTask_EffectAppliedToTarget::SetExternalTarget(AActor* Actor) { if (Actor) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h index eec8f41..665f5a4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h @@ -36,7 +36,9 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffec virtual void GameplayEventCallback(FAFContextHandle Context , FAFPropertytHandle Property , FAFEffectSpecHandle Spec); - + + virtual void OnTaskEnded() override; + UPROPERTY() UAFEffectsComponent* OptionalExternalTarget; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp index c8fefff..c59cda4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -50,6 +50,15 @@ void UAFEffectTask_EffectEvent::GameplayEventCallback(FAFEventData Payload) } } +void UAFEffectTask_EffectEvent::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->RemoveEvent(Tag, MyHandle); + } +} + void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) { if (Actor) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h index fe4518f..52f79d4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -33,6 +33,8 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask virtual void GameplayEventCallback(FAFEventData Payload); + virtual void OnTaskEnded() override; + FGameplayTag Tag; UPROPERTY() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp index 512551c..cdeaaa0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp @@ -50,6 +50,15 @@ void UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback(FAFEventData Paylo } } +void UAFEffectTask_ExecutedEffectEvent::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->RemoveExecuteEvent(Tag, MyHandle); + } +} + void UAFEffectTask_ExecutedEffectEvent::SetExternalTarget(AActor* Actor) { if (Actor) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h index 22f848f..c4253e3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h @@ -34,6 +34,8 @@ class ABILITYFRAMEWORK_API UAFEffectTask_ExecutedEffectEvent : public UAFEffectT virtual void GameplayEventCallback(FAFEventData Payload); + virtual void OnTaskEnded() override; + FGameplayTag Tag; UPROPERTY() From d9146632758e8ef86203cb1507856efa63603d3b Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 8 Apr 2018 20:27:11 +0200 Subject: [PATCH 112/187] refactored AbilityFramework to use TSoftClassPtr instead of GameplayTags for Ability loading, Map indexes and network, using FGameplayTag was redunant and required to hand maintain seprate static tag list for abilities, while abilities assets are inhenerntly static data --- Config/DefaultGameplayTags.ini | 3 + .../AbilityFramework/AFAbilityComponent.cpp | 217 +++++++++--------- .../AbilityFramework/AFAbilityComponent.h | 140 ++++++----- .../AbilityFramework/AFEffectsComponent.cpp | 2 +- .../AbilityFramework/AFEffectsComponent.h | 1 + .../AbilityFramework/Effects/GAGameEffect.h | 38 +++ .../Source/AbilityFramework/GAGlobalTypes.h | 6 - .../AFAbilityInfinitePeriodSpecDetails.cpp | 12 +- .../AFAbilityPeriodSpecDetails.cpp | 12 +- .../AFDAbilityGiveTrigger.cpp | 6 +- .../AFDAbilityGiveTrigger.h | 6 +- .../AMAbilityManagerComponent.cpp | 21 +- .../AMAbilityManagerComponent.h | 25 +- Source/ActionRPGGame/ARPlayerController.cpp | 22 +- Source/ActionRPGGame/ARPlayerController.h | 12 +- .../Abilities/ARAbilityManagerComponent.cpp | 6 +- .../Abilities/ARAbilityManagerComponent.h | 4 +- .../Abilities/ARAbilityListSlotDragWidget.cpp | 30 +-- .../Abilities/ARAbilityListSlotDragWidget.h | 6 +- .../UI/Abilities/ARAbilityListWidget.cpp | 2 +- .../UI/Abilities/ARAbilityListWidget.h | 2 +- .../UI/Weapons/ARWeaponListSlotDragWidget.cpp | 30 +-- .../UI/Weapons/ARWeaponListSlotDragWidget.h | 2 +- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 2 +- .../Weapons/ARMagazineUpgradeEffect.cpp | 7 + .../Weapons/ARMagazineUpgradeEffect.h | 20 ++ .../Weapons/ARWeaponAbilityBase.h | 12 + .../Weapons/ARWeaponManagerComponent.cpp | 28 +-- .../Weapons/ARWeaponManagerComponent.h | 10 +- 29 files changed, 371 insertions(+), 313 deletions(-) create mode 100644 Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.h diff --git a/Config/DefaultGameplayTags.ini b/Config/DefaultGameplayTags.ini index 900a43d..17e90cc 100644 --- a/Config/DefaultGameplayTags.ini +++ b/Config/DefaultGameplayTags.ini @@ -29,6 +29,7 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Ability.Shotgun",DevComment="") +GameplayTagList=(Tag="Ability.UI.NextWeapon",DevComment="") +GameplayTagList=(Tag="Ability.UI.PreviousWeapon",DevComment="") ++GameplayTagList=(Tag="Action.Shooting",DevComment="") +GameplayTagList=(Tag="AI.HaveAxe",DevComment="") +GameplayTagList=(Tag="AI.HaveOre",DevComment="") +GameplayTagList=(Tag="AI.HavePick",DevComment="") @@ -41,6 +42,7 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Effect.InstancedDuration",DevComment="") +GameplayTagList=(Tag="EffectEvent.Expired.InstancedDuration",DevComment="") +GameplayTagList=(Tag="Event.Executed.Damage.Fire",DevComment="") ++GameplayTagList=(Tag="Event.Executed.Shoot.AssaultRifle",DevComment="") +GameplayTagList=(Tag="Fire",DevComment="") +GameplayTagList=(Tag="Input.Ability01.Activate",DevComment="") +GameplayTagList=(Tag="Input.Ability02",DevComment="") @@ -54,5 +56,6 @@ NetIndexFirstBitSegment=16 +GameplayTagList=(Tag="Input.UI.SetAbilityGroup02",DevComment="") +GameplayTagList=(Tag="Input.UI.WeaponNext",DevComment="") +GameplayTagList=(Tag="Input.UI.WeaponPrevious",DevComment="") ++GameplayTagList=(Tag="Item.Weapon.AssaultRifle",DevComment="") diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 557e7ac..917c7d9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -210,10 +210,6 @@ void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContain } } -const bool FGASAbilityItem::operator==(const FGameplayTag& AbilityTag) const -{ - return Ability->AbilityTag == AbilityTag; -} void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer) { if (InArraySerializer.AbilitiesComp.IsValid()) @@ -222,10 +218,9 @@ void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InA //remove attributes //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = nullptr; - FGameplayTag AbilityTag = Ability->AbilityTag; - InArraySerializerC.RemoveAbilityFromAction(AbilityTag); - InArraySerializerC.AbilitiesInputs.Remove(AbilityTag); - InArraySerializerC.TagToAbility.Remove(AbilityTag); + InArraySerializerC.RemoveAbilityFromAction(AbilityClass); + InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); + InArraySerializerC.TagToAbility.Remove(AbilityClass); } } void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) @@ -244,11 +239,14 @@ void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArr } Ability->InitAbility(); Ability->Attributes = nullptr; + + //TODO - CHANGE ATTRIBUTE HANDLING UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = attr; - InArraySerializerC.AbilitiesInputs.Add(Ability->AbilityTag, Ability); //.Add(Ability->AbilityTag, Ability); - InArraySerializerC.TagToAbility.Add(Ability->AbilityTag, Ability); - InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(Ability->AbilityTag); + + InArraySerializerC.AbilitiesInputs.Add(AbilityClass, Ability); //.Add(Ability->AbilityTag, Ability); + InArraySerializerC.TagToAbility.Add(AbilityClass, Ability); + InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(AbilityClass); } } void FGASAbilityItem::PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer) @@ -266,8 +264,8 @@ void FGASAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, boo BlockedInput.Add(InActionName, bBlock); } } -UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn, - AActor* InAvatar) +UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn + , TSoftClassPtr InClassPtr) { if (AbilityIn && AbilitiesComp.IsValid()) { @@ -280,23 +278,22 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOfPOwner = POwner; ability->PCOwner = Cast(POwner->Controller); ability->OwnerCamera = nullptr; - ability->AvatarActor = InAvatar; } ability->InitAbility(); FGameplayTag Tag = ability->AbilityTag; - AbilitiesInputs.Add(Tag, ability); - FGASAbilityItem AbilityItem; + AbilitiesInputs.Add(InClassPtr, ability); + FGASAbilityItem AbilityItem(ability, InClassPtr); MarkItemDirty(AbilityItem); AbilityItem.Ability = ability; AbilitiesItems.Add(AbilityItem); - TagToAbility.Add(Tag, ability); + TagToAbility.Add(InClassPtr, ability); MarkArrayDirty(); if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) { - AbilitiesComp->NotifyOnAbilityReady(ability->AbilityTag); + AbilitiesComp->NotifyOnAbilityReady(InClassPtr); } /* if (ActionName.IsValid()) { @@ -307,7 +304,7 @@ UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf& AbilityIn) { int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); @@ -327,10 +324,10 @@ void FGASAbilityContainer::RemoveAbility(const FGameplayTag& AbilityIn) AbilitiesItems.RemoveAt(Index); MarkArrayDirty(); } -FGameplayTag FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) +TSoftClassPtr FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) { - FGameplayTag Ability; - FGameplayTag* AbilityTag = ActionToAbility.Find(InInputTag); + TSoftClassPtr Ability; + TSoftClassPtr* AbilityTag = ActionToAbility.Find(InInputTag); if (AbilityTag) { Ability = *AbilityTag; @@ -338,7 +335,7 @@ FGameplayTag FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& In return Ability; } -void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag) +void FGASAbilityContainer::RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr) { /*TArray OutActions; AbilityToAction.RemoveAndCopyValue(InAbilityTag, OutActions); @@ -350,13 +347,13 @@ void FGASAbilityContainer::RemoveAbilityFromAction(const FGameplayTag& InAbility //AbilitiesInputs.Remove(InAbilityTag); } -void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag) +void FGASAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) { for (const FGameplayTag& InputTag : InInputTag) { if (ActionToAbility.Contains(InputTag)) { - FGameplayTag AbilityTag = ActionToAbility.FindRef(InputTag); + TSoftClassPtr AbilityTag = ActionToAbility.FindRef(InputTag); UE_LOG(AbilityFramework, Log, TEXT("FGASAbilityContainer: Input %s is already abount to Ability %s"), *InputTag.ToString(), *AbilityTag.ToString() @@ -365,16 +362,15 @@ void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, //return; } - FGameplayTag& AbilityTag = ActionToAbility.FindOrAdd(InputTag); - AbilityTag = InAbilityTag; - - TArray& ActionTag = AbilityToAction.FindOrAdd(InAbilityTag); + TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); + AbilityClassPtr = InAbiltyPtr; + TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); ActionTag.Add(InputTag); } if (!AbilitiesComp.IsValid()) return; - UGAAbilityBase* Ability = TagToAbility.FindRef(InAbilityTag); + UGAAbilityBase* Ability = TagToAbility.FindRef(InAbiltyPtr); if (Ability) { Ability->OnAbilityInputReady(); @@ -382,13 +378,13 @@ void FGASAbilityContainer::SetAbilityToAction(const FGameplayTag& InAbilityTag, if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) { - AbilitiesComp->ClientNotifyAbilityInputReady(InAbilityTag); + AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); } } -UGAAbilityBase* FGASAbilityContainer::GetAbility(FGameplayTag TagIn) +UGAAbilityBase* FGASAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) { - UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(TagIn); + UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); return retAbility; } void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) @@ -397,8 +393,8 @@ void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAF { return; } - FGameplayTag abilityTag = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); + TSoftClassPtr AbiltyPtr = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(AbiltyPtr); if (ability) { if (ability->IsWaitingForConfirm()) @@ -415,7 +411,7 @@ void FGASAbilityContainer::HandleInputReleased(FGameplayTag ActionName) { return; } - FGameplayTag abilityTag = ActionToAbility.FindRef(ActionName); + TSoftClassPtr abilityTag = ActionToAbility.FindRef(ActionName); UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); if (ability) { @@ -423,7 +419,7 @@ void FGASAbilityContainer::HandleInputReleased(FGameplayTag ActionName) } } -void FGASAbilityContainer::TriggerAbylityByTag(FGameplayTag InTag) +void FGASAbilityContainer::TriggerAbylityByTag(TSoftClassPtr InTag) { UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); if (ability) @@ -509,18 +505,18 @@ void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, F } SetBlockedInput(ActionName, false); } -void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag +void UAFAbilityComponent::SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag , const FAFOnAbilityReady& InputDelegate) { for (const FGameplayTag& Tag : InInputTag) { if (AbilityContainer.IsAbilityBoundToAction(Tag).IsValid()) { - RemoveAbilityFromAction(InAbilityTag, FGameplayTag()); + RemoveAbilityFromAction(InAbilityPtr, FGameplayTag()); } } - AbilityContainer.SetAbilityToAction(InAbilityTag, InInputTag); + AbilityContainer.SetAbilityToAction(InAbilityPtr, InInputTag); ENetRole role = GetOwnerRole(); if (GetOwner()->GetNetMode() == ENetMode::NM_Client @@ -528,41 +524,41 @@ void UAFAbilityComponent::SetAbilityToAction(const FGameplayTag& InAbilityTag, c { if (InputDelegate.IsBound()) { - AddOnAbilityInputReadyDelegate(InAbilityTag, InputDelegate); + AddOnAbilityInputReadyDelegate(InAbilityPtr, InputDelegate); } - ServerSetAbilityToAction(InAbilityTag, InInputTag); + ServerSetAbilityToAction(InAbilityPtr, InInputTag); } } -FGameplayTag UAFAbilityComponent::IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag) +TSoftClassPtr UAFAbilityComponent::IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) { for (const FGameplayTag& Tag : InInputTag) { return AbilityContainer.IsAbilityBoundToAction(Tag); break; } - return FGameplayTag(); + return TSoftClassPtr(); } -void UAFAbilityComponent::RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag) +void UAFAbilityComponent::RemoveAbilityFromAction(const TSoftClassPtr& InAbilityPtr, const FGameplayTag& InInputTag) { - AbilityContainer.RemoveAbilityFromAction(InAbilityTag); + AbilityContainer.RemoveAbilityFromAction(InAbilityPtr); } -void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const TArray& InInputTag) +void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) { if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) { - SetAbilityToAction(InAbilityTag, InInputTag, FAFOnAbilityReady()); + SetAbilityToAction(InAbilityPtr, InInputTag, FAFOnAbilityReady()); } } -bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const TArray& InInputTag) +bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) { return true; } -void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag) +void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr) { - NotifyOnAbilityInputReady(AbilityTag); - UGAAbilityBase* Ability = AbilityContainer.TagToAbility.FindRef(AbilityTag); + NotifyOnAbilityInputReady(InAbilityPtr); + UGAAbilityBase* Ability = AbilityContainer.TagToAbility.FindRef(InAbilityPtr); if (Ability) { Ability->OnAbilityInputReady(); @@ -666,88 +662,64 @@ bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag Action { return true; } -void UAFAbilityComponent::BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, TArray InInputTag) + +void UAFAbilityComponent::BP_AddAbility(TSoftClassPtr InAbility, + TArray InInputTag) { - NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); + NativeAddAbility(InAbility, InInputTag); } -void UAFAbilityComponent::NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag) + +void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbility, + const TArray& InInputTag) { - FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); + //FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); - if (AlreadyBound.IsValid()) + ServerNativeAddAbility(InAbility, InInputTag); + /*if (AlreadyBound.IsValid()) { for (const FGameplayTag& Input : InInputTag) { AbilityContainer.RemoveAbilityFromAction(AlreadyBound); } - } + }*/ } else { - if (AlreadyBound.IsValid()) + /*if (AlreadyBound.IsValid()) { AbilityContainer.RemoveAbilityFromAction(AlreadyBound); - } + }*/ if (UAssetManager* Manager = UAssetManager::GetIfValid()) { FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - - TArray AssetData; - FARFilter Filter; - Filter.TagsAndValues.Add("AbilityTagSearch", InAbilityTag.ToString()); - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + FStreamableManager& StreamManager = UAssetManager::GetStreamableManager(); { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbilityTag, PrimaryAssetId, InAvatar); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbility); - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); + StreamManager.RequestAsyncLoad(InAbility.ToSoftObjectPath() + , del); } } } - -} - -void UAFAbilityComponent::ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag) -{ - NativeAddAbilityFromTag(InAbilityTag, InAvatar, InInputTag); } -bool UAFAbilityComponent::ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag) -{ - return true; -} -void UAFAbilityComponent::BP_RemoveAbility(FGameplayTag TagIn) -{ -} -void UAFAbilityComponent::NativeRemoveAbility(const FGameplayTag& InAbilityTag) -{ - AbilityContainer.RemoveAbility(InAbilityTag); -} -void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(FGameplayTag InAbilityTag) +void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const TSoftClassPtr& InAbility, + const TArray& InInputTag) { - NativeRemoveAbility(InAbilityTag); + NativeAddAbility(InAbility, InInputTag); } -bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(FGameplayTag InAbilityTag) +bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const TSoftClassPtr& InAbility, + const TArray& InInputTag) { return true; } -void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, - FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar) +void UAFAbilityComponent::OnFinishedLoad(TSoftClassPtr InAbility) { - if (AbilityContainer.AbilityExists(InAbilityTag)) + if (AbilityContainer.AbilityExists(InAbility)) { return; } @@ -755,33 +727,50 @@ void UAFAbilityComponent::OnFinishedLoad(FGameplayTag InAbilityTag, { return; } - if (UAssetManager* Manager = UAssetManager::GetIfValid()) + + + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + + TSubclassOf cls = InAbility.Get(); + if (cls) { - UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); - TSubclassOf cls = Cast(loaded); - if (cls) - { - InstanceAbility(cls, InAvatar); - } + InstanceAbility(cls, InAbility); + } - { - Manager->UnloadPrimaryAsset(InPrimaryAssetId); - } + { + Manager.Unload(InAbility.ToSoftObjectPath()); } } +void UAFAbilityComponent::BP_RemoveAbility(TSoftClassPtr TagIn) +{ + +} +void UAFAbilityComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag) +{ + AbilityContainer.RemoveAbility(InAbilityTag); +} +void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const TSoftClassPtr& InAbilityTag) +{ + NativeRemoveAbility(InAbilityTag); +} + +bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const TSoftClassPtr& InAbilityTag) +{ + return true; +} -UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(FGameplayTag TagIn) +UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(TSoftClassPtr TagIn) { UGAAbilityBase* retVal = AbilityContainer.GetAbility(TagIn); return retVal; } -UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass, - AActor* InAvatar) +UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass + , TSoftClassPtr InClassPtr) { if (AbilityClass) { - UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InAvatar); + UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InClassPtr); AbilityContainer.MarkArrayDirty(); return ability; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 7bf4d6c..c37f7b6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -113,12 +113,26 @@ struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem public: UPROPERTY() UGAAbilityBase* Ability; + UPROPERTY() + TSoftClassPtr AbilityClass; + + FGASAbilityItem() + {}; + + FGASAbilityItem(UGAAbilityBase* InAbility, TSoftClassPtr InAbilityClass) + : Ability(InAbility) + , AbilityClass(InAbilityClass) + {} void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); - const bool operator==(const FGameplayTag& AbilityTag) const; + const bool operator==(const TSoftClassPtr& OtherAbility) const + { + return AbilityClass == OtherAbility; + } + const bool operator==(UGAAbilityBase* OtherAbility) const { return Ability == OtherAbility; @@ -140,35 +154,41 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer TWeakObjectPtr AbilitiesComp; TMap BlockedInput; + TMap, FGameplayTag> AbilityToInput; //Custom binding, for server side validation. - //ActionInput, AbilityTag - TMap ActionToAbility; + + //ActionInput, AbilityClassPtr + TMap> ActionToAbility; + //AbilityTag, ActionInput - TMap> AbilityToAction; + TMap, TArray> AbilityToAction; + //abilityTag, Ability Ptr - TMap AbilitiesInputs; + TMap, UGAAbilityBase*> AbilitiesInputs; - TMap TagToAbility; + TMap, UGAAbilityBase*> TagToAbility; void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, - AActor* InAvatar); - void RemoveAbility(const FGameplayTag& AbilityIn); + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn + , TSoftClassPtr InClassPtr); + + void RemoveAbility(const TSoftClassPtr& AbilityIn); - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InInputTag); - void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag); + void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); + TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); + void RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr); - UGAAbilityBase* GetAbility(FGameplayTag TagIn); + UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); void HandleInputReleased(FGameplayTag ActionName); - void TriggerAbylityByTag(FGameplayTag InTag); - bool AbilityExists(const FGameplayTag& AbilityTag) const + void TriggerAbylityByTag(TSoftClassPtr InTag); + + bool AbilityExists(TSoftClassPtr InAbiltyPtr) const { - return AbilitiesInputs.Contains(AbilityTag); + return AbilityToInput.Contains(InAbiltyPtr); } bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { @@ -255,7 +275,7 @@ struct ABILITYFRAMEWORK_API FAFAbilityActionSet GENERATED_BODY() public: UPROPERTY() - FGameplayTag AbilityTag; + TSoftClassPtr AbilityTag; UPROPERTY() TArray AbilityInputs; }; @@ -457,37 +477,37 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public bool bIsAnyAbilityActive; //AbilityTag, Delegate - TMap OnAbilityReadyMap; + TMap, FAFOnAbilityReady> OnAbilityReadyMap; - void AddOnAbilityReadyDelegate(const FGameplayTag& InAbilityTag, FAFOnAbilityReady& InDelegate) + void AddOnAbilityReadyDelegate(const TSoftClassPtr& InAbilityPtr, FAFOnAbilityReady& InDelegate) { if(InDelegate.IsBound()) - OnAbilityReadyMap.Add(InAbilityTag, InDelegate); + OnAbilityReadyMap.Add(InAbilityPtr, InDelegate); } - void NotifyOnAbilityReady(const FGameplayTag& InAbilityTag) + void NotifyOnAbilityReady(const TSoftClassPtr& InAbilityPtr) { - if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityTag)) + if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityPtr)) { Ready->ExecuteIfBound(); - OnAbilityReadyMap.Remove(InAbilityTag); + OnAbilityReadyMap.Remove(InAbilityPtr); } } - TMap OnAbilityInputReadyMap; + TMap, FAFOnAbilityReady> OnAbilityInputReadyMap; - void AddOnAbilityInputReadyDelegate(const FGameplayTag& InAbilityTag, const FAFOnAbilityReady& InDelegate) + void AddOnAbilityInputReadyDelegate(const TSoftClassPtr& InAbilityPtr, const FAFOnAbilityReady& InDelegate) { if(InDelegate.IsBound()) - OnAbilityInputReadyMap.Add(InAbilityTag, InDelegate); + OnAbilityInputReadyMap.Add(InAbilityPtr, InDelegate); } - void NotifyOnAbilityInputReady(const FGameplayTag& InAbilityTag) + void NotifyOnAbilityInputReady(const TSoftClassPtr& InAbilityPtr) { - if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityTag)) + if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityPtr)) { Ready->ExecuteIfBound(); - OnAbilityInputReadyMap.Remove(InAbilityTag); + OnAbilityInputReadyMap.Remove(InAbilityPtr); } } @@ -566,8 +586,9 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public } TMap BlockedInput; - //TSharedPtr AbilityLoadedHandle; - void OnFinishedLoad(FGameplayTag InAbilityTag, FPrimaryAssetId InPrimaryAssetId, AActor* InAvatar); + + + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); void BindInputs(class UInputComponent* InputComponent); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") @@ -576,20 +597,20 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public //need to be called on both client and server. //Change InInputTag To Array, clear previous binds on the same tag. - void SetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); + void SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); - FGameplayTag IsAbilityBoundToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - void RemoveAbilityFromAction(const FGameplayTag& InAbilityTag, const FGameplayTag& InInputTag); + TSoftClassPtr IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); + void RemoveAbilityFromAction(const TSoftClassPtr& InAbilityPtr, const FGameplayTag& InInputTag); protected: UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilityToAction(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - void ServerSetAbilityToAction_Implementation(const FGameplayTag& InAbilityTag, const TArray& InInputTag); - bool ServerSetAbilityToAction_Validate(const FGameplayTag& InAbilityTag, const TArray& InInputTag); + void ServerSetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); + void ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); + bool ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); public: /* Called when ability action has been binded on server. */ UFUNCTION(Client, Reliable) - void ClientNotifyAbilityInputReady(FGameplayTag AbilityTag); - void ClientNotifyAbilityInputReady_Implementation(FGameplayTag AbilityTag); + void ClientNotifyAbilityInputReady(const TSoftClassPtr& InAbilityPtr); + void ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr); void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); @@ -627,39 +648,42 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public Does not check if component can or can't have given ability. So it must be checked before this function is called. */ - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Add Ability From Tag"), Category = "AbilityFramework|Abilities") - void BP_AddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, TArray InInputTag); - void NativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); + UFUNCTION(BlueprintCallable, meta=(DisplayName = "Add Ability"), Category = "AbilityFramework|Ability Component") + void BP_AddAbility(TSoftClassPtr InAbility, + TArray InInputTag); + + void NativeAddAbility(TSoftClassPtr InAbility, + const TArray& InInputTag); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeAddAbilityFromTag(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); + void ServerNativeAddAbility(const TSoftClassPtr& InAbility, + const TArray& InInputTag); + + void ServerNativeAddAbility_Implementation(const TSoftClassPtr& InAbility, + const TArray& InInputTag); - void ServerNativeAddAbilityFromTag_Implementation(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); + bool ServerNativeAddAbility_Validate(const TSoftClassPtr& InAbility, + const TArray& InInputTag); - bool ServerNativeAddAbilityFromTag_Validate(FGameplayTag InAbilityTag, - AActor* InAvatar, const TArray& InInputTag); + void OnFinishedLoad(TSoftClassPtr InAbility); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") - void BP_RemoveAbility(FGameplayTag TagIn); + void BP_RemoveAbility(TSoftClassPtr TagIn); - void NativeRemoveAbility(const FGameplayTag& InAbilityTag); + void NativeRemoveAbility(TSoftClassPtr InAbilityTag); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeRemoveAbility(const FGameplayTag& InAbilityTag); + void ServerNativeRemoveAbility(const TSoftClassPtr& InAbilityTag); - void ServerNativeRemoveAbility_Implementation(FGameplayTag InAbilityTag); + void ServerNativeRemoveAbility_Implementation(const TSoftClassPtr& InAbilityTag); - bool ServerNativeRemoveAbility_Validate(FGameplayTag InAbilityTag); + bool ServerNativeRemoveAbility_Validate(const TSoftClassPtr& InAbilityTag); //TODO: Make it procted UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") - UGAAbilityBase* BP_GetAbilityByTag(FGameplayTag TagIn); + UGAAbilityBase* BP_GetAbilityByTag(TSoftClassPtr TagIn); bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; @@ -668,8 +692,8 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); protected: void InitializeInstancedAbilities(); - UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass, - AActor* InAvatar); + UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass + , TSoftClassPtr InClassPtr); public: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp index a76739d..87b6110 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp @@ -146,7 +146,7 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn //apply execution events: const FGameplayTagContainer& ExecuteEventTags = Property.GetSpec()->ExecuteEventTags; - FAFEventData Data; + FAFEventData Data(Params); for (const FGameplayTag& Tag : ExecuteEventTags) { TriggerExecuteEvent(Tag, Data); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h index 76574f2..0a5c7b1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h @@ -56,6 +56,7 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent public: FAFApplicationDelegate OnAppliedToTarget; FAFApplicationDelegate OnAppliedToSelf; + FAFApplicationDelegate OnEffectExecuted; public: // Sets default values for this component's properties UAFEffectsComponent(const FObjectInitializer& ObjectInitializer); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 98cbcd6..31d62f3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -123,6 +123,12 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject { GENERATED_BODY() public: + /* + Replicate effect back to clients ? + */ + UPROPERTY(EditAnywhere, Category = "Network") + bool bReplicate; + /* Individual Tag descrbing effect type. ie. Condition.Burning @@ -1026,6 +1032,38 @@ struct FAFEffectParams }; +USTRUCT(BlueprintType) +struct FAFEventData +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly) + FAFContextHandle ContextHandle; + UPROPERTY(BlueprintReadOnly) + FAFEffectSpecHandle SpecHandle; + UPROPERTY(BlueprintReadOnly) + FAFPropertytHandle PropertyHandle; + + FAFEventData() + {}; + + FAFEventData(FAFContextHandle InContextHandle + , FAFEffectSpecHandle InSpecHandle + , FAFPropertytHandle InPropertyHandle + ) + : ContextHandle(InContextHandle) + , SpecHandle(InSpecHandle) + , PropertyHandle(InPropertyHandle) + {}; + + FAFEventData(const FAFEffectParams& EffectParams) + : ContextHandle(EffectParams.Context) + , SpecHandle(EffectParams.EffectSpec) + , PropertyHandle(EffectParams.Property) + {}; + +}; + struct FAFStatics { static float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h index da340d9..015aabd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h @@ -153,12 +153,6 @@ enum class EGAEffectAggregation : uint8 AggregateByTarget }; -USTRUCT() -struct FAFEventData -{ - GENERATED_USTRUCT_BODY() -}; - USTRUCT() struct FAFAtributeRowData : public FTableRowBase { diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp index de096d4..38f91d2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp @@ -42,17 +42,17 @@ void FAFAbilityInfinitePeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp index 9119b69..8fe5b22 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp @@ -42,17 +42,17 @@ void FAFAbilityPeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailL FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp index dcf743c..705f984 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp @@ -66,7 +66,7 @@ void AAFDAbilityGiveTrigger::BeginOverlap(UPrimitiveComponent* OverlappedCompone } if(AbilityManager) - AbilityManager->BP_EquipAbility(AbilityConfig.AbilityTag, AbilityConfig.Group, AbilityConfig.Slot); + AbilityManager->NativeEquipAbility(AbilityConfig.AbilityTag, AbilityConfig.Group, AbilityConfig.Slot); } } @@ -84,7 +84,7 @@ void AAFDAbilityGiveTrigger::EndOverlap(UPrimitiveComponent* OverlappedComponent return; } -void AAFDAbilityGiveTrigger::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput) +void AAFDAbilityGiveTrigger::OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) { UGAAbilityBase* Ability = Cast(CurrentComponent->BP_GetAbilityByTag(InAbilityTag)); if (GetOwner()->GetNetMode() == ENetMode::NM_Client) @@ -101,7 +101,7 @@ void AAFDAbilityGiveTrigger::OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput) +void AAFDAbilityGiveTrigger::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) { } \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h index ad8794f..2df3625 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h @@ -21,7 +21,7 @@ struct FAFDAbilityConfig UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") EAMSlot Slot; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - FGameplayTag AbilityTag; + TSoftClassPtr AbilityTag; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") TArray InputTag; }; @@ -74,10 +74,10 @@ class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor void EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex); UFUNCTION() - void OnAbilityReady(FGameplayTag InAbilityTag, TArray InAbilityInput); + void OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); UFUNCTION() - void OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput); + void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); }; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index d1b580e..96d4002 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -74,24 +74,21 @@ void UAMAbilityManagerComponent::SetInputTag(EAMGroup InGroup, EAMSlot InSlot, T { } -void UAMAbilityManagerComponent::BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) -{ - NativeEquipAbility(InAbilityTag, InGroup, InSlot, nullptr, bBindInput); -} -FGameplayTag UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) + +TSoftClassPtr UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) { if (AbilityTagsSet.IsValidIndex(AMEnumToInt(InGroup)) && AbilityTagsSet[AMEnumToInt(InGroup)].IsValidIndex(AMEnumToInt(InSlot))) { return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; } - return FGameplayTag(); + return TSoftClassPtr(); } -void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, FGameplayTag InAbilityTag) +void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag) { AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; } -void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar, bool bBindInput) +void UAMAbilityManagerComponent::NativeEquipAbility(const TSoftClassPtr& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar, bool bBindInput) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -117,9 +114,9 @@ void UAMAbilityManagerComponent::NativeEquipAbility(const FGameplayTag& InAbilit AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); } - AbilityComp->NativeAddAbilityFromTag(InAbilityTag, InAvatar, IAbilityInput);// , /*Input*/ ShootInput); + AbilityComp->NativeAddAbility(InAbilityTag, IAbilityInput);// , /*Input*/ ShootInput); } -void UAMAbilityManagerComponent::OnAbilityReadyInternal(FGameplayTag InAbilityTag, TArray InAbilityInput, +void UAMAbilityManagerComponent::OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) { APlayerController* MyPC = Cast(GetOwner()); @@ -154,7 +151,7 @@ void UAMAbilityManagerComponent::OnAbilityReadyInternal(FGameplayTag InAbilityTa OnAbilityReady(InAbilityTag, InAbilityInput, InGroup, InSlot); } -void UAMAbilityManagerComponent::OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput, +void UAMAbilityManagerComponent::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) { APlayerController* MyPC = Cast(GetOwner()); @@ -398,7 +395,7 @@ bool UAMAbilityManagerComponent::IsClient() const return false; } -void UAMAbilityManagerComponent::BindOnAbilityReadDelegate(FGameplayTag InAbilityTag, TArray InAbilityInput, +void UAMAbilityManagerComponent::BindOnAbilityReadDelegate(TSoftClassPtr InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) { diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index fe930f3..8a342e5 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -90,10 +90,10 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent EAMGroup ActiveGroup; - TArray> AbilityTagsSet; + TArray>> AbilityTagsSet; TArray>> AbilitySet; TArray> ValidGroups; - TMap AbilityReadyEvents; + TMap, FSimpleDelegate> AbilityReadyEvents; DECLARE_DELEGATE_TwoParams(FGroupConfirmDelegate, int32, bool) @@ -115,27 +115,24 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); - FGameplayTag GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); - void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, FGameplayTag InAbilityTag); + TSoftClassPtr GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); + void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag); TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Equip Ability"), Category = "Ability Manager") - void BP_EquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); - - void NativeEquipAbility(const FGameplayTag& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); + void NativeEquipAbility(const TSoftClassPtr& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); protected: - virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, + virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) {}; private: UFUNCTION() - void OnAbilityReadyInternal(FGameplayTag InAbilityTag, TArray InAbilityInput, + void OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); public: UFUNCTION() - void OnAbilityInputReady(FGameplayTag InAbilityTag, TArray InAbilityInput, + void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); UFUNCTION(BlueprintCallable) @@ -175,7 +172,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent void ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess); - void AddOnAbilityReadyEvent(const FGameplayTag& Ability, const FSimpleDelegate& Delegate) + void AddOnAbilityReadyEvent(const TSoftClassPtr& Ability, const FSimpleDelegate& Delegate) { if (!AbilityReadyEvents.Contains(Ability)) { @@ -183,7 +180,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent } } - void ExecuteAbilityReadyEvent(const FGameplayTag& Ability) + void ExecuteAbilityReadyEvent(const TSoftClassPtr& Ability) { if (FSimpleDelegate* Event = AbilityReadyEvents.Find(Ability)) { @@ -193,7 +190,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent } protected: class UAFAbilityComponent* GetAbilityComponent(); - void BindOnAbilityReadDelegate(FGameplayTag InAbilityTag, TArray InAbilityInput, + void BindOnAbilityReadDelegate(TSoftClassPtr, TArray InAbilityInput, EAMGroup InGroup, EAMSlot InSlot); bool IsServerOrStandalone() const; bool IsClientOrStandalone() const; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 31b769c..7df1685 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -53,46 +53,46 @@ void AARPlayerController::SetPawn(APawn* InPawn) bInputBount = true; } //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. - if (AbilitytNextWeapon.IsValid()) + if (!AbilitytNextWeapon.IsNull()) { FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); TArray NextWeap; NextWeap.Add(InputNextWeapon); - AbilityComp->NativeAddAbilityFromTag(AbilitytNextWeapon, nullptr, NextWeap); + AbilityComp->NativeAddAbility(AbilitytNextWeapon, NextWeap); } - if (AbilitytPreviousWeapon.IsValid()) + if (!AbilitytPreviousWeapon.IsNull()) { FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); TArray PrevWeap; PrevWeap.Add(InputPreviousWeapon); - AbilityComp->NativeAddAbilityFromTag(AbilitytPreviousWeapon, nullptr, PrevWeap); + AbilityComp->NativeAddAbility(AbilitytPreviousWeapon, PrevWeap); } - if (AbilitytHolstersWeapon.IsValid()) + if (!AbilitytHolstersWeapon.IsNull()) { FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytHolstersWeapon, InputHolsterWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytHolstersWeapon, del3); TArray HolsterInput; HolsterInput.Add(InputHolsterWeapon); - AbilityComp->NativeAddAbilityFromTag(AbilitytHolstersWeapon, nullptr, HolsterInput); + AbilityComp->NativeAddAbility(AbilitytHolstersWeapon, HolsterInput); } - if (SetAbilityGroup01.IsValid()) + if (!SetAbilityGroup01.IsNull()) { FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, SetAbilityGroup01, InputSetAbilityGroup01); AbilityComp->AddOnAbilityReadyDelegate(SetAbilityGroup01, del3); TArray HolsterInput; HolsterInput.Add(InputSetAbilityGroup01); - AbilityComp->NativeAddAbilityFromTag(SetAbilityGroup01, nullptr, HolsterInput); + AbilityComp->NativeAddAbility(SetAbilityGroup01, HolsterInput); } - if (SetAbilityGroup02.IsValid()) + if (!SetAbilityGroup02.IsNull()) { FAFOnAbilityReady del3 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, SetAbilityGroup02, InputSetAbilityGroup02); AbilityComp->AddOnAbilityReadyDelegate(SetAbilityGroup02, del3); TArray HolsterInput; HolsterInput.Add(InputSetAbilityGroup02); - AbilityComp->NativeAddAbilityFromTag(SetAbilityGroup02, nullptr, HolsterInput); + AbilityComp->NativeAddAbility(SetAbilityGroup02, HolsterInput); } } @@ -118,7 +118,7 @@ void AARPlayerController::InputShowHideInventory() { WeaponManager->ShowHideAbilityManager(); } -void AARPlayerController::OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag) +void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag) { IAFAbilityInterface* ABInt = Cast(GetPawn()); if (!ABInt) diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index c7ae2cb..5efb048 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -26,27 +26,27 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputNextWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") - FGameplayTag AbilitytNextWeapon; + TSoftClassPtr AbilitytNextWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputPreviousWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") - FGameplayTag AbilitytPreviousWeapon; + TSoftClassPtr AbilitytPreviousWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputHolsterWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") - FGameplayTag AbilitytHolstersWeapon; + TSoftClassPtr AbilitytHolstersWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputSetAbilityGroup01; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") - FGameplayTag SetAbilityGroup01; + TSoftClassPtr SetAbilityGroup01; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputSetAbilityGroup02; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") - FGameplayTag SetAbilityGroup02; + TSoftClassPtr SetAbilityGroup02; bool bInputBount; public: @@ -57,7 +57,7 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController void InputSwitchAbilitySet(); void InputShowHideAbilityManager(); void InputShowHideInventory(); - void OnInputAbilityReady(FGameplayTag InAbilityTag, FGameplayTag InInputTag); + void OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag); UFUNCTION(BlueprintPure, Category = "Hud") float GetObjectScreenRadius(AActor* InActor); diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index 18ca938..e7cedd2 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -96,7 +96,7 @@ void UARAbilityManagerComponent::OnGroupSelectionConfirmed(EAMGroup ValidGroup, for (int32 Idx = 0; Idx < AbilityTagsSet[AMEnumToInt(ValidGroup)].Num(); Idx++) { TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); - FGameplayTag NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); + TSoftClassPtr NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); FAFAbilityActionSet Set; Set.AbilityInputs = WeaponInput; @@ -119,7 +119,7 @@ void UARAbilityManagerComponent::OnGroupSelectionConfirmed(EAMGroup ValidGroup, for (int32 Idx = 0; Idx < AbilityTagsSet[AMEnumToInt(ValidGroup)].Num(); Idx++) { TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); - FGameplayTag NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); + TSoftClassPtr NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); FAFAbilityActionSet Set; Set.AbilityInputs = WeaponInput; @@ -136,7 +136,7 @@ void UARAbilityManagerComponent::OnGroupSelectionConfirmed(EAMGroup ValidGroup, } } -void UARAbilityManagerComponent::OnInputReady(FGameplayTag WeaponAbilityTag, TArray InInputTags) +void UARAbilityManagerComponent::OnInputReady(TSoftClassPtr WeaponAbilityTag, TArray InInputTags) { OnAbilitySetChanged.Broadcast(ActiveGroup); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h index 1c4fdf0..4f9e6d8 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -21,7 +21,7 @@ struct FARAbilityItem GENERATED_BODY() public: UPROPERTY(EditAnywhere) - FGameplayTag Ability; + TSoftClassPtr Ability; }; UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerComponent @@ -71,5 +71,5 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; - void OnInputReady(FGameplayTag WeaponAbilityTag, TArray InInputTags); + void OnInputReady(TSoftClassPtr WeaponAbilityTag, TArray InInputTags); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp index 492c311..192645e 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp @@ -34,41 +34,27 @@ void UARAbilityListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeome void UARAbilityListSlotDragWidget::OnItemAdded() { - if (UAssetManager* Manager = UAssetManager::GetIfValid()) + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); { - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityListSlotDragWidget::OnItemLoaded, AbilityTag); - TArray AssetData; - FARFilter Filter; - Filter.TagsAndValues.Add("AbilityTagSearch", AbilityTag.ToString()); - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityListSlotDragWidget::OnItemLoaded, PrimaryAssetId); - - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); - } + Manager.RequestAsyncLoad(AbilityTag.ToSoftObjectPath() + , del); } } -void UARAbilityListSlotDragWidget::OnItemLoaded(FPrimaryAssetId InPrimaryAssetId) +void UARAbilityListSlotDragWidget::OnItemLoaded(TSoftClassPtr InPrimaryAssetId) { - if (UAssetManager* Manager = UAssetManager::GetIfValid()) + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); { - UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); - TSubclassOf AbilityClass = Cast(loaded); + TSubclassOf AbilityClass = InPrimaryAssetId.Get(); if (AbilityClass) { IconImage->SetBrushFromTexture(AbilityClass.GetDefaultObject()->UIData->Icon); } { - Manager->UnloadPrimaryAsset(InPrimaryAssetId); + Manager.Unload(InPrimaryAssetId.ToSoftObjectPath()); } } } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h index 4f69c68..21c4981 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h @@ -16,7 +16,7 @@ class ACTIONRPGGAME_API UARAbilityListSlotDragWidget : public UARAbilityWidget GENERATED_BODY() public: UPROPERTY(EditAnywhere, Category = "Config") - FGameplayTag AbilityTag; + TSoftClassPtr AbilityTag; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UImage* IconImage; @@ -26,12 +26,12 @@ class ACTIONRPGGAME_API UARAbilityListSlotDragWidget : public UARAbilityWidget virtual void NativeOnDragDetected(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; - inline const FGameplayTag& GetAbilityTag() const + inline const TSoftClassPtr& GetAbilityTag() const { return AbilityTag; } void OnItemAdded(); protected: - void OnItemLoaded(FPrimaryAssetId InPrimaryAssetId); + void OnItemLoaded(TSoftClassPtr InPrimaryAssetId); }; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp index 7d28091..d6da4dc 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp @@ -5,7 +5,7 @@ #include "ARPlayerController.h" -void UARAbilityListWidget::AddItem(TSubclassOf DragWidgetClass, const FGameplayTag& Ability) +void UARAbilityListWidget::AddItem(TSubclassOf DragWidgetClass, const TSoftClassPtr& Ability) { UARAbilityListSlotDragWidget* Item = CreateWidget(ARPC.Get(), DragWidgetClass); Item->AbilityTag = Ability; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h index 0f4f279..fecd6a4 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h +++ b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h @@ -38,5 +38,5 @@ class ACTIONRPGGAME_API UARAbilityListWidget : public UUserWidget UPROPERTY() TArray Items; public: - void AddItem(TSubclassOf DragWidgetClass, const FGameplayTag& Ability); + void AddItem(TSubclassOf DragWidgetClass, const TSoftClassPtr& Ability); }; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp index 2669fb6..4638055 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp @@ -33,41 +33,31 @@ void UARWeaponListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeomet void UARWeaponListSlotDragWidget::OnItemAdded() { - if (UAssetManager* Manager = UAssetManager::GetIfValid()) + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); { - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - FGameplayTag AbilityTag = WeaponManager->WeaponClasses[WeaponIdx].GetDefaultObject()->Ability; - TArray AssetData; - FARFilter Filter; - Filter.TagsAndValues.Add("AbilityTagSearch", AbilityTag.ToString()); - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("Ability"), AssetData[0].AssetName); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + TSoftClassPtr AbilityTag = WeaponManager->WeaponClasses[WeaponIdx].GetDefaultObject()->Ability; + { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARWeaponListSlotDragWidget::OnItemLoaded, PrimaryAssetId); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARWeaponListSlotDragWidget::OnItemLoaded, AbilityTag); - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); + Manager.RequestAsyncLoad(AbilityTag.ToSoftObjectPath() + , del); } } } -void UARWeaponListSlotDragWidget::OnItemLoaded(FPrimaryAssetId InPrimaryAssetId) +void UARWeaponListSlotDragWidget::OnItemLoaded(TSoftClassPtr InPrimaryAssetId) { - if (UAssetManager* Manager = UAssetManager::GetIfValid()) + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); { - UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); - TSubclassOf AbilityClass = Cast(loaded); + TSubclassOf AbilityClass = InPrimaryAssetId.Get(); if (AbilityClass) { IconImage->SetBrushFromTexture(AbilityClass.GetDefaultObject()->UIData->Icon); } { - Manager->UnloadPrimaryAsset(InPrimaryAssetId); + Manager.Unload(InPrimaryAssetId.ToSoftObjectPath()); } } } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h index 8cff988..46e23ff 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h @@ -33,5 +33,5 @@ class ACTIONRPGGAME_API UARWeaponListSlotDragWidget : public UARWeaponBaseWidget } void OnItemAdded(); protected: - void OnItemLoaded(FPrimaryAssetId InPrimaryAssetId); + void OnItemLoaded(TSoftClassPtr InPrimaryAssetId); }; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index 63c6f60..40b2eab 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -16,7 +16,7 @@ class ACTIONRPGGAME_API UARItemWeapon : public UObject GENERATED_BODY() public: UPROPERTY(EditAnywhere, Category = "Ability") - FGameplayTag Ability; + TSoftClassPtr Ability; UPROPERTY(EditAnywhere, Category = "Visual") TSoftClassPtr Weapon; diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.cpp b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.cpp new file mode 100644 index 0000000..2ecaf41 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARMagazineUpgradeEffect.h" + + + + diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.h b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.h new file mode 100644 index 0000000..0416e00 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "ARMagazineUpgradeEffect.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARMagazineUpgradeEffect : public UAFEffectSpecBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h index 0d1c6b6..0eb03ff 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -46,6 +46,18 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase void AddDamageEffects(const TArray& InEffects); void ResetDamageEffects(); + /* + Replaces current DamageEffects with the one provided as Paremeter. + */ + virtual void InstallAmmoType(TSubclassOf AmmoType) {}; + + virtual void InstallAmmoType(TSoftClassPtr AmmoType) {}; + + virtual void InstallMagazineUpgrade(TSubclassOf MagazineUpgrade) {}; + /* + */ + virtual void OnAmmoTypeInstalled(TSubclassOf AmmoType) {}; + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapon") void ApplyDamageEffect(UObject* Target, FAFFunctionModifier Modifier); }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index efab2c3..2e62f37 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -127,7 +127,7 @@ bool UARWeaponManagerComponent::ServerAddWeaponToManager_Validate(EAMGroup Group void UARWeaponManagerComponent::NextWeapon() { EAMGroup OldGroup = ActiveGroup; - FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); ENetMode NetMode = GetOwner()->GetNetMode(); if (NetMode == ENetMode::NM_Client || NetMode == ENetMode::NM_Standalone) @@ -145,7 +145,7 @@ void UARWeaponManagerComponent::NextWeapon() } - FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { NextWeaponAbility = FindNextValid(); @@ -160,7 +160,7 @@ void UARWeaponManagerComponent::NextWeapon() void UARWeaponManagerComponent::PreviousWeapon() { EAMGroup OldGroup = ActiveGroup; - FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); int32 CurrentIndex = AMEnumToInt(ActiveGroup); CurrentIndex--; ActiveGroup = AMIntToEnum(CurrentIndex); @@ -168,7 +168,7 @@ void UARWeaponManagerComponent::PreviousWeapon() { ActiveGroup = AMIntToEnum(Groups.Num() - 1); } - FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { NextWeaponAbility = FindPreviousValid(); @@ -197,7 +197,7 @@ void UARWeaponManagerComponent::HolsterWeapon() void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponIndex) { EAMGroup OldGroup = ActiveGroup; - FGameplayTag CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); int32 CurrentIndex = AMEnumToInt(ActiveGroup); if(WeaponIndex > CurrentIndex) @@ -212,7 +212,7 @@ void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponInde ActiveGroup = AMIntToEnum(CurrentIndex); } - FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { NextWeaponAbility = FindNextValid(); @@ -253,7 +253,7 @@ void UARWeaponManagerComponent::ServerPreviousWeapon_Implementation(int32 Weapon ActiveGroup = AMIntToEnum(CurrentIndex); } - FGameplayTag NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); + TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); if (!NextWeaponAbility.IsValid()) { NextWeaponAbility = FindPreviousValid(); @@ -295,14 +295,14 @@ bool UARWeaponManagerComponent::ServerHolsterWeapon_Validate(int32 WeaponIndex) return true; } -void UARWeaponManagerComponent::OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags) +void UARWeaponManagerComponent::OnWeaponInputRead(TSoftClassPtr WeaponAbilityTag, TArray InInputTags) { UAFAbilityComponent* AbilityComp = GetAbilityComponent(); //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); } -void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag, EAMGroup OldGroup) +void UARWeaponManagerComponent::EquipWeapon(const TSoftClassPtr& PreviousWeaponTag, const TSoftClassPtr& NextWeaponTag, EAMGroup OldGroup) { if (!NextWeaponTag.IsValid()) { @@ -334,9 +334,9 @@ void UARWeaponManagerComponent::EquipWeapon(const FGameplayTag& PreviousWeaponTa ExecuteAbilityReadyEvent(NextWeaponTag); } } -FGameplayTag UARWeaponManagerComponent::FindNextValid() +TSoftClassPtr UARWeaponManagerComponent::FindNextValid() { - FGameplayTag WeaponAbilityTag; + TSoftClassPtr WeaponAbilityTag; int32 Idx = AMEnumToInt(ActiveGroup); while (!WeaponAbilityTag.IsValid()) @@ -362,9 +362,9 @@ FGameplayTag UARWeaponManagerComponent::FindNextValid() return WeaponAbilityTag; } -FGameplayTag UARWeaponManagerComponent::FindPreviousValid() +TSoftClassPtr UARWeaponManagerComponent::FindPreviousValid() { - FGameplayTag WeaponAbilityTag; + TSoftClassPtr WeaponAbilityTag; int32 Idx = AMEnumToInt(ActiveGroup); while (!WeaponAbilityTag.IsValid()) { @@ -402,7 +402,7 @@ bool UARWeaponManagerComponent::ReplicateSubobjects(class UActorChannel *Channel return WroteSomething; } -void UARWeaponManagerComponent::OnAbilityReady(const FGameplayTag& InAbilityTag +void UARWeaponManagerComponent::OnAbilityReady(TSoftClassPtr InAbilityTag , const TArray& InAbilityInput , EAMGroup InGroup, EAMSlot InSlot) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 7eda862..b47e786 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -131,18 +131,18 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UFUNCTION() - void OnWeaponInputRead(FGameplayTag WeaponAbilityTag, TArray InInputTags); + void OnWeaponInputRead(TSoftClassPtr WeaponAbilityTag, TArray InInputTags); public: bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; protected: - virtual void OnAbilityReady(const FGameplayTag& InAbilityTag, const TArray& InAbilityInput, + virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) override; - void EquipWeapon(const FGameplayTag& PreviousWeaponTag, const FGameplayTag& NextWeaponTag, EAMGroup OldGroup); + void EquipWeapon(const TSoftClassPtr& PreviousWeaponTag, const TSoftClassPtr& NextWeaponTag, EAMGroup OldGroup); - FGameplayTag FindNextValid(); - FGameplayTag FindPreviousValid(); + TSoftClassPtr FindNextValid(); + TSoftClassPtr FindPreviousValid(); public: void ShowHideAbilityManager(); }; From 605ab78086716fd9e2be8016fe8a1928c76ad73d Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 9 Apr 2018 22:04:48 +0200 Subject: [PATCH 113/187] ARG-31 removed redunant input validation --- .../AbilityFramework/AFAbilityComponent.cpp | 48 +------------------ .../AbilityFramework/AFAbilityComponent.h | 3 +- 2 files changed, 3 insertions(+), 48 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 917c7d9..9321889 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -218,7 +218,7 @@ void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InA //remove attributes //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = nullptr; - InArraySerializerC.RemoveAbilityFromAction(AbilityClass); + InArraySerializerC.AbilityToAction.Remove(AbilityClass); InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); InArraySerializerC.TagToAbility.Remove(AbilityClass); } @@ -320,7 +320,6 @@ void FGASAbilityContainer::RemoveAbility(const TSoftClassPtr& Ab TagToAbility.Remove(AbilityIn); MarkItemDirty(AbilitiesItems[Index]); - RemoveAbilityFromAction(AbilityIn); AbilitiesItems.RemoveAt(Index); MarkArrayDirty(); } @@ -335,33 +334,11 @@ TSoftClassPtr FGASAbilityContainer::IsAbilityBoundToAction(const return Ability; } -void FGASAbilityContainer::RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr) -{ - /*TArray OutActions; - AbilityToAction.RemoveAndCopyValue(InAbilityTag, OutActions); - - for(const FGameplayTag& Action : OutActions) - { - ActionToAbility.Remove(Action); - }*/ - //AbilitiesInputs.Remove(InAbilityTag); -} void FGASAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) { for (const FGameplayTag& InputTag : InInputTag) { - if (ActionToAbility.Contains(InputTag)) - { - TSoftClassPtr AbilityTag = ActionToAbility.FindRef(InputTag); - UE_LOG(AbilityFramework, Log, TEXT("FGASAbilityContainer: Input %s is already abount to Ability %s"), - *InputTag.ToString(), - *AbilityTag.ToString() - ); - - //return; - } - TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); AbilityClassPtr = InAbiltyPtr; TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); @@ -508,14 +485,6 @@ void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, F void UAFAbilityComponent::SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag , const FAFOnAbilityReady& InputDelegate) { - for (const FGameplayTag& Tag : InInputTag) - { - if (AbilityContainer.IsAbilityBoundToAction(Tag).IsValid()) - { - RemoveAbilityFromAction(InAbilityPtr, FGameplayTag()); - } - } - AbilityContainer.SetAbilityToAction(InAbilityPtr, InInputTag); ENetRole role = GetOwnerRole(); @@ -539,10 +508,7 @@ TSoftClassPtr UAFAbilityComponent::IsAbilityBoundToAction(const } return TSoftClassPtr(); } -void UAFAbilityComponent::RemoveAbilityFromAction(const TSoftClassPtr& InAbilityPtr, const FGameplayTag& InInputTag) -{ - AbilityContainer.RemoveAbilityFromAction(InAbilityPtr); -} + void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) { if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) @@ -568,16 +534,6 @@ void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSo void UAFAbilityComponent::SetAbilitiesToActions(const TArray& InAbilitiesActions , const TArray& InputDelegate) { - for (const FAFAbilityActionSet& Set : InAbilitiesActions) - { - for (const FGameplayTag& Tag : Set.AbilityInputs) - { - if (AbilityContainer.IsAbilityBoundToAction(Tag).IsValid()) - { - RemoveAbilityFromAction(Set.AbilityTag, FGameplayTag()); - } - } - } for (const FAFAbilityActionSet& Set : InAbilitiesActions) { AbilityContainer.SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index c37f7b6..ba2d31c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -177,7 +177,6 @@ struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); - void RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr); UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); @@ -600,7 +599,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); TSoftClassPtr IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); - void RemoveAbilityFromAction(const TSoftClassPtr& InAbilityPtr, const FGameplayTag& InInputTag); + protected: UFUNCTION(Server, Reliable, WithValidation) void ServerSetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); From d89ab4cb32053f8d6b160edf41a4a8978e05e203 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 9 Apr 2018 22:18:28 +0200 Subject: [PATCH 114/187] cleaned up ability component code --- .../AbilityFramework/AFAbilityComponent.cpp | 205 +----------------- .../AbilityFramework/AFAbilityComponent.h | 102 +-------- .../AbilityFramework/AFAbilityTypes.cpp | 203 +++++++++++++++++ .../Source/AbilityFramework/AFAbilityTypes.h | 98 ++++++++- 4 files changed, 298 insertions(+), 310 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 9321889..cbe19d9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -14,13 +14,13 @@ #include "AFAbilityInterface.h" #include "Effects/GAEffectExecution.h" #include "Effects/GAGameEffect.h" -#include "MessageEndpoint.h" -#include "MessageEndpointBuilder.h" + #include "Effects/GAEffectExtension.h" #include "Effects/GAEffectCue.h" #include "AFCueManager.h" #include "Effects/GABlueprintLibrary.h" #include "Async.h" + #include "AFAbilityComponent.h" #include "AFEffectsComponent.h" #include "AFAbilityInterface.h" @@ -174,7 +174,7 @@ bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, clas { WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); } - for (const FGASAbilityItem& Ability : AbilityContainer.AbilitiesItems) + for (const FAFAbilityItem& Ability : AbilityContainer.AbilitiesItems) { //if (Set.InputOverride) // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); @@ -210,206 +210,7 @@ void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContain } } -void FGASAbilityItem::PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer) -{ - if (InArraySerializer.AbilitiesComp.IsValid()) - { - FGASAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); - //remove attributes - //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); - Ability->Attributes = nullptr; - InArraySerializerC.AbilityToAction.Remove(AbilityClass); - InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); - InArraySerializerC.TagToAbility.Remove(AbilityClass); - } -} -void FGASAbilityItem::PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer) -{ - if (InArraySerializer.AbilitiesComp.IsValid()) - { - //should be safe, since we only modify the non replicated part of struct. - FGASAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); - Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); - if (InArraySerializer.AbilitiesComp.IsValid()) - { - APawn* POwner = Cast(InArraySerializer.AbilitiesComp->GetOwner()); - Ability->POwner = POwner; - Ability->PCOwner = Cast(POwner->Controller); - Ability->OwnerCamera = nullptr; - } - Ability->InitAbility(); - Ability->Attributes = nullptr; - - //TODO - CHANGE ATTRIBUTE HANDLING - UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); - Ability->Attributes = attr; - - InArraySerializerC.AbilitiesInputs.Add(AbilityClass, Ability); //.Add(Ability->AbilityTag, Ability); - InArraySerializerC.TagToAbility.Add(AbilityClass, Ability); - InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(AbilityClass); - } -} -void FGASAbilityItem::PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer) -{ - -} -void FGASAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) -{ - if (BlockedInput.Contains(InActionName)) - { - BlockedInput[InActionName] = bBlock; - } - else - { - BlockedInput.Add(InActionName, bBlock); - } -} -UGAAbilityBase* FGASAbilityContainer::AddAbility(TSubclassOf AbilityIn - , TSoftClassPtr InClassPtr) -{ - if (AbilityIn && AbilitiesComp.IsValid()) - { - - UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); - ability->AbilityComponent = AbilitiesComp.Get(); - if (AbilitiesComp.IsValid()) - { - APawn* POwner = Cast(AbilitiesComp->GetOwner()); - ability->POwner = POwner; - ability->PCOwner = Cast(POwner->Controller); - ability->OwnerCamera = nullptr; - } - ability->InitAbility(); - FGameplayTag Tag = ability->AbilityTag; - - AbilitiesInputs.Add(InClassPtr, ability); - FGASAbilityItem AbilityItem(ability, InClassPtr); - MarkItemDirty(AbilityItem); - AbilityItem.Ability = ability; - AbilitiesItems.Add(AbilityItem); - TagToAbility.Add(InClassPtr, ability); - - MarkArrayDirty(); - if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone - || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) - { - AbilitiesComp->NotifyOnAbilityReady(InClassPtr); - } - /* if (ActionName.IsValid()) - { - UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); - AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); - }*/ - return ability; - } - return nullptr; -} -void FGASAbilityContainer::RemoveAbility(const TSoftClassPtr& AbilityIn) -{ - int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); - - if (Index == INDEX_NONE) - return; - - UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); - for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) - { - AbilitiesComp->ReplicatedTasks.Remove(It->Value); - } - - TagToAbility.Remove(AbilityIn); - MarkItemDirty(AbilitiesItems[Index]); - AbilitiesItems.RemoveAt(Index); - MarkArrayDirty(); -} -TSoftClassPtr FGASAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) -{ - TSoftClassPtr Ability; - TSoftClassPtr* AbilityTag = ActionToAbility.Find(InInputTag); - if (AbilityTag) - { - Ability = *AbilityTag; - } - - return Ability; -} - -void FGASAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) -{ - for (const FGameplayTag& InputTag : InInputTag) - { - TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); - AbilityClassPtr = InAbiltyPtr; - TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); - ActionTag.Add(InputTag); - } - if (!AbilitiesComp.IsValid()) - return; - - UGAAbilityBase* Ability = TagToAbility.FindRef(InAbiltyPtr); - if (Ability) - { - Ability->OnAbilityInputReady(); - } - - if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); - } -} - -UGAAbilityBase* FGASAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) -{ - UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); - return retAbility; -} -void FGASAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) -{ - if (BlockedInput.FindRef(ActionName)) - { - return; - } - TSoftClassPtr AbiltyPtr = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(AbiltyPtr); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - ability->OnNativeInputPressed(ActionName, InPredictionHandle); - } -} -void FGASAbilityContainer::HandleInputReleased(FGameplayTag ActionName) -{ - if (BlockedInput.FindRef(ActionName)) - { - return; - } - TSoftClassPtr abilityTag = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); - if (ability) - { - ability->OnNativeInputReleased(ActionName); - } -} - -void FGASAbilityContainer::TriggerAbylityByTag(TSoftClassPtr InTag) -{ - UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - FAFPredictionHandle PredHandle = FAFPredictionHandle::GenerateClientHandle(AbilitiesComp.Get()); - ability->OnNativeInputPressed(FGameplayTag(), PredHandle); - } -} void UAFAbilityComponent::InitializeComponent() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index ba2d31c..426a40a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -105,106 +105,6 @@ struct ABILITYFRAMEWORK_API FGASMontageRepData uint8 ForceRep; }; -USTRUCT() -struct ABILITYFRAMEWORK_API FGASAbilityItem : public FFastArraySerializerItem -{ - GENERATED_BODY() - -public: - UPROPERTY() - UGAAbilityBase* Ability; - UPROPERTY() - TSoftClassPtr AbilityClass; - - FGASAbilityItem() - {}; - - FGASAbilityItem(UGAAbilityBase* InAbility, TSoftClassPtr InAbilityClass) - : Ability(InAbility) - , AbilityClass(InAbilityClass) - {} - - void PreReplicatedRemove(const struct FGASAbilityContainer& InArraySerializer); - void PostReplicatedAdd(const struct FGASAbilityContainer& InArraySerializer); - void PostReplicatedChange(const struct FGASAbilityContainer& InArraySerializer); - - const bool operator==(const TSoftClassPtr& OtherAbility) const - { - return AbilityClass == OtherAbility; - } - - const bool operator==(UGAAbilityBase* OtherAbility) const - { - return Ability == OtherAbility; - } - const bool operator==(const FGASAbilityItem& OtherItem) const - { - return Ability == OtherItem.Ability; - } -}; -USTRUCT() -struct ABILITYFRAMEWORK_API FGASAbilityContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - - UPROPERTY() - TArray AbilitiesItems; - - TWeakObjectPtr AbilitiesComp; - TMap BlockedInput; - - TMap, FGameplayTag> AbilityToInput; - - //Custom binding, for server side validation. - - //ActionInput, AbilityClassPtr - TMap> ActionToAbility; - - //AbilityTag, ActionInput - TMap, TArray> AbilityToAction; - - //abilityTag, Ability Ptr - TMap, UGAAbilityBase*> AbilitiesInputs; - - TMap, UGAAbilityBase*> TagToAbility; - - void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - UGAAbilityBase* AddAbility(TSubclassOf AbilityIn - , TSoftClassPtr InClassPtr); - - void RemoveAbility(const TSoftClassPtr& AbilityIn); - - void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); - TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); - - UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); - - void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); - void HandleInputReleased(FGameplayTag ActionName); - - void TriggerAbylityByTag(TSoftClassPtr InTag); - - bool AbilityExists(TSoftClassPtr InAbiltyPtr) const - { - return AbilityToInput.Contains(InAbiltyPtr); - } - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FGASAbilityContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; - - USTRUCT() struct FAFReplicatedAttributeItem : public FFastArraySerializerItem { @@ -450,7 +350,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public UFUNCTION() void OnRep_InstancedAbilities(); UPROPERTY(Replicated) - FGASAbilityContainer AbilityContainer; + FAFAbilityContainer AbilityContainer; UPROPERTY() TArray AbilitiesRefs; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp index 1df88dc..e43261c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp @@ -2,5 +2,208 @@ #include "AbilityFramework.h" #include "AFAbilityComponent.h" +#include "Abilities/GAAbilityBase.h" #include "AFAbilityTypes.h" +void FAFAbilityItem::PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer) +{ + if (InArraySerializer.AbilitiesComp.IsValid()) + { + FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + //remove attributes + //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); + Ability->Attributes = nullptr; + InArraySerializerC.AbilityToAction.Remove(AbilityClass); + InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); + InArraySerializerC.TagToAbility.Remove(AbilityClass); + } +} +void FAFAbilityItem::PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer) +{ + if (InArraySerializer.AbilitiesComp.IsValid()) + { + //should be safe, since we only modify the non replicated part of struct. + FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); + if (InArraySerializer.AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(InArraySerializer.AbilitiesComp->GetOwner()); + Ability->POwner = POwner; + Ability->PCOwner = Cast(POwner->Controller); + Ability->OwnerCamera = nullptr; + } + Ability->InitAbility(); + Ability->Attributes = nullptr; + + //TODO - CHANGE ATTRIBUTE HANDLING + UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); + Ability->Attributes = attr; + + InArraySerializerC.AbilitiesInputs.Add(AbilityClass, Ability); //.Add(Ability->AbilityTag, Ability); + InArraySerializerC.TagToAbility.Add(AbilityClass, Ability); + InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(AbilityClass); + } +} +void FAFAbilityItem::PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer) +{ + +} + + +void FAFAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) +{ + if (BlockedInput.Contains(InActionName)) + { + BlockedInput[InActionName] = bBlock; + } + else + { + BlockedInput.Add(InActionName, bBlock); + } +} +UGAAbilityBase* FAFAbilityContainer::AddAbility(TSubclassOf AbilityIn + , TSoftClassPtr InClassPtr) +{ + if (AbilityIn && AbilitiesComp.IsValid()) + { + + UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); + ability->AbilityComponent = AbilitiesComp.Get(); + if (AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(AbilitiesComp->GetOwner()); + ability->POwner = POwner; + ability->PCOwner = Cast(POwner->Controller); + ability->OwnerCamera = nullptr; + } + ability->InitAbility(); + FGameplayTag Tag = ability->AbilityTag; + + AbilitiesInputs.Add(InClassPtr, ability); + FAFAbilityItem AbilityItem(ability, InClassPtr); + MarkItemDirty(AbilityItem); + AbilityItem.Ability = ability; + AbilitiesItems.Add(AbilityItem); + TagToAbility.Add(InClassPtr, ability); + + MarkArrayDirty(); + if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone + || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) + { + AbilitiesComp->NotifyOnAbilityReady(InClassPtr); + } + /* if (ActionName.IsValid()) + { + UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); + AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); + }*/ + return ability; + } + return nullptr; +} +void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& AbilityIn) +{ + int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); + + if (Index == INDEX_NONE) + return; + + UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); + + for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) + { + AbilitiesComp->ReplicatedTasks.Remove(It->Value); + } + + TagToAbility.Remove(AbilityIn); + MarkItemDirty(AbilitiesItems[Index]); + AbilitiesItems.RemoveAt(Index); + MarkArrayDirty(); +} +TSoftClassPtr FAFAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) +{ + TSoftClassPtr Ability; + TSoftClassPtr* AbilityTag = ActionToAbility.Find(InInputTag); + if (AbilityTag) + { + Ability = *AbilityTag; + } + + return Ability; +} + +void FAFAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) +{ + for (const FGameplayTag& InputTag : InInputTag) + { + TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); + AbilityClassPtr = InAbiltyPtr; + TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); + ActionTag.Add(InputTag); + } + if (!AbilitiesComp.IsValid()) + return; + + UGAAbilityBase* Ability = TagToAbility.FindRef(InAbiltyPtr); + if (Ability) + { + Ability->OnAbilityInputReady(); + } + + if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); + } +} + +UGAAbilityBase* FAFAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) +{ + UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); + return retAbility; +} +void FAFAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) +{ + if (BlockedInput.FindRef(ActionName)) + { + return; + } + TSoftClassPtr AbiltyPtr = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(AbiltyPtr); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + ability->OnNativeInputPressed(ActionName, InPredictionHandle); + } +} +void FAFAbilityContainer::HandleInputReleased(FGameplayTag ActionName) +{ + if (BlockedInput.FindRef(ActionName)) + { + return; + } + TSoftClassPtr abilityTag = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); + if (ability) + { + ability->OnNativeInputReleased(ActionName); + } +} + +void FAFAbilityContainer::TriggerAbylityByTag(TSoftClassPtr InTag) +{ + UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + FAFPredictionHandle PredHandle = FAFPredictionHandle::GenerateClientHandle(AbilitiesComp.Get()); + ability->OnNativeInputPressed(FGameplayTag(), PredHandle); + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h index fff88cb..4e7ef4b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h @@ -4,21 +4,105 @@ #include "Engine/NetSerialization.h" #include "GameplayTags.h" #include "AFAbilityTypes.generated.h" -/** - * - */ + +class UGAAbilityBase; + USTRUCT() -struct FAFAb +struct ABILITYFRAMEWORK_API FAFAbilityItem : public FFastArraySerializerItem { GENERATED_BODY() + +public: + UPROPERTY() + UGAAbilityBase* Ability; + UPROPERTY() + TSoftClassPtr AbilityClass; + + FAFAbilityItem() + {}; + + FAFAbilityItem(UGAAbilityBase* InAbility, TSoftClassPtr InAbilityClass) + : Ability(InAbility) + , AbilityClass(InAbilityClass) + {} + + void PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer); + void PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer); + void PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer); + + const bool operator==(const TSoftClassPtr& OtherAbility) const + { + return AbilityClass == OtherAbility; + } + + const bool operator==(UGAAbilityBase* OtherAbility) const + { + return Ability == OtherAbility; + } + const bool operator==(const FAFAbilityItem& OtherItem) const + { + return Ability == OtherItem.Ability; + } }; -struct FAFAbilityItem +USTRUCT() +struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer { + GENERATED_BODY() +public: + + UPROPERTY() + TArray AbilitiesItems; + + TWeakObjectPtr AbilitiesComp; + TMap BlockedInput; + + TMap, FGameplayTag> AbilityToInput; + //Custom binding, for server side validation. + + //ActionInput, AbilityClassPtr + TMap> ActionToAbility; + + //AbilityTag, ActionInput + TMap, TArray> AbilityToAction; + + //abilityTag, Ability Ptr + TMap, UGAAbilityBase*> AbilitiesInputs; + + TMap, UGAAbilityBase*> TagToAbility; + + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn + , TSoftClassPtr InClassPtr); + + void RemoveAbility(const TSoftClassPtr& AbilityIn); + + void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); + TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); + + UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); + + void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); + void HandleInputReleased(FGameplayTag ActionName); + + void TriggerAbylityByTag(TSoftClassPtr InTag); + + bool AbilityExists(TSoftClassPtr InAbiltyPtr) const + { + return AbilityToInput.Contains(InAbiltyPtr); + } + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); + } }; -struct FAFAbilityContainer +template<> +struct TStructOpsTypeTraits< FAFAbilityContainer > : public TStructOpsTypeTraitsBase2 { - + enum + { + WithNetDeltaSerializer = true, + }; }; \ No newline at end of file From f918ba1c22aafa16fa91d4e1a7247039ed4e0269 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 10 Apr 2018 23:37:47 +0200 Subject: [PATCH 115/187] protptyping weapon modifications/upgrades --- .../AbilityFramework/AFAbilityComponent.cpp | 1 + Source/ActionRPGGame/ARCharacter.cpp | 6 ++-- Source/ActionRPGGame/ARCharacter.h | 13 +++++--- .../UI/Weapons/ARMagazineUpgradeWidget.cpp | 11 +++++++ .../UI/Weapons/ARMagazineUpgradeWidget.h | 21 +++++++++++++ .../UI/Weapons/ARUpgradeBaseWidget.cpp | 7 +++++ .../UI/Weapons/ARUpgradeBaseWidget.h | 20 +++++++++++++ .../UI/Weapons/ARWeaponListSlotDragWidget.cpp | 2 +- .../UI/Weapons/ARWeaponListSlotDragWidget.h | 1 + .../UI/Weapons/ARWeaponListSlotDropWidget.cpp | 24 +++++++++++++++ .../UI/Weapons/ARWeaponListSlotDropWidget.h | 4 ++- .../UI/Weapons/ARWeaponListWidget.cpp | 11 +++++++ .../UI/Weapons/ARWeaponListWidget.h | 9 ++++++ .../UI/Weapons/ARWeaponUpgradeListWidget.cpp | 30 +++++++++++++++++++ .../UI/Weapons/ARWeaponUpgradeListWidget.h | 24 +++++++++++++++ Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 3 ++ Source/ActionRPGGame/Weapons/ARItemWeapon.h | 10 +++++++ .../Weapons/ARMagazineUpgradeItem.cpp | 7 +++++ .../Weapons/ARMagazineUpgradeItem.h | 22 ++++++++++++++ .../Weapons/ARWeaponAbilityBase.cpp | 4 +++ .../Weapons/ARWeaponAbilityBase.h | 14 +++++++++ .../Weapons/ARWeaponManagerComponent.cpp | 10 +++++++ .../Weapons/ARWeaponManagerComponent.h | 16 +++++++++- .../Weapons/ARWeaponPawnManagerComponent.cpp | 10 +++++++ .../Weapons/ARWeaponPawnManagerComponent.h | 7 ++++- .../Weapons/ARWeaponUpgradeItem.cpp | 7 +++++ .../Weapons/ARWeaponUpgradeItem.h | 16 ++++++++++ 27 files changed, 299 insertions(+), 11 deletions(-) create mode 100644 Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h create mode 100644 Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.cpp create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index cbe19d9..ba1c665 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -99,6 +99,7 @@ void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHa Data.Location = Context.HitResult.Location; OnAttributeModifed.Broadcast(Data); NotifyInstigatorTargetAttributeChanged(Data, Context); + //add default replication (PropertyRep) that attribute changed. }; void UAFAbilityComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, const FGAEffectContext& InContext) diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 7ad6fac..1f522c5 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -59,10 +59,10 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) //CameraBoom->SetupAttachment(GetMesh()); CameraBoom->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, TEXT("headSocket")); - CameraBoom->TargetArmLength = 265; // The camera follows at this distance behind the character + CameraBoom->TargetArmLength = 275; // The camera follows at this distance behind the character CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller - CameraBoom->SocketOffset = FVector(0, 25, 95); - CameraBoom->TargetOffset = FVector(0, 0, -75); + CameraBoom->SocketOffset = FVector(0, 25, 65); + CameraBoom->TargetOffset = FVector(0, 0, -45); CameraBoom->bEnableCameraLag = true; CameraBoom->bEnableCameraRotationLag = true; CameraBoom->CameraLagSpeed = 8; diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index fb0fce1..da9c768 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -133,12 +133,17 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UChildActorComponent* HolsteredBackDown; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponHolsteredSideLeft; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponEquipedMain; - - - +public: + UPROPERTY() + class UARItemWeapon* WeaponRightItem; + UPROPERTY() + class UARItemWeapon* WeaponLeftItem; + UPROPERTY() + class UARItemWeapon* WeaponBackItem; + UPROPERTY() + class UARItemWeapon* WeaponSideItem; public: UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") FARCameraTransform CameraTransform; diff --git a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp new file mode 100644 index 0000000..5ee82ed --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp @@ -0,0 +1,11 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARMagazineUpgradeWidget.h" + + + + +FReply UARMagazineUpgradeWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + return FReply::Unhandled(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h new file mode 100644 index 0000000..dff1dcc --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h @@ -0,0 +1,21 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Weapons/ARUpgradeBaseWidget.h" +#include "ARMagazineUpgradeWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARMagazineUpgradeWidget : public UARUpgradeBaseWidget +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UImage* Icon; + + virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp new file mode 100644 index 0000000..284bcf9 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARUpgradeBaseWidget.h" + + + + diff --git a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h new file mode 100644 index 0000000..0643b5a --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Weapons/ARWeaponBaseWidget.h" +#include "ARUpgradeBaseWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARUpgradeBaseWidget : public UARWeaponBaseWidget +{ + GENERATED_BODY() +public: + TSoftClassPtr WeaponUpgrade; + + +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp index 4638055..c3a461c 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp @@ -25,7 +25,7 @@ void UARWeaponListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeomet //DragIcon->AbilityManager = AbilityManager; DragDropOp->Payload = this; - //DragDropOp->DefaultDragVisual = DragIcon; + DragDropOp->DefaultDragVisual = IconImage; OutOperation = DragDropOp; } diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h index 46e23ff..9164df7 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h @@ -21,6 +21,7 @@ class ACTIONRPGGAME_API UARWeaponListSlotDragWidget : public UARWeaponBaseWidget UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UImage* IconImage; + TWeakObjectPtr WeaponList; public: virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) override; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp index 0f43820..26db76d 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp @@ -2,10 +2,19 @@ #include "ARWeaponListSlotDropWidget.h" +#include "Components/TextBlock.h" + #include "AFAbilityComponent.h" +#include "ARCharacter.h" +#include "ARPlayerController.h" + +#include "Weapons/ARItemWeapon.h" #include "Weapons/ARWeaponManagerComponent.h" #include "Weapons/ARWeaponAbilityBase.h" + +#include "ARWeaponListWidget.h" + #include "ARWeaponListSlotDragWidget.h" bool UARWeaponListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry @@ -15,6 +24,21 @@ bool UARWeaponListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry FSlateBrush Brush = Payload->IconImage->Brush; IconImage->SetBrush(Brush); + WeaponList = Payload->WeaponList; + WeaponManager->AddWeaponToManager(WeaponSlot, EAMSlot::Slot001, Payload->GetWeapon()); return true; +} + +FReply UARWeaponListSlotDropWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + AARPlayerController* PC = Cast(WeaponManager->GetOwner()); + + AARCharacter* Character = Cast(PC->GetPawn()); + UGAAbilityBase* WeaponAbility = WeaponManager->GetAbility(WeaponSlot, EAMSlot::Slot001); + + WeaponList->SelectedWeaponName->SetText(FText::FromString(Character->WeaponRightItem->GetName())); + WeaponManager->WeaponToModify = Character->WeaponRightItem; + + return FReply::Unhandled(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h index 83c5381..6f62476 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h @@ -20,10 +20,12 @@ class ACTIONRPGGAME_API UARWeaponListSlotDropWidget : public UARWeaponBaseWidget UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UImage* IconImage; + + TWeakObjectPtr WeaponList; public: virtual bool NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; - + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp index 4e792ba..149113b 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp @@ -3,6 +3,7 @@ #include "ARWeaponListWidget.h" #include "ARPlayerController.h" +#include "ARWeaponUpgradeListWidget.h" #include "Weapons/ARWeaponManagerComponent.h" @@ -23,6 +24,7 @@ void UARWeaponListWidget::NativeConstruct() ARPC = MyPC; WeaponManager = MyPC->WeaponManager; } + Magazine->OnClicked.AddDynamic(this, &UARWeaponListWidget::OnMagazineClicked); Super::NativeConstruct(); } void UARWeaponListWidget::AddItem(TSubclassOf DragWidgetClass, int32 WeaponIdx) @@ -30,8 +32,17 @@ void UARWeaponListWidget::AddItem(TSubclassOf UARWeaponListSlotDragWidget* Item = CreateWidget(ARPC.Get(), DragWidgetClass); Item->WeaponManager = WeaponManager; Item->WeaponIdx = WeaponIdx; + Item->WeaponList = this; Items.Add(Item); Item->OnItemAdded(); ItemContainer->AddChild(Item); } +void UARWeaponListWidget::OnMagazineClicked() +{ + if (WeaponManager->WeaponToModify.IsValid()) + { + WeaponManager->MagazineUpgradeListWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + WeaponManager->MagazineUpgradeListWidget->OnShow(); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h index 2ba9532..2850f5a 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h @@ -27,6 +27,12 @@ class ACTIONRPGGAME_API UARWeaponListWidget : public UUserWidget class UARWeaponListSlotDropWidget* BackDownWeapon; UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) class UARWeaponListSlotDropWidget* SideLeftWeapon; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UButton* Magazine; +public: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UTextBlock* SelectedWeaponName; protected: UPROPERTY() @@ -36,4 +42,7 @@ class ACTIONRPGGAME_API UARWeaponListWidget : public UUserWidget void NativeConstruct(); public: void AddItem(TSubclassOf DragWidgetClass, int32 WeaponIdx); + + UFUNCTION() + void OnMagazineClicked(); }; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp new file mode 100644 index 0000000..1b6fe7e --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponUpgradeListWidget.h" + +#include "ARPlayerController.h" +#include "Weapons/ARMagazineUpgradeItem.h" +#include "UI/Weapons/ARMagazineUpgradeWidget.h" +#include "Components/WrapBox.h" +#include "Components/Image.h" +#include "Weapons/ARWeaponManagerComponent.h" + + + +void UARWeaponUpgradeListWidget::OnShow() +{ + UpgradeList.Empty(); + ItemContainer->ClearChildren(); + + for (const TSubclassOf& Upgrade : WeaponManager->MagazineUpgradesClasses) + { + UARMagazineUpgradeItem* CDO = Upgrade->GetDefaultObject(); + + UARMagazineUpgradeWidget* Item = CreateWidget(Cast(WeaponManager->GetOwner()), WeaponManager->MagazineUpgradeClass); + Item->WeaponManager = WeaponManager; + Item->WeaponUpgrade = Upgrade; + Item->Icon->SetBrushFromTexture(CDO->Icon); + UpgradeList.Add(Item); + ItemContainer->AddChild(Item); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h new file mode 100644 index 0000000..6056578 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "ARWeaponBaseWidget.h" +#include "ARWeaponUpgradeListWidget.generated.h" + +/** + * Contains list of upgrades for weapon, for selected slot. + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponUpgradeListWidget : public UARWeaponBaseWidget +{ + GENERATED_BODY() +protected: + UPROPERTY() + TArray UpgradeList; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UWrapBox* ItemContainer; +public: + void OnShow(); +}; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 64da854..2b3596d 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -4,4 +4,7 @@ +void UARItemWeapon::OnMagazineUpdateAdded() +{ +} diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index 40b2eab..b4e160d 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -30,4 +30,14 @@ class ACTIONRPGGAME_API UARItemWeapon : public UObject FVector EquipedPosition; UPROPERTY(EditAnywhere, Category = "Transforms") FRotator EquipedRotation; + + /* Wrap it later into it's own item. */ + UPROPERTY(EditAnywhere, Category = "Upgrades") + TSoftClassPtr MagazineUpgrade; + + void AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade) + { + MagazineUpgrade = InMagazineUpgrade; + } + void OnMagazineUpdateAdded(); }; diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.cpp b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.cpp new file mode 100644 index 0000000..b344720 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARMagazineUpgradeItem.h" + + + + diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h new file mode 100644 index 0000000..c06c516 --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Weapons/ARWeaponUpgradeItem.h" +#include "ARMagazineUpgradeItem.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + UTexture2D* Icon; + + UPROPERTY(EditAnywhere) + TSoftClassPtr UpgradeEffect; +}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp index f75c137..a4bf8ef 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp @@ -55,4 +55,8 @@ void UARWeaponAbilityBase::ApplyDamageEffect(UObject* Target, FAFFunctionModifie , this , Modifier); } +} +void UARWeaponAbilityBase::ReloadWeapon() +{ + } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h index 0eb03ff..fde9fc9 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h @@ -17,6 +17,16 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase GENERATED_BODY() protected: + /* Amount of ammunition to add to magazine */ + UPROPERTY(EditAnywhere, Category = "Weapon Reload Effects") + FAFPropertytHandle AmmoToAdd; + FGAEffectHandle AmmoToAddHandle; + + /* Amount of ammo to take from owner */ + UPROPERTY(EditAnywhere, Category = "Weapon Reload Effects") + FAFPropertytHandle AmmoToTake; + FGAEffectHandle AmmoToTakeHandle; + /* Default damage effects used, when no upgrades are present for this weapon ability. */ @@ -58,6 +68,10 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase */ virtual void OnAmmoTypeInstalled(TSubclassOf AmmoType) {}; + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapon") void ApplyDamageEffect(UObject* Target, FAFFunctionModifier Modifier); + + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapon") + void ReloadWeapon(); }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 2e62f37..051f36f 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -7,6 +7,7 @@ #include "ARItemWeapon.h" #include "ARCharacter.h" #include "UI/Weapons/ARWeaponListWidget.h" +#include "UI/Weapons/ARWeaponUpgradeListWidget.h" #include "DWBPFunctionLibrary.h" #include "SDraggableWindowWidget.h" @@ -58,6 +59,15 @@ void UARWeaponManagerComponent::BeginPlay() WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); } + if (MagazineUpgradeListClass) + { + MagazineUpgradeListWidget = CreateWidget(MyPC, MagazineUpgradeListClass); + MagazineUpgradeListWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + //MagazineUpgradeListWidget->ARPC = Cast(GetOwner()); + MagazineUpgradeListWidget->WeaponManager = this; + MagazineUpgradeListWidget->AddToViewport(); + } + //POwner = MyPC->GetPawn(); } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index b47e786..c7b3778 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -48,6 +48,9 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> WeaponClasses; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") + TArray> MagazineUpgradesClasses; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray EquipedWeapons; @@ -61,12 +64,23 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp TSubclassOf WeaponListClass; - UPROPERTY(BlueprintReadOnly, Category = "Widgets") + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon|Widgets") UARWeaponListWidget* WeaponListWidget; UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf DragSlotClass; + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf MagazineUpgradeListClass; + + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf MagazineUpgradeClass; + + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon|Widgets") + class UARWeaponUpgradeListWidget* MagazineUpgradeListWidget; + + //maybe not reference directly ? + TWeakObjectPtr WeaponToModify; FDWWWindowHandle WeaponListWindowHandle; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp index b7902d5..d308cc3 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp @@ -32,6 +32,11 @@ void UARWeaponPawnManagerComponent::BeginPlay() GroupToComponent.Add(EAMGroup::Group002, Character->GetHolsteredLeftWeapon()); GroupToComponent.Add(EAMGroup::Group003, Character->GetHolsteredBackDownWeapon()); GroupToComponent.Add(EAMGroup::Group004, Character->GetHolsteredSideLeftWeapon()); + + GroupToItem.Add(EAMGroup::Group001, Character->WeaponRightItem); + GroupToItem.Add(EAMGroup::Group002, Character->WeaponLeftItem); + GroupToItem.Add(EAMGroup::Group003, Character->WeaponBackItem); + GroupToItem.Add(EAMGroup::Group004, Character->WeaponSideItem); } } @@ -127,6 +132,7 @@ void UARWeaponPawnManagerComponent::EquipInactive(EAMGroup Group, UARItemWeapon* void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) { WeaponHelper[AMEnumToInt(Group)]->Weapon = InWeapon->Weapon; + WeaponHelper[AMEnumToInt(Group)]->Item = InWeapon->GetClass(); WeaponHelper[AMEnumToInt(Group)]->Position = InWeapon->HolsteredPosition; WeaponHelper[AMEnumToInt(Group)]->Rotation = InWeapon->HolsteredRotation; WeaponHelper[AMEnumToInt(Group)]->Group = Group; @@ -135,6 +141,10 @@ void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, class UARItemWeapon* { //Character->GetHolsteredRightWeapon()->SetSkeletalMesh(nullptr); SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + if (Group == EAMGroup::Group001) + { + Character->WeaponRightItem = DuplicateObject(InWeapon, Character); + } } } void UARWeaponPawnManagerComponent::HolsterActive(EAMGroup Group) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h index 12e51f2..52c28cf 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h @@ -19,6 +19,9 @@ struct FARWeapon public: UPROPERTY(EditAnywhere, Category = "Attachment Test") TSoftClassPtr Weapon; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + TSubclassOf Item; + UPROPERTY(EditAnywhere, Category = "Attachment Test") FName SocketName; @@ -53,7 +56,9 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent class APawn* POwner; TMap GroupToComponent; - + TMap GroupToItem; + + TArray WeaponHelper; public: diff --git a/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.cpp b/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.cpp new file mode 100644 index 0000000..1e691da --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponUpgradeItem.h" + + + + diff --git a/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h new file mode 100644 index 0000000..1836c4f --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "ARWeaponUpgradeItem.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class ACTIONRPGGAME_API UARWeaponUpgradeItem : public UObject +{ + GENERATED_BODY() +}; From c3147b67846370148910823c4858e52d6137f47f Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 11 Apr 2018 00:08:52 +0200 Subject: [PATCH 116/187] more prototype code for weapon mods/upgrades --- .../UI/Weapons/ARMagazineUpgradeWidget.cpp | 4 +++- .../UI/Weapons/ARMagazineUpgradeWidget.h | 2 +- .../UI/Weapons/ARUpgradeBaseWidget.h | 2 +- Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 9 +++++++-- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 16 ++++++++-------- .../Weapons/ARMagazineUpgradeItem.h | 2 +- .../Weapons/ARWeaponManagerComponent.cpp | 17 ++++++----------- .../Weapons/ARWeaponPawnManagerComponent.cpp | 2 +- 8 files changed, 28 insertions(+), 26 deletions(-) diff --git a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp index 5ee82ed..c83f6d7 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp +++ b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp @@ -1,11 +1,13 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARMagazineUpgradeWidget.h" - +#include "Weapons/ARWeaponManagerComponent.h" +#include "Weapons/ARItemWeapon.h" FReply UARMagazineUpgradeWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { + WeaponManager->WeaponToModify->AddMagazineUpgrade(WeaponUpgrade); return FReply::Unhandled(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h index dff1dcc..6920324 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h @@ -16,6 +16,6 @@ class ACTIONRPGGAME_API UARMagazineUpgradeWidget : public UARUpgradeBaseWidget public: UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UImage* Icon; - + TSoftClassPtr WeaponUpgrade; virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h index 0643b5a..5a36e02 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h +++ b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h @@ -14,7 +14,7 @@ class ACTIONRPGGAME_API UARUpgradeBaseWidget : public UARWeaponBaseWidget { GENERATED_BODY() public: - TSoftClassPtr WeaponUpgrade; + }; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 2b3596d..9b2757c 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -1,9 +1,14 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARItemWeapon.h" +#include "Weapons/ARMagazineUpgradeItem.h" - - +void UARItemWeapon::AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade) +{ + TSubclassOf clas = InMagazineUpgrade.LoadSynchronous(); + MagazineEffect = clas->GetDefaultObject()->UpgradeEffect.LoadSynchronous(); + OnMagazineUpdateAdded(); +} void UARItemWeapon::OnMagazineUpdateAdded() { diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index b4e160d..ea38612 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "UObject/NoExportTypes.h" +#include "Effects/GAGameEffect.h" #include "GameplayTags.h" #include "ARItemWeapon.generated.h" @@ -16,7 +17,7 @@ class ACTIONRPGGAME_API UARItemWeapon : public UObject GENERATED_BODY() public: UPROPERTY(EditAnywhere, Category = "Ability") - TSoftClassPtr Ability; + TSoftClassPtr Ability; UPROPERTY(EditAnywhere, Category = "Visual") TSoftClassPtr Weapon; @@ -31,13 +32,12 @@ class ACTIONRPGGAME_API UARItemWeapon : public UObject UPROPERTY(EditAnywhere, Category = "Transforms") FRotator EquipedRotation; - /* Wrap it later into it's own item. */ - UPROPERTY(EditAnywhere, Category = "Upgrades") - TSoftClassPtr MagazineUpgrade; + UPROPERTY(EditAnywhere, Category = "Ability") + UARWeaponAbilityBase* AbilityInstance; + + FAFPropertytHandle MagazineEffect; + FGAEffectHandle MagazineEffectHandle; - void AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade) - { - MagazineUpgrade = InMagazineUpgrade; - } + void AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade); void OnMagazineUpdateAdded(); }; diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h index c06c516..624e38b 100644 --- a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h @@ -18,5 +18,5 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem UTexture2D* Icon; UPROPERTY(EditAnywhere) - TSoftClassPtr UpgradeEffect; + TSoftClassPtr UpgradeEffect; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 051f36f..557b923 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -96,10 +96,11 @@ void UARWeaponManagerComponent::BP_AddWeaponToManager(EAMGroup Group, EAMSlot Sl void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) { AARCharacter* Character = Cast(POwner); + UARItemWeapon* Item = DuplicateObject(WeaponClasses[Idx].GetDefaultObject(), Character); if (Character) { - Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()); - EquipedWeapons[AMEnumToInt(Group)] = WeaponClasses[Idx].GetDefaultObject(); + Character->GetWeapons()->Holster(Group, Item); + EquipedWeapons[AMEnumToInt(Group)] = Item; ActiveGroup = EAMGroup::Group005; } NativeEquipAbility(WeaponClasses[Idx].GetDefaultObject()->Ability, @@ -119,8 +120,8 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (!ABInt) return; - Character->GetWeapons()->Holster(Group, WeaponClasses[Idx].GetDefaultObject()); - EquipedWeapons[AMEnumToInt(Group)] = WeaponClasses[Idx].GetDefaultObject(); + Character->GetWeapons()->Holster(Group, Item); + EquipedWeapons[AMEnumToInt(Group)] = Item; ActiveGroup = EAMGroup::Group005; } @@ -416,13 +417,7 @@ void UARWeaponManagerComponent::OnAbilityReady(TSoftClassPtr InA , const TArray& InAbilityInput , EAMGroup InGroup, EAMSlot InSlot) { - /*UAFAbilityComponent* AbilityComponent = GetAbilityComponent(); - if (!AbilityComponent) - return; - - UGAAbilityBase* Ability = Cast(AbilityComponent->BP_GetAbilityByTag(InAbilityTag)); - SetAbility(InGroup, EAMSlot::Slot001, Ability); - SetAbilityTag(InGroup, EAMSlot::Slot001, InAbilityTag);*/ + EquipedWeapons[AMEnumToInt(InGroup)]->AbilityInstance = Cast(GetAbility(InGroup, InSlot)); } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp index d308cc3..dbb06cd 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp @@ -143,7 +143,7 @@ void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, class UARItemWeapon* SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); if (Group == EAMGroup::Group001) { - Character->WeaponRightItem = DuplicateObject(InWeapon, Character); + Character->WeaponRightItem = InWeapon; } } } From f38c914b4c1661935a7ffeffdaf0e2116e8a294b Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 12 Apr 2018 00:05:12 +0200 Subject: [PATCH 117/187] ARG-33 base inventory --- ActionRPGGame.uproject | 354 +++++++++--------- .../InventoryFramework.uplugin | 23 ++ .../InventoryFramework.Build.cs | 55 +++ .../Private/IFInventoryComponent.cpp | 182 +++++++++ .../Private/IFItemActorBase.cpp | 27 ++ .../InventoryFramework/Private/IFItemBase.cpp | 7 + .../Private/InventoryFramework.cpp | 20 + .../Public/IFInventoryComponent.h | 174 +++++++++ .../Public/IFItemActorBase.h | 28 ++ .../InventoryFramework/Public/IFItemBase.h | 28 ++ .../Public/InventoryFramework.h | 15 + Source/ActionRPGGame/ARCharacter.cpp | 3 +- Source/ActionRPGGame/ARCharacter.h | 4 + Source/ActionRPGGame/ARPlayerController.cpp | 10 +- Source/ActionRPGGame/ARPlayerController.h | 6 + Source/ActionRPGGame/ActionRPGGame.Build.cs | 3 +- 16 files changed, 761 insertions(+), 178 deletions(-) create mode 100644 Plugins/InventoryFramework/InventoryFramework.uplugin create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/InventoryFramework.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 3fe96b4..2d29322 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -11,7 +11,8 @@ "AdditionalDependencies": [ "AbilityFramework", "AbilityFrameworkDebugger", - "AbilityManager", + "AbilityManager", + "InventoryFramework", "Engine", "AIModule", "UMG", @@ -24,181 +25,186 @@ "Name": "ActionRPGGameEditor", "Type": "Editor", "LoadingPhase": "Default", - "AdditionalDependencies": [ - "AbilityFramework", - "AbilityFrameworkEditor", - "AbilityFrameworkDebugger", - "AbilityManager", - "Engine", - "AIModule", - "UMG", - "CoreUObject" - ] - } - ], - "Plugins": [ - { - "Name": "ActorSequence", - "Enabled": true - }, - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "AbilityFrameworkDebugger", - "Enabled": true - }, - { - "Name": "AbilityManager", - "Enabled": true - }, - { - "Name": "ActorSequenceEditor", - "Enabled": true - }, - { - "Name": "ImagePlate", - "Enabled": true - }, - { - "Name": "PerformanceMonitor", - "Enabled": true - }, - { - "Name": "OnlineSubsystemAmazon", - "Enabled": true - }, - { - "Name": "OnlineFramework", - "Enabled": true - }, - { - "Name": "SteamVR", - "Enabled": false - }, - { - "Name": "OculusVR", - "Enabled": false - }, - { - "Name": "Niagara", - "Enabled": true - }, - { - "Name": "SoundUtilities", - "Enabled": true - }, - { - "Name": "SoundVisualizations", - "Enabled": true - }, - { - "Name": "BlueprintStats", - "Enabled": true - }, - { - "Name": "LocationServicesBPLibrary", - "Enabled": false - }, - { - "Name": "WindowsDeviceProfileSelector", - "Enabled": true - }, - { - "Name": "AndroidDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "IOSDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "AndroidMedia", - "Enabled": false - }, - { - "Name": "MobileLauncherProfileWizard", - "Enabled": false - }, - { - "Name": "MobilePatchingUtils", - "Enabled": false - }, - { - "Name": "AndroidMoviePlayer", - "Enabled": false - }, - { - "Name": "AppleMoviePlayer", - "Enabled": false - }, - { - "Name": "GoogleCloudMessaging", - "Enabled": false - }, - { - "Name": "OnlineSubsystemIOS", - "Enabled": false, - "SupportedTargetPlatforms": [ - "IOS", - "TVOS" - ] - }, - { - "Name": "OnlineSubsystemGooglePlay", - "Enabled": false, - "SupportedTargetPlatforms": [ - "Android" - ] - }, - { - "Name": "ApexDestruction", - "Enabled": true - }, - { - "Name": "AndroidPermission", - "Enabled": false - }, - { - "Name": "AppleARKit", - "Enabled": false - }, - { - "Name": "GLTFImporter", - "Enabled": true - }, - { - "Name": "SteamAudio", - "Enabled": true - }, - { - "Name": "ResonanceAudio", - "Enabled": false - }, - { - "Name": "CodeView", - "Enabled": true - }, - { - "Name": "SignificanceManager", - "Enabled": true - }, - { - "Name": "CustomAnimNode", - "Enabled": true, - "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" - }, - { - "Name": "Substance", - "Enabled": true, - "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" - }, - { - "Name": "LiveLink", - "Enabled": true + "AdditionalDependencies": [ + "AbilityFramework", + "AbilityFrameworkEditor", + "AbilityFrameworkDebugger", + "AbilityManager", + "InventoryFramework", + "Engine", + "AIModule", + "UMG", + "CoreUObject" + ] } ], + "Plugins": [ + { + "Name": "ActorSequence", + "Enabled": true + }, + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "AbilityFrameworkDebugger", + "Enabled": true + }, + { + "Name": "AbilityManager", + "Enabled": true + }, + { + "Name": "InventoryFramework", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false + }, + { + "Name": "Niagara", + "Enabled": true + }, + { + "Name": "SoundUtilities", + "Enabled": true + }, + { + "Name": "SoundVisualizations", + "Enabled": true + }, + { + "Name": "BlueprintStats", + "Enabled": true + }, + { + "Name": "LocationServicesBPLibrary", + "Enabled": false + }, + { + "Name": "WindowsDeviceProfileSelector", + "Enabled": true + }, + { + "Name": "AndroidDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "IOSDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "AndroidMedia", + "Enabled": false + }, + { + "Name": "MobileLauncherProfileWizard", + "Enabled": false + }, + { + "Name": "MobilePatchingUtils", + "Enabled": false + }, + { + "Name": "AndroidMoviePlayer", + "Enabled": false + }, + { + "Name": "AppleMoviePlayer", + "Enabled": false + }, + { + "Name": "GoogleCloudMessaging", + "Enabled": false + }, + { + "Name": "OnlineSubsystemIOS", + "Enabled": false, + "SupportedTargetPlatforms": [ + "IOS", + "TVOS" + ] + }, + { + "Name": "OnlineSubsystemGooglePlay", + "Enabled": false, + "SupportedTargetPlatforms": [ + "Android" + ] + }, + { + "Name": "ApexDestruction", + "Enabled": true + }, + { + "Name": "AndroidPermission", + "Enabled": false + }, + { + "Name": "AppleARKit", + "Enabled": false + }, + { + "Name": "GLTFImporter", + "Enabled": true + }, + { + "Name": "SteamAudio", + "Enabled": true + }, + { + "Name": "ResonanceAudio", + "Enabled": false + }, + { + "Name": "CodeView", + "Enabled": true + }, + { + "Name": "SignificanceManager", + "Enabled": true + }, + { + "Name": "CustomAnimNode", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" + }, + { + "Name": "Substance", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" + }, + { + "Name": "LiveLink", + "Enabled": true + } + ], "TargetPlatforms": [ "LinuxNoEditor", "WindowsNoEditor" diff --git a/Plugins/InventoryFramework/InventoryFramework.uplugin b/Plugins/InventoryFramework/InventoryFramework.uplugin new file mode 100644 index 0000000..c8137f5 --- /dev/null +++ b/Plugins/InventoryFramework/InventoryFramework.uplugin @@ -0,0 +1,23 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "InventoryFramework", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": true, + "Installed": false, + "Modules": [ + { + "Name": "InventoryFramework", + "Type": "Developer", + "LoadingPhase": "Default" + } + ] +} \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs new file mode 100644 index 0000000..4debc05 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs @@ -0,0 +1,55 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class InventoryFramework : ModuleRules +{ + public InventoryFramework(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "InventoryFramework/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "InventoryFramework/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp new file mode 100644 index 0000000..80d936a --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -0,0 +1,182 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFInventoryComponent.h" + +#include "GameFramework/Actor.h" +#include "Engine/AssetManager.h" + +#include "IFItemBase.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + + +void FIFItemData::PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer) +{ + +} + +void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerializer) +{ + int32 Idx = InArraySerializer.Items.IndexOfByKey(*this); + + LocalIndex = static_cast(Idx); + const_cast(InArraySerializer).NetToLocal.Add(NetIndex, LocalIndex); + const_cast(InArraySerializer).LocalToNet.Add(LocalIndex, NetIndex); +} + +void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySerializer) +{ + int asd = 0; + if (asd) + { + + } +} + +void FIFItemContainer::AddItem(uint8 InNetIndex) +{ + uint8 LocalIndex = NetToLocal.FindRef(InNetIndex); + FIFItemData& Item = Items[LocalIndex]; + + +} +void FIFItemContainer::AddItem(class UIFItemBase* InItem, uint8 InNetIndex) +{ + uint8 LocalIndex = NetToLocal.FindRef(InNetIndex); + FIFItemData& Item = Items[LocalIndex]; + Item.Item = InItem; + MarkItemDirty(Item); +} +// Sets default values for this component's properties +UIFInventoryComponent::UIFInventoryComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + bWantsInitializeComponent = true; + bAutoActivate = true; + bAutoRegister = true; + // ... +} + + +// Called when the game starts +void UIFInventoryComponent::BeginPlay() +{ + Super::BeginPlay(); + + ENetMode NM = GetOwner()->GetNetMode(); + ENetRole NR = GetOwnerRole(); + + //Preallocate inventory items. We are not going to add/remove struct items + //but we are going to modify their internals later. + if ((NM == ENetMode::NM_DedicatedServer) + || (NM == ENetMode::NM_ListenServer) + || (NM == ENetMode::NM_Standalone)) + { + for (int32 Idx = 0; Idx < 8; Idx++) + { + FIFItemData NewItem(Idx, Idx); + + Inventory.AddData(NewItem); + } + } + /* + Further steps + 2. Load Properties from external data source (JSON); + */ + // ... + +} + + +// Called every frame +void UIFInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly replicate it to everyone + //to allow prediction for UI. + DOREPLIFETIME_CONDITION(UIFInventoryComponent, Inventory, COND_OwnerOnly); +} + +void UIFInventoryComponent::AddItemFromActor(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InLocalIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); + ServerAddItem(NetIndex); + return; + } + Inventory.AddItem(InLocalIndex); + +} +void UIFInventoryComponent::ServerAddItem_Implementation(uint8 InNetIndex) +{ + Inventory.AddItem(InNetIndex); +} +bool UIFInventoryComponent::ServerAddItem_Validate(uint8 InNetIndex) +{ + return true; +} + +void UIFInventoryComponent::AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); + ServerAddItemFromClass(Item.ToSoftObjectPath(), NetIndex); + return; + } + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); + FStreamableDelegate Delegate = FStreamableDelegate::CreateUObject(this, &UIFInventoryComponent::OnItemLoaded, Item, NetIndex); + Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); +} +void UIFInventoryComponent::ServerAddItemFromClass_Implementation(FSoftObjectPath Item, uint8 InNetIndex) +{ + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + TSoftClassPtr It(Item); + FStreamableDelegate Delegate = FStreamableDelegate::CreateUObject(this, &UIFInventoryComponent::OnItemLoaded, It, InNetIndex); + + UE_LOG(LogTemp, Warning, TEXT("ServerAddItemFromClass_Implementation %s"), *Item.ToString()); + Manager.RequestAsyncLoad(Item, Delegate); +} +bool UIFInventoryComponent::ServerAddItemFromClass_Validate(FSoftObjectPath Item, uint8 InNetIndex) +{ + return true; +} +void UIFInventoryComponent::BP_AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex) +{ + AddItemFromClass(Item, InLocalIndex); +} +void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex) +{ + TSubclassOf ItemClass = InItem.Get(); + + UIFItemBase* Item = NewObject(this, ItemClass); + Inventory.AddItem(Item, InNetIndex); + + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + Manager.Unload(InItem.ToSoftObjectPath()); +} + +bool UIFInventoryComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) +{ + bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); + for (const FIFItemData& Item : Inventory.Items) + { + if (Item.Item) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Item.Item), *Bunch, *RepFlags); + } + return WroteSomething; +} \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp new file mode 100644 index 0000000..d4018a7 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFItemActorBase.h" + + +// Sets default values +AIFItemActorBase::AIFItemActorBase() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AIFItemActorBase::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void AIFItemActorBase::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp new file mode 100644 index 0000000..8740edc --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFItemBase.h" + + + + diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp new file mode 100644 index 0000000..56055b0 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "InventoryFramework.h" + +#define LOCTEXT_NAMESPACE "FInventoryFrameworkModule" + +void FInventoryFrameworkModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FInventoryFrameworkModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FInventoryFrameworkModule, InventoryFramework) \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h new file mode 100644 index 0000000..51d2727 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -0,0 +1,174 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "IFInventoryComponent.generated.h" + + +USTRUCT() +struct FIFItemData : public FFastArraySerializerItem +{ + GENERATED_BODY() + friend class UIFInventoryComponent; + friend struct FIFItemContainer; + +protected: + UPROPERTY() + class UIFItemBase* Item; + + /* + Indexes below are used to resolve item mapping between server and client, + because there is no guarnteed order of replication. + */ + /* + Index in Array of this item on Server. + */ + UPROPERTY() + uint8 NetIndex; + + /* + LIndex in Array of this item on Client. + */ + UPROPERTY(NotReplicated) + uint8 LocalIndex; +public: + + FIFItemData() + : Item(nullptr) + , NetIndex(INDEX_NONE) + , LocalIndex(INDEX_NONE) + {} + + FIFItemData(uint8 InNetIndex, uint8 InLocalIndex) + : Item(nullptr) + , NetIndex(InNetIndex) + , LocalIndex(InLocalIndex) + {} + + /** + * Called right before deleting element during replication. + * + * @param InArraySerializer Array serializer that owns the item and has triggered the replication call + * + * NOTE: intentionally not virtual; invoked via templated code, @see FExampleItemEntry + */ + void PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer); + /** + * Called after adding and serializing a new element + * + * @param InArraySerializer Array serializer that owns the item and has triggered the replication call + * + * NOTE: intentionally not virtual; invoked via templated code, @see FExampleItemEntry + */ + void PostReplicatedAdd(const struct FIFItemContainer& InArraySerializer); + /** + * Called after updating an existing element with new data + * + * @param InArraySerializer Array serializer that owns the item and has triggered the replication call + * NOTE: intentionally not virtual; invoked via templated code, @see FExampleItemEntry + */ + void PostReplicatedChange(const struct FIFItemContainer& InArraySerializer); + + bool operator==(const FIFItemData& Right) const + { + return NetIndex == Right.NetIndex; + } +}; + +USTRUCT() +struct FIFItemContainer : public FFastArraySerializer +{ + GENERATED_BODY() + friend class UIFInventoryComponent; + UPROPERTY() + TArray Items; + + /* NetIndex, LocalIndex */ + TMap NetToLocal; + TMap LocalToNet; + +protected: + void AddData(const FIFItemData& InItem) + { + + int32 Idx = Items.Add(InItem); + MarkItemDirty(Items[Idx]); + MarkArrayDirty(); + NetToLocal.Add(InItem.NetIndex, InItem.LocalIndex); + LocalToNet.Add(InItem.LocalIndex, InItem.NetIndex); + } + uint8 GetNetIndex(uint8 LocalIndex) + { + return LocalToNet.FindRef(LocalIndex); + } + void AddItem(uint8 InNetIndex); + void AddItem(class UIFItemBase* InItem, uint8 InNetIndex); + +public: + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(Items, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FIFItemContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent +{ + GENERATED_BODY() + +protected: + UPROPERTY(Replicated) + FIFItemContainer Inventory; +public: + // Sets default values for this component's properties + UIFInventoryComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + /* + Adds new item at slot specified slot + Source - Droped item from which we will transfer item + SourceIndex - Index + */ + void AddItemFromActor(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InNetIndex); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItem(uint8 LocalIndex); + void ServerAddItem_Implementation(uint8 InNetIndex); + bool ServerAddItem_Validate(uint8 InNetIndex); + + /* Adds item from class. Realistically you should never call it on client. */ + void AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItemFromClass(const FSoftObjectPath& Item, uint8 InLocalIndex); + + void ServerAddItemFromClass_Implementation(FSoftObjectPath Item, uint8 InNetIndex); + bool ServerAddItemFromClass_Validate(FSoftObjectPath Item, uint8 InNetIndex); + UFUNCTION(BlueprintCallable, Category = "InventoryFramework") + void BP_AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); + + UFUNCTION() + void OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex); + + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; +}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h new file mode 100644 index 0000000..5b027ac --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "IFItemActorBase.generated.h" + +UCLASS() +class INVENTORYFRAMEWORK_API AIFItemActorBase : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + AIFItemActorBase(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h new file mode 100644 index 0000000..28e7559 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "IFItemBase.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType) +class INVENTORYFRAMEWORK_API UIFItemBase : public UObject +{ + GENERATED_BODY() + + bool IsNameStableForNetworking() const override + { + return false; + } + + bool IsSupportedForNetworking() const override + { + return true; + } + + +}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/InventoryFramework.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/InventoryFramework.h new file mode 100644 index 0000000..8d7df26 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/InventoryFramework.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FInventoryFrameworkModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 1f522c5..95fdb61 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -145,7 +145,8 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) WeaponEquipedMain->SetupAttachment(GetMesh(), WeaponSocket::EquipedMainWeapon); bUseControllerRotationYaw = true; - + MainInventory = CreateDefaultSubobject("MainInventory"); + MainInventory->SetIsReplicated(true); // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) } diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index da9c768..467b250 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -11,6 +11,7 @@ #include "AFAbilityInterface.h" #include "OrionInterface.h" #include "OrionAnimComponent.h" +#include "IFInventoryComponent.h" #include "ARCharacter.generated.h" UENUM(BlueprintType) @@ -135,6 +136,9 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UChildActorComponent* WeaponHolsteredSideLeft; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponEquipedMain; +public: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UIFInventoryComponent* MainInventory; public: UPROPERTY() class UARItemWeapon* WeaponRightItem; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 7df1685..babfc95 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -18,11 +18,17 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); WeaponManager = ObjectInitializer.CreateDefaultSubobject(this, "WeaponManager"); AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); - + MainInventory = ObjectInitializer.CreateDefaultSubobject(this, "MainInventory"); + MainInventory->SetIsReplicated(true); + AbilityManager->ComponentTags.Add(TEXT("AbilityManager")); bInputBount = false; } - +void AARPlayerController::BeginPlay() +{ + Super::BeginPlay(); + MainInventory->SetIsReplicated(true); +} void AARPlayerController::SetPawn(APawn* InPawn) { Super::SetPawn(InPawn); diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 5efb048..471a23d 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -5,6 +5,7 @@ #include "CoreMinimal.h" #include "GameFramework/PlayerController.h" #include "GameplayTags.h" +#include "IFInventoryComponent.h" #include "ARPlayerController.generated.h" /** @@ -23,6 +24,10 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARAbilityManagerComponent* AbilityManager; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UIFInventoryComponent* MainInventory; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputNextWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") @@ -51,6 +56,7 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController bool bInputBount; public: AARPlayerController(const FObjectInitializer& ObjectInitializer); + virtual void BeginPlay() override; virtual void SetPawn(APawn* InPawn) override; void SetupInputComponent(); diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 5646e5f..405ea0a 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -60,7 +60,8 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) //"OnlineSubsystemUtils", "ActorSequence", "AbilityManager", - "DraggableWindow" + "DraggableWindow", + "InventoryFramework" }); if (Target.Type == TargetRules.TargetType.Editor) { From d7e25f24e349c809c0ef68c73e93d3de02345843 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 12 Apr 2018 00:49:07 +0200 Subject: [PATCH 118/187] prototype item pickup from actor --- .../Private/IFInventoryComponent.cpp | 72 +++++++++++++++++-- .../Private/IFItemActorBase.cpp | 7 +- .../Public/IFInventoryComponent.h | 43 +++++++++-- .../Public/IFItemActorBase.h | 10 ++- .../InventoryFramework/Public/IFItemBase.h | 2 +- 5 files changed, 120 insertions(+), 14 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 80d936a..da56cdd 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -6,7 +6,7 @@ #include "Engine/AssetManager.h" #include "IFItemBase.h" - +#include "IFItemActorBase.h" #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" @@ -48,6 +48,18 @@ void FIFItemContainer::AddItem(class UIFItemBase* InItem, uint8 InNetIndex) Item.Item = InItem; MarkItemDirty(Item); } +void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) +{ + for (FIFItemData& Item : Items) + { + if (!Item.Item) + { + Item.Item = InItem; + MarkItemDirty(Item); + break; + } + } +} // Sets default values for this component's properties UIFInventoryComponent::UIFInventoryComponent() { @@ -65,6 +77,8 @@ UIFInventoryComponent::UIFInventoryComponent() void UIFInventoryComponent::BeginPlay() { Super::BeginPlay(); + + Inventory.IC = this; ENetMode NM = GetOwner()->GetNetMode(); ENetRole NR = GetOwnerRole(); @@ -114,21 +128,53 @@ void UIFInventoryComponent::AddItemFromActor(class AIFItemActorBase* Source if (GetOwnerRole() < ENetRole::ROLE_Authority) { uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); - ServerAddItem(NetIndex); + ServerAddItemFromActor(Source, SourceIndex, NetIndex); return; } Inventory.AddItem(InLocalIndex); } -void UIFInventoryComponent::ServerAddItem_Implementation(uint8 InNetIndex) +void UIFInventoryComponent::ServerAddItemFromActor_Implementation(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InNetIndex) { - Inventory.AddItem(InNetIndex); + TArray> Items = Source->GetAllItems(); + for (const TSoftClassPtr Item : Items) + { + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + + FStreamableDelegate Delegate = FStreamableDelegate::CreateUObject(this, &UIFInventoryComponent::OnItemLoadedFreeSlot, Item); + + Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); + } + } -bool UIFInventoryComponent::ServerAddItem_Validate(uint8 InNetIndex) +bool UIFInventoryComponent::ServerAddItemFromActor_Validate(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InNetIndex) { return true; } + +void UIFInventoryComponent::AddItemFromOtherInventory(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex) +{ + +} +void UIFInventoryComponent::ServerAddItemFromOtherInventory_Implementation(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex) +{ + +} +bool UIFInventoryComponent::ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex) +{ + return true; +} void UIFInventoryComponent::AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex) { if (GetOwnerRole() < ENetRole::ROLE_Authority) @@ -142,6 +188,12 @@ void UIFInventoryComponent::AddItemFromClass(TSoftClassPtr It FStreamableDelegate Delegate = FStreamableDelegate::CreateUObject(this, &UIFInventoryComponent::OnItemLoaded, Item, NetIndex); Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); } +void UIFInventoryComponent::BP_AddAllItemsFromActor(class AIFItemActorBase* Source) +{ + AddItemFromActor(Source, 0, 0); +} + + void UIFInventoryComponent::ServerAddItemFromClass_Implementation(FSoftObjectPath Item, uint8 InNetIndex) { FStreamableManager& Manager = UAssetManager::GetStreamableManager(); @@ -159,6 +211,16 @@ void UIFInventoryComponent::BP_AddItemFromClass(TSoftClassPtr { AddItemFromClass(Item, InLocalIndex); } +void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem) +{ + TSubclassOf ItemClass = InItem.Get(); + + UIFItemBase* Item = NewObject(this, ItemClass); + Inventory.AddItemToFreeSlot(Item); + + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + Manager.Unload(InItem.ToSoftObjectPath()); +} void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex) { TSubclassOf ItemClass = InItem.Get(); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp index d4018a7..6512ab3 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp @@ -8,7 +8,7 @@ AIFItemActorBase::AIFItemActorBase() { // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. PrimaryActorTick.bCanEverTick = true; - + bReplicates = true; } // Called when the game starts or when spawned @@ -25,3 +25,8 @@ void AIFItemActorBase::Tick(float DeltaTime) } +TArray> AIFItemActorBase::GetAllItems() +{ + Destroy(); + return Items; +} \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 51d2727..319a87c 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -6,6 +6,9 @@ #include "Components/ActorComponent.h" #include "IFInventoryComponent.generated.h" +//local index +DECLARE_MULTICAST_DELEGATE_OneParam(FIFOnItemChanged, uint8); +DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); USTRUCT() struct FIFItemData : public FFastArraySerializerItem @@ -85,6 +88,7 @@ struct FIFItemContainer : public FFastArraySerializer UPROPERTY() TArray Items; + TWeakObjectPtr IC; /* NetIndex, LocalIndex */ TMap NetToLocal; TMap LocalToNet; @@ -105,7 +109,7 @@ struct FIFItemContainer : public FFastArraySerializer } void AddItem(uint8 InNetIndex); void AddItem(class UIFItemBase* InItem, uint8 InNetIndex); - + void AddItemToFreeSlot(class UIFItemBase* InItem); public: bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { @@ -130,6 +134,10 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent protected: UPROPERTY(Replicated) FIFItemContainer Inventory; + + FIFOnItemChanged OnItemChanged; + FIFOnInventoryChanged OnInventoryChanged; + public: // Sets default values for this component's properties UIFInventoryComponent(); @@ -149,12 +157,34 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent */ void AddItemFromActor(class AIFItemActorBase* Source , uint8 SourceIndex - , uint8 InNetIndex); + , uint8 InLocalIndex); UFUNCTION(Server, Reliable, WithValidation) - void ServerAddItem(uint8 LocalIndex); - void ServerAddItem_Implementation(uint8 InNetIndex); - bool ServerAddItem_Validate(uint8 InNetIndex); + void ServerAddItemFromActor(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InLocalIndex); + void ServerAddItemFromActor_Implementation(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InNetIndex); + bool ServerAddItemFromActor_Validate(class AIFItemActorBase* Source + , uint8 SourceIndex + , uint8 InNetIndex); + UFUNCTION(BlueprintCallable, Category = "InventoryFramework") + void BP_AddAllItemsFromActor(class AIFItemActorBase* Source); + + void AddItemFromOtherInventory(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItemFromOtherInventory(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex); + void ServerAddItemFromOtherInventory_Implementation(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex); + bool ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InLocalIndex); /* Adds item from class. Realistically you should never call it on client. */ void AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); @@ -167,6 +197,9 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION(BlueprintCallable, Category = "InventoryFramework") void BP_AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); + UFUNCTION() + void OnItemLoadedFreeSlot(TSoftClassPtr InItem); + UFUNCTION() void OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h index 5b027ac..34dc04f 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h @@ -10,7 +10,11 @@ UCLASS() class INVENTORYFRAMEWORK_API AIFItemActorBase : public AActor { GENERATED_BODY() - + friend class UIFInventoryComponent; +protected: + //temp + UPROPERTY(EditAnywhere, Category = "Loot") + TArray> Items; public: // Sets default values for this actor's properties AIFItemActorBase(); @@ -23,6 +27,8 @@ class INVENTORYFRAMEWORK_API AIFItemActorBase : public AActor // Called every frame virtual void Tick(float DeltaTime) override; - +protected: + + TArray> GetAllItems(); }; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 28e7559..ff2931a 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -13,7 +13,7 @@ UCLASS(Blueprintable, BlueprintType) class INVENTORYFRAMEWORK_API UIFItemBase : public UObject { GENERATED_BODY() - +public: bool IsNameStableForNetworking() const override { return false; From 131bf2c0f07c176e909fc106e240225468a22b59 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 12 Apr 2018 22:35:53 +0200 Subject: [PATCH 119/187] added moveITem function --- .../Private/IFInventoryComponent.cpp | 77 +++++++++++++++---- .../Private/IFItemActorBase.cpp | 11 ++- .../Public/IFInventoryComponent.h | 28 ++++--- .../Public/IFItemActorBase.h | 3 + 4 files changed, 91 insertions(+), 28 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index da56cdd..0e91aba 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -60,6 +60,31 @@ void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) } } } +void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) +{ + uint8 NewLocal = NetToLocal[NewPosition]; + uint8 OldLocal = NetToLocal[OldPosition]; + + UIFItemBase* NewItem = Items[NewLocal].Item; + UIFItemBase* OldItem = Items[OldLocal].Item; + UIFItemBase* NewSlotBackup = nullptr; + + if (NewItem) + { + NewSlotBackup = DuplicateObject(NewItem, IC.Get()); + NewItem->MarkPendingKill(); + Items[NewLocal].Item = nullptr; + } + + NewItem = DuplicateObject(OldItem, IC.Get()); + OldItem->MarkPendingKill(); + OldItem = nullptr; + if (NewSlotBackup) + { + OldItem = NewSlotBackup; //duplicate ? + } + +} // Sets default values for this component's properties UIFInventoryComponent::UIFInventoryComponent() { @@ -104,7 +129,6 @@ void UIFInventoryComponent::BeginPlay() } - // Called every frame void UIFInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) { @@ -121,22 +145,48 @@ void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimePr DOREPLIFETIME_CONDITION(UIFInventoryComponent, Inventory, COND_OwnerOnly); } -void UIFInventoryComponent::AddItemFromActor(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InLocalIndex) +void UIFInventoryComponent::MoveItemInInventory(uint8 NewLocalPostion, uint8 OldLocalPositin) { if (GetOwnerRole() < ENetRole::ROLE_Authority) { - uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); - ServerAddItemFromActor(Source, SourceIndex, NetIndex); + uint8 NewNetPosition = Inventory.GetNetIndex(NewLocalPostion); + uint8 OldNetPosition = Inventory.GetNetIndex(OldLocalPositin); + + ServerMoveItemInInventory(NewNetPosition, OldNetPosition); + return; + } + uint8 NewNetPosition = Inventory.GetNetIndex(NewLocalPostion); + uint8 OldNetPosition = Inventory.GetNetIndex(OldLocalPositin); + Inventory.MoveItem(NewNetPosition, OldNetPosition); +} + +void UIFInventoryComponent::ServerMoveItemInInventory_Implementation(uint8 NewNetPostion, uint8 OldNetPositin) +{ + Inventory.MoveItem(NewNetPostion, OldNetPositin); +} +bool UIFInventoryComponent::ServerMoveItemInInventory_Validate(uint8 NewNetPostion, uint8 OldNetPositin) +{ + return true; +} + +void UIFInventoryComponent::AddAllItemsFromActor(class AIFItemActorBase* Source) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerAddAllItemsFromActor(Source); return; } - Inventory.AddItem(InLocalIndex); + TArray> Items = Source->GetAllItems(); + for (const TSoftClassPtr Item : Items) + { + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + FStreamableDelegate Delegate = FStreamableDelegate::CreateUObject(this, &UIFInventoryComponent::OnItemLoadedFreeSlot, Item); + + Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); + } } -void UIFInventoryComponent::ServerAddItemFromActor_Implementation(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InNetIndex) +void UIFInventoryComponent::ServerAddAllItemsFromActor_Implementation(class AIFItemActorBase* Source) { TArray> Items = Source->GetAllItems(); for (const TSoftClassPtr Item : Items) @@ -147,11 +197,8 @@ void UIFInventoryComponent::ServerAddItemFromActor_Implementation(class AIFItemA Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); } - } -bool UIFInventoryComponent::ServerAddItemFromActor_Validate(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InNetIndex) +bool UIFInventoryComponent::ServerAddAllItemsFromActor_Validate(class AIFItemActorBase* Sourcex) { return true; } @@ -190,7 +237,7 @@ void UIFInventoryComponent::AddItemFromClass(TSoftClassPtr It } void UIFInventoryComponent::BP_AddAllItemsFromActor(class AIFItemActorBase* Source) { - AddItemFromActor(Source, 0, 0); + AddAllItemsFromActor(Source); } diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp index 6512ab3..9401e9d 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemActorBase.cpp @@ -1,7 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "IFItemActorBase.h" - +#include "IFInventoryComponent.h" // Sets default values AIFItemActorBase::AIFItemActorBase() @@ -29,4 +29,13 @@ TArray> AIFItemActorBase::GetAllItems() { Destroy(); return Items; +} + +void AIFItemActorBase::GiveAllItemsToInstigator(class UIFInventoryComponent* Inventory) +{ + Inventory->AddAllItemsFromActor(this); +} +void AIFItemActorBase::BP_GiveAllItemsToInstigator(class UIFInventoryComponent* Inventory) +{ + GiveAllItemsToInstigator(Inventory); } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 319a87c..7d67118 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -110,6 +110,7 @@ struct FIFItemContainer : public FFastArraySerializer void AddItem(uint8 InNetIndex); void AddItem(class UIFItemBase* InItem, uint8 InNetIndex); void AddItemToFreeSlot(class UIFItemBase* InItem); + void MoveItem(uint8 NewPosition, uint8 OldPosition); public: bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { @@ -150,25 +151,28 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + /* + Move item from old position to new position. + If there was already item in new position it will be swapped with the moved item; + */ + void MoveItemInInventory(uint8 NewLocalPostion, uint8 OldLocalPositin); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerMoveItemInInventory(uint8 NewNetPostion, uint8 OldNetPositin); + void ServerMoveItemInInventory_Implementation(uint8 NewNetPostion, uint8 OldNetPositin); + bool ServerMoveItemInInventory_Validate(uint8 NewNetPostion, uint8 OldNetPositin); /* Adds new item at slot specified slot Source - Droped item from which we will transfer item SourceIndex - Index */ - void AddItemFromActor(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InLocalIndex); + void AddAllItemsFromActor(class AIFItemActorBase* Source); UFUNCTION(Server, Reliable, WithValidation) - void ServerAddItemFromActor(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InLocalIndex); - void ServerAddItemFromActor_Implementation(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InNetIndex); - bool ServerAddItemFromActor_Validate(class AIFItemActorBase* Source - , uint8 SourceIndex - , uint8 InNetIndex); + void ServerAddAllItemsFromActor(class AIFItemActorBase* Source); + void ServerAddAllItemsFromActor_Implementation(class AIFItemActorBase* Source); + bool ServerAddAllItemsFromActor_Validate(class AIFItemActorBase* Source); UFUNCTION(BlueprintCallable, Category = "InventoryFramework") void BP_AddAllItemsFromActor(class AIFItemActorBase* Source); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h index 34dc04f..2958dbf 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h @@ -31,4 +31,7 @@ class INVENTORYFRAMEWORK_API AIFItemActorBase : public AActor TArray> GetAllItems(); + void GiveAllItemsToInstigator(class UIFInventoryComponent* Inventory); + UFUNCTION(BlueprintCallable, Category = "InventoryFramework") + void BP_GiveAllItemsToInstigator(class UIFInventoryComponent* Inventory); }; From 5c62ff1b617316a51cb70c7d847e9a33422432e6 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 13 Apr 2018 02:19:18 +0200 Subject: [PATCH 120/187] working on basic inventory widgets --- .../Private/IFInventoryComponent.cpp | 24 +++++++- .../Public/IFInventoryComponent.h | 40 +++++++++++-- .../InventoryFrameworkUI.uplugin | 29 ++++++++++ .../InventoryFrameworkUI.Build.cs | 57 +++++++++++++++++++ .../Private/IFItemContainerWidget.cpp | 27 +++++++++ .../Private/IFItemWidget.cpp | 14 +++++ .../Private/InventoryFrameworkUI.cpp | 20 +++++++ .../Public/IFItemContainerWidget.h | 25 ++++++++ .../Public/IFItemWidget.h | 29 ++++++++++ .../Public/InventoryFrameworkUI.h | 15 +++++ Source/ActionRPGGame/ARCharacter.cpp | 2 - Source/ActionRPGGame/ARCharacter.h | 4 +- 12 files changed, 275 insertions(+), 11 deletions(-) create mode 100644 Plugins/InventoryFrameworkUI/InventoryFrameworkUI.uplugin create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/InventoryFrameworkUI.cpp create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h create mode 100644 Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/InventoryFrameworkUI.h diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 0e91aba..4a1f495 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -10,7 +10,10 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" - +void FIFItemData::SetOnItemChanged(FIFOnItemChangedEvent& Event) +{ + OnItemChanged = Event; +} void FIFItemData::PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer) { @@ -23,10 +26,16 @@ void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerial LocalIndex = static_cast(Idx); const_cast(InArraySerializer).NetToLocal.Add(NetIndex, LocalIndex); const_cast(InArraySerializer).LocalToNet.Add(LocalIndex, NetIndex); + if (InArraySerializer.IC->MaxSlots == (InArraySerializer.Items.Num())) + { + InArraySerializer.IC->OnInventoryReady.Broadcast(); + } } void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySerializer) { + InArraySerializer.IC->OnItemChanged.Broadcast(NetIndex, LocalIndex); + OnItemChanged.ExecuteIfBound(NetIndex, LocalIndex); int asd = 0; if (asd) { @@ -94,6 +103,8 @@ UIFInventoryComponent::UIFInventoryComponent() bWantsInitializeComponent = true; bAutoActivate = true; bAutoRegister = true; + + MaxSlots = 8; // ... } @@ -114,12 +125,13 @@ void UIFInventoryComponent::BeginPlay() || (NM == ENetMode::NM_ListenServer) || (NM == ENetMode::NM_Standalone)) { - for (int32 Idx = 0; Idx < 8; Idx++) + for (uint8 Idx = 0; Idx < MaxSlots; Idx++) { FIFItemData NewItem(Idx, Idx); Inventory.AddData(NewItem); } + OnInventoryReady.Broadcast(); } /* Further steps @@ -278,7 +290,15 @@ void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); } +FSimpleMulticastDelegate& UIFInventoryComponent::GetOnInventoryRead() +{ + return OnInventoryReady; +} +FIFOnItemChanged& UIFInventoryComponent::GetItemChangedEvent() +{ + return OnItemChanged; +} bool UIFInventoryComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) { bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 7d67118..8486812 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -6,9 +6,10 @@ #include "Components/ActorComponent.h" #include "IFInventoryComponent.generated.h" -//local index -DECLARE_MULTICAST_DELEGATE_OneParam(FIFOnItemChanged, uint8); +//NetIndex, LocalIndex +DECLARE_MULTICAST_DELEGATE_TwoParams(FIFOnItemChanged, uint8, uint8); DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); +DECLARE_DELEGATE_TwoParams(FIFOnItemChangedEvent, uint8, uint8); USTRUCT() struct FIFItemData : public FFastArraySerializerItem @@ -36,6 +37,8 @@ struct FIFItemData : public FFastArraySerializerItem */ UPROPERTY(NotReplicated) uint8 LocalIndex; + + FIFOnItemChangedEvent OnItemChanged; public: FIFItemData() @@ -49,6 +52,16 @@ struct FIFItemData : public FFastArraySerializerItem , NetIndex(InNetIndex) , LocalIndex(InLocalIndex) {} + inline uint8 GetNetIndex() const + { + return NetIndex; + } + inline uint8 GetLocalIndex() const + { + return LocalIndex; + } + + void SetOnItemChanged(FIFOnItemChangedEvent& Event); /** * Called right before deleting element during replication. @@ -131,7 +144,8 @@ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent { GENERATED_BODY() - + friend struct FIFItemContainer; + friend struct FIFItemData; protected: UPROPERTY(Replicated) FIFItemContainer Inventory; @@ -139,6 +153,12 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent FIFOnItemChanged OnItemChanged; FIFOnInventoryChanged OnInventoryChanged; + UPROPERTY(EditAnywhere, Category = "Inventory") + uint8 MaxSlots; + + /* Called when all alots are created */ + FSimpleMulticastDelegate OnInventoryReady; + public: // Sets default values for this component's properties UIFInventoryComponent(); @@ -151,7 +171,15 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + inline uint8 GetMaxSlots() + { + return MaxSlots; + } + + inline const FIFItemData& GetSlot(uint8 Idx) + { + return Inventory.Items[Idx]; + } /* Move item from old position to new position. If there was already item in new position it will be swapped with the moved item; @@ -207,5 +235,9 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION() void OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex); + FSimpleMulticastDelegate& GetOnInventoryRead(); + + FIFOnItemChanged& GetItemChangedEvent(); + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; }; diff --git a/Plugins/InventoryFrameworkUI/InventoryFrameworkUI.uplugin b/Plugins/InventoryFrameworkUI/InventoryFrameworkUI.uplugin new file mode 100644 index 0000000..d1a40fa --- /dev/null +++ b/Plugins/InventoryFrameworkUI/InventoryFrameworkUI.uplugin @@ -0,0 +1,29 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "InventoryFrameworkUI", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "InventoryFrameworkUI", + "Type": "Runtime", + "LoadingPhase": "Default" + } + ], + "Plugins": [ + { + "Name": "InventoryFramework", + "Enabled": true + } + ] +} \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs new file mode 100644 index 0000000..7025464 --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs @@ -0,0 +1,57 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class InventoryFrameworkUI : ModuleRules +{ + public InventoryFrameworkUI(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "InventoryFrameworkUI/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "InventoryFrameworkUI/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "InventoryFramework", + "UMG" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp new file mode 100644 index 0000000..cc43e46 --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFItemContainerWidget.h" +#include "IFInventoryComponent.h" +#include "IFItemWidget.h" + +void UIFItemContainerWidget::SetInventory(UIFInventoryComponent* InInventory) +{ + Inventory = InInventory; +} + +void UIFItemContainerWidget::CreateInventory() +{ + APlayerController* PC = GetOwningPlayer(); + uint8 MaxSlots = Inventory->GetMaxSlots(); + + for (uint8 Idx = 0; Idx < MaxSlots; Idx++) + { + UIFItemWidget* Widget = CreateWidget(PC, UIFItemWidget::StaticClass()); + const FIFItemData Slot = Inventory->GetSlot(Idx); + + Widget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); + + InventoryWidgets.Add(Widget); + } + +} \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp new file mode 100644 index 0000000..03b4234 --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFItemWidget.h" + + +void UIFItemWidget::OnSlotCreated(uint8 InNetIndex, uint8 InLocaIndex) +{ + +} + +void UIFItemWidget::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex) +{ + +} \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/InventoryFrameworkUI.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/InventoryFrameworkUI.cpp new file mode 100644 index 0000000..40d2c06 --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/InventoryFrameworkUI.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "InventoryFrameworkUI.h" + +#define LOCTEXT_NAMESPACE "FInventoryFrameworkUIModule" + +void FInventoryFrameworkUIModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FInventoryFrameworkUIModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FInventoryFrameworkUIModule, InventoryFrameworkUI) \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h new file mode 100644 index 0000000..897b3a8 --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "IFItemContainerWidget.generated.h" + +/** + * + */ +UCLASS() +class INVENTORYFRAMEWORKUI_API UIFItemContainerWidget : public UUserWidget +{ + GENERATED_BODY() + + TWeakObjectPtr Inventory; + + TArray InventoryWidgets; + +public: + void SetInventory(UIFInventoryComponent* InInventory); + + void CreateInventory(); +}; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h new file mode 100644 index 0000000..db75392 --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "IFItemWidget.generated.h" + +/** + * + */ +UCLASS() +class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget +{ + GENERATED_BODY() + friend class UIFItemContainerWidget; +protected: + /* + Those indexes correponds to the client copy of items; + */ + UPROPERTY() + uint8 NetIndex; + UPROPERTY() + uint8 LocalIndex; + + void OnSlotCreated(uint8 InNetINdex, uint8 InLocaIndex); + + void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex); +}; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/InventoryFrameworkUI.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/InventoryFrameworkUI.h new file mode 100644 index 0000000..1c74e9a --- /dev/null +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/InventoryFrameworkUI.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FInventoryFrameworkUIModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 95fdb61..cac729d 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -145,8 +145,6 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) WeaponEquipedMain->SetupAttachment(GetMesh(), WeaponSocket::EquipedMainWeapon); bUseControllerRotationYaw = true; - MainInventory = CreateDefaultSubobject("MainInventory"); - MainInventory->SetIsReplicated(true); // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) } diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 467b250..53eaebf 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -136,9 +136,7 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UChildActorComponent* WeaponHolsteredSideLeft; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponEquipedMain; -public: - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") - class UIFInventoryComponent* MainInventory; + public: UPROPERTY() class UARItemWeapon* WeaponRightItem; From c04b9114cdc6cddae9599f961cf837e5bf05c427 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 13 Apr 2018 02:20:46 +0200 Subject: [PATCH 121/187] selectable item widget class --- .../InventoryFrameworkUI/Private/IFItemContainerWidget.cpp | 2 +- .../Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h | 3 +++ 2 files changed, 4 insertions(+), 1 deletion(-) diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp index cc43e46..a5806ac 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp @@ -16,7 +16,7 @@ void UIFItemContainerWidget::CreateInventory() for (uint8 Idx = 0; Idx < MaxSlots; Idx++) { - UIFItemWidget* Widget = CreateWidget(PC, UIFItemWidget::StaticClass()); + UIFItemWidget* Widget = CreateWidget(PC, ItemClass); const FIFItemData Slot = Inventory->GetSlot(Idx); Widget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h index 897b3a8..378d17d 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h @@ -18,6 +18,9 @@ class INVENTORYFRAMEWORKUI_API UIFItemContainerWidget : public UUserWidget TArray InventoryWidgets; + UPROPERTY(EditAnywhere, CAtegory = "Widgets") + TSubclassOf ItemClass; + public: void SetInventory(UIFInventoryComponent* InInventory); From 45b82764e7346929b424376d1d32bfa9b04bfa81 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 13 Apr 2018 19:47:56 +0200 Subject: [PATCH 122/187] added OrionAnimation module (it doesn't really do anything) --- Plugins/OrionAnimation/OrionAnimation.uplugin | 31 + .../AnimNode_BlendLocomotionFour.cpp | 548 ++++++++++++++++++ .../AnimNode_BlendLocomotionFour.h | 146 +++++ .../OrionAnimation/OrionAnimComponent.cpp | 34 ++ .../OrionAnimation/OrionAnimComponent.h | 29 + .../OrionAnimation/OrionAnimation.Build.cs | 57 ++ .../Source/OrionAnimation/OrionAnimation.cpp | 20 + .../Source/OrionAnimation/OrionAnimation.h | 15 + .../Source/OrionAnimation/OrionInterface.cpp | 6 + .../Source/OrionAnimation/OrionInterface.h | 42 ++ .../AnimGraphNode_BlendLocomotionFour.cpp | 130 +++++ .../AnimGraphNode_BlendLocomotionFour.h | 35 ++ .../OrionAnimationEditor.Build.cs | 59 ++ .../OrionAnimationEditor.cpp | 20 + .../OrionAnimationEditor.h | 15 + 15 files changed, 1187 insertions(+) create mode 100644 Plugins/OrionAnimation/OrionAnimation.uplugin create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h diff --git a/Plugins/OrionAnimation/OrionAnimation.uplugin b/Plugins/OrionAnimation/OrionAnimation.uplugin new file mode 100644 index 0000000..8cdc53a --- /dev/null +++ b/Plugins/OrionAnimation/OrionAnimation.uplugin @@ -0,0 +1,31 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "OrionAnimation", + "Description": "", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "OrionAnimation", + "Type": "Runtime", + "LoadingPhase": "PreDefault" + }, + { + "Name": "OrionAnimationEditor", + "Type": "Editor", + "LoadingPhase": "PreDefault", + "WhitelistPlatforms": [ + "Win64" + ] + } + ] +} \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp new file mode 100644 index 0000000..33f85b1 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp @@ -0,0 +1,548 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "AnimNode_BlendLocomotionFour.h" +#include "AnimationRuntime.h" +#include "GameFramework/CharacterMovementComponent.h" +#include "GameFramework/Character.h" +#include "Animation/AnimClassInterface.h" +#include "Animation/AnimInstanceProxy.h" +#include "Animation/BlendProfile.h" +#include "DrawDebugHelpers.h" + +#include "Engine.h" +///////////////////////////////////////////////////// +// FAnimNode_BlendLocomotionFour +FString FDirToString(EFCardinalDirection Dir) +{ + switch (Dir) + { + case EFCardinalDirection::N: + return "N"; + case EFCardinalDirection::E: + return "E"; + case EFCardinalDirection::S: + return "S"; + case EFCardinalDirection::W: + return "W"; + default: + break; + } + return "Invalid"; +} +void FAnimNode_BlendLocomotionFour::Initialize_AnyThread(const FAnimationInitializeContext& Context) +{ + FAnimNode_Base::Initialize_AnyThread(Context); + + UAnimInstance* AnimInst = Cast(Context.AnimInstanceProxy->GetAnimInstanceObject()); + Character = Cast(AnimInst->TryGetPawnOwner()); + if (!Character) + return; + + CMC = Character->GetCharacterMovement(); + + if (!CMC) + return; + + const int NumPoses = BlendPose.Num(); + checkSlow(BlendTime.Num() == NumPoses); + + BlendWeights.Reset(NumPoses); + PosesToEvaluate.Reset(NumPoses); + if (NumPoses > 0) + { + // If we have at least 1 pose we initialize to full weight on + // the first pose + BlendWeights.AddZeroed(NumPoses); + BlendWeights[0] = 1.0f; + + PosesToEvaluate.Add(0); + + for (int32 ChildIndex = 0; ChildIndex < NumPoses; ++ChildIndex) + { + BlendPose[ChildIndex].Initialize(Context); + } + } + + RemainingBlendTimes.Empty(NumPoses); + RemainingBlendTimes.AddZeroed(NumPoses); + Blends.Empty(NumPoses); + Blends.AddZeroed(NumPoses); + + LastActiveChildIndex = INDEX_NONE; + + for (int32 i = 0; i < Blends.Num(); ++i) + { + FAlphaBlend& Blend = Blends[i]; + + Blend.SetBlendTime(0.0f); + Blend.SetBlendOption(BlendType); + Blend.SetCustomCurve(CustomBlendCurve); + } + Blends[0].SetAlpha(1.0f); + + if (BlendProfile) + { + // Initialise per-bone data + PerBoneSampleData.Empty(NumPoses); + PerBoneSampleData.AddZeroed(NumPoses); + + for (int32 Idx = 0; Idx < NumPoses; ++Idx) + { + FBlendSampleData& SampleData = PerBoneSampleData[Idx]; + SampleData.SampleDataIndex = Idx; + SampleData.PerBoneBlendData.AddZeroed(BlendProfile->GetNumBlendEntries()); + } + } +} + +void FAnimNode_BlendLocomotionFour::CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) +{ + for (int32 ChildIndex = 0; ChildIndexGetActorRightVector(); + FVector Forward = Character->GetActorForwardVector(); + + FTransform Transform = Character->GetTransform(); + FVector CurrentAcceleration = CMC->GetCurrentAcceleration(); + FVector CurrentVelocity = CMC->Velocity; + + FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal2D(); + FVector VelocityDirection = CurrentVelocity.GetSafeNormal2D(); + + FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); + FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); + + float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); + int32 Dir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; + DotBlendTime = FMath::Abs(FVector::DotProduct(LocalVelocity, LocalAcceleration)); + BlendTime[0] = DotBlendTime; + BlendTime[1] = DotBlendTime; + BlendTime[2] = DotBlendTime; + BlendTime[3] = DotBlendTime; + + NDot = FMath::RoundToInt(FVector::DotProduct(Forward, VelocityDirection)); + EDot = FMath::RoundToInt(FVector::DotProduct(Right, VelocityDirection)); + + const int NumPoses = BlendPose.Num(); + checkSlow((BlendTime.Num() == NumPoses) && (BlendWeights.Num() == NumPoses)); + + PosesToEvaluate.Empty(NumPoses); + + if (NumPoses > 0) + { + // Handle a change in the active child index; adjusting the target weights + const int32 ChildIndex = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4;; + + if (ChildIndex != LastActiveChildIndex) + { + bool LastChildIndexIsInvalid = (LastActiveChildIndex == INDEX_NONE); + + const float CurrentWeight = BlendWeights[ChildIndex]; + const float DesiredWeight = 1.0f; + const float WeightDifference = FMath::Clamp(FMath::Abs(DesiredWeight - CurrentWeight), 0.0f, 1.0f); + + // scale by the weight difference since we want always consistency: + // - if you're moving from 0 to full weight 1, it will use the normal blend time + // - if you're moving from 0.5 to full weight 1, it will get there in half the time + const float RemainingBlendTime = LastChildIndexIsInvalid ? 0.0f : (BlendTime[ChildIndex] * WeightDifference); + + for (int32 i = 0; i < RemainingBlendTimes.Num(); ++i) + { + RemainingBlendTimes[i] = RemainingBlendTime; + } + + // If we have a valid previous child and we're instantly blending - update that pose with zero weight + if (RemainingBlendTime == 0.0f && !LastChildIndexIsInvalid) + { + BlendPose[LastActiveChildIndex].Update(Context.FractionalWeight(0.0f)); + } + + for (int32 i = 0; i < Blends.Num(); ++i) + { + FAlphaBlend& Blend = Blends[i]; + + Blend.SetBlendTime(RemainingBlendTime); + + if (i == ChildIndex) + { + Blend.SetValueRange(BlendWeights[i], 1.0f); + } + else + { + Blend.SetValueRange(BlendWeights[i], 0.0f); + } + } + + // when this flag is true, we'll reinitialize the children + if (bResetChildOnActivation) + { + FAnimationInitializeContext ReinitializeContext(Context.AnimInstanceProxy); + + // reinitialize + BlendPose[ChildIndex].Initialize(ReinitializeContext); + } + + LastActiveChildIndex = ChildIndex; + } + + // Advance the weights + //@TODO: This means we advance even in a frame where the target weights/times just got modified; is that desirable? + float SumWeight = 0.0f; + for (int32 i = 0; i < Blends.Num(); ++i) + { + float& BlendWeight = BlendWeights[i]; + + FAlphaBlend& Blend = Blends[i]; + Blend.Update(Context.GetDeltaTime()); + BlendWeight = Blend.GetBlendedValue(); + + SumWeight += BlendWeight; + } + + // Renormalize the weights + if ((SumWeight > ZERO_ANIMWEIGHT_THRESH) && (FMath::Abs(SumWeight - 1.0f) > ZERO_ANIMWEIGHT_THRESH)) + { + float ReciprocalSum = 1.0f / SumWeight; + for (int32 i = 0; i < BlendWeights.Num(); ++i) + { + BlendWeights[i] *= ReciprocalSum; + } + } + + // Update our active children + for (int32 i = 0; i < BlendPose.Num(); ++i) + { + const float BlendWeight = BlendWeights[i]; + if (BlendWeight > ZERO_ANIMWEIGHT_THRESH) + { + BlendPose[i].Update(Context.FractionalWeight(BlendWeight)); + PosesToEvaluate.Add(i); + } + } + + // If we're using a blend profile, extract the scales and build blend sample data + if (BlendProfile) + { + for (int32 i = 0; i < BlendPose.Num(); ++i) + { + // Update Per-Bone Info + const float BlendWeight = BlendWeights[i]; + FBlendSampleData& PoseSampleData = PerBoneSampleData[i]; + PoseSampleData.TotalWeight = BlendWeight; + + for (int32 j = 0; j < PoseSampleData.PerBoneBlendData.Num(); ++j) + { + float& BoneBlend = PoseSampleData.PerBoneBlendData[j]; + float WeightScale = BlendProfile->GetEntryBlendScale(j); + + if (ChildIndex != i) + { + WeightScale = 1.0f / WeightScale; + } + + BoneBlend = BlendWeight * WeightScale; + } + } + + FBlendSampleData::NormalizeDataWeight(PerBoneSampleData); + } + } + + + switch (Dir) + { + case EFCardinalDirection::N: + { + FQuat ForwardQuat = FQuat::FindBetween(Forward, CurrentVelocity); + OrientN = FRotator(ForwardQuat).Yaw; + CurrentOrient = OrientN;// + //if (NDot == EDot) + /*{ + NorthPose.Update(Context.FractionalWeight(DotBlendTime)); + EastPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); + }*/ + /*else + { + NorthPose.Update(Context); + }*/ + + break; + } + case EFCardinalDirection::E: + { + FQuat LeftQuat = FQuat::FindBetween(Right, CurrentVelocity); + OrientE = FRotator(LeftQuat).Yaw; + CurrentOrient = OrientE; + //if (NDot == EDot) + /*{ + NorthPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); + EastPose.Update(Context.FractionalWeight(DotBlendTime)); + }*/ + /*else + { + EastPose.Update(Context); + }*/ + + // FMath::FInterpConstantTo(OldOrient, OrientE, DeltaTime, 300.0f); + break; + } + case EFCardinalDirection::S: + { + FQuat BackQuat = FQuat::FindBetween(Forward*(-1), CurrentVelocity); + OrientS = FRotator(BackQuat).Yaw; + CurrentOrient = OrientS; + break; + } + case EFCardinalDirection::W: + { + FQuat RightQuat = FQuat::FindBetween(Right*(-1), CurrentVelocity); + OrientW = FRotator(RightQuat).Yaw; + CurrentOrient = OrientW;// FMath::FInterpConstantTo(OldOrient, OrientW, DeltaTime, 300.0f); + break; + } + default: + break; + } + +} + +void FAnimNode_BlendLocomotionFour::Evaluate_AnyThread(FPoseContext& Output) +{ + ANIM_MT_SCOPE_CYCLE_COUNTER(BlendPosesInGraph, !IsInGameThread()); + { + //BlendPose[CurrentPose].Evaluate(Output); + } + const int32 NumPoses = PosesToEvaluate.Num(); + if ((NDot == EDot) && (NumPoses > 0) && (BlendPose.Num() == BlendWeights.Num())) + { + // Scratch arrays for evaluation, stack allocated + TArray> FilteredPoses; + TArray> FilteredCurve; + FilteredPoses.SetNum(NumPoses, false); + FilteredCurve.SetNum(NumPoses, false); + + int32 NumActivePoses = 0; + for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) + { + int32 PoseIndex = PosesToEvaluate[i]; + + FPoseContext EvaluateContext(Output); + + FPoseLink& CurrentPose = BlendPose[PoseIndex]; + CurrentPose.Evaluate(EvaluateContext); + + FilteredPoses[i].CopyBonesFrom(EvaluateContext.Pose); + FilteredCurve[i] = EvaluateContext.Curve; + } + + // Use the calculated blend sample data if we're blending per-bone + if (BlendProfile) + { + FAnimationRuntime::BlendPosesTogetherPerBone(FilteredPoses, FilteredCurve, BlendProfile, PerBoneSampleData, PosesToEvaluate, Output.Pose, Output.Curve); + } + else + { + FAnimationRuntime::BlendPosesTogether(FilteredPoses, FilteredCurve, BlendWeights, PosesToEvaluate, Output.Pose, Output.Curve); + } + + } + else + { + for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) + { + int32 PoseIndex = PosesToEvaluate[i]; + + FPoseLink& CurrentPose = BlendPose[PoseIndex]; + CurrentPose.Evaluate(Output); + + } + //Output.ResetToRefPose(); + } + + //FPoseContext EvaluateContext(Output); + //const FBoneContainer& BoneContainer = Output.AnimInstanceProxy->GetRequiredBones(); + //FComponentSpacePoseContext CSOutput(Output.AnimInstanceProxy); + //EFCardinalDirection ghf = Cast(Character)->GetCardianlDirection(); + //switch (Dir) + //{ + //case EFCardinalDirection::N: + //{ + // //if (OldDirection != Dir) + // { + // //if (NDot == EDot) + // { + // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); + + // FPoseContext Pose1(Output); + // FPoseContext Pose2(Output); + + // NorthPose.Evaluate(Pose1); + // EastPose.Evaluate(Pose2); + // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); + // + // } + // /*else + // { + // NorthPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); + // }*/ + // } + // /*else + // { + // NorthPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); + // }*/ + // break; + //} + //case EFCardinalDirection::E: + //{ + // + // //if (OldDirection != Dir) + // { + // //if (NDot == EDot) + // { + // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); + + // FPoseContext Pose1(Output); + // FPoseContext Pose2(Output); + + // NorthPose.Evaluate(Pose2); + // EastPose.Evaluate(Pose1); + // + // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); + // + // + // } + // /*else + // { + // EastPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); + // }*/ + + // } + // /*else + // { + // EastPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); + // }*/ + // break; + //} + //case EFCardinalDirection::S: + //{ + // break; + //} + //case EFCardinalDirection::W: + //{ + // break; + //} + //{ + //default: + // break; + //} + //} + +} + +void FAnimNode_BlendLocomotionFour::GatherDebugData(FNodeDebugData& DebugData) +{ + //const int32 ChildIndex = GetActiveChildIndex(); + + //FString DebugLine = GetNodeName(DebugData); + //DebugLine += FString::Printf(TEXT("(BlendTime: %f "), DotBlendTime); + + //DebugData.AddDebugItem(DebugLine); + + //NorthPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); + //EastPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); +} + + +void FAnimNode_BlendLocomotionFour::Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient) +{ + if (!FMath::IsNearlyZero(Orient, KINDA_SMALL_NUMBER)) + { + const FRotator DeltaRotation(0.0f, Orient, 0.f); + const FQuat DeltaQuat(DeltaRotation); + const FQuat MeshToComponentQuat(FRotator::ZeroRotator); + + // Convert our rotation from Component Space to Mesh Space. + const FQuat MeshSpaceDeltaQuat = MeshToComponentQuat.Inverse() * DeltaQuat * MeshToComponentQuat; + + // Apply rotation to root bone. + FCompactPoseBoneIndex RootBoneIndex(0); + CompactPose[RootBoneIndex].SetRotation(CompactPose[RootBoneIndex].GetRotation() * DeltaQuat); + CompactPose[RootBoneIndex].NormalizeRotation(); + } + // if (IKFootRootBone.IsValidToEvaluate(BoneContainer)) + // { + // // Prepare convert Quat and BoneContainer. + // const FQuat MeshToComponentQuat(FRotator(0.f, 0.f, 0.f)); + + // CSOutput.Pose.InitPose(CompactPose); + + // //Build our desired rotation for IK root bone. + // FRotator DeltaRotation(0.0f, 0.0f, 0.f); + // switch (Settings.YawRotationAxis) + // { + // case EAxis::X: + // DeltaRotation.Roll = Orient; + // case EAxis::Y: + // DeltaRotation.Pitch = Orient; + // case EAxis::Z: + // DeltaRotation.Yaw = Orient; + // default: + // break; + // } + // const FQuat DeltaQuat(DeltaRotation); + // // Convert our rotation from Component Space to Mesh Space. + // const FQuat MeshSpaceDeltaQuat = DeltaQuat; + // // Apply rotation to IK root bone. + // FCompactPoseBoneIndex RotateBoneIndex = IKFootRootBone.GetCompactPoseIndex(BoneContainer); + // CompactPose[RotateBoneIndex].SetRotation(CompactPose[RotateBoneIndex].GetRotation() * MeshSpaceDeltaQuat); + // CompactPose[RotateBoneIndex].NormalizeRotation(); + + + // // Do the same things like IK foot root bone to pelvis, but in the reversed orientation. + // FCompactPoseBoneIndex PelvisBoneIndex(1); + // FTransform PelvisBoneTM = CSOutput.Pose.GetComponentSpaceTransform(PelvisBoneIndex); + + // const FRotator PelvisDeltaRotation(DeltaRotation.Pitch * Settings.BodyOrientationAlpha, DeltaRotation.Yaw * Settings.BodyOrientationAlpha, DeltaRotation.Roll * Settings.BodyOrientationAlpha); + // FQuat PelvisDeltaQuat(PelvisDeltaRotation); + + // //const FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse() *PelvisDeltaQuat * PelvisBoneTM.GetRotation(); + // FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse()*PelvisDeltaQuat * PelvisBoneTM.GetRotation(); + + // CompactPose[PelvisBoneIndex].ConcatenateRotation(MeshSpacePelvisDeltaQuat); + // CompactPose[PelvisBoneIndex].NormalizeRotation(); + + // // Apply rotation to spine + // if (SpineBones.Num()) + // { + // for (int32 j = 0; j < SpineBones.Num(); j++) + // { + // if (SpineBones[j].Bone.IsValidToEvaluate(BoneContainer)) + // { + // FCompactPoseBoneIndex SpineBoneIndex = SpineBones[j].Bone.GetCompactPoseIndex(BoneContainer); + // FTransform SpineBoneTM = CSOutput.Pose.GetComponentSpaceTransform(SpineBoneIndex); + // const FRotator SpineDeltaRotation((-PelvisDeltaRotation.Pitch / SpineBones.Num()), (-PelvisDeltaRotation.Yaw / SpineBones.Num()), (-PelvisDeltaRotation.Roll / SpineBones.Num())); + // const FQuat SpineDeltaQuat(SpineDeltaRotation); + // const FQuat MeshSpaceSpineDeltaQuat = SpineBoneTM.GetRotation().Inverse() * SpineDeltaQuat * SpineBoneTM.GetRotation(); + // CompactPose[SpineBoneIndex].ConcatenateRotation(MeshSpaceSpineDeltaQuat); + // CompactPose[SpineBoneIndex].NormalizeRotation(); + // //GEngine->AddOnScreenDebugMessage(-1, DeltaTime, FColor::Yellow, (FString::Printf(TEXT(" SpineDeltaQuat: %s, MeshSpaceSpineDeltaQuat: %s PelvisDeltaQuat: %s"), *SpineDeltaQuat.ToString(), *MeshSpaceSpineDeltaQuat.ToString(), *PelvisDeltaQuat.ToString()))); + // } + // } + // } + // } + //} +} diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h b/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h new file mode 100644 index 0000000..1165134 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h @@ -0,0 +1,146 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Animation/AnimationAsset.h" +#include "Animation/AnimNodeBase.h" +#include "AlphaBlend.h" +#include "BoneContainer.h" +#include "OrionInterface.h" +#include "Animation/InputScaleBias.h" +#include "AnimNode_BlendLocomotionFour.generated.h" + +class UBlendProfile; +class UCurveFloat; + +enum class EECardinalDirection : uint8 +{ + N = 0, + SW = 1, + E = 2, + NW = 3, + S = 4, + NE = 5, + W = 6, + SE = 7 +}; +USTRUCT(BlueprintType) +struct FOAxisSettings +{ + GENERATED_BODY() + + UPROPERTY(EditAnywhere, Category = "FAxisSettings") + TEnumAsByte YawRotationAxis; + + UPROPERTY(EditAnywhere, Category = "FAxisSettings") + float BodyOrientationAlpha; + + FOAxisSettings() :YawRotationAxis(EAxis::Z) + , BodyOrientationAlpha(0.5f) {} +}; +USTRUCT() +struct FOBoneRef +{ + GENERATED_BODY() + + UPROPERTY(EditAnywhere, Category = "Settings") + FBoneReference Bone; +}; +// Blend list node; has many children +USTRUCT(BlueprintInternalUseOnly) +struct ORIONANIMATION_API FAnimNode_BlendLocomotionFour : public FAnimNode_Base +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, EditFixedSize, BlueprintReadWrite, Category = Links) + TArray BlendPose; + + UPROPERTY(EditAnywhere, EditFixedSize, BlueprintReadWrite, Category = Config, meta = (PinShownByDefault)) + TArray BlendTime; + + UPROPERTY(EditAnywhere, Category = BlendType) + EAlphaBlendOption BlendType; + + UPROPERTY(EditAnywhere, Category = BlendType) + UCurveFloat* CustomBlendCurve; + + UPROPERTY(EditAnywhere, Category = BlendType) + UBlendProfile* BlendProfile; + + UPROPERTY() + TArray Blends; + +protected: + UPROPERTY() + TArray BlendWeights; + + UPROPERTY() + TArray RemainingBlendTimes; + + UPROPERTY() + int32 LastActiveChildIndex; + + UPROPERTY() + TArray PerBoneSampleData; + + //Store which poses we need to evaluate + TArray PosesToEvaluate; + + /** This reinitializes child pose when re-activated. For example, when active child changes */ + UPROPERTY(EditAnywhere, Category = Option) + bool bResetChildOnActivation; + +protected: + int32 CurrentDirection; + EFCardinalDirection OldDirection; + EFCardinalDirection Dir; + float OrientN; + float OrientE; + float OrientS; + float OrientW; + float CurrentOrient; + bool bDirectionChanged; + int32 CurrentPose; + + UPROPERTY(Transient) + mutable float InternalBlendAlpha; + + UPROPERTY(Transient) + class ACharacter* Character; + + UPROPERTY(Transient) + class UCharacterMovementComponent* CMC; + + float RemainingBlendTime; + FAlphaBlend AlphaBlend; + + FAlphaBlend NorthBlend; + FAlphaBlend EastBlend; + + float DotBlendTime; + int32 NDot; + int32 EDot; +public: + FAnimNode_BlendLocomotionFour() + : LastActiveChildIndex(0) + , bResetChildOnActivation(false) + { + BlendTime.SetNum(4); + BlendPose.SetNum(4); + } + + // FAnimNode_Base interface + virtual void Initialize_AnyThread(const FAnimationInitializeContext& Context) override; + virtual void CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) override; + virtual void Update_AnyThread(const FAnimationUpdateContext& Context) override; + virtual void Evaluate_AnyThread(FPoseContext& Output) override; + virtual void GatherDebugData(FNodeDebugData& DebugData) override; + // End of FAnimNode_Base interface + +protected: + virtual int32 GetActiveChildIndex() { return 0; } + virtual FString GetNodeName(FNodeDebugData& DebugData) { return DebugData.GetNodeName(this); } + void Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient); +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp new file mode 100644 index 0000000..1cf28be --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "OrionAnimComponent.h" + + +// Sets default values for this component's properties +UOrionAnimComponent::UOrionAnimComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UOrionAnimComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UOrionAnimComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h new file mode 100644 index 0000000..93b3c69 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "OrionAnimComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ORIONANIMATION_API UOrionAnimComponent : public UActorComponent +{ + GENERATED_BODY() + +public: + // Sets default values for this component's properties + UOrionAnimComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs new file mode 100644 index 0000000..ba1d632 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs @@ -0,0 +1,57 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class OrionAnimation : ModuleRules +{ + public OrionAnimation(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "OrionAnimation/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "OrionAnimation/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "AnimationCore", + "AnimGraphRuntime" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp new file mode 100644 index 0000000..835b245 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "OrionAnimation.h" + +#define LOCTEXT_NAMESPACE "FOrionAnimationModule" + +void FOrionAnimationModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FOrionAnimationModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FOrionAnimationModule, OrionAnimation) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h new file mode 100644 index 0000000..da88bbe --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FOrionAnimationModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp new file mode 100644 index 0000000..da8cfef --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp @@ -0,0 +1,6 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "OrionInterface.h" + + +// Add default functionality here for any IOrionInterface functions that are not pure virtual. diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h b/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h new file mode 100644 index 0000000..66aee9d --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h @@ -0,0 +1,42 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/Interface.h" +#include "OrionInterface.generated.h" + +enum class EFCardinalDirection : uint8 +{ + N = 0, + E = 1, + S = 2, + W = 3 +}; + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UOrionInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class ORIONANIMATION_API IOrionInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + virtual float GetAnimOrient() { return 0; } + + virtual float GetAnimOrientN() { return 0; } + virtual float GetAnimOrientE() { return 0; } + virtual float GetAnimOrientS() { return 0; } + virtual float GetAnimOrientW() { return 0; } + + virtual EFCardinalDirection GetCardianlDirection() { return EFCardinalDirection::N; } +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp new file mode 100644 index 0000000..359a7c0 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp @@ -0,0 +1,130 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#include "AnimGraphNode_BlendLocomotionFour.h" +#include "OrionAnimationEditor.h" + +#define LOCTEXT_NAMESPACE "A3Nodes" + +UAnimGraphNode_BlendLocomotionFour::UAnimGraphNode_BlendLocomotionFour() +{ + +} + +FLinearColor UAnimGraphNode_BlendLocomotionFour::GetNodeTitleColor() const +{ + return FLinearColor(0.7f, 0.7f, 0.7f); +} + +FText UAnimGraphNode_BlendLocomotionFour::GetTooltipText() const +{ + return LOCTEXT("LocomotionFour", "Locomotion Four Direction"); +} + +FText UAnimGraphNode_BlendLocomotionFour::GetNodeTitle(ENodeTitleType::Type TitleType) const +{ + return LOCTEXT("LocomotionFour", "Locomotion Four Direction"); +} + +FString UAnimGraphNode_BlendLocomotionFour::GetNodeCategory() const +{ + return TEXT("Orion Animation"); +} +void GetPinInformation(const FString& InPinName, int32& Out_PinIndex, bool& Out_bIsPosePin, bool& Out_bIsTimePin) +{ + const int32 UnderscoreIndex = InPinName.Find(TEXT("_"), ESearchCase::CaseSensitive); + if (UnderscoreIndex != INDEX_NONE) + { + const FString ArrayName = InPinName.Left(UnderscoreIndex); + Out_PinIndex = FCString::Atoi(*(InPinName.Mid(UnderscoreIndex + 1))); + + Out_bIsPosePin = (ArrayName == TEXT("BlendPose")); + Out_bIsTimePin = (ArrayName == TEXT("BlendTime")); + } + else + { + Out_bIsPosePin = false; + Out_bIsTimePin = false; + Out_PinIndex = INDEX_NONE; + } +} +void UAnimGraphNode_BlendLocomotionFour::CustomizePinData(UEdGraphPin* Pin, FName SourcePropertyName, int32 ArrayIndex) const +{ + // if pin name starts with BlendPose or BlendWeight, change to enum name + bool bIsPosePin; + bool bIsTimePin; + int32 RawArrayIndex; + GetPinInformation(Pin->PinName.ToString(), /*out*/ RawArrayIndex, /*out*/ bIsPosePin, /*out*/ bIsTimePin); + checkSlow(RawArrayIndex == ArrayIndex); + + + if (bIsPosePin) + { + if (RawArrayIndex == 0) + { + //Pin->PinFriendlyName = FText::FromName("North Pose"); + //FFormatNamedArguments Args; + //Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); + Pin->PinFriendlyName = FText::FromString("N Pose"); + } + else if (RawArrayIndex == 1) + { + Pin->PinFriendlyName = FText::FromString("E Pose"); + } + else if (RawArrayIndex == 2) + { + Pin->PinFriendlyName = FText::FromString("S Pose"); + } + else if (RawArrayIndex == 3) + { + Pin->PinFriendlyName = FText::FromString("W Pose"); + } + } + //if (bIsPosePin || bIsTimePin) + //{ + // if (RawArrayIndex > 0) + // { + // const int32 ExposedEnumPinIndex = RawArrayIndex - 1; + + // // find pose index and see if it's mapped already or not + // if (VisibleEnumEntries.IsValidIndex(ExposedEnumPinIndex) && (BoundEnum != NULL)) + // { + // const FName& EnumElementName = VisibleEnumEntries[ExposedEnumPinIndex]; + // const int32 EnumIndex = BoundEnum->GetIndexByName(EnumElementName); + // if (EnumIndex != INDEX_NONE) + // { + // Pin->PinFriendlyName = BoundEnum->GetDisplayNameTextByIndex(EnumIndex); + // } + // else + // { + // Pin->PinFriendlyName = FText::FromName(EnumElementName); + // } + // } + // else + // { + // Pin->PinFriendlyName = LOCTEXT("InvalidIndex", "Invalid index"); + // } + // } + // else if (ensure(RawArrayIndex == 0)) + // { + // Pin->PinFriendlyName = LOCTEXT("Default", "Default"); + // } + + // // Append the pin type + // if (bIsPosePin) + // { + // FFormatNamedArguments Args; + // Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); + // Pin->PinFriendlyName = FText::Format(LOCTEXT("FriendlyNamePose", "{PinFriendlyName} Pose"), Args); + // } + + // if (bIsTimePin) + // { + // FFormatNamedArguments Args; + // Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); + // Pin->PinFriendlyName = FText::Format(LOCTEXT("FriendlyNameBlendTime", "{PinFriendlyName} Blend Time"), Args); + // } + //} +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h b/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h new file mode 100644 index 0000000..71f79fb --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h @@ -0,0 +1,35 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "AnimGraphNode_Base.h" +#include "AnimNode_BlendLocomotionFour.h" +#include "AnimGraphNode_BlendLocomotionFour.generated.h" + +struct FAnimMode_OrientationWarping; +/** +* +*/ +UCLASS() +class ORIONANIMATIONEDITOR_API UAnimGraphNode_BlendLocomotionFour : public UAnimGraphNode_Base +{ + GENERATED_BODY() + + UPROPERTY(EditAnywhere, Category = "Settings") + FAnimNode_BlendLocomotionFour Node; + + //~ Begin UEdGraphNode Interface. + virtual FLinearColor GetNodeTitleColor() const override; + virtual FText GetTooltipText() const override; + virtual FText GetNodeTitle(ENodeTitleType::Type TitleType) const override; + //~ End UEdGraphNode Interface. + + //~ Begin UAnimGraphNode_Base Interface + virtual FString GetNodeCategory() const override; + //~ End UAnimGraphNode_Base Interface + virtual void CustomizePinData(UEdGraphPin* Pin, FName SourcePropertyName, int32 ArrayIndex) const override; + UAnimGraphNode_BlendLocomotionFour(); + + +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs new file mode 100644 index 0000000..59aa1b7 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs @@ -0,0 +1,59 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +using UnrealBuildTool; + +public class OrionAnimationEditor : ModuleRules +{ + public OrionAnimationEditor(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "OrionAnimationEditor/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "OrionAnimationEditor/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + "OrionAnimation" + + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "AnimGraph", + "BlueprintGraph" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp new file mode 100644 index 0000000..05b5d7f --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp @@ -0,0 +1,20 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#include "OrionAnimationEditor.h" + +#define LOCTEXT_NAMESPACE "OrionAnimationEditorModule" + +void FOrionAnimationEditorModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FOrionAnimationEditorModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FOrionAnimationEditorModule, OrionAnimationEditor) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h new file mode 100644 index 0000000..e60cb6a --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h @@ -0,0 +1,15 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FOrionAnimationEditorModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file From aa569d2f116d6223e07714fa56d7f3208019161c Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 13 Apr 2018 23:35:07 +0200 Subject: [PATCH 123/187] created base UMG widgets for inventory, and exposed more hook from inventory --- ActionRPGGame.uproject | 4 ++ .../Private/IFInventoryComponent.cpp | 38 ++++++++++++++----- .../Public/IFInventoryComponent.h | 37 +++++++++++++++--- .../InventoryFramework/Public/IFItemBase.h | 13 ++++++- .../InventoryFrameworkUI.Build.cs | 4 +- .../Private/IFItemContainerWidget.cpp | 13 ++++++- .../Private/IFItemWidget.cpp | 38 ++++++++++++++++++- .../Public/IFItemContainerWidget.h | 13 ++++++- .../Public/IFItemWidget.h | 19 +++++++++- Source/ActionRPGGame/ARItemBase.cpp | 7 ++++ Source/ActionRPGGame/ARItemBase.h | 22 +++++++++++ Source/ActionRPGGame/ActionRPGGame.Build.cs | 3 +- Source/ActionRPGGame/UI/ARUIComponent.cpp | 8 ++++ Source/ActionRPGGame/UI/ARUIComponent.h | 8 ++++ 14 files changed, 203 insertions(+), 24 deletions(-) create mode 100644 Source/ActionRPGGame/ARItemBase.cpp create mode 100644 Source/ActionRPGGame/ARItemBase.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 2d29322..9df21fd 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -59,6 +59,10 @@ "Name": "InventoryFramework", "Enabled": true }, + { + "Name": "InventoryFrameworkUI", + "Enabled": true + }, { "Name": "ActorSequenceEditor", "Enabled": true diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 4a1f495..0f66e6d 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -65,6 +65,8 @@ void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) { Item.Item = InItem; MarkItemDirty(Item); + //should be safe to call. On server it probabaly won't do anything and on standalone/clients will update widget. + Item.OnSlotChanged(); break; } } @@ -74,23 +76,27 @@ void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) uint8 NewLocal = NetToLocal[NewPosition]; uint8 OldLocal = NetToLocal[OldPosition]; - UIFItemBase* NewItem = Items[NewLocal].Item; - UIFItemBase* OldItem = Items[OldLocal].Item; + FIFItemData& NewItem = Items[NewLocal]; + FIFItemData& OldItem = Items[OldLocal]; + if (!OldItem.Item) + { + return; + } UIFItemBase* NewSlotBackup = nullptr; - if (NewItem) + if (NewItem.Item) { - NewSlotBackup = DuplicateObject(NewItem, IC.Get()); - NewItem->MarkPendingKill(); + NewSlotBackup = DuplicateObject(NewItem.Item, IC.Get()); + NewItem.Item->MarkPendingKill(); Items[NewLocal].Item = nullptr; } - NewItem = DuplicateObject(OldItem, IC.Get()); - OldItem->MarkPendingKill(); - OldItem = nullptr; + NewItem.Item = DuplicateObject(OldItem.Item, IC.Get()); + OldItem.Item->MarkPendingKill(); + OldItem.Item = nullptr; if (NewSlotBackup) { - OldItem = NewSlotBackup; //duplicate ? + OldItem.Item = NewSlotBackup; //duplicate ? } } @@ -105,6 +111,7 @@ UIFInventoryComponent::UIFInventoryComponent() bAutoRegister = true; MaxSlots = 8; + AvailableSlots = 8; // ... } @@ -125,10 +132,15 @@ void UIFInventoryComponent::BeginPlay() || (NM == ENetMode::NM_ListenServer) || (NM == ENetMode::NM_Standalone)) { + uint8 AvailableCounter = 0; for (uint8 Idx = 0; Idx < MaxSlots; Idx++) { FIFItemData NewItem(Idx, Idx); - + if (AvailableCounter < AvailableSlots) + { + NewItem.bAvailable = true; + } + AvailableCounter++; Inventory.AddData(NewItem); } OnInventoryReady.Broadcast(); @@ -170,6 +182,12 @@ void UIFInventoryComponent::MoveItemInInventory(uint8 NewLocalPostion, uint8 Old uint8 NewNetPosition = Inventory.GetNetIndex(NewLocalPostion); uint8 OldNetPosition = Inventory.GetNetIndex(OldLocalPositin); Inventory.MoveItem(NewNetPosition, OldNetPosition); + + const FIFItemData& NewSlot = GetSlot(NewLocalPostion); + const FIFItemData& OldSlot = GetSlot(OldLocalPositin); + + NewSlot.OnSlotChanged(); + OldSlot.OnSlotChanged(); } void UIFInventoryComponent::ServerMoveItemInInventory_Implementation(uint8 NewNetPostion, uint8 OldNetPositin) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 8486812..88a9b2c 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -11,8 +11,8 @@ DECLARE_MULTICAST_DELEGATE_TwoParams(FIFOnItemChanged, uint8, uint8); DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); DECLARE_DELEGATE_TwoParams(FIFOnItemChangedEvent, uint8, uint8); -USTRUCT() -struct FIFItemData : public FFastArraySerializerItem +USTRUCT(BlueprintType) +struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem { GENERATED_BODY() friend class UIFInventoryComponent; @@ -29,15 +29,19 @@ struct FIFItemData : public FFastArraySerializerItem /* Index in Array of this item on Server. */ - UPROPERTY() + UPROPERTY(BlueprintReadOnly) uint8 NetIndex; /* LIndex in Array of this item on Client. */ - UPROPERTY(NotReplicated) + UPROPERTY(NotReplicated, BlueprintReadOnly) uint8 LocalIndex; + /* Is slot currently available */ + UPROPERTY(BlueprintReadOnly) + bool bAvailable; + FIFOnItemChangedEvent OnItemChanged; public: @@ -45,12 +49,14 @@ struct FIFItemData : public FFastArraySerializerItem : Item(nullptr) , NetIndex(INDEX_NONE) , LocalIndex(INDEX_NONE) + , bAvailable(false) {} FIFItemData(uint8 InNetIndex, uint8 InLocalIndex) : Item(nullptr) , NetIndex(InNetIndex) , LocalIndex(InLocalIndex) + , bAvailable(false) {} inline uint8 GetNetIndex() const { @@ -61,6 +67,11 @@ struct FIFItemData : public FFastArraySerializerItem return LocalIndex; } + void OnSlotChanged() const + { + OnItemChanged.ExecuteIfBound(NetIndex, LocalIndex); + } + void SetOnItemChanged(FIFOnItemChangedEvent& Event); /** @@ -94,7 +105,7 @@ struct FIFItemData : public FFastArraySerializerItem }; USTRUCT() -struct FIFItemContainer : public FFastArraySerializer +struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer { GENERATED_BODY() friend class UIFInventoryComponent; @@ -156,6 +167,12 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Inventory") uint8 MaxSlots; + /* + Currently available slots (must be smaller or equal to max slots); + */ + UPROPERTY(EditAnywhere, Category = "Inventory") + uint8 AvailableSlots; + /* Called when all alots are created */ FSimpleMulticastDelegate OnInventoryReady; @@ -180,6 +197,16 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent { return Inventory.Items[Idx]; } + + inline const UIFItemBase* GetItem(uint8 InLocalIndex) + { + return Inventory.Items[InLocalIndex].Item; + } + template + const T* GetItem(uint8 InLocalIndex) + { + return Cast(Inventory.Items[InLocalIndex].Item); + } /* Move item from old position to new position. If there was already item in new position it will be swapped with the moved item; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index ff2931a..5d759e2 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -24,5 +24,16 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject return true; } - + /* + Called after item has been added to inventory. + */ + virtual void OnItemAdded() {}; + /* + Called when item changed slots within THE SAME inventory; + */ + virtual void OnItemChanged() {}; + /* + Called after item has been removed from inventory; + */ + virtual void OnItemRemoved() {}; }; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs index 7025464..6f78497 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs @@ -36,9 +36,11 @@ public InventoryFrameworkUI(ReadOnlyTargetRules Target) : base(Target) PrivateDependencyModuleNames.AddRange( new string[] { + "Core", "CoreUObject", "Engine", - "Slate", + "InputCore", + "Slate", "SlateCore", "InventoryFramework", "UMG" diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp index a5806ac..9e81642 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp @@ -7,6 +7,7 @@ void UIFItemContainerWidget::SetInventory(UIFInventoryComponent* InInventory) { Inventory = InInventory; + Inventory->GetOnInventoryRead().AddUObject(this, &UIFItemContainerWidget::CreateInventory); } void UIFItemContainerWidget::CreateInventory() @@ -17,11 +18,21 @@ void UIFItemContainerWidget::CreateInventory() for (uint8 Idx = 0; Idx < MaxSlots; Idx++) { UIFItemWidget* Widget = CreateWidget(PC, ItemClass); - const FIFItemData Slot = Inventory->GetSlot(Idx); + Widget->Inventory = Inventory; + + const FIFItemData& Slot = Inventory->GetSlot(Idx); + + FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(Widget, &UIFItemWidget::OnItemChanged); + const_cast(Slot).SetOnItemChanged(Event); Widget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); InventoryWidgets.Add(Widget); } + NativeOnInventoryCreated(); +} +void UIFItemContainerWidget::NativeOnInventoryCreated() +{ + BP_OnInventoryCreated(); } \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp index 03b4234..74e15ea 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp @@ -1,14 +1,48 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "IFItemWidget.h" +#include "Blueprint/WidgetBlueprintLibrary.h" +#include "IFInventoryComponent.h" -void UIFItemWidget::OnSlotCreated(uint8 InNetIndex, uint8 InLocaIndex) +void UIFItemWidget::OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex) { - + NetIndex = InNetIndex; + LocalIndex = InLocalIndex; + //const UIFItemBase* Item = Inventory->GetItem(InLocalIndex); + //BP_OnItemCreated(const_cast(Item)); } void UIFItemWidget::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex) { + const UIFItemBase* Item = Inventory->GetItem(InLocalIndex); + BP_OnItemChanged(const_cast(Item)); +} + +FReply UIFItemWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) +{ + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; +} +void UIFItemWidget::NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) +{ + UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); + if (DragDropOp) + { + APlayerController* PC = GetOwningPlayer(); + + DragDropOp->Payload = this; + DragDropOp->DefaultDragVisual = DragVisual; + + OutOperation = DragDropOp; + } +} +bool UIFItemWidget::NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) +{ + UIFItemWidget* Payload = Cast(InOperation->Payload); + Inventory->MoveItemInInventory(LocalIndex, Payload->LocalIndex); + return true; } \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h index 378d17d..65a697b 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemContainerWidget.h @@ -13,10 +13,11 @@ UCLASS() class INVENTORYFRAMEWORKUI_API UIFItemContainerWidget : public UUserWidget { GENERATED_BODY() - +protected: TWeakObjectPtr Inventory; - TArray InventoryWidgets; + UPROPERTY(BlueprintReadOnly, Category = "InventoryFramework") + TArray InventoryWidgets; UPROPERTY(EditAnywhere, CAtegory = "Widgets") TSubclassOf ItemClass; @@ -25,4 +26,12 @@ class INVENTORYFRAMEWORKUI_API UIFItemContainerWidget : public UUserWidget void SetInventory(UIFInventoryComponent* InInventory); void CreateInventory(); + + /* + Called after all widgets in InvetoryWidgets array has been created. + */ + virtual void NativeOnInventoryCreated(); + + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Inventory Created")) + void BP_OnInventoryCreated(); }; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h index db75392..239643d 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -15,6 +15,7 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget GENERATED_BODY() friend class UIFItemContainerWidget; protected: + TWeakObjectPtr Inventory; /* Those indexes correponds to the client copy of items; */ @@ -23,7 +24,23 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget UPROPERTY() uint8 LocalIndex; - void OnSlotCreated(uint8 InNetINdex, uint8 InLocaIndex); + UPROPERTY(BlueprintReadWrite, Category = "InventoryFramework") + UWidget* DragVisual; + + void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex); void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex); + + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Created")) + void BP_OnItemCreated(class UIFItemBase* Item); + + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Changed")) + void BP_OnItemChanged(class UIFItemBase* Item); + + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent) override; + virtual void NativeOnDragDetected(const FGeometry& InGeometry + , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; + virtual bool NativeOnDrop(const FGeometry& InGeometry + , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; }; diff --git a/Source/ActionRPGGame/ARItemBase.cpp b/Source/ActionRPGGame/ARItemBase.cpp new file mode 100644 index 0000000..122d41c --- /dev/null +++ b/Source/ActionRPGGame/ARItemBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemBase.h" + + + + diff --git a/Source/ActionRPGGame/ARItemBase.h b/Source/ActionRPGGame/ARItemBase.h new file mode 100644 index 0000000..97a19ce --- /dev/null +++ b/Source/ActionRPGGame/ARItemBase.h @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFItemBase.h" +#include "ARItemBase.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARItemBase : public UIFItemBase +{ + GENERATED_BODY() +protected: + //obviously we want TSoftObjectPtr<> + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") + UTexture2D* Icon; + + +}; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 405ea0a..05d0442 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -61,7 +61,8 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "ActorSequence", "AbilityManager", "DraggableWindow", - "InventoryFramework" + "InventoryFramework", + "InventoryFrameworkUI" }); if (Target.Type == TargetRules.TargetType.Editor) { diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index d192e22..214b2b3 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -55,6 +55,14 @@ void UARUIComponent::BeginPlay() HUDWidget->AddToViewport(); } + if (InventoryWidgetClass) + { + InventoryWidget = CreateWidget(MyPC, InventoryWidgetClass); + InventoryWidget->SetInventory(MyPC->MainInventory); + + InventoryWidget->AddToViewport(); + } + //DrawWidget = SNew(SHorizontalBox) // +SHorizontalBox::Slot() // .HAlign(EHorizontalAlignment::HAlign_Fill) diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index bc5d93d..aa6284b 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -8,6 +8,8 @@ #include "ARHUDWidget.h" #include "SARDrawTestWidget.h" +#include "IFItemContainerWidget.h" + #include "ARUIComponent.generated.h" @@ -39,6 +41,12 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf HUDWidgetClass; + + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf InventoryWidgetClass; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets") + UIFItemContainerWidget* InventoryWidget; public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") UARHUDWidget* HUDWidget; From 7cea8e5037f6dcd2e4e53ec633aafe63dba45c38 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 13 Apr 2018 23:48:36 +0200 Subject: [PATCH 124/187] better handling for null items --- .../InventoryFrameworkUI/Private/IFItemWidget.cpp | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp index 74e15ea..11b208a 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp @@ -22,7 +22,15 @@ void UIFItemWidget::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex) FReply UIFItemWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent) { - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + const UIFItemBase* Item = Inventory->GetItem(LocalIndex); + if (Item) + { + return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; + } + else + { + return FReply::Unhandled(); + } } void UIFItemWidget::NativeOnDragDetected(const FGeometry& InGeometry , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) From 8487f91ca2412e9f9edf4f836809eba3577e57c5 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 14 Apr 2018 11:20:57 +0200 Subject: [PATCH 125/187] moving weapon manager to new Inventory system --- .../AssetTypeActions_GAAbilityBlueprint.h | 2 +- .../AssetTypeActions_GAEffectCueBlueprint.h | 2 +- .../AssetTypeActions_GAEffectBlueprint.h | 2 +- .../AMAbilityManagerComponent.cpp | 2 +- .../AMAbilityManagerComponent.h | 2 +- .../Private/IFInventoryComponent.cpp | 88 +++- .../Public/IFInventoryComponent.h | 46 +- .../InventoryFramework/Public/IFItemBase.h | 6 +- .../Private/IFItemWidget.cpp | 10 +- Source/ActionRPGGame/ARCharacter.cpp | 6 +- Source/ActionRPGGame/ARCharacter.h | 10 +- Source/ActionRPGGame/UI/ARUIComponent.cpp | 12 + Source/ActionRPGGame/UI/ARUIComponent.h | 8 + Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 8 + Source/ActionRPGGame/Weapons/ARItemWeapon.h | 7 +- .../Weapons/ARWeaponInventoryComponent.cpp | 488 ++++++++++++++++++ ...mponent.h => ARWeaponInventoryComponent.h} | 56 +- .../Weapons/ARWeaponManagerComponent.cpp | 304 ++--------- .../Weapons/ARWeaponManagerComponent.h | 42 +- .../Weapons/ARWeaponPawnManagerComponent.cpp | 216 -------- 20 files changed, 745 insertions(+), 572 deletions(-) create mode 100644 Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp rename Source/ActionRPGGame/Weapons/{ARWeaponPawnManagerComponent.h => ARWeaponInventoryComponent.h} (57%) delete mode 100644 Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h index b1762c2..78b71c1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h @@ -3,7 +3,7 @@ #include "Toolkits/IToolkitHost.h" #include "AssetTypeCategories.h" //#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" -#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_Blueprint.h" +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" class UFactory; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h index d0b4f17..55a06ad 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h @@ -3,7 +3,7 @@ #include "Toolkits/IToolkitHost.h" #include "AssetTypeCategories.h" //#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" -#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_Blueprint.h" +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" class UFactory; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h index 7f507b8..ad3cabd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h @@ -3,7 +3,7 @@ #include "Toolkits/IToolkitHost.h" #include "AssetTypeCategories.h" //#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" -#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_Blueprint.h" +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" class UFactory; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index 96d4002..c836e5f 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -88,7 +88,7 @@ void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, { AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; } -void UAMAbilityManagerComponent::NativeEquipAbility(const TSoftClassPtr& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar, bool bBindInput) +void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar, bool bBindInput) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index 8a342e5..89a0ac8 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -121,7 +121,7 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); - void NativeEquipAbility(const TSoftClassPtr& InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); + void NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); protected: virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) {}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 0f66e6d..e85b700 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -16,7 +16,8 @@ void FIFItemData::SetOnItemChanged(FIFOnItemChangedEvent& Event) } void FIFItemData::PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer) { - + if(Item) + Item->OnItemRemoved(LocalIndex); } void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerializer) @@ -30,16 +31,35 @@ void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerial { InArraySerializer.IC->OnInventoryReady.Broadcast(); } + if (Item) + { + Item->OnItemAdded(LocalIndex); + InArraySerializer.IC->OnItemAdded(Item, LocalIndex); + } } void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySerializer) { - InArraySerializer.IC->OnItemChanged.Broadcast(NetIndex, LocalIndex); + InArraySerializer.IC->OnItemChangedEvent.Broadcast(NetIndex, LocalIndex); OnItemChanged.ExecuteIfBound(NetIndex, LocalIndex); - int asd = 0; - if (asd) + if (Item) { - + switch (ChangeType) + { + case EIFChangeType::Added: + Item->OnItemAdded(LocalIndex); + InArraySerializer.IC->OnItemAdded(Item, LocalIndex); + break; + case EIFChangeType::Updated: + Item->OnItemChanged(LocalIndex); + break; + case EIFChangeType::Removed: + Item->OnItemRemoved(LocalIndex); + break; + default: + break; + } + } } @@ -55,7 +75,10 @@ void FIFItemContainer::AddItem(class UIFItemBase* InItem, uint8 InNetIndex) uint8 LocalIndex = NetToLocal.FindRef(InNetIndex); FIFItemData& Item = Items[LocalIndex]; Item.Item = InItem; + Item.ChangeType = EIFChangeType::Added; MarkItemDirty(Item); + Item.Item->OnItemAdded(LocalIndex); + IC->OnItemAdded(Item.Item, Item.LocalIndex); } void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) { @@ -67,6 +90,9 @@ void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) MarkItemDirty(Item); //should be safe to call. On server it probabaly won't do anything and on standalone/clients will update widget. Item.OnSlotChanged(); + Item.Item->OnItemAdded(Item.LocalIndex); + IC->OnItemAdded(Item.Item, Item.LocalIndex); + Item.ChangeType = EIFChangeType::Added; break; } } @@ -83,7 +109,7 @@ void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) return; } UIFItemBase* NewSlotBackup = nullptr; - + if (NewItem.Item) { NewSlotBackup = DuplicateObject(NewItem.Item, IC.Get()); @@ -98,8 +124,35 @@ void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) { OldItem.Item = NewSlotBackup; //duplicate ? } + if (NewItem.Item) + { + NewItem.Item->OnItemChanged(NewItem.LocalIndex); + NewItem.ChangeType = EIFChangeType::Updated; + } + if (OldItem.Item) + { + OldItem.Item->OnItemChanged(OldItem.LocalIndex); + OldItem.ChangeType = EIFChangeType::Updated; + } + +} +void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InNetIndex) +{ + uint8 SourceLocalIdx = Source->Inventory.NetToLocal[SourceNetIndex]; + uint8 LocalIdx = Source->Inventory.NetToLocal[InNetIndex]; + + FIFItemData& SourceItem = const_cast(Source->GetSlot(SourceLocalIdx)); + FIFItemData& LocalItem = Items[LocalIdx]; + + LocalItem.Item = DuplicateObject(SourceItem.Item, IC.Get()); + LocalItem.Item->OnItemAdded(LocalItem.LocalIndex); + IC->OnItemAdded(LocalItem.Item, LocalItem.LocalIndex); + LocalItem.OnSlotChanged(); } + // Sets default values for this component's properties UIFInventoryComponent::UIFInventoryComponent() { @@ -235,20 +288,27 @@ bool UIFInventoryComponent::ServerAddAllItemsFromActor_Validate(class AIFItemAct void UIFInventoryComponent::AddItemFromOtherInventory(class UIFInventoryComponent* Source - , uint8 SourceNetIndex + , uint8 SourceLocalIndex , uint8 InLocalIndex) { - + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + uint8 SourceNetIndex = Source->Inventory.GetNetIndex(SourceLocalIndex); + uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); + ServerAddItemFromOtherInventory(Source, SourceNetIndex, NetIndex); + return; + } + Inventory.AddFromOtherInventory(Source, SourceLocalIndex, InLocalIndex); } void UIFInventoryComponent::ServerAddItemFromOtherInventory_Implementation(class UIFInventoryComponent* Source , uint8 SourceNetIndex - , uint8 InLocalIndex) + , uint8 InNetIndex) { } bool UIFInventoryComponent::ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source , uint8 SourceNetIndex - , uint8 InLocalIndex) + , uint8 InNetIndex) { return true; } @@ -288,6 +348,12 @@ void UIFInventoryComponent::BP_AddItemFromClass(TSoftClassPtr { AddItemFromClass(Item, InLocalIndex); } + +void UIFInventoryComponent::RemoveItem(uint8 InLocalIndex) +{ + +} + void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem) { TSubclassOf ItemClass = InItem.Get(); @@ -315,7 +381,7 @@ FSimpleMulticastDelegate& UIFInventoryComponent::GetOnInventoryRead() FIFOnItemChanged& UIFInventoryComponent::GetItemChangedEvent() { - return OnItemChanged; + return OnItemChangedEvent; } bool UIFInventoryComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) { diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 88a9b2c..ab507a7 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -11,6 +11,14 @@ DECLARE_MULTICAST_DELEGATE_TwoParams(FIFOnItemChanged, uint8, uint8); DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); DECLARE_DELEGATE_TwoParams(FIFOnItemChangedEvent, uint8, uint8); +UENUM() +enum class EIFChangeType : uint8 +{ + Added, + Updated, + Removed +}; + USTRUCT(BlueprintType) struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem { @@ -40,7 +48,17 @@ struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem /* Is slot currently available */ UPROPERTY(BlueprintReadOnly) - bool bAvailable; + uint8 bAvailable:1; + + /* + Do Not set Item to nullptr instead set this item to dirty, to indicate that items has been "removed", so we have a Chance + to call OnItemRemoved() on item on clients. + */ + UPROPERTY(BlueprintReadOnly) + uint8 bDirty : 1; + + UPROPERTY() + EIFChangeType ChangeType; FIFOnItemChangedEvent OnItemChanged; public: @@ -135,6 +153,10 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer void AddItem(class UIFItemBase* InItem, uint8 InNetIndex); void AddItemToFreeSlot(class UIFItemBase* InItem); void MoveItem(uint8 NewPosition, uint8 OldPosition); + + void AddFromOtherInventory(class UIFInventoryComponent* Source + , uint8 SourceNetIndex + , uint8 InNetIndex); public: bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { @@ -161,7 +183,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UPROPERTY(Replicated) FIFItemContainer Inventory; - FIFOnItemChanged OnItemChanged; + FIFOnItemChanged OnItemChangedEvent; FIFOnInventoryChanged OnInventoryChanged; UPROPERTY(EditAnywhere, Category = "Inventory") @@ -197,13 +219,13 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent { return Inventory.Items[Idx]; } - - inline const UIFItemBase* GetItem(uint8 InLocalIndex) + + inline UIFItemBase* GetItem(uint8 InLocalIndex) { return Inventory.Items[InLocalIndex].Item; } template - const T* GetItem(uint8 InLocalIndex) + T* GetItem(uint8 InLocalIndex) { return Cast(Inventory.Items[InLocalIndex].Item); } @@ -231,6 +253,10 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION(BlueprintCallable, Category = "InventoryFramework") void BP_AddAllItemsFromActor(class AIFItemActorBase* Source); + + /* + Moves item to this inventory from the source Inventory. If item already exist it will be swapped (if possible). + */ void AddItemFromOtherInventory(class UIFInventoryComponent* Source , uint8 SourceNetIndex , uint8 InLocalIndex); @@ -240,10 +266,10 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent , uint8 InLocalIndex); void ServerAddItemFromOtherInventory_Implementation(class UIFInventoryComponent* Source , uint8 SourceNetIndex - , uint8 InLocalIndex); + , uint8 InNetIndex); bool ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source , uint8 SourceNetIndex - , uint8 InLocalIndex); + , uint8 InNetIndex); /* Adds item from class. Realistically you should never call it on client. */ void AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); @@ -256,6 +282,12 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION(BlueprintCallable, Category = "InventoryFramework") void BP_AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); + virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; + virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; + + void RemoveItem(uint8 InLocalIndex); + + UFUNCTION() void OnItemLoadedFreeSlot(TSoftClassPtr InItem); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 5d759e2..24d3095 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -27,13 +27,13 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject /* Called after item has been added to inventory. */ - virtual void OnItemAdded() {}; + virtual void OnItemAdded(uint8 LocalIndex) {}; /* Called when item changed slots within THE SAME inventory; */ - virtual void OnItemChanged() {}; + virtual void OnItemChanged(uint8 LocalIndex) {}; /* Called after item has been removed from inventory; */ - virtual void OnItemRemoved() {}; + virtual void OnItemRemoved(uint8 LocalIndex) {}; }; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp index 11b208a..cad2d6e 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp @@ -50,7 +50,13 @@ bool UIFItemWidget::NativeOnDrop(const FGeometry& InGeometry , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) { UIFItemWidget* Payload = Cast(InOperation->Payload); - - Inventory->MoveItemInInventory(LocalIndex, Payload->LocalIndex); + if (Payload->Inventory == Inventory) + { + Inventory->MoveItemInInventory(LocalIndex, Payload->LocalIndex); + } + else if (Payload->Inventory != Inventory) + { + Inventory->AddItemFromOtherInventory(Payload->Inventory.Get(), Payload->LocalIndex, LocalIndex); + } return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index cac729d..6d5047c 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -12,7 +12,7 @@ #include "Weapons/ARWeaponBase.h" -#include "Weapons/ARWeaponPawnManagerComponent.h" +#include "Weapons/ARWeaponInventoryComponent.h" #include "ARCharacterMovementComponent.h" #include "ARPlayerController.h" @@ -82,7 +82,7 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) FollowCamera->TransformUpdated.AddUObject(this, &AARCharacter::OnCameraTransformUpdate); - Weapons = CreateDefaultSubobject(TEXT("Weapons")); + Weapons2 = CreateDefaultSubobject(TEXT("Weapons2")); Head = CreateDefaultSubobject(TEXT("Head")); Head->SetupAttachment(GetMesh()); @@ -153,7 +153,7 @@ void AARCharacter::BeginPlay() { Super::BeginPlay(); - Weapons->SetPOwner(this); + Weapons2->SetPOwner(this); } FString DirToString(EFourCardinalDirection dir) diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 53eaebf..17de4a8 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -89,10 +89,10 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio class UAFAbilityComponent* Abilities; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFEffectsComponent* EffectsComponent; - +public: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) - class UARWeaponPawnManagerComponent* Weapons; - + class UARWeaponInventoryComponent* Weapons2; +protected: UPROPERTY(EditAnywhere, Category = "Default Abilities") TArray AbilitiesToGive; @@ -257,9 +257,9 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio void OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport); - inline UARWeaponPawnManagerComponent* GetWeapons() + inline UARWeaponInventoryComponent* GetWeapons() { - return Weapons; + return Weapons2; } inline UChildActorComponent* GetHolsteredRightWeapon() diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 214b2b3..88fd710 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -3,6 +3,7 @@ #include "ARUIComponent.h" #include "Blueprint/UserWidget.h" +#include "ARCharacter.h" #include "ARPlayerController.h" #include "Inventory/ARInventoryManagerWidget.h" @@ -63,6 +64,17 @@ void UARUIComponent::BeginPlay() InventoryWidget->AddToViewport(); } + if (WeaponInventoryWidgetClass) + { + WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); + if (AARCharacter* Character = Cast(MyPC->GetPawn())) + { + WeaponInventoryWidget->SetInventory(Character->Weapons2); + + WeaponInventoryWidget->AddToViewport(); + } + } + //DrawWidget = SNew(SHorizontalBox) // +SHorizontalBox::Slot() // .HAlign(EHorizontalAlignment::HAlign_Fill) diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index aa6284b..9db5a84 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -47,6 +47,14 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY(BlueprintReadOnly, Category = "Widgets") UIFItemContainerWidget* InventoryWidget; + + + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf WeaponInventoryWidgetClass; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets") + UIFItemContainerWidget* WeaponInventoryWidget; + public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") UARHUDWidget* HUDWidget; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 9b2757c..232557a 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -13,3 +13,11 @@ void UARItemWeapon::OnMagazineUpdateAdded() { } +void UARItemWeapon::OnItemAdded(uint8 LocalIndex) +{ + +} +void UARItemWeapon::OnItemRemoved(uint8 LocalIndex) +{ + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index ea38612..9739bac 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -5,6 +5,7 @@ #include "CoreMinimal.h" #include "UObject/NoExportTypes.h" #include "Effects/GAGameEffect.h" +#include "ARItemBase.h" #include "GameplayTags.h" #include "ARItemWeapon.generated.h" @@ -12,7 +13,7 @@ * */ UCLASS(Blueprintable, BlueprintType) -class ACTIONRPGGAME_API UARItemWeapon : public UObject +class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase { GENERATED_BODY() public: @@ -40,4 +41,8 @@ class ACTIONRPGGAME_API UARItemWeapon : public UObject void AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade); void OnMagazineUpdateAdded(); + + + virtual void OnItemAdded(uint8 LocalIndex) override; + virtual void OnItemRemoved(uint8 LocalIndex) override; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp new file mode 100644 index 0000000..28b901c --- /dev/null +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -0,0 +1,488 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponInventoryComponent.h" +#include "Engine/AssetManager.h" +#include "ARItemWeapon.h" +#include "ARCharacter.h" +#include "ARPlayerController.h" +#include "Weapons/ARWeaponManagerComponent.h" + +// Sets default values for this component's properties +UARWeaponInventoryComponent::UARWeaponInventoryComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + WeaponHelper.Add(&Group001HolsteredAttachment); + WeaponHelper.Add(&Group002HolsteredAttachment); + WeaponHelper.Add(&Group003HolsteredAttachment); + WeaponHelper.Add(&Group004HolsteredAttachment); + + MaxSlots = 4; + AvailableSlots = 4; + + // ... +} + + +// Called when the game starts +void UARWeaponInventoryComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + if (AARCharacter* Character = Cast(GetOwner())) + { + GroupToComponent.Add(0, Character->GetHolsteredRightWeapon()); + GroupToComponent.Add(1, Character->GetHolsteredLeftWeapon()); + GroupToComponent.Add(2, Character->GetHolsteredBackDownWeapon()); + GroupToComponent.Add(3, Character->GetHolsteredSideLeftWeapon()); + + GroupToItem.Add(EAMGroup::Group001, Character->WeaponRightItem); + GroupToItem.Add(EAMGroup::Group002, Character->WeaponLeftItem); + GroupToItem.Add(EAMGroup::Group003, Character->WeaponBackItem); + GroupToItem.Add(EAMGroup::Group004, Character->WeaponSideItem); + } +} + + +// Called every frame +void UARWeaponInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + // ... +} + +void UARWeaponInventoryComponent::SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component) +{ + if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) + { + Component->SetChildActorClass(InWeapon.Weapon.Get()); + Component->SetRelativeLocation(FVector(0, 0, 0)); + Component->SetRelativeRotation(FRotator(0, 0, 0)); + + Component->SetRelativeLocation(InWeapon.Position); + Component->SetRelativeRotation(InWeapon.Rotation); + } + else + { + FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponInventoryComponent::AsynWeaponLoaded, Component, InWeapon); + UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); + } +} + +void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) +{ + UARItemWeapon* InWeapon = Cast(Item); + //if (InOldWeapon) + //{ + // WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; + // //WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; + // //WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; + // WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; + // //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); + // SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); + //} + + MainHandWeapon.Weapon = InWeapon->Weapon; + MainHandWeapon.Position = InWeapon->EquipedPosition; + MainHandWeapon.Rotation = InWeapon->EquipedRotation; + MainHandWeapon.NetIndex = Inventory.LocalToNet[LocalIndex]; + MainHandWeapon.RepCounter++; + + WeaponHelper[LocalIndex]->Weapon.Reset(); + WeaponHelper[LocalIndex]->RepCounter++; + //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); + if (AARCharacter* Character = Cast(GetOwner())) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + FSoftObjectPath d = InWeapon->Ability.ToSoftObjectPath(); + TSoftClassPtr dd(d); + PC->WeaponManager->NativeEquipAbility(dd, AMIntToEnum(LocalIndex), EAMSlot::Slot001); + } + } + //if (!InOldWeapon) + //{ + // WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); + // WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + // //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + // SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + //} + //if (AARCharacter* Character = Cast(POwner)) + //{ + + // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + // //GroupToComponent[Group]->SetChildActorClass(nullptr); + //} +} + +void UARWeaponInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + + DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group001HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group002HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group003HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group004HolsteredAttachment, COND_SkipOwner); + DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, MainHandWeapon, COND_SkipOwner); +} + +void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon) +{ + MainHandWeapon.Weapon = InWeapon->Weapon; + MainHandWeapon.Position = InWeapon->EquipedPosition; + MainHandWeapon.Rotation = InWeapon->EquipedRotation; + MainHandWeapon.NetIndex = Inventory.LocalToNet[WeaponIndex]; + MainHandWeapon.RepCounter++; + WeaponHelper[WeaponIndex]->Weapon.Reset(); + WeaponHelper[WeaponIndex]->RepCounter++; + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + } +} +void UARWeaponInventoryComponent::EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon) +{ + //if (InOldWeapon) + //{ + // WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; + // //WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; + // //WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; + // WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; + // //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); + // SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); + //} + + //MainHandWeapon.Weapon = WeaponHelper[AMEnumToInt(Group)]->Weapon; + //MainHandWeapon.Position = InWeapon->EquipedPosition; + //MainHandWeapon.Rotation = InWeapon->EquipedRotation; + //MainHandWeapon.Group = Group; + //MainHandWeapon.RepCounter++; + + //WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); + //WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + ////GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + //SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + + //if(!InOldWeapon) + //{ + // WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); + // WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + // //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + // SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + //} + //if (AARCharacter* Character = Cast(POwner)) + //{ + // + // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + // //GroupToComponent[Group]->SetChildActorClass(nullptr); + //} +} +void UARWeaponInventoryComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) +{ + //WeaponHelper[AMEnumToInt(Group)]->Weapon = InWeapon->Weapon; + //WeaponHelper[AMEnumToInt(Group)]->Item = InWeapon->GetClass(); + //WeaponHelper[AMEnumToInt(Group)]->Position = InWeapon->HolsteredPosition; + //WeaponHelper[AMEnumToInt(Group)]->Rotation = InWeapon->HolsteredRotation; + //WeaponHelper[AMEnumToInt(Group)]->Group = Group; + //WeaponHelper[AMEnumToInt(Group)]->RepCounter++; + //if (AARCharacter* Character = Cast(POwner)) + //{ + // //Character->GetHolsteredRightWeapon()->SetSkeletalMesh(nullptr); + // SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); + // if (Group == EAMGroup::Group001) + // { + // Character->WeaponRightItem = InWeapon; + // } + //} +} +void UARWeaponInventoryComponent::HolsterActive(EAMGroup Group) +{ + //WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Weapon = MainHandWeapon.Weapon; + //WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Group = MainHandWeapon.Group; + //WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->RepCounter++; + + //MainHandWeapon.Weapon.Reset(); + //MainHandWeapon.RepCounter++; + + //if (AARCharacter* Character = Cast(POwner)) + //{ + // Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + // SetWeapon(*WeaponHelper[AMEnumToInt(MainHandWeapon.Group)], GroupToComponent[MainHandWeapon.Group]); + //} +} + +void UARWeaponInventoryComponent::NextWeapon() +{ + uint8 OldGroup = CurrentWeaponIndex; + + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + uint8 CurrentIndex = CurrentWeaponIndex; + CurrentIndex++; + if (CurrentIndex > 4) + { + CurrentWeaponIndex = 0; + } + else + { + CurrentWeaponIndex = CurrentIndex; + } + + } + + UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); + if (!NextWeaponAbility) + { + NextWeaponAbility = FindNextValid(); + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNextWeapon(CurrentWeaponIndex); + } +} +void UARWeaponInventoryComponent::PreviousWeapon() +{ + uint8 OldGroup = CurrentWeaponIndex; + + uint8 CurrentIndex = CurrentWeaponIndex; + CurrentIndex--; + CurrentWeaponIndex = CurrentIndex; + if (CurrentIndex < 0) + { + CurrentWeaponIndex = 3; + } + UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); + if (!NextWeaponAbility) + { + NextWeaponAbility = FindPreviousValid(); + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerPreviousWeapon(CurrentWeaponIndex); + } +} + +void UARWeaponInventoryComponent::HolsterWeapon() +{ + //ActiveGroup = EAMGroup::Group005; + //if (AARCharacter* Character = Cast(POwner)) + //{ + // Character->GetWeapons()->HolsterActive(ActiveGroup); + //} + //if (GetOwnerRole() < ENetRole::ROLE_Authority) + //{ + // ServerHolsterWeapon(static_cast(ActiveGroup)); + //} +} +void UARWeaponInventoryComponent::ServerHolsterWeapon_Implementation(uint8 WeaponIndex) +{ + //ActiveGroup = EAMGroup::Group005; + //if (AARCharacter* Character = Cast(POwner)) + //{ + // Character->GetWeapons()->HolsterActive(ActiveGroup); + //} +} +bool UARWeaponInventoryComponent::ServerHolsterWeapon_Validate(uint8 WeaponIndex) +{ + return true; +} +void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIndex) +{ + uint8 OldGroup = CurrentWeaponIndex; + + uint8 CurrentIndex = CurrentWeaponIndex; + //if (WeaponIndex > CurrentIndex) + CurrentIndex++; + + if (CurrentIndex > 4) + { + CurrentWeaponIndex = 0; + } + else + { + CurrentWeaponIndex = CurrentIndex; + } + + UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); + if (!NextWeaponAbility) + { + NextWeaponAbility = FindNextValid(); + } + if (WeaponIndex == CurrentWeaponIndex) + { + ClientNextWeapon(CurrentWeaponIndex, true); + } + else + { + ClientNextWeapon(CurrentWeaponIndex, false); + } +} +bool UARWeaponInventoryComponent::ServerNextWeapon_Validate(uint8 WeaponIndex) +{ + return true; +} +void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess) +{ + if (bPredictionSuccess) + return; +} + +void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 WeaponIndex) +{ + uint8 CurrentIndex = CurrentWeaponIndex; + if (CurrentIndex > WeaponIndex) + CurrentIndex--; + + if (CurrentIndex < 0) + { + CurrentWeaponIndex = 3; + } + else + { + CurrentWeaponIndex = CurrentIndex; + } + + UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); + if (!NextWeaponAbility) + { + NextWeaponAbility = FindPreviousValid(); + } + //so Server index is different. Client might tried to cheat + //or sometrhing. We will override it. + //situation where client can chage multiple weapons within second + //should not have place, as there is animation and/or internal cooldown on weapon change. + //since it will be done trough ability. + if (CurrentWeaponIndex != WeaponIndex) + { + ClientPreviousWeapon(CurrentWeaponIndex, false); + } + else + { + ClientPreviousWeapon(CurrentWeaponIndex, true); + } +} +bool UARWeaponInventoryComponent::ServerPreviousWeapon_Validate(uint8 WeaponIndex) +{ + return true; +} +void UARWeaponInventoryComponent::ClientPreviousWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess) +{ + if (bPredictionSuccess) + return; +} + + + +UARItemWeapon* UARWeaponInventoryComponent::FindNextValid() +{ + UARItemWeapon* WeaponAbilityTag = nullptr; + + uint8 Idx = CurrentWeaponIndex; + while (!WeaponAbilityTag) + { + Idx++; + if (Idx > 4 - 1) + { + Idx = 0; + } + WeaponAbilityTag = GetItem(Idx); + + //no weapon at first index, just assume there is nothing equipped. + if ((Idx == 0) && !WeaponAbilityTag) + { + break; + } + } + if (WeaponAbilityTag) + { + CurrentWeaponIndex = Idx; + } + return WeaponAbilityTag; +} + +UARItemWeapon* UARWeaponInventoryComponent::FindPreviousValid() +{ + UARItemWeapon* WeaponAbilityTag = nullptr; + uint8 Idx = CurrentWeaponIndex; + while (!WeaponAbilityTag) + { + Idx--; + if (Idx < 0) + { + Idx = 4 - 1; + } + + //again no ability for weapon. + if ((Idx == (4 - 1)) && !WeaponAbilityTag) + { + break; + } + WeaponAbilityTag = GetItem(Idx); + } + if (WeaponAbilityTag) + { + CurrentWeaponIndex = Idx; + } + return WeaponAbilityTag; +} + + +void UARWeaponInventoryComponent::OnRep_Group001HolsteredAttachment() +{ + ///if (Group001HolsteredAttachment.WeaponMesh.IsPending()) + ///{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group001HolsteredAttachment, Character->GetHolsteredRightWeapon()); + } + ///} +} +void UARWeaponInventoryComponent::OnRep_Group002HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group002HolsteredAttachment, Character->GetHolsteredLeftWeapon()); + } +} +void UARWeaponInventoryComponent::OnRep_Group003HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group003HolsteredAttachment, Character->GetHolsteredRightWeapon()); + } +} +void UARWeaponInventoryComponent::OnRep_Group004HolsteredAttachment() +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(Group004HolsteredAttachment, Character->GetHolsteredRightWeapon()); + } +} + +void UARWeaponInventoryComponent::OnRep_MainHandWeapon(FARWeapon OldWeapon) +{ + if (AARCharacter* Character = Cast(POwner)) + { + //SetWeapon(OldWeapon, GroupToComponent[OldWeapon.Group]); + SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + //GroupToComponent[MainHandWeapon.Group]->SetChildActorClass(nullptr); + } +} + +void UARWeaponInventoryComponent::AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon) +{ + Component->SetChildActorClass(InWeapon.Weapon.Get()); + + Component->SetRelativeLocation(FVector(0,0,0)); + Component->SetRelativeRotation(FRotator(0,0,0)); + + Component->SetRelativeLocation(InWeapon.Position); + Component->SetRelativeRotation(InWeapon.Rotation); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h similarity index 57% rename from Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h rename to Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index 52c28cf..5c6d4a7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -7,10 +7,10 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" - +#include "IFInventoryComponent.h" #include "AMTypes.h" -#include "ARWeaponPawnManagerComponent.generated.h" +#include "ARWeaponInventoryComponent.generated.h" USTRUCT() struct FARWeapon @@ -30,14 +30,17 @@ struct FARWeapon UPROPERTY(EditAnywhere, Category = "Attachment Test") FRotator Rotation; UPROPERTY(EditAnywhere, Category = "Attachment Test") - EAMGroup Group; + uint8 NetIndex; UPROPERTY(EditAnywhere, Category = "Attachment Test") uint8 RepCounter; }; -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent +/* + Manages currently equipped weapons (holstered and unholstered). +*/ +UCLASS( ClassGroup=(Inventory), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryComponent { GENERATED_BODY() protected: @@ -55,15 +58,17 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent UPROPERTY() class APawn* POwner; - TMap GroupToComponent; + TMap GroupToComponent; TMap GroupToItem; TArray WeaponHelper; + uint8 CurrentWeaponIndex; + public: // Sets default values for this component's properties - UARWeaponPawnManagerComponent(); + UARWeaponInventoryComponent(); protected: // Called when the game starts @@ -72,9 +77,9 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; - void Equip(EAMGroup Group, class UARItemWeapon* InWeapon); + void Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon); void EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon); void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); void HolsterActive(EAMGroup Group); @@ -82,6 +87,39 @@ class ACTIONRPGGAME_API UARWeaponPawnManagerComponent : public UActorComponent { POwner = InPawn; } + void SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility) {} + UFUNCTION(BlueprintCallable) + void NextWeapon(); + UFUNCTION(BlueprintCallable) + void PreviousWeapon(); + + UFUNCTION(BlueprintCallable) + void HolsterWeapon(); + +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerNextWeapon(uint8 WeaponIndex); + void ServerNextWeapon_Implementation(uint8 WeaponIndex); + bool ServerNextWeapon_Validate(uint8 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientNextWeapon(uint8 WeaponIndex, bool bPredictionSuccess); + void ClientNextWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerPreviousWeapon(uint8 WeaponIndex); + void ServerPreviousWeapon_Implementation(uint8 WeaponIndex); + bool ServerPreviousWeapon_Validate(uint8 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientPreviousWeapon(uint8 WeaponIndex, bool bPredictionSuccess); + void ClientPreviousWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerHolsterWeapon(uint8 WeaponIndex); + void ServerHolsterWeapon_Implementation(uint8 WeaponIndex); + bool ServerHolsterWeapon_Validate(uint8 WeaponIndex); + + UARItemWeapon* FindNextValid(); + UARItemWeapon* FindPreviousValid(); protected: void SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 557b923..55cc3a7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -79,6 +79,34 @@ void UARWeaponManagerComponent::TickComponent(float DeltaTime, ELevelTick TickTy // ... } +void UARWeaponManagerComponent::EquipWeapon(TSoftClassPtr WeaponAbility) +{ + if (!WeaponAbility.IsValid()) + { + return; + } + + TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); + UAFAbilityComponent* AbilityComp = GetAbilityComponent(); + if (!AbilityComp) + return; + + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(WeaponAbility)); + AARCharacter* Character = Cast(POwner); + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, + WeaponAbility, WeaponInput); + + AbilityComp->SetAbilityToAction(WeaponAbility, WeaponInput, ReadyDelegate); + } + else + { + AbilityComp->SetAbilityToAction(WeaponAbility, WeaponInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(WeaponAbility); + } +} UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() { return GetAbility(ActiveGroup, EAMSlot::Slot001); @@ -121,7 +149,6 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, return; Character->GetWeapons()->Holster(Group, Item); - EquipedWeapons[AMEnumToInt(Group)] = Item; ActiveGroup = EAMGroup::Group005; } @@ -135,176 +162,7 @@ bool UARWeaponManagerComponent::ServerAddWeaponToManager_Validate(EAMGroup Group return true; } -void UARWeaponManagerComponent::NextWeapon() -{ - EAMGroup OldGroup = ActiveGroup; - TSoftClassPtr CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex++; - if (CurrentIndex > MAX_WEAPONS) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - - } - - TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - if (!NextWeaponAbility.IsValid()) - { - NextWeaponAbility = FindNextValid(); - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNextWeapon(AMEnumToInt(ActiveGroup)); - } - - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility, OldGroup); -} -void UARWeaponManagerComponent::PreviousWeapon() -{ - EAMGroup OldGroup = ActiveGroup; - TSoftClassPtr CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex--; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex < 0) - { - ActiveGroup = AMIntToEnum(Groups.Num() - 1); - } - TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - if (!NextWeaponAbility.IsValid()) - { - NextWeaponAbility = FindPreviousValid(); - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerPreviousWeapon(static_cast(ActiveGroup)); - } - - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility, OldGroup); -} - -void UARWeaponManagerComponent::HolsterWeapon() -{ - ActiveGroup = EAMGroup::Group005; - if (AARCharacter* Character = Cast(POwner)) - { - Character->GetWeapons()->HolsterActive(ActiveGroup); - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerHolsterWeapon(static_cast(ActiveGroup)); - } -} - -void UARWeaponManagerComponent::ServerNextWeapon_Implementation(int32 WeaponIndex) -{ - EAMGroup OldGroup = ActiveGroup; - TSoftClassPtr CurrentWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - if(WeaponIndex > CurrentIndex) - CurrentIndex++; - - if (CurrentIndex > MAX_WEAPONS) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - - TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - if (!NextWeaponAbility.IsValid()) - { - NextWeaponAbility = FindNextValid(); - } - if (WeaponIndex == AMEnumToInt(ActiveGroup)) - { - ClientNextWeapon(AMEnumToInt(ActiveGroup), true); - } - else - { - ClientNextWeapon(AMEnumToInt(ActiveGroup), false); - } - - EquipWeapon(CurrentWeaponAbility, NextWeaponAbility, OldGroup); -} -bool UARWeaponManagerComponent::ServerNextWeapon_Validate(int32 WeaponIndex) -{ - return true; -} -void UARWeaponManagerComponent::ClientNextWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess) -{ - if (bPredictionSuccess) - return; -} - -void UARWeaponManagerComponent::ServerPreviousWeapon_Implementation(int32 WeaponIndex) -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - if(CurrentIndex > WeaponIndex) - CurrentIndex--; - - if (CurrentIndex < 0) - { - ActiveGroup = AMIntToEnum(MAX_WEAPONS - 1); - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - TSoftClassPtr NextWeaponAbility = GetAbilityTag(ActiveGroup, EAMSlot::Slot001); - if (!NextWeaponAbility.IsValid()) - { - NextWeaponAbility = FindPreviousValid(); - } - //so Server index is different. Client might tried to cheat - //or sometrhing. We will override it. - //situation where client can chage multiple weapons within second - //should not have place, as there is animation and/or internal cooldown on weapon change. - //since it will be done trough ability. - if (ActiveGroup != AMIntToEnum(WeaponIndex)) - { - ClientNextGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientNextGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UARWeaponManagerComponent::ServerPreviousWeapon_Validate(int32 WeaponIndex) -{ - return true; -} -void UARWeaponManagerComponent::ClientPreviousWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess) -{ - if (bPredictionSuccess) - return; -} - -void UARWeaponManagerComponent::ServerHolsterWeapon_Implementation(int32 WeaponIndex) -{ - ActiveGroup = EAMGroup::Group005; - if (AARCharacter* Character = Cast(POwner)) - { - Character->GetWeapons()->HolsterActive(ActiveGroup); - } -} -bool UARWeaponManagerComponent::ServerHolsterWeapon_Validate(int32 WeaponIndex) -{ - return true; -} void UARWeaponManagerComponent::OnWeaponInputRead(TSoftClassPtr WeaponAbilityTag, TArray InInputTags) { @@ -313,111 +171,17 @@ void UARWeaponManagerComponent::OnWeaponInputRead(TSoftClassPtr //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); } -void UARWeaponManagerComponent::EquipWeapon(const TSoftClassPtr& PreviousWeaponTag, const TSoftClassPtr& NextWeaponTag, EAMGroup OldGroup) -{ - if (!NextWeaponTag.IsValid()) - { - return; - } - TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); - if (!AbilityComp) - return; - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(NextWeaponTag)); - AARCharacter* Character = Cast(POwner); - if (Character) - { - Character->GetWeapons()->EquipInactive(ActiveGroup, EquipedWeapons[AMEnumToInt(ActiveGroup)] - , OldGroup - , EquipedWeapons[AMEnumToInt(OldGroup)]); - } - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, - NextWeaponTag, WeaponInput); - - AbilityComp->SetAbilityToAction(NextWeaponTag, WeaponInput, ReadyDelegate); - } - else - { - AbilityComp->SetAbilityToAction(NextWeaponTag, WeaponInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(NextWeaponTag); - } -} -TSoftClassPtr UARWeaponManagerComponent::FindNextValid() -{ - TSoftClassPtr WeaponAbilityTag; - - int32 Idx = AMEnumToInt(ActiveGroup); - while (!WeaponAbilityTag.IsValid()) - { - Idx++; - if (Idx > MAX_WEAPONS - 1) - { - Idx = 0; - } - WeaponAbilityTag = GetAbilityTag(AMIntToEnum(Idx), EAMSlot::Slot001); - - //no weapon at first index, just assume there is nothing equipped. - if ((Idx == 0) && !WeaponAbilityTag.IsValid()) - { - SelectGroup(EAMGroup::Group005); - break; - } - } - if (WeaponAbilityTag.IsValid()) - { - SelectGroup(AMIntToEnum(Idx)); - } - return WeaponAbilityTag; -} - -TSoftClassPtr UARWeaponManagerComponent::FindPreviousValid() -{ - TSoftClassPtr WeaponAbilityTag; - int32 Idx = AMEnumToInt(ActiveGroup); - while (!WeaponAbilityTag.IsValid()) - { - Idx--; - if (Idx < 0) - { - Idx = MAX_WEAPONS - 1; - } - - //again no ability for weapon. - if ((Idx == (MAX_WEAPONS - 1) ) && !WeaponAbilityTag.IsValid()) - { - SelectGroup(EAMGroup::Group005); - break; - } - WeaponAbilityTag = GetAbilityTag(AMIntToEnum(Idx), EAMSlot::Slot001); - } - if (WeaponAbilityTag.IsValid()) - { - SelectGroup(AMIntToEnum(Idx)); - } - return WeaponAbilityTag; -} - -//void UARWeaponManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -//{ -// Super::GetLifetimeReplicatedProps(OutLifetimeProps); -// -// DOREPLIFETIME(UARWeaponManagerComponent, EquippedWeapons); -//} - -bool UARWeaponManagerComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) -{ - bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); - - return WroteSomething; -} void UARWeaponManagerComponent::OnAbilityReady(TSoftClassPtr InAbilityTag , const TArray& InAbilityInput , EAMGroup InGroup, EAMSlot InSlot) { - EquipedWeapons[AMEnumToInt(InGroup)]->AbilityInstance = Cast(GetAbility(InGroup, InSlot)); + AARCharacter* Character = Cast(POwner); + if (Character) + { + UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); + Character->Weapons2->SetAbilityToItem(static_cast(InGroup), AbilityInstance); + } } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index c7b3778..6e94ce3 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -51,9 +51,6 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") TArray> MagazineUpgradesClasses; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") - TArray EquipedWeapons; - UPROPERTY(EditAnywhere, Category = "Attachment Config") FName EquipSocketName; UPROPERTY(EditAnywhere, Category = "Attachment Config") @@ -98,6 +95,8 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + void EquipWeapon(TSoftClassPtr WeaponAbility); UGAAbilityBase* GetCurrentWeapon(); UFUNCTION(BlueprintCallable, Category = "Weapon Manager") @@ -113,50 +112,13 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp virtual void ServerAddWeaponToManager_Implementation(EAMGroup Group, EAMSlot Slot, int32 Idx); bool ServerAddWeaponToManager_Validate(EAMGroup Group, EAMSlot Slot, int32 Idx); - UFUNCTION(BlueprintCallable) - void NextWeapon(); - UFUNCTION(BlueprintCallable) - void PreviousWeapon(); - - UFUNCTION(BlueprintCallable) - void HolsterWeapon(); - -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerNextWeapon(int32 WeaponIndex); - void ServerNextWeapon_Implementation(int32 WeaponIndex); - bool ServerNextWeapon_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientNextWeapon(int32 WeaponIndex, bool bPredictionSuccess); - void ClientNextWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerPreviousWeapon(int32 WeaponIndex); - void ServerPreviousWeapon_Implementation(int32 WeaponIndex); - bool ServerPreviousWeapon_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientPreviousWeapon(int32 WeaponIndex, bool bPredictionSuccess); - void ClientPreviousWeapon_Implementation(int32 WeaponIndex, bool bPredictionSuccess); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerHolsterWeapon(int32 WeaponIndex); - void ServerHolsterWeapon_Implementation(int32 WeaponIndex); - bool ServerHolsterWeapon_Validate(int32 WeaponIndex); - - UFUNCTION() void OnWeaponInputRead(TSoftClassPtr WeaponAbilityTag, TArray InInputTags); - -public: - bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; protected: virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) override; - void EquipWeapon(const TSoftClassPtr& PreviousWeaponTag, const TSoftClassPtr& NextWeaponTag, EAMGroup OldGroup); - TSoftClassPtr FindNextValid(); - TSoftClassPtr FindPreviousValid(); public: void ShowHideAbilityManager(); }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp deleted file mode 100644 index dbb06cd..0000000 --- a/Source/ActionRPGGame/Weapons/ARWeaponPawnManagerComponent.cpp +++ /dev/null @@ -1,216 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponPawnManagerComponent.h" -#include "Engine/AssetManager.h" -#include "ARItemWeapon.h" -#include "../ARCharacter.h" - -// Sets default values for this component's properties -UARWeaponPawnManagerComponent::UARWeaponPawnManagerComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - - WeaponHelper.Add(&Group001HolsteredAttachment); - WeaponHelper.Add(&Group002HolsteredAttachment); - WeaponHelper.Add(&Group003HolsteredAttachment); - WeaponHelper.Add(&Group004HolsteredAttachment); - // ... -} - - -// Called when the game starts -void UARWeaponPawnManagerComponent::BeginPlay() -{ - Super::BeginPlay(); - - // ... - if (AARCharacter* Character = Cast(GetOwner())) - { - GroupToComponent.Add(EAMGroup::Group001, Character->GetHolsteredRightWeapon()); - GroupToComponent.Add(EAMGroup::Group002, Character->GetHolsteredLeftWeapon()); - GroupToComponent.Add(EAMGroup::Group003, Character->GetHolsteredBackDownWeapon()); - GroupToComponent.Add(EAMGroup::Group004, Character->GetHolsteredSideLeftWeapon()); - - GroupToItem.Add(EAMGroup::Group001, Character->WeaponRightItem); - GroupToItem.Add(EAMGroup::Group002, Character->WeaponLeftItem); - GroupToItem.Add(EAMGroup::Group003, Character->WeaponBackItem); - GroupToItem.Add(EAMGroup::Group004, Character->WeaponSideItem); - } -} - - -// Called every frame -void UARWeaponPawnManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - // ... -} - -void UARWeaponPawnManagerComponent::SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component) -{ - if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) - { - Component->SetChildActorClass(InWeapon.Weapon.Get()); - Component->SetRelativeLocation(FVector(0, 0, 0)); - Component->SetRelativeRotation(FRotator(0, 0, 0)); - - Component->SetRelativeLocation(InWeapon.Position); - Component->SetRelativeRotation(InWeapon.Rotation); - } - else - { - FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponPawnManagerComponent::AsynWeaponLoaded, Component, InWeapon); - UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); - } -} - -void UARWeaponPawnManagerComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - - DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group001HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group002HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group003HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, Group004HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponPawnManagerComponent, MainHandWeapon, COND_SkipOwner); -} - -void UARWeaponPawnManagerComponent::Equip(EAMGroup Group, class UARItemWeapon* InWeapon) -{ - MainHandWeapon.Weapon = InWeapon->Weapon; - MainHandWeapon.Position = InWeapon->EquipedPosition; - MainHandWeapon.Rotation = InWeapon->EquipedRotation; - MainHandWeapon.Group = Group; - MainHandWeapon.RepCounter++; - WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); - WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - GroupToComponent[Group]->SetChildActorClass(nullptr); - } -} -void UARWeaponPawnManagerComponent::EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon) -{ - if (InOldWeapon) - { - WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; - //WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; - //WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; - WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; - //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); - SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); - } - - MainHandWeapon.Weapon = WeaponHelper[AMEnumToInt(Group)]->Weapon; - MainHandWeapon.Position = InWeapon->EquipedPosition; - MainHandWeapon.Rotation = InWeapon->EquipedRotation; - MainHandWeapon.Group = Group; - MainHandWeapon.RepCounter++; - - WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); - WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); - SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - - if(!InOldWeapon) - { - WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); - WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); - SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - } - if (AARCharacter* Character = Cast(POwner)) - { - - SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - //GroupToComponent[Group]->SetChildActorClass(nullptr); - } -} -void UARWeaponPawnManagerComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) -{ - WeaponHelper[AMEnumToInt(Group)]->Weapon = InWeapon->Weapon; - WeaponHelper[AMEnumToInt(Group)]->Item = InWeapon->GetClass(); - WeaponHelper[AMEnumToInt(Group)]->Position = InWeapon->HolsteredPosition; - WeaponHelper[AMEnumToInt(Group)]->Rotation = InWeapon->HolsteredRotation; - WeaponHelper[AMEnumToInt(Group)]->Group = Group; - WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - if (AARCharacter* Character = Cast(POwner)) - { - //Character->GetHolsteredRightWeapon()->SetSkeletalMesh(nullptr); - SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - if (Group == EAMGroup::Group001) - { - Character->WeaponRightItem = InWeapon; - } - } -} -void UARWeaponPawnManagerComponent::HolsterActive(EAMGroup Group) -{ - WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Weapon = MainHandWeapon.Weapon; - WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Group = MainHandWeapon.Group; - WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->RepCounter++; - - MainHandWeapon.Weapon.Reset(); - MainHandWeapon.RepCounter++; - - if (AARCharacter* Character = Cast(POwner)) - { - Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); - SetWeapon(*WeaponHelper[AMEnumToInt(MainHandWeapon.Group)], GroupToComponent[MainHandWeapon.Group]); - } -} -void UARWeaponPawnManagerComponent::OnRep_Group001HolsteredAttachment() -{ - ///if (Group001HolsteredAttachment.WeaponMesh.IsPending()) - ///{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group001HolsteredAttachment, Character->GetHolsteredRightWeapon()); - } - ///} -} -void UARWeaponPawnManagerComponent::OnRep_Group002HolsteredAttachment() -{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group002HolsteredAttachment, Character->GetHolsteredLeftWeapon()); - } -} -void UARWeaponPawnManagerComponent::OnRep_Group003HolsteredAttachment() -{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group003HolsteredAttachment, Character->GetHolsteredRightWeapon()); - } -} -void UARWeaponPawnManagerComponent::OnRep_Group004HolsteredAttachment() -{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group004HolsteredAttachment, Character->GetHolsteredRightWeapon()); - } -} - -void UARWeaponPawnManagerComponent::OnRep_MainHandWeapon(FARWeapon OldWeapon) -{ - if (AARCharacter* Character = Cast(POwner)) - { - //SetWeapon(OldWeapon, GroupToComponent[OldWeapon.Group]); - SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - //GroupToComponent[MainHandWeapon.Group]->SetChildActorClass(nullptr); - } -} - -void UARWeaponPawnManagerComponent::AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon) -{ - Component->SetChildActorClass(InWeapon.Weapon.Get()); - - Component->SetRelativeLocation(FVector(0,0,0)); - Component->SetRelativeRotation(FRotator(0,0,0)); - - Component->SetRelativeLocation(InWeapon.Position); - Component->SetRelativeRotation(InWeapon.Rotation); -} \ No newline at end of file From d814e90ffd7d7ef2b779b511389d486593f01bdf Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 14 Apr 2018 14:13:38 +0200 Subject: [PATCH 126/187] fixed compilation, and adding more missing functionality to weapons/inventory --- .../Weapons/ARWeaponInventoryComponent.cpp | 16 ++++++++++++++-- .../Weapons/ARWeaponInventoryComponent.h | 1 - .../Weapons/ARWeaponManagerComponent.cpp | 2 -- 3 files changed, 14 insertions(+), 5 deletions(-) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index 28b901c..513eab1 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -58,7 +58,7 @@ void UARWeaponInventoryComponent::SetWeapon(const FARWeapon& InWeapon, UChildAct { if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) { - Component->SetChildActorClass(InWeapon.Weapon.Get()); + Component->SetChildActorClass(InWeapon.Weapon.LoadSynchronous()); Component->SetRelativeLocation(FVector(0, 0, 0)); Component->SetRelativeRotation(FRotator(0, 0, 0)); @@ -92,6 +92,7 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde MainHandWeapon.RepCounter++; WeaponHelper[LocalIndex]->Weapon.Reset(); + WeaponHelper[LocalIndex]->Weapon = InWeapon->Weapon; WeaponHelper[LocalIndex]->RepCounter++; //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); @@ -143,6 +144,12 @@ void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* { SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + if (AARPlayerController* PC = Cast(Character->Controller)) + { + FSoftObjectPath Path = InWeapon->Ability.ToSoftObjectPath(); + TSoftClassPtr ab(Path); + PC->WeaponManager->EquipWeapon(ab); + } } } void UARWeaponInventoryComponent::EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon) @@ -234,7 +241,6 @@ void UARWeaponInventoryComponent::NextWeapon() { CurrentWeaponIndex = CurrentIndex; } - } UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); @@ -242,6 +248,7 @@ void UARWeaponInventoryComponent::NextWeapon() { NextWeaponAbility = FindNextValid(); } + Equip(CurrentWeaponIndex, NextWeaponAbility); if (GetOwnerRole() < ENetRole::ROLE_Authority) { ServerNextWeapon(CurrentWeaponIndex); @@ -315,6 +322,7 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIn { NextWeaponAbility = FindNextValid(); } + if (WeaponIndex == CurrentWeaponIndex) { ClientNextWeapon(CurrentWeaponIndex, true); @@ -332,6 +340,10 @@ void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(uint8 WeaponIn { if (bPredictionSuccess) return; + + CurrentWeaponIndex = WeaponIndex; + UARItemWeapon* NextWeaponAbility = GetItem(WeaponIndex); + Equip(WeaponIndex, NextWeaponAbility); } void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 WeaponIndex) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index 5c6d4a7..31aa59c 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -61,7 +61,6 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone TMap GroupToComponent; TMap GroupToItem; - TArray WeaponHelper; uint8 CurrentWeaponIndex; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 55cc3a7..068ffa9 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -28,7 +28,6 @@ UARWeaponManagerComponent::UARWeaponManagerComponent() void UARWeaponManagerComponent::BeginPlay() { Super::BeginPlay(); - EquipedWeapons.SetNum(MAX_WEAPONS+1); APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) return; @@ -128,7 +127,6 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (Character) { Character->GetWeapons()->Holster(Group, Item); - EquipedWeapons[AMEnumToInt(Group)] = Item; ActiveGroup = EAMGroup::Group005; } NativeEquipAbility(WeaponClasses[Idx].GetDefaultObject()->Ability, From 8083b1b92d05ae088630cbbfda23b5844e69e855 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 14 Apr 2018 14:56:02 +0200 Subject: [PATCH 127/187] removing dead code --- Source/ActionRPGGame/ARCharacter.h | 10 --- Source/ActionRPGGame/ARPlayerController.cpp | 1 - .../UI/Weapons/ARWeaponListSlotDragWidget.cpp | 63 ---------------- .../UI/Weapons/ARWeaponListSlotDragWidget.h | 38 ---------- .../UI/Weapons/ARWeaponListSlotDropWidget.cpp | 44 ------------ .../UI/Weapons/ARWeaponListSlotDropWidget.h | 31 -------- .../UI/Weapons/ARWeaponListWidget.cpp | 48 ------------- .../UI/Weapons/ARWeaponListWidget.h | 48 ------------- .../Weapons/ARWeaponInventoryComponent.cpp | 72 +------------------ .../Weapons/ARWeaponInventoryComponent.h | 4 +- .../Weapons/ARWeaponManagerComponent.cpp | 47 ------------ .../Weapons/ARWeaponManagerComponent.h | 18 ----- 12 files changed, 4 insertions(+), 420 deletions(-) delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 17de4a8..0b82229 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -136,16 +136,6 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UChildActorComponent* WeaponHolsteredSideLeft; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Weapons", meta = (AllowPrivateAccess = "true")) UChildActorComponent* WeaponEquipedMain; - -public: - UPROPERTY() - class UARItemWeapon* WeaponRightItem; - UPROPERTY() - class UARItemWeapon* WeaponLeftItem; - UPROPERTY() - class UARItemWeapon* WeaponBackItem; - UPROPERTY() - class UARItemWeapon* WeaponSideItem; public: UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") FARCameraTransform CameraTransform; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index babfc95..13fad77 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -122,7 +122,6 @@ void AARPlayerController::InputShowHideAbilityManager() } void AARPlayerController::InputShowHideInventory() { - WeaponManager->ShowHideAbilityManager(); } void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag) { diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp deleted file mode 100644 index c3a461c..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.cpp +++ /dev/null @@ -1,63 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponListSlotDragWidget.h" -#include "Blueprint/WidgetBlueprintLibrary.h" - -#include "ARAbilityDragVisual.h" -#include "Weapons/ARItemWeapon.h" -#include "Weapons/ARWeaponManagerComponent.h" - -FReply UARWeaponListSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) -{ - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; - //return FReply::Unhandled(); -} - -void UARWeaponListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) -{ - UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); - if (DragDropOp) - { - APlayerController* MyPC = Cast(WeaponManager->GetOwner()); - //UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); - //DragIcon->AbilityManager = AbilityManager; - - DragDropOp->Payload = this; - DragDropOp->DefaultDragVisual = IconImage; - - OutOperation = DragDropOp; - } -} - -void UARWeaponListSlotDragWidget::OnItemAdded() -{ - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - { - TSoftClassPtr AbilityTag = WeaponManager->WeaponClasses[WeaponIdx].GetDefaultObject()->Ability; - - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARWeaponListSlotDragWidget::OnItemLoaded, AbilityTag); - - Manager.RequestAsyncLoad(AbilityTag.ToSoftObjectPath() - , del); - } - } -} - -void UARWeaponListSlotDragWidget::OnItemLoaded(TSoftClassPtr InPrimaryAssetId) -{ - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - { - TSubclassOf AbilityClass = InPrimaryAssetId.Get(); - if (AbilityClass) - { - IconImage->SetBrushFromTexture(AbilityClass.GetDefaultObject()->UIData->Icon); - } - - { - Manager.Unload(InPrimaryAssetId.ToSoftObjectPath()); - } - } -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h deleted file mode 100644 index 9164df7..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDragWidget.h +++ /dev/null @@ -1,38 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/Weapons/ARWeaponBaseWidget.h" -#include "Components/Image.h" -#include "ARWeaponListSlotDragWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponListSlotDragWidget : public UARWeaponBaseWidget -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintReadWrite, meta=(ExposeOnSpawn), Category = "Weapon Widget") - int32 WeaponIdx; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* IconImage; - - TWeakObjectPtr WeaponList; -public: - virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) override; - virtual void NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; - - inline int32 GetWeapon() - { - return WeaponIdx; - } - void OnItemAdded(); -protected: - void OnItemLoaded(TSoftClassPtr InPrimaryAssetId); -}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp deleted file mode 100644 index 26db76d..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.cpp +++ /dev/null @@ -1,44 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponListSlotDropWidget.h" - -#include "Components/TextBlock.h" - -#include "AFAbilityComponent.h" - -#include "ARCharacter.h" -#include "ARPlayerController.h" - -#include "Weapons/ARItemWeapon.h" -#include "Weapons/ARWeaponManagerComponent.h" -#include "Weapons/ARWeaponAbilityBase.h" - -#include "ARWeaponListWidget.h" - -#include "ARWeaponListSlotDragWidget.h" - -bool UARWeaponListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - UARWeaponListSlotDragWidget* Payload = Cast(InOperation->Payload); - FSlateBrush Brush = Payload->IconImage->Brush; - - IconImage->SetBrush(Brush); - WeaponList = Payload->WeaponList; - - WeaponManager->AddWeaponToManager(WeaponSlot, EAMSlot::Slot001, Payload->GetWeapon()); - return true; -} - -FReply UARWeaponListSlotDropWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) -{ - AARPlayerController* PC = Cast(WeaponManager->GetOwner()); - - AARCharacter* Character = Cast(PC->GetPawn()); - UGAAbilityBase* WeaponAbility = WeaponManager->GetAbility(WeaponSlot, EAMSlot::Slot001); - - WeaponList->SelectedWeaponName->SetText(FText::FromString(Character->WeaponRightItem->GetName())); - WeaponManager->WeaponToModify = Character->WeaponRightItem; - - return FReply::Unhandled(); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h deleted file mode 100644 index 6f62476..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListSlotDropWidget.h +++ /dev/null @@ -1,31 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "ARWeaponBaseWidget.h" -#include "AMTypes.h" -#include "ARWeaponListSlotDropWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponListSlotDropWidget : public UARWeaponBaseWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Config") - EAMGroup WeaponSlot; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* IconImage; - - TWeakObjectPtr WeaponList; -public: - virtual bool NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; - - virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; - -}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp deleted file mode 100644 index 149113b..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.cpp +++ /dev/null @@ -1,48 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponListWidget.h" - -#include "ARPlayerController.h" -#include "ARWeaponUpgradeListWidget.h" -#include "Weapons/ARWeaponManagerComponent.h" - - - -void UARWeaponListWidget::NativePreConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - ARPC = MyPC; - WeaponManager = MyPC->WeaponManager; - } - Super::NativePreConstruct(); -} -void UARWeaponListWidget::NativeConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - ARPC = MyPC; - WeaponManager = MyPC->WeaponManager; - } - Magazine->OnClicked.AddDynamic(this, &UARWeaponListWidget::OnMagazineClicked); - Super::NativeConstruct(); -} -void UARWeaponListWidget::AddItem(TSubclassOf DragWidgetClass, int32 WeaponIdx) -{ - UARWeaponListSlotDragWidget* Item = CreateWidget(ARPC.Get(), DragWidgetClass); - Item->WeaponManager = WeaponManager; - Item->WeaponIdx = WeaponIdx; - Item->WeaponList = this; - Items.Add(Item); - Item->OnItemAdded(); - ItemContainer->AddChild(Item); -} - -void UARWeaponListWidget::OnMagazineClicked() -{ - if (WeaponManager->WeaponToModify.IsValid()) - { - WeaponManager->MagazineUpgradeListWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); - WeaponManager->MagazineUpgradeListWidget->OnShow(); - } -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h deleted file mode 100644 index 2850f5a..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponListWidget.h +++ /dev/null @@ -1,48 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "ARWeaponListWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponListWidget : public UUserWidget -{ - GENERATED_BODY() -public: - TWeakObjectPtr WeaponManager; - TWeakObjectPtr ARPC; -protected: - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UWrapBox* ItemContainer; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARWeaponListSlotDropWidget* RightWeapon; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARWeaponListSlotDropWidget* LeftWeapon; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARWeaponListSlotDropWidget* BackDownWeapon; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARWeaponListSlotDropWidget* SideLeftWeapon; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UButton* Magazine; -public: - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UTextBlock* SelectedWeaponName; -protected: - - UPROPERTY() - TArray Items; -public: - void NativePreConstruct(); - void NativeConstruct(); -public: - void AddItem(TSubclassOf DragWidgetClass, int32 WeaponIdx); - - UFUNCTION() - void OnMagazineClicked(); -}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index 513eab1..bb343fd 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -38,11 +38,6 @@ void UARWeaponInventoryComponent::BeginPlay() GroupToComponent.Add(1, Character->GetHolsteredLeftWeapon()); GroupToComponent.Add(2, Character->GetHolsteredBackDownWeapon()); GroupToComponent.Add(3, Character->GetHolsteredSideLeftWeapon()); - - GroupToItem.Add(EAMGroup::Group001, Character->WeaponRightItem); - GroupToItem.Add(EAMGroup::Group002, Character->WeaponLeftItem); - GroupToItem.Add(EAMGroup::Group003, Character->WeaponBackItem); - GroupToItem.Add(EAMGroup::Group004, Character->WeaponSideItem); } } @@ -103,6 +98,7 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde FSoftObjectPath d = InWeapon->Ability.ToSoftObjectPath(); TSoftClassPtr dd(d); PC->WeaponManager->NativeEquipAbility(dd, AMIntToEnum(LocalIndex), EAMSlot::Slot001); + } } //if (!InOldWeapon) @@ -152,77 +148,15 @@ void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* } } } -void UARWeaponInventoryComponent::EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon) -{ - //if (InOldWeapon) - //{ - // WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; - // //WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; - // //WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; - // WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; - // //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); - // SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); - //} - - //MainHandWeapon.Weapon = WeaponHelper[AMEnumToInt(Group)]->Weapon; - //MainHandWeapon.Position = InWeapon->EquipedPosition; - //MainHandWeapon.Rotation = InWeapon->EquipedRotation; - //MainHandWeapon.Group = Group; - //MainHandWeapon.RepCounter++; - //WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); - //WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - ////GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); - //SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - - //if(!InOldWeapon) - //{ - // WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); - // WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - // //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); - // SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - //} - //if (AARCharacter* Character = Cast(POwner)) - //{ - // - // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - // //GroupToComponent[Group]->SetChildActorClass(nullptr); - //} -} void UARWeaponInventoryComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) { - //WeaponHelper[AMEnumToInt(Group)]->Weapon = InWeapon->Weapon; - //WeaponHelper[AMEnumToInt(Group)]->Item = InWeapon->GetClass(); - //WeaponHelper[AMEnumToInt(Group)]->Position = InWeapon->HolsteredPosition; - //WeaponHelper[AMEnumToInt(Group)]->Rotation = InWeapon->HolsteredRotation; - //WeaponHelper[AMEnumToInt(Group)]->Group = Group; - //WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - //if (AARCharacter* Character = Cast(POwner)) - //{ - // //Character->GetHolsteredRightWeapon()->SetSkeletalMesh(nullptr); - // SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - // if (Group == EAMGroup::Group001) - // { - // Character->WeaponRightItem = InWeapon; - // } - //} + } -void UARWeaponInventoryComponent::HolsterActive(EAMGroup Group) +void UARWeaponInventoryComponent::SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility) { - //WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Weapon = MainHandWeapon.Weapon; - //WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->Group = MainHandWeapon.Group; - //WeaponHelper[AMEnumToInt(MainHandWeapon.Group)]->RepCounter++; - - //MainHandWeapon.Weapon.Reset(); - //MainHandWeapon.RepCounter++; - //if (AARCharacter* Character = Cast(POwner)) - //{ - // Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); - // SetWeapon(*WeaponHelper[AMEnumToInt(MainHandWeapon.Group)], GroupToComponent[MainHandWeapon.Group]); - //} } - void UARWeaponInventoryComponent::NextWeapon() { uint8 OldGroup = CurrentWeaponIndex; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index 31aa59c..bd49e35 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -79,14 +79,12 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; void Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon); - void EquipInactive(EAMGroup Group, UARItemWeapon* InWeapon, EAMGroup OldGroup, UARItemWeapon* InOldWeapon); void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); - void HolsterActive(EAMGroup Group); inline void SetPOwner(APawn* InPawn) { POwner = InPawn; } - void SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility) {} + void SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility); UFUNCTION(BlueprintCallable) void NextWeapon(); UFUNCTION(BlueprintCallable) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 068ffa9..c307db1 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -6,7 +6,6 @@ #include "ARWeaponAbilityBase.h" #include "ARItemWeapon.h" #include "ARCharacter.h" -#include "UI/Weapons/ARWeaponListWidget.h" #include "UI/Weapons/ARWeaponUpgradeListWidget.h" #include "DWBPFunctionLibrary.h" @@ -40,34 +39,6 @@ void UARWeaponManagerComponent::BeginPlay() if (!AbilityComp) return; - if (WeaponListClass) - { - WeaponListWidget = CreateWidget(MyPC, WeaponListClass); - WeaponListWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); - WeaponListWidget->ARPC = Cast(GetOwner()); - WeaponListWidget->WeaponManager = this; - int32 Idx = 0; - for (const TSubclassOf& Weapon : WeaponClasses) - { - WeaponListWidget->AddItem(DragSlotClass, Idx); - Idx++; - } - - WeaponListWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(WeaponListWidget, "Weapon List"); - WeaponListWindowHandle.Window.Pin()->bDestroyOnClose = false; - WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); - } - - if (MagazineUpgradeListClass) - { - MagazineUpgradeListWidget = CreateWidget(MyPC, MagazineUpgradeListClass); - MagazineUpgradeListWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); - //MagazineUpgradeListWidget->ARPC = Cast(GetOwner()); - MagazineUpgradeListWidget->WeaponManager = this; - MagazineUpgradeListWidget->AddToViewport(); - } - - //POwner = MyPC->GetPawn(); } @@ -180,22 +151,4 @@ void UARWeaponManagerComponent::OnAbilityReady(TSoftClassPtr InA UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); Character->Weapons2->SetAbilityToItem(static_cast(InGroup), AbilityInstance); } -} - - -void UARWeaponManagerComponent::ShowHideAbilityManager() -{ - if (!WeaponListWidget) - return; - - EVisibility Visibility = WeaponListWindowHandle.Window.Pin()->GetVisibility(); - - if (Visibility == EVisibility::Collapsed) - { - WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::SelfHitTestInvisible); - } - else if (Visibility == EVisibility::SelfHitTestInvisible) - { - WeaponListWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); - } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 6e94ce3..956441d 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -53,19 +53,6 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp UPROPERTY(EditAnywhere, Category = "Attachment Config") FName EquipSocketName; - UPROPERTY(EditAnywhere, Category = "Attachment Config") - TArray WeaponAttachment; - - //Widgets - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf WeaponListClass; - - - UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon|Widgets") - UARWeaponListWidget* WeaponListWidget; - - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf DragSlotClass; UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf MagazineUpgradeListClass; @@ -79,7 +66,6 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp //maybe not reference directly ? TWeakObjectPtr WeaponToModify; - FDWWWindowHandle WeaponListWindowHandle; public: UPROPERTY() @@ -117,8 +103,4 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp protected: virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) override; - - - public: - void ShowHideAbilityManager(); }; From 75164dd817da78362dc51eb03fd0a4df398603d1 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 14 Apr 2018 20:56:56 +0200 Subject: [PATCH 128/187] working on initialization order in network, for inventories --- .../InventoryFramework.uplugin | 2 +- .../Private/IFInventoryComponent.cpp | 76 ++++++++++++++----- .../Private/IFInventoryInterface.cpp | 6 ++ .../Public/IFInventoryComponent.h | 35 +++++++++ .../Public/IFInventoryInterface.h | 27 +++++++ .../Private/IFItemContainerWidget.cpp | 1 - Source/ActionRPGGame/ARCharacter.cpp | 48 +++++++++--- Source/ActionRPGGame/ARCharacter.h | 28 ++++--- Source/ActionRPGGame/ARPlayerController.cpp | 18 ++++- Source/ActionRPGGame/ARPlayerController.h | 9 ++- Source/ActionRPGGame/UI/ARUIComponent.cpp | 61 ++++++++++----- Source/ActionRPGGame/UI/ARUIComponent.h | 4 +- .../Weapons/ARWeaponInventoryComponent.cpp | 20 +++-- .../Weapons/ARWeaponInventoryComponent.h | 1 + .../Weapons/ARWeaponManagerComponent.cpp | 15 ++-- 15 files changed, 272 insertions(+), 79 deletions(-) create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryInterface.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryInterface.h diff --git a/Plugins/InventoryFramework/InventoryFramework.uplugin b/Plugins/InventoryFramework/InventoryFramework.uplugin index c8137f5..dc182a0 100644 --- a/Plugins/InventoryFramework/InventoryFramework.uplugin +++ b/Plugins/InventoryFramework/InventoryFramework.uplugin @@ -16,7 +16,7 @@ "Modules": [ { "Name": "InventoryFramework", - "Type": "Developer", + "Type": "Runtime", "LoadingPhase": "Default" } ] diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index e85b700..253422b 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -7,6 +7,7 @@ #include "IFItemBase.h" #include "IFItemActorBase.h" +#include "IFInventoryInterface.h" #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" @@ -27,9 +28,13 @@ void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerial LocalIndex = static_cast(Idx); const_cast(InArraySerializer).NetToLocal.Add(NetIndex, LocalIndex); const_cast(InArraySerializer).LocalToNet.Add(LocalIndex, NetIndex); - if (InArraySerializer.IC->MaxSlots == (InArraySerializer.Items.Num())) + if (InArraySerializer.IC.IsValid() && InArraySerializer.IC->MaxSlots == (NetIndex+1)) { InArraySerializer.IC->OnInventoryReady.Broadcast(); + if (IIFInventoryInterface* Interface = Cast(InArraySerializer.IC->GetOwner())) + { + Interface->OnInventoryReplicated(InArraySerializer.IC.Get()); + } } if (Item) { @@ -62,7 +67,10 @@ void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySer } } +void FIFItemContainer::PostReplicatedAdd(const TArrayView& AddedIndices, int32 FinalSize) +{ +} void FIFItemContainer::AddItem(uint8 InNetIndex) { uint8 LocalIndex = NetToLocal.FindRef(InNetIndex); @@ -76,9 +84,10 @@ void FIFItemContainer::AddItem(class UIFItemBase* InItem, uint8 InNetIndex) FIFItemData& Item = Items[LocalIndex]; Item.Item = InItem; Item.ChangeType = EIFChangeType::Added; - MarkItemDirty(Item); Item.Item->OnItemAdded(LocalIndex); IC->OnItemAdded(Item.Item, Item.LocalIndex); + + MarkItemDirty(Item); } void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) { @@ -87,12 +96,12 @@ void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) if (!Item.Item) { Item.Item = InItem; - MarkItemDirty(Item); //should be safe to call. On server it probabaly won't do anything and on standalone/clients will update widget. Item.OnSlotChanged(); Item.Item->OnItemAdded(Item.LocalIndex); IC->OnItemAdded(Item.Item, Item.LocalIndex); Item.ChangeType = EIFChangeType::Added; + MarkItemDirty(Item); break; } } @@ -135,22 +144,33 @@ void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) OldItem.ChangeType = EIFChangeType::Updated; } + MarkItemDirty(NewItem); + MarkItemDirty(OldItem); + } void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source , uint8 SourceNetIndex , uint8 InNetIndex) { uint8 SourceLocalIdx = Source->Inventory.NetToLocal[SourceNetIndex]; - uint8 LocalIdx = Source->Inventory.NetToLocal[InNetIndex]; + uint8 LocalIdx = NetToLocal[InNetIndex]; FIFItemData& SourceItem = const_cast(Source->GetSlot(SourceLocalIdx)); FIFItemData& LocalItem = Items[LocalIdx]; LocalItem.Item = DuplicateObject(SourceItem.Item, IC.Get()); LocalItem.Item->OnItemAdded(LocalItem.LocalIndex); + LocalItem.ChangeType = EIFChangeType::Added; + LocalItem.Counter++; + IC->OnItemAdded(LocalItem.Item, LocalItem.LocalIndex); LocalItem.OnSlotChanged(); + SourceItem.Item->MarkPendingKill(); + SourceItem.Item = nullptr; + SourceItem.OnSlotChanged(); + MarkItemDirty(LocalItem); + Source->Inventory.MarkItemDirty(SourceItem); } // Sets default values for this component's properties @@ -168,14 +188,37 @@ UIFInventoryComponent::UIFInventoryComponent() // ... } +void UIFInventoryComponent::InitializeComponent() +{ + Super::InitializeComponent(); + Inventory.IC = this; +} // Called when the game starts void UIFInventoryComponent::BeginPlay() { + Inventory.IC = this; Super::BeginPlay(); - Inventory.IC = this; + /* + Further steps + 2. Load Properties from external data source (JSON); + */ + // ... + +} + +// Called every frame +void UIFInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +void UIFInventoryComponent::InitializeInventory() +{ ENetMode NM = GetOwner()->GetNetMode(); ENetRole NR = GetOwnerRole(); @@ -198,20 +241,13 @@ void UIFInventoryComponent::BeginPlay() } OnInventoryReady.Broadcast(); } - /* - Further steps - 2. Load Properties from external data source (JSON); - */ - // ... - -} - -// Called every frame -void UIFInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... + if (NM == ENetMode::NM_Standalone) + { + if (IIFInventoryInterface* Interface = Cast(GetOwner())) + { + Interface->OnInventoryReplicated(this); + } + } } void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const @@ -304,7 +340,7 @@ void UIFInventoryComponent::ServerAddItemFromOtherInventory_Implementation(class , uint8 SourceNetIndex , uint8 InNetIndex) { - + Inventory.AddFromOtherInventory(Source, SourceNetIndex, InNetIndex); } bool UIFInventoryComponent::ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source , uint8 SourceNetIndex diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryInterface.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryInterface.cpp new file mode 100644 index 0000000..7846e17 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryInterface.cpp @@ -0,0 +1,6 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFInventoryInterface.h" + + +// Add default functionality here for any IIFInventoryInterface functions that are not pure virtual. diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index ab507a7..94116dc 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -60,6 +60,9 @@ struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem UPROPERTY() EIFChangeType ChangeType; + UPROPERTY() + uint8 Counter; + FIFOnItemChangedEvent OnItemChanged; public: @@ -68,6 +71,7 @@ struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem , NetIndex(INDEX_NONE) , LocalIndex(INDEX_NONE) , bAvailable(false) + , Counter(0) {} FIFItemData(uint8 InNetIndex, uint8 InLocalIndex) @@ -75,6 +79,7 @@ struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem , NetIndex(InNetIndex) , LocalIndex(InLocalIndex) , bAvailable(false) + , Counter(0) {} inline uint8 GetNetIndex() const { @@ -136,6 +141,8 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer TMap LocalToNet; protected: + + void AddData(const FIFItemData& InItem) { @@ -158,6 +165,7 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer , uint8 SourceNetIndex , uint8 InNetIndex); public: + void PostReplicatedAdd(const TArrayView& AddedIndices, int32 FinalSize); bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { return FFastArraySerializer::FastArrayDeltaSerialize(Items, DeltaParms, *this); @@ -173,6 +181,16 @@ struct TStructOpsTypeTraits< FIFItemContainer > : public TStructOpsTypeTraitsBas }; }; +USTRUCT(BlueprintType) +struct FIFSlotAcceptedClasses +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray> AcceptedClasses; + +}; + UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent { @@ -186,6 +204,20 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent FIFOnItemChanged OnItemChangedEvent; FIFOnInventoryChanged OnInventoryChanged; + /* + Which items this inventory accept. + */ + UPROPERTY(EditAnywhere, Category = "Inventory") + TArray> AcceptedClasses; + + /* + Which items slot will accept. + + Order is Equvalent to slot order on server. + */ + UPROPERTY(EditAnywhere, Category = "Inventory") + TArray AcceptedSlotClasses; + UPROPERTY(EditAnywhere, Category = "Inventory") uint8 MaxSlots; @@ -203,6 +235,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UIFInventoryComponent(); protected: + virtual void InitializeComponent() override;; // Called when the game starts virtual void BeginPlay() override; @@ -210,6 +243,8 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + void InitializeInventory(); + inline uint8 GetMaxSlots() { return MaxSlots; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryInterface.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryInterface.h new file mode 100644 index 0000000..3d7e9eb --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryInterface.h @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/Interface.h" +#include "IFInventoryInterface.generated.h" + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UIFInventoryInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class INVENTORYFRAMEWORK_API IIFInventoryInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + virtual void OnInventoryReplicated(class UIFInventoryComponent* Inventory) = 0; +}; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp index 9e81642..c4f1651 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp @@ -7,7 +7,6 @@ void UIFItemContainerWidget::SetInventory(UIFInventoryComponent* InInventory) { Inventory = InInventory; - Inventory->GetOnInventoryRead().AddUObject(this, &UIFItemContainerWidget::CreateInventory); } void UIFItemContainerWidget::CreateInventory() diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 6d5047c..0aa5915 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -11,6 +11,7 @@ #include "Engine/ActorChannel.h" #include "Weapons/ARWeaponBase.h" +#include "UI/ARUIComponent.h" #include "Weapons/ARWeaponInventoryComponent.h" #include "ARCharacterMovementComponent.h" @@ -80,9 +81,10 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) EffectsComponent = CreateDefaultSubobject(TEXT("EffectsComponent")); EffectsComponent->SetIsReplicated(true); - FollowCamera->TransformUpdated.AddUObject(this, &AARCharacter::OnCameraTransformUpdate); + WeaponInventory = ObjectInitializer.CreateDefaultSubobject(this, TEXT("WeaponInventory")); + WeaponInventory->SetIsReplicated(true); - Weapons2 = CreateDefaultSubobject(TEXT("Weapons2")); + FollowCamera->TransformUpdated.AddUObject(this, &AARCharacter::OnCameraTransformUpdate); Head = CreateDefaultSubobject(TEXT("Head")); Head->SetupAttachment(GetMesh()); @@ -152,8 +154,8 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) void AARCharacter::BeginPlay() { Super::BeginPlay(); - - Weapons2->SetPOwner(this); + WeaponInventory->SetIsReplicated(true); + WeaponInventory->InitializeWeapons(this); } FString DirToString(EFourCardinalDirection dir) @@ -420,10 +422,7 @@ void AARCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputC Abilities->BindInputs(PlayerInputComponent); } -void AARCharacter::PossessedBy(AController* NewController) -{ - Super::PossessedBy(NewController); -} + void AARCharacter::TurnAtRate(float Rate) { // calculate delta for this frame from the rate information @@ -544,4 +543,35 @@ FVector AARCharacter::GetMainWeaponSocket(const FName& Socket) const return GetMesh()->GetSocketLocation(TEXT("headSocket")); return Component->GetSocketLocation(Socket); -} \ No newline at end of file +} +void AARCharacter::PossessedBy(AController* NewController) +{ + Super::PossessedBy(NewController); + ClientPossesedBy(NewController); + if (AARPlayerController* PC = Cast(Controller)) + { + + WeaponInventory->InitializeInventory(); + } +} +void AARCharacter::ClientPossesedBy_Implementation(AController* NewController) +{ + +} +void AARCharacter::OnRep_Controller() +{ + Super::OnRep_Controller(); + +} +/* IIFInventoryInterface */ +void AARCharacter::OnInventoryReplicated(class UIFInventoryComponent* Inventory) +{ + if (Cast(Inventory)) + { + if (AARPlayerController* PC = Cast(Controller)) + { + PC->UIComponent->InitializeWeaponInventory(); + } + } +} +/* IIFInventoryInterface */ \ No newline at end of file diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/ARCharacter.h index 0b82229..1df545c 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/ARCharacter.h @@ -11,7 +11,8 @@ #include "AFAbilityInterface.h" #include "OrionInterface.h" #include "OrionAnimComponent.h" -#include "IFInventoryComponent.h" +#include "IFInventoryInterface.h" +#include "Weapons/ARWeaponInventoryComponent.h" #include "ARCharacter.generated.h" UENUM(BlueprintType) @@ -73,7 +74,7 @@ struct WeaponSocket static const FName EquipedMainWeapon; }; UCLASS(config=Game) -class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrionInterface +class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrionInterface, public IIFInventoryInterface { GENERATED_BODY() @@ -91,7 +92,8 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio class UAFEffectsComponent* EffectsComponent; public: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) - class UARWeaponInventoryComponent* Weapons2; + class UARWeaponInventoryComponent* WeaponInventory; + protected: UPROPERTY(EditAnywhere, Category = "Default Abilities") TArray AbilitiesToGive; @@ -219,7 +221,6 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio // APawn interface virtual void SetupPlayerInputComponent(class UInputComponent* PlayerInputComponent) override; // End of APawn interface - virtual void PossessedBy(AController* NewController) override; public: /** Returns CameraBoom subobject **/ FORCEINLINE class USpringArmComponent* GetCameraBoom() const { return CameraBoom; } @@ -247,11 +248,6 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio void OnCameraTransformUpdate(USceneComponent* UpdatedComponent, EUpdateTransformFlags UpdateTransformFlags, ETeleportType Teleport); - inline UARWeaponInventoryComponent* GetWeapons() - { - return Weapons2; - } - inline UChildActorComponent* GetHolsteredRightWeapon() { return WeaponHolsteredRight; @@ -288,5 +284,19 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UFUNCTION(BlueprintPure, Category = "Character | Weapons") FVector GetMainWeaponSocket(const FName& Socket) const; + + virtual void PossessedBy(AController* NewController) override; + + UFUNCTION(Client, Reliable) + void ClientPossesedBy(AController* NewController); + void ClientPossesedBy_Implementation(AController* NewController); + + UFUNCTION() + virtual void OnRep_Controller() override; + + /* IIFInventoryInterface */ + virtual void OnInventoryReplicated(class UIFInventoryComponent* Inventory) override; + /* IIFInventoryInterface */ + }; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 13fad77..98dd709 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -20,14 +20,16 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); MainInventory = ObjectInitializer.CreateDefaultSubobject(this, "MainInventory"); MainInventory->SetIsReplicated(true); - + AbilityManager->ComponentTags.Add(TEXT("AbilityManager")); bInputBount = false; } void AARPlayerController::BeginPlay() { Super::BeginPlay(); + MainInventory->SetIsReplicated(true); + } void AARPlayerController::SetPawn(APawn* InPawn) { @@ -103,6 +105,9 @@ void AARPlayerController::SetPawn(APawn* InPawn) } WeaponManager->POwner = InPawn; + + MainInventory->InitializeInventory(); + //UIAbilityManagerComponent->BindInputs(); } @@ -198,3 +203,14 @@ void AARPlayerController::GetObjectBoundSphere(float Distance, AActor* InActor, Radius = InActor->GetRootComponent()->Bounds.SphereRadius; SphereRadius = ScreenMultiple * Radius / FMath::Max(1.0f, Distance); } + + +/* IIFInventoryInterface */ +void AARPlayerController::OnInventoryReplicated(class UIFInventoryComponent* Inventory) +{ + if (Inventory == MainInventory) + { + UIComponent->InitializeInventory(); + } +} +/* IIFInventoryInterface */ \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index 471a23d..c1ef38c 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -6,13 +6,14 @@ #include "GameFramework/PlayerController.h" #include "GameplayTags.h" #include "IFInventoryComponent.h" +#include "IFInventoryInterface.h" #include "ARPlayerController.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API AARPlayerController : public APlayerController +class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public IIFInventoryInterface { GENERATED_BODY() public: @@ -24,7 +25,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARAbilityManagerComponent* AbilityManager; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UIFInventoryComponent* MainInventory; @@ -71,4 +71,9 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController UFUNCTION(BlueprintPure, Category = "Hud") void GetObjectBoundSphere(float Distance, AActor* InActor, FVector& Origin, float& Radius, float& Scale , float& SphereRadius); + + /* IIFInventoryInterface */ + virtual void OnInventoryReplicated(class UIFInventoryComponent* Inventory) override; + /* IIFInventoryInterface */ + }; diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 88fd710..1135fce 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -56,24 +56,7 @@ void UARUIComponent::BeginPlay() HUDWidget->AddToViewport(); } - if (InventoryWidgetClass) - { - InventoryWidget = CreateWidget(MyPC, InventoryWidgetClass); - InventoryWidget->SetInventory(MyPC->MainInventory); - - InventoryWidget->AddToViewport(); - } - - if (WeaponInventoryWidgetClass) - { - WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); - if (AARCharacter* Character = Cast(MyPC->GetPawn())) - { - WeaponInventoryWidget->SetInventory(Character->Weapons2); - - WeaponInventoryWidget->AddToViewport(); - } - } + //DrawWidget = SNew(SHorizontalBox) // +SHorizontalBox::Slot() @@ -103,6 +86,48 @@ void UARUIComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorC // ... } +void UARUIComponent::InitializeInventory() +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + { + AARPlayerController* MyPC = Cast(GetOwner()); + if (InventoryWidgetClass) + { + InventoryWidget = CreateWidget(MyPC, InventoryWidgetClass); + InventoryWidget->SetInventory(MyPC->MainInventory); + InventoryWidget->CreateInventory(); + InventoryWidget->AddToViewport(); + } + + /*if (WeaponInventoryWidgetClass) + { + WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); + + WeaponInventoryWidget->SetInventory(MyPC->WeaponInventory); + WeaponInventoryWidget->CreateInventory(); + WeaponInventoryWidget->AddToViewport(); + }*/ + } +} +void UARUIComponent::InitializeWeaponInventory() +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + { + AARPlayerController* MyPC = Cast(GetOwner()); + AARCharacter* Character = Cast(MyPC->GetPawn()); + if (WeaponInventoryWidgetClass && Character) + { + WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); + + WeaponInventoryWidget->SetInventory(Character->WeaponInventory); + WeaponInventoryWidget->CreateInventory(); + WeaponInventoryWidget->AddToViewport(); + + } + } +} void UARUIComponent::ShowHideInventory() { if (InventoryManagerWidget->GetVisibility() == ESlateVisibility::Collapsed) diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index 9db5a84..65166b4 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -74,6 +74,8 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + void InitializeInventory(); + void InitializeWeaponInventory(); + void ShowHideInventory(); }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index bb343fd..ea2c80b 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -32,16 +32,20 @@ void UARWeaponInventoryComponent::BeginPlay() Super::BeginPlay(); // ... - if (AARCharacter* Character = Cast(GetOwner())) + +} + +void UARWeaponInventoryComponent::InitializeWeapons(APawn* Pawn) +{ + if (AARCharacter* Character = Cast(Pawn)) { GroupToComponent.Add(0, Character->GetHolsteredRightWeapon()); GroupToComponent.Add(1, Character->GetHolsteredLeftWeapon()); GroupToComponent.Add(2, Character->GetHolsteredBackDownWeapon()); GroupToComponent.Add(3, Character->GetHolsteredSideLeftWeapon()); + POwner = Character; } } - - // Called every frame void UARWeaponInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) { @@ -80,18 +84,12 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde // SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); //} - MainHandWeapon.Weapon = InWeapon->Weapon; - MainHandWeapon.Position = InWeapon->EquipedPosition; - MainHandWeapon.Rotation = InWeapon->EquipedRotation; - MainHandWeapon.NetIndex = Inventory.LocalToNet[LocalIndex]; - MainHandWeapon.RepCounter++; - WeaponHelper[LocalIndex]->Weapon.Reset(); WeaponHelper[LocalIndex]->Weapon = InWeapon->Weapon; WeaponHelper[LocalIndex]->RepCounter++; - //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); + SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); - if (AARCharacter* Character = Cast(GetOwner())) + if (AARCharacter* Character = Cast(POwner)) { if (AARPlayerController* PC = Cast(Character->Controller)) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index bd49e35..6b7a40b 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -74,6 +74,7 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone virtual void BeginPlay() override; public: + void InitializeWeapons(APawn* Pawn); // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index c307db1..9da5d66 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -6,6 +6,7 @@ #include "ARWeaponAbilityBase.h" #include "ARItemWeapon.h" #include "ARCharacter.h" +#include "ARPlayerController.h" #include "UI/Weapons/ARWeaponUpgradeListWidget.h" #include "DWBPFunctionLibrary.h" @@ -97,7 +98,6 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, UARItemWeapon* Item = DuplicateObject(WeaponClasses[Idx].GetDefaultObject(), Character); if (Character) { - Character->GetWeapons()->Holster(Group, Item); ActiveGroup = EAMGroup::Group005; } NativeEquipAbility(WeaponClasses[Idx].GetDefaultObject()->Ability, @@ -117,7 +117,6 @@ void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, if (!ABInt) return; - Character->GetWeapons()->Holster(Group, Item); ActiveGroup = EAMGroup::Group005; } @@ -145,10 +144,14 @@ void UARWeaponManagerComponent::OnAbilityReady(TSoftClassPtr InA , const TArray& InAbilityInput , EAMGroup InGroup, EAMSlot InSlot) { - AARCharacter* Character = Cast(POwner); - if (Character) + AARPlayerController* PC = Cast(GetOwner()); + if (PC) { - UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); - Character->Weapons2->SetAbilityToItem(static_cast(InGroup), AbilityInstance); + if (AARCharacter* Character = Cast(PC->GetPawn())) + { + UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); + Character->WeaponInventory->SetAbilityToItem(static_cast(InGroup), AbilityInstance); + } + } } \ No newline at end of file From a09bc34671839b13302cdffc9d609b82bb12a22a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 14 Apr 2018 23:43:36 +0200 Subject: [PATCH 129/187] removing more dead code --- Config/DefaultEngine.ini | 1 + .../InventoryFramework.uplugin | 2 +- .../Private/IFInventoryComponent.cpp | 2 +- Source/ActionRPGGame/UI/ARUIComponent.cpp | 28 ------------------- 4 files changed, 3 insertions(+), 30 deletions(-) diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index ddd73ef..03dc4ee 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -177,3 +177,4 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 + diff --git a/Plugins/InventoryFramework/InventoryFramework.uplugin b/Plugins/InventoryFramework/InventoryFramework.uplugin index dc182a0..323ecd1 100644 --- a/Plugins/InventoryFramework/InventoryFramework.uplugin +++ b/Plugins/InventoryFramework/InventoryFramework.uplugin @@ -4,7 +4,7 @@ "VersionName": "1.0", "FriendlyName": "InventoryFramework", "Description": "", - "Category": "Other", + "Category": "Gameplay", "CreatedBy": "", "CreatedByURL": "", "DocsURL": "", diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 253422b..fe28b1d 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -165,6 +165,7 @@ void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source IC->OnItemAdded(LocalItem.Item, LocalItem.LocalIndex); LocalItem.OnSlotChanged(); + SourceItem.Item->MarkPendingKill(); SourceItem.Item = nullptr; SourceItem.OnSlotChanged(); @@ -200,7 +201,6 @@ void UIFInventoryComponent::BeginPlay() Inventory.IC = this; Super::BeginPlay(); - /* Further steps 2. Load Properties from external data source (JSON); diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 1135fce..364416f 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -55,25 +55,6 @@ void UARUIComponent::BeginPlay() HUDWidget = CreateWidget(MyPC, HUDWidgetClass); HUDWidget->AddToViewport(); } - - - - //DrawWidget = SNew(SHorizontalBox) - // +SHorizontalBox::Slot() - // .HAlign(EHorizontalAlignment::HAlign_Fill) - // .VAlign(EVerticalAlignment::VAlign_Center) - // [ - // SNew(SVerticalBox) - // +SVerticalBox::Slot() - // .HAlign(EHorizontalAlignment::HAlign_Center) - // .VAlign(EVerticalAlignment::VAlign_Fill) - // [ - // SAssignNew(CrosshairWidget2, SARDrawTestWidget) - // ] - // ]; - - //CrosshairWidget2->Brush = &Brush; - //GEngine->GameViewport->AddViewportWidgetContent(DrawWidget.ToSharedRef()); } } @@ -99,15 +80,6 @@ void UARUIComponent::InitializeInventory() InventoryWidget->CreateInventory(); InventoryWidget->AddToViewport(); } - - /*if (WeaponInventoryWidgetClass) - { - WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); - - WeaponInventoryWidget->SetInventory(MyPC->WeaponInventory); - WeaponInventoryWidget->CreateInventory(); - WeaponInventoryWidget->AddToViewport(); - }*/ } } void UARUIComponent::InitializeWeaponInventory() From 0233908a0fcfe59f02d29a626dcaee696d5d32b6 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 15 Apr 2018 00:04:34 +0200 Subject: [PATCH 130/187] added ability to specify which type of item will be accepted by inventory, and removed some dead code --- .../Private/IFInventoryComponent.cpp | 65 +++++++++++++++++++ .../Public/IFInventoryComponent.h | 6 ++ Source/ActionRPGGame/ARCharacter.cpp | 1 - .../Weapons/ARWeaponInventoryComponent.cpp | 22 ------- 4 files changed, 71 insertions(+), 23 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index fe28b1d..4f454ac 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -258,6 +258,58 @@ void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimePr DOREPLIFETIME_CONDITION(UIFInventoryComponent, Inventory, COND_OwnerOnly); } +bool UIFInventoryComponent::AcceptItem(UIFItemBase* Item, uint8 InLocaLIndex) +{ + bool bAccept = false; + + if (AcceptedClasses.Num() == 0) + { + bAccept = true; + } + else + { + for (TSubclassOf& ItemClass : AcceptedClasses) + { + bAccept = false; + if (Item->IsA(ItemClass)) + { + bAccept = true; + break; //no reason to check further. + } + } + } + + if (bAccept) + { + if (AcceptedSlotClasses.Num() == 0) + { + bAccept = true; + } + else + { + FIFSlotAcceptedClasses AC = AcceptedSlotClasses[InLocaLIndex]; + if (AC.AcceptedClasses.Num() == 0) + { + bAccept = true; + } + else + { + for (TSubclassOf& ItemClass : AC.AcceptedClasses) + { + bAccept = false; + if (Item->IsA(ItemClass)) + { + bAccept = true; + break; //no reason to check further. + } + } + } + } + + } + return bAccept; +} + void UIFInventoryComponent::MoveItemInInventory(uint8 NewLocalPostion, uint8 OldLocalPositin) { if (GetOwnerRole() < ENetRole::ROLE_Authority) @@ -327,6 +379,12 @@ void UIFInventoryComponent::AddItemFromOtherInventory(class UIFInventoryComponen , uint8 SourceLocalIndex , uint8 InLocalIndex) { + UIFItemBase* ItemToCheck = Source->GetItem(SourceLocalIndex); + if (!AcceptItem(ItemToCheck, InLocalIndex)) + { + return; + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) { uint8 SourceNetIndex = Source->Inventory.GetNetIndex(SourceLocalIndex); @@ -340,6 +398,13 @@ void UIFInventoryComponent::ServerAddItemFromOtherInventory_Implementation(class , uint8 SourceNetIndex , uint8 InNetIndex) { + uint8 SourceLocalIdx = Source->Inventory.NetToLocal[SourceNetIndex]; + uint8 LocalIdx = Inventory.NetToLocal[InNetIndex]; + UIFItemBase* ItemToCheck = Source->GetItem(SourceLocalIdx); + if (!AcceptItem(ItemToCheck, LocalIdx)) + { + return; + } Inventory.AddFromOtherInventory(Source, SourceNetIndex, InNetIndex); } bool UIFInventoryComponent::ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 94116dc..31035a0 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -264,6 +264,12 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent { return Cast(Inventory.Items[InLocalIndex].Item); } + + /* + Check if item can be droped/added to this inventory/slot. + First check if inventory accepts, If it passes it will check slot. + */ + bool AcceptItem(UIFItemBase* Item, uint8 InLocaLIndex); /* Move item from old position to new position. If there was already item in new position it will be swapped with the moved item; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 0aa5915..b4ae7af 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -550,7 +550,6 @@ void AARCharacter::PossessedBy(AController* NewController) ClientPossesedBy(NewController); if (AARPlayerController* PC = Cast(Controller)) { - WeaponInventory->InitializeInventory(); } } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index ea2c80b..60b24d4 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -74,15 +74,6 @@ void UARWeaponInventoryComponent::SetWeapon(const FARWeapon& InWeapon, UChildAct void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) { UARItemWeapon* InWeapon = Cast(Item); - //if (InOldWeapon) - //{ - // WeaponHelper[AMEnumToInt(OldGroup)]->Weapon = MainHandWeapon.Weapon; - // //WeaponHelper[AMEnumToInt(OldGroup)]->Position = InOldWeapon->HolsteredPosition; - // //WeaponHelper[AMEnumToInt(OldGroup)]->Rotation = InOldWeapon->HolsteredRotation; - // WeaponHelper[AMEnumToInt(OldGroup)]->RepCounter++; - // //GroupToComponent[OldGroup]->SetChildActorClass(WeaponHelper[AMEnumToInt(OldGroup)]->Weapon.Get()); - // SetWeapon(*WeaponHelper[AMEnumToInt(OldGroup)], GroupToComponent[OldGroup]); - //} WeaponHelper[LocalIndex]->Weapon.Reset(); WeaponHelper[LocalIndex]->Weapon = InWeapon->Weapon; @@ -99,19 +90,6 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde } } - //if (!InOldWeapon) - //{ - // WeaponHelper[AMEnumToInt(Group)]->Weapon.Reset(); - // WeaponHelper[AMEnumToInt(Group)]->RepCounter++; - // //GroupToComponent[Group]->SetChildActorClass(WeaponHelper[AMEnumToInt(Group)]->Weapon.Get()); - // SetWeapon(*WeaponHelper[AMEnumToInt(Group)], GroupToComponent[Group]); - //} - //if (AARCharacter* Character = Cast(POwner)) - //{ - - // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - // //GroupToComponent[Group]->SetChildActorClass(nullptr); - //} } void UARWeaponInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const From aceb7fdba9ec84df8739486fd2b1697f0ac26c3e Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 15 Apr 2018 00:50:17 +0200 Subject: [PATCH 131/187] inventory now handle item removal event, swapping items between components should work properly --- .../Private/IFInventoryComponent.cpp | 30 +++++++++++++++ .../Public/IFInventoryComponent.h | 2 +- .../Weapons/ARWeaponInventoryComponent.cpp | 38 ++++++++++++++++++- .../Weapons/ARWeaponInventoryComponent.h | 3 +- 4 files changed, 70 insertions(+), 3 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 4f454ac..b9efef2 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -57,9 +57,11 @@ void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySer break; case EIFChangeType::Updated: Item->OnItemChanged(LocalIndex); + InArraySerializer.IC->OnItemChanged(Item, LocalIndex); break; case EIFChangeType::Removed: Item->OnItemRemoved(LocalIndex); + InArraySerializer.IC->OnItemRemoved(LocalIndex); break; default: break; @@ -136,13 +138,21 @@ void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) if (NewItem.Item) { NewItem.Item->OnItemChanged(NewItem.LocalIndex); + IC->OnItemChanged(NewItem.Item, NewItem.LocalIndex); NewItem.ChangeType = EIFChangeType::Updated; } if (OldItem.Item) { OldItem.Item->OnItemChanged(OldItem.LocalIndex); + IC->OnItemChanged(OldItem.Item, OldItem.LocalIndex); OldItem.ChangeType = EIFChangeType::Updated; } + else + { + OldItem.ChangeType = EIFChangeType::Removed; + IC->OnItemRemoved(OldItem.LocalIndex); + OldItem.Counter++; + } MarkItemDirty(NewItem); MarkItemDirty(OldItem); @@ -158,6 +168,12 @@ void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source FIFItemData& SourceItem = const_cast(Source->GetSlot(SourceLocalIdx)); FIFItemData& LocalItem = Items[LocalIdx]; + UIFItemBase* LocalOld = nullptr; + if (LocalItem.Item) + { + LocalOld = LocalItem.Item; + } + LocalItem.Item = DuplicateObject(SourceItem.Item, IC.Get()); LocalItem.Item->OnItemAdded(LocalItem.LocalIndex); LocalItem.ChangeType = EIFChangeType::Added; @@ -168,6 +184,20 @@ void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source SourceItem.Item->MarkPendingKill(); SourceItem.Item = nullptr; + if (LocalOld) + { + SourceItem.Item = DuplicateObject(LocalOld, Source); + LocalOld->MarkPendingKill(); + LocalOld = nullptr; + SourceItem.ChangeType = EIFChangeType::Added; + SourceItem.Counter++; + } + else + { + SourceItem.ChangeType = EIFChangeType::Removed; + SourceItem.Counter++; + Source->OnItemRemoved(SourceItem.LocalIndex); + } SourceItem.OnSlotChanged(); MarkItemDirty(LocalItem); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 31035a0..bb481a5 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -325,7 +325,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; - + virtual void OnItemRemoved(uint8 LocalIndex) {}; void RemoveItem(uint8 InLocalIndex); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index 60b24d4..20915d0 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -57,7 +57,7 @@ void UARWeaponInventoryComponent::SetWeapon(const FARWeapon& InWeapon, UChildAct { if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) { - Component->SetChildActorClass(InWeapon.Weapon.LoadSynchronous()); + Component->SetChildActorClass(InWeapon.Weapon.Get()); Component->SetRelativeLocation(FVector(0, 0, 0)); Component->SetRelativeRotation(FRotator(0, 0, 0)); @@ -91,6 +91,23 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde } } } +void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) +{ + WeaponHelper[LocalIndex]->Weapon.Reset(); + WeaponHelper[LocalIndex]->RepCounter++; + SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); + if (AARCharacter* Character = Cast(POwner)) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + //remove ability. + } + } + if (LocalIndex == CurrentWeaponIndex) + { + Unequip(LocalIndex); + } +} void UARWeaponInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const { @@ -124,7 +141,26 @@ void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* } } } +void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) +{ + MainHandWeapon.Weapon.Reset(); + MainHandWeapon.Position = FVector(0,0,0); + MainHandWeapon.Rotation = FRotator(0,0,0); + MainHandWeapon.NetIndex = 0; + MainHandWeapon.RepCounter++; + WeaponHelper[WeaponIndex]->Weapon.Reset(); + WeaponHelper[WeaponIndex]->RepCounter++; + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + if (AARPlayerController* PC = Cast(Character->Controller)) + { + //remove ability (bindings ?) + } + } +} void UARWeaponInventoryComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index 6b7a40b..dd0f46f 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -78,8 +78,9 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; - + virtual void OnItemRemoved(uint8 LocalIndex) override; void Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon); + void Unequip(uint8 WeaponIndex); void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); inline void SetPOwner(APawn* InPawn) { From 728c186969d524e2a5eaeccc913d1aafb4d688f2 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 15 Apr 2018 11:02:45 +0200 Subject: [PATCH 132/187] changed how weapon input is bound, Now wait till the weapon is actually inholstered, instead of binding it upon equiping --- .../AbilityFramework/AFAbilityComponent.cpp | 6 +- .../AbilityFramework/AFAbilityTypes.cpp | 4 ++ .../AMAbilityManagerComponent.cpp | 67 ++++++++++++++++--- .../AMAbilityManagerComponent.h | 9 ++- .../Weapons/ARWeaponInventoryComponent.cpp | 18 +++-- .../Weapons/ARWeaponManagerComponent.cpp | 2 +- 6 files changed, 82 insertions(+), 24 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index ba1c665..dafc2b3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -506,11 +506,15 @@ void UAFAbilityComponent::BP_RemoveAbility(TSoftClassPtr TagIn) } void UAFAbilityComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag) { + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeRemoveAbility(InAbilityTag); + } AbilityContainer.RemoveAbility(InAbilityTag); } void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const TSoftClassPtr& InAbilityTag) { - NativeRemoveAbility(InAbilityTag); + AbilityContainer.RemoveAbility(InAbilityTag); } bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const TSoftClassPtr& InAbilityTag) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp index e43261c..95a306e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp @@ -109,12 +109,16 @@ void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& Abi return; UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); + for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) { AbilitiesComp->ReplicatedTasks.Remove(It->Value); } + Ability->AbilityTasks.Reset(); + AbilityToAction.Remove(AbilityIn); + AbilitiesInputs.Remove(AbilityIn); TagToAbility.Remove(AbilityIn); MarkItemDirty(AbilitiesItems[Index]); AbilitiesItems.RemoveAt(Index); diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp index c836e5f..38779ca 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp @@ -54,6 +54,7 @@ void UAMAbilityManagerComponent::BindInputs(UInputComponent* InputComponent, cla AbilityComponent->BindAbilityToAction(InputComponent, Input); } } + UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) { return AbilitySet.Num() >= Groups.Num() ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; @@ -65,6 +66,13 @@ void UAMAbilityManagerComponent::SetAbility(EAMGroup InGroup, EAMSlot InSlot, UG AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbility; } +void UAMAbilityManagerComponent::RemoveAbility(EAMGroup InGroup, EAMSlot InSlot) +{ + if (AbilitySet.Num() < Groups.Num()) + return; + + AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset();; +} TArray UAMAbilityManagerComponent::GetInputTag(EAMGroup InGroup, EAMSlot InSlot) { @@ -88,7 +96,12 @@ void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, { AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; } -void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar, bool bBindInput) +void UAMAbilityManagerComponent::RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot) +{ + AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset(); +} + +void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -110,14 +123,43 @@ void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtrAddOnAbilityReadyDelegate(InAbilityTag, del); } AbilityComp->NativeAddAbility(InAbilityTag, IAbilityInput);// , /*Input*/ ShootInput); } +void UAMAbilityManagerComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + FAFOnAbilityReady del; + //if (IsClient()) + { + //del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, + // IAbilityInput, InGroup, InSlot); + //AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + } + if (InAbilityTag.IsNull()) + InAbilityTag = GetAbilityTag(InGroup, InSlot); + + RemoveAbility(InGroup, InSlot); + RemoveAbilityTag(InGroup, InSlot); + + AbilityComp->NativeRemoveAbility(InAbilityTag); +} void UAMAbilityManagerComponent::OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) + EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) { APlayerController* MyPC = Cast(GetOwner()); if (!MyPC) @@ -134,19 +176,26 @@ void UAMAbilityManagerComponent::OnAbilityReadyInternal(TSoftClassPtr(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityInputReady, - InAbilityTag, InAbilityInput, InGroup, InSlot); + if (bBindInput) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityInputReady, + InAbilityTag, InAbilityInput, InGroup, InSlot); + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - ExecuteAbilityReadyEvent(InAbilityTag); + ExecuteAbilityReadyEvent(InAbilityTag); + } + } else { SetAbility(InGroup, InSlot, Ability); SetAbilityTag(InGroup, InSlot, InAbilityTag); SetInputTag(InGroup, InSlot, InAbilityInput); - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(InAbilityTag); + if (bBindInput) + { + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(InAbilityTag); + } } OnAbilityReady(InAbilityTag, InAbilityInput, InGroup, InSlot); } diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h index 89a0ac8..08d1adf 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h @@ -114,21 +114,24 @@ class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent void BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent); UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); + void RemoveAbility(EAMGroup InGroup, EAMSlot InSlot); TSoftClassPtr GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag); - + void RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot); + TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); - void NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, AActor* InAvatar = nullptr, bool bBindInput = true); + void NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); + void NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); protected: virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, EAMGroup InGroup, EAMSlot InSlot) {}; private: UFUNCTION() void OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot); + EAMGroup InGroup, EAMSlot InSlot, bool bBindInput); public: UFUNCTION() diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index 20915d0..f0cf02a 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -84,25 +84,22 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde { if (AARPlayerController* PC = Cast(Character->Controller)) { - FSoftObjectPath d = InWeapon->Ability.ToSoftObjectPath(); - TSoftClassPtr dd(d); - PC->WeaponManager->NativeEquipAbility(dd, AMIntToEnum(LocalIndex), EAMSlot::Slot001); - + PC->WeaponManager->NativeEquipAbility(InWeapon->Ability, static_cast(LocalIndex), EAMSlot::Slot001, false); } } } void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) { - WeaponHelper[LocalIndex]->Weapon.Reset(); - WeaponHelper[LocalIndex]->RepCounter++; - SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); if (AARCharacter* Character = Cast(POwner)) { if (AARPlayerController* PC = Cast(Character->Controller)) { - //remove ability. + PC->WeaponManager->NativeRemoveAbility(TSoftClassPtr(), static_cast(LocalIndex), EAMSlot::Slot001); } } + WeaponHelper[LocalIndex]->Weapon.Reset(); + WeaponHelper[LocalIndex]->RepCounter++; + SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); if (LocalIndex == CurrentWeaponIndex) { Unequip(LocalIndex); @@ -157,7 +154,7 @@ void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); if (AARPlayerController* PC = Cast(Character->Controller)) { - //remove ability (bindings ?) + PC->WeaponManager->RemoveAbility(static_cast(WeaponIndex), EAMSlot::Slot001); } } } @@ -268,7 +265,7 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIn { NextWeaponAbility = FindNextValid(); } - + Equip(CurrentWeaponIndex, NextWeaponAbility); if (WeaponIndex == CurrentWeaponIndex) { ClientNextWeapon(CurrentWeaponIndex, true); @@ -317,6 +314,7 @@ void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 Weap //situation where client can chage multiple weapons within second //should not have place, as there is animation and/or internal cooldown on weapon change. //since it will be done trough ability. + Equip(CurrentWeaponIndex, NextWeaponAbility); if (CurrentWeaponIndex != WeaponIndex) { ClientPreviousWeapon(CurrentWeaponIndex, false); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 9da5d66..89dbcc7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -52,7 +52,7 @@ void UARWeaponManagerComponent::TickComponent(float DeltaTime, ELevelTick TickTy } void UARWeaponManagerComponent::EquipWeapon(TSoftClassPtr WeaponAbility) { - if (!WeaponAbility.IsValid()) + if (WeaponAbility.IsNull()) { return; } From eabc835bc2da0a0afde63f0b13a10f417065ac68 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 16 Apr 2018 21:56:11 +0200 Subject: [PATCH 133/187] working on inventory screen widget --- ActionRPGGame.uproject | 371 +++++++++--------- Config/DefaultEngine.ini | 1 + .../Private/IFInventoryComponent.cpp | 13 + .../Public/IFInventoryComponent.h | 35 +- .../Public/IFItemWidget.h | 5 +- Source/ActionRPGGame/ARItemBase.h | 2 +- Source/ActionRPGGame/ARPlayerController.cpp | 26 +- Source/ActionRPGGame/ARPlayerController.h | 5 + .../UI/ARCharacterEquipmentWidget.cpp | 7 + .../UI/ARCharacterEquipmentWidget.h | 20 + Source/ActionRPGGame/UI/ARUIComponent.cpp | 133 +++++-- Source/ActionRPGGame/UI/ARUIComponent.h | 12 +- .../UI/Inventory/ARInventoryScreenWidget.cpp | 39 ++ .../UI/Inventory/ARInventoryScreenWidget.h | 47 +++ .../UI/Inventory/ARWeaponContainerWidget.cpp | 28 ++ .../UI/Inventory/ARWeaponContainerWidget.h | 20 + .../UI/Weapons/ARItemWeaponWidget.cpp | 28 ++ .../UI/Weapons/ARItemWeaponWidget.h | 25 ++ .../Weapons/ARMagazineUpgradeItem.h | 3 - .../Weapons/ARWeaponUpgradeItem.h | 3 +- 20 files changed, 600 insertions(+), 223 deletions(-) create mode 100644 Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp create mode 100644 Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h create mode 100644 Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h create mode 100644 Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.h create mode 100644 Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp create mode 100644 Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 9df21fd..8d791e5 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -11,204 +11,205 @@ "AdditionalDependencies": [ "AbilityFramework", "AbilityFrameworkDebugger", - "AbilityManager", - "InventoryFramework", + "AbilityManager", + "InventoryFramework", "Engine", "AIModule", "UMG", "CoreUObject", "Slate", - "SlateCore" + "SlateCore", + "InventoryFrameworkUI" ] }, { "Name": "ActionRPGGameEditor", "Type": "Editor", "LoadingPhase": "Default", - "AdditionalDependencies": [ - "AbilityFramework", - "AbilityFrameworkEditor", - "AbilityFrameworkDebugger", - "AbilityManager", - "InventoryFramework", - "Engine", - "AIModule", - "UMG", - "CoreUObject" - ] + "AdditionalDependencies": [ + "AbilityFramework", + "AbilityFrameworkEditor", + "AbilityFrameworkDebugger", + "AbilityManager", + "InventoryFramework", + "Engine", + "AIModule", + "UMG", + "CoreUObject" + ] + } + ], + "Plugins": [ + { + "Name": "ActorSequence", + "Enabled": true + }, + { + "Name": "AbilityFramework", + "Enabled": true + }, + { + "Name": "AbilityFrameworkDebugger", + "Enabled": true + }, + { + "Name": "AbilityManager", + "Enabled": true + }, + { + "Name": "InventoryFramework", + "Enabled": true + }, + { + "Name": "InventoryFrameworkUI", + "Enabled": true + }, + { + "Name": "ActorSequenceEditor", + "Enabled": true + }, + { + "Name": "ImagePlate", + "Enabled": true + }, + { + "Name": "PerformanceMonitor", + "Enabled": true + }, + { + "Name": "OnlineSubsystemAmazon", + "Enabled": true + }, + { + "Name": "OnlineFramework", + "Enabled": true + }, + { + "Name": "SteamVR", + "Enabled": false + }, + { + "Name": "OculusVR", + "Enabled": false + }, + { + "Name": "Niagara", + "Enabled": true + }, + { + "Name": "SoundUtilities", + "Enabled": true + }, + { + "Name": "SoundVisualizations", + "Enabled": true + }, + { + "Name": "BlueprintStats", + "Enabled": true + }, + { + "Name": "LocationServicesBPLibrary", + "Enabled": false + }, + { + "Name": "WindowsDeviceProfileSelector", + "Enabled": true + }, + { + "Name": "AndroidDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "IOSDeviceProfileSelector", + "Enabled": false + }, + { + "Name": "AndroidMedia", + "Enabled": false + }, + { + "Name": "MobileLauncherProfileWizard", + "Enabled": false + }, + { + "Name": "MobilePatchingUtils", + "Enabled": false + }, + { + "Name": "AndroidMoviePlayer", + "Enabled": false + }, + { + "Name": "AppleMoviePlayer", + "Enabled": false + }, + { + "Name": "GoogleCloudMessaging", + "Enabled": false + }, + { + "Name": "OnlineSubsystemIOS", + "Enabled": false, + "SupportedTargetPlatforms": [ + "IOS", + "TVOS" + ] + }, + { + "Name": "OnlineSubsystemGooglePlay", + "Enabled": false, + "SupportedTargetPlatforms": [ + "Android" + ] + }, + { + "Name": "ApexDestruction", + "Enabled": true + }, + { + "Name": "AndroidPermission", + "Enabled": false + }, + { + "Name": "AppleARKit", + "Enabled": false + }, + { + "Name": "GLTFImporter", + "Enabled": true + }, + { + "Name": "SteamAudio", + "Enabled": true + }, + { + "Name": "ResonanceAudio", + "Enabled": false + }, + { + "Name": "CodeView", + "Enabled": true + }, + { + "Name": "SignificanceManager", + "Enabled": true + }, + { + "Name": "CustomAnimNode", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" + }, + { + "Name": "Substance", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" + }, + { + "Name": "LiveLink", + "Enabled": true } ], - "Plugins": [ - { - "Name": "ActorSequence", - "Enabled": true - }, - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "AbilityFrameworkDebugger", - "Enabled": true - }, - { - "Name": "AbilityManager", - "Enabled": true - }, - { - "Name": "InventoryFramework", - "Enabled": true - }, - { - "Name": "InventoryFrameworkUI", - "Enabled": true - }, - { - "Name": "ActorSequenceEditor", - "Enabled": true - }, - { - "Name": "ImagePlate", - "Enabled": true - }, - { - "Name": "PerformanceMonitor", - "Enabled": true - }, - { - "Name": "OnlineSubsystemAmazon", - "Enabled": true - }, - { - "Name": "OnlineFramework", - "Enabled": true - }, - { - "Name": "SteamVR", - "Enabled": false - }, - { - "Name": "OculusVR", - "Enabled": false - }, - { - "Name": "Niagara", - "Enabled": true - }, - { - "Name": "SoundUtilities", - "Enabled": true - }, - { - "Name": "SoundVisualizations", - "Enabled": true - }, - { - "Name": "BlueprintStats", - "Enabled": true - }, - { - "Name": "LocationServicesBPLibrary", - "Enabled": false - }, - { - "Name": "WindowsDeviceProfileSelector", - "Enabled": true - }, - { - "Name": "AndroidDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "IOSDeviceProfileSelector", - "Enabled": false - }, - { - "Name": "AndroidMedia", - "Enabled": false - }, - { - "Name": "MobileLauncherProfileWizard", - "Enabled": false - }, - { - "Name": "MobilePatchingUtils", - "Enabled": false - }, - { - "Name": "AndroidMoviePlayer", - "Enabled": false - }, - { - "Name": "AppleMoviePlayer", - "Enabled": false - }, - { - "Name": "GoogleCloudMessaging", - "Enabled": false - }, - { - "Name": "OnlineSubsystemIOS", - "Enabled": false, - "SupportedTargetPlatforms": [ - "IOS", - "TVOS" - ] - }, - { - "Name": "OnlineSubsystemGooglePlay", - "Enabled": false, - "SupportedTargetPlatforms": [ - "Android" - ] - }, - { - "Name": "ApexDestruction", - "Enabled": true - }, - { - "Name": "AndroidPermission", - "Enabled": false - }, - { - "Name": "AppleARKit", - "Enabled": false - }, - { - "Name": "GLTFImporter", - "Enabled": true - }, - { - "Name": "SteamAudio", - "Enabled": true - }, - { - "Name": "ResonanceAudio", - "Enabled": false - }, - { - "Name": "CodeView", - "Enabled": true - }, - { - "Name": "SignificanceManager", - "Enabled": true - }, - { - "Name": "CustomAnimNode", - "Enabled": true, - "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" - }, - { - "Name": "Substance", - "Enabled": true, - "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" - }, - { - "Name": "LiveLink", - "Enabled": true - } - ], "TargetPlatforms": [ "LinuxNoEditor", "WindowsNoEditor" diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 03dc4ee..02d58ad 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -27,6 +27,7 @@ r.TemporalAA.Upsampling=False bDefaultParticleCutouts=True r.SupportMaterialLayers=True r.GBufferFormat=3 +r.UsePreExposure=True [/Script/Engine.StreamingSettings] s.AsyncLoadingThreadEnabled=True diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index b9efef2..4b52320 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -204,6 +204,19 @@ void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source Source->Inventory.MarkItemDirty(SourceItem); } +TArray FIFItemContainer::GetLocalItemIdxs(TSubclassOf ItemClass) +{ + TArray Indexes; + for (uint8 Idx = 0; Idx < Items.Num(); Idx++) + { + if (Items[Idx].Item && Items[Idx].Item->IsA(ItemClass)) + { + Indexes.Add(Items[Idx].LocalIndex); + } + } + return Indexes; +} + // Sets default values for this component's properties UIFInventoryComponent::UIFInventoryComponent() { diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index bb481a5..bfebe72 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -141,8 +141,6 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer TMap LocalToNet; protected: - - void AddData(const FIFItemData& InItem) { @@ -164,7 +162,27 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer void AddFromOtherInventory(class UIFInventoryComponent* Source , uint8 SourceNetIndex , uint8 InNetIndex); + + TArray GetLocalItemIdxs(TSubclassOf ItemClass); + + template + TArray GetItems(TSubclassOf ItemClass) + { + TArray Indexes; + for (uint8 Idx = 0; Idx < Items.Num(); Idx++) + { + if (Items[Idx].Item && Items[Idx].Item->IsA(ItemClass)) + { + Indexes.Add(Cast(Items[Idx].Item)); + } + } + return Indexes; + } + public: + inline TArray& GetItems() { return Items; } + + void PostReplicatedAdd(const TArrayView& AddedIndices, int32 FinalSize); bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { @@ -245,6 +263,8 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent void InitializeInventory(); + inline FIFItemContainer& GetInventory() { return Inventory; } + inline uint8 GetMaxSlots() { return MaxSlots; @@ -265,6 +285,17 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent return Cast(Inventory.Items[InLocalIndex].Item); } + TArray GetLocalItemIdxs(TSubclassOf ItemClass) + { + return Inventory.GetLocalItemIdxs(ItemClass); + } + + template + TArray GetItems(TSubclassOf ItemClass) + { + return Inventory.GetItems(ItemClass); + } + /* Check if item can be droped/added to this inventory/slot. First check if inventory accepts, If it passes it will check slot. diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h index 239643d..73343a8 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -14,11 +14,12 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget { GENERATED_BODY() friend class UIFItemContainerWidget; -protected: +public: TWeakObjectPtr Inventory; /* Those indexes correponds to the client copy of items; */ + UPROPERTY() uint8 NetIndex; UPROPERTY() @@ -26,7 +27,7 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget UPROPERTY(BlueprintReadWrite, Category = "InventoryFramework") UWidget* DragVisual; - +public: void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex); void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex); diff --git a/Source/ActionRPGGame/ARItemBase.h b/Source/ActionRPGGame/ARItemBase.h index 97a19ce..1423846 100644 --- a/Source/ActionRPGGame/ARItemBase.h +++ b/Source/ActionRPGGame/ARItemBase.h @@ -13,7 +13,7 @@ UCLASS() class ACTIONRPGGAME_API UARItemBase : public UIFItemBase { GENERATED_BODY() -protected: +public: //obviously we want TSoftObjectPtr<> UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") UTexture2D* Icon; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 98dd709..26b64a4 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -34,6 +34,13 @@ void AARPlayerController::BeginPlay() void AARPlayerController::SetPawn(APawn* InPawn) { Super::SetPawn(InPawn); + + + //UIAbilityManagerComponent->BindInputs(); +} +void AARPlayerController::Possess(APawn* aPawn) +{ + Super::Possess(aPawn); ENetMode NetMode = GetNetMode(); if (NetMode == ENetMode::NM_Client || NetMode == ENetMode::NM_Standalone) @@ -102,13 +109,23 @@ void AARPlayerController::SetPawn(APawn* InPawn) HolsterInput.Add(InputSetAbilityGroup02); AbilityComp->NativeAddAbility(SetAbilityGroup02, HolsterInput); } - + + } + + if (NetMode == ENetMode::NM_DedicatedServer + || NetMode == ENetMode::NM_ListenServer) + { + ClientPossesed(aPawn); } - WeaponManager->POwner = InPawn; + WeaponManager->POwner = aPawn; + MainInventory->InitializeInventory(); - - //UIAbilityManagerComponent->BindInputs(); +} + +void AARPlayerController::ClientPossesed_Implementation(APawn* InPawn) +{ + } void AARPlayerController::SetupInputComponent() @@ -127,6 +144,7 @@ void AARPlayerController::InputShowHideAbilityManager() } void AARPlayerController::InputShowHideInventory() { + UIComponent->ShowHideInventory(); } void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag) { diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/ARPlayerController.h index c1ef38c..e294c8f 100644 --- a/Source/ActionRPGGame/ARPlayerController.h +++ b/Source/ActionRPGGame/ARPlayerController.h @@ -58,6 +58,7 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I AARPlayerController(const FObjectInitializer& ObjectInitializer); virtual void BeginPlay() override; virtual void SetPawn(APawn* InPawn) override; + virtual void Possess(APawn* aPawn) override; void SetupInputComponent(); void InputSwitchAbilitySet(); @@ -65,6 +66,10 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I void InputShowHideInventory(); void OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag); + UFUNCTION(Client, Reliable) + void ClientPossesed(APawn* InPawn); + void ClientPossesed_Implementation(APawn* InPawn); + UFUNCTION(BlueprintPure, Category = "Hud") float GetObjectScreenRadius(AActor* InActor); diff --git a/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp b/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp new file mode 100644 index 0000000..d6ee0f6 --- /dev/null +++ b/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARCharacterEquipmentWidget.h" + + + + diff --git a/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h b/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h new file mode 100644 index 0000000..64facea --- /dev/null +++ b/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARCharacterEquipmentWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARCharacterEquipmentWidget : public UARUMGWidgetBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 364416f..04a64a1 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -5,9 +5,12 @@ #include "ARCharacter.h" #include "ARPlayerController.h" -#include "Inventory/ARInventoryManagerWidget.h" +#include "Inventory/ARInventoryManagerWidget.h" +#include "Inventory/ARWeaponContainerWidget.h" +#include "Inventory/ARInventoryScreenWidget.h" +#include "UI/Weapons/ARItemWeaponWidget.h" // Sets default values for this component's properties UARUIComponent::UARUIComponent() @@ -16,10 +19,15 @@ UARUIComponent::UARUIComponent() // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; EnemyHealthBarClass = UAREnemyHealthBar::StaticClass(); + bAutoRegister = true; + bWantsInitializeComponent = true; // ... } - +void UARUIComponent::InitializeComponent() +{ + Super::InitializeComponent(); +} // Called when the game starts void UARUIComponent::BeginPlay() { @@ -36,12 +44,12 @@ void UARUIComponent::BeginPlay() CrosshairWidget->SetVisibility(ESlateVisibility::HitTestInvisible); CrosshairWidget->AddToViewport(); } - if (InventoryManagerClass) + /*if (InventoryManagerClass) { InventoryManagerWidget = CreateWidget(MyPC, InventoryManagerClass); InventoryManagerWidget->SetVisibility(ESlateVisibility::Collapsed); InventoryManagerWidget->AddToViewport(); - } + }*/ if (EnemyHealthBarClass) { @@ -55,6 +63,81 @@ void UARUIComponent::BeginPlay() HUDWidget = CreateWidget(MyPC, HUDWidgetClass); HUDWidget->AddToViewport(); } + + if (InventoryScreenWidgetClass) + { + InventoryScreenWidget = CreateWidget(MyPC, InventoryScreenWidgetClass); + InventoryScreenWidget->SetVisibility(ESlateVisibility::Collapsed); + InventoryScreenWidget->AddToViewport(); + } + AARCharacter* Character = Cast(MyPC->GetPawn()); + if (WeaponInventoryWidgetClass && Character) + { + InventoryScreenWidget->UI = this; + InventoryScreenWidget->PC = MyPC; + InventoryScreenWidget->Inventory = MyPC->MainInventory; + + UARWeaponInventoryComponent* WeapInv = Character->WeaponInventory; + + for (FIFItemData& Item : WeapInv->GetInventory().GetItems()) + { + switch (Item.GetLocalIndex()) + { + case 0: + { + InventoryScreenWidget->RightWeaponWidget->Inventory = MyPC->MainInventory; + InventoryScreenWidget->RightWeaponWidget->WeaponInventory = WeapInv; + InventoryScreenWidget->RightWeaponWidget->UI = this; + InventoryScreenWidget->RightWeaponWidget->InventoryWidget = InventoryScreenWidget; + + InventoryScreenWidget->RightWeaponWidget->LocalIndex = Item.GetLocalIndex(); + InventoryScreenWidget->RightWeaponWidget->NetIndex = Item.GetNetIndex(); + + FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->RightWeaponWidget, &UIFItemWidget::OnItemChanged); + Item.SetOnItemChanged(Event); + } + case 1: + { + InventoryScreenWidget->LeftWeaponWidget->Inventory = MyPC->MainInventory; + InventoryScreenWidget->LeftWeaponWidget->WeaponInventory = WeapInv; + InventoryScreenWidget->LeftWeaponWidget->UI = this; + InventoryScreenWidget->LeftWeaponWidget->InventoryWidget = InventoryScreenWidget; + + InventoryScreenWidget->LeftWeaponWidget->LocalIndex = Item.GetLocalIndex(); + InventoryScreenWidget->LeftWeaponWidget->NetIndex = Item.GetNetIndex(); + + FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->LeftWeaponWidget, &UIFItemWidget::OnItemChanged); + Item.SetOnItemChanged(Event); + } + case 2: + { + InventoryScreenWidget->SideWeaponWidget->Inventory = MyPC->MainInventory; + InventoryScreenWidget->SideWeaponWidget->WeaponInventory = WeapInv; + InventoryScreenWidget->SideWeaponWidget->UI = this; + InventoryScreenWidget->RightWeaponWidget->InventoryWidget = InventoryScreenWidget; + + InventoryScreenWidget->SideWeaponWidget->LocalIndex = Item.GetLocalIndex(); + InventoryScreenWidget->SideWeaponWidget->NetIndex = Item.GetNetIndex(); + + FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->SideWeaponWidget, &UIFItemWidget::OnItemChanged); + Item.SetOnItemChanged(Event); + } + case 3: + { + InventoryScreenWidget->BottomBackWeaponWidget->Inventory = MyPC->MainInventory; + InventoryScreenWidget->BottomBackWeaponWidget->WeaponInventory = WeapInv; + InventoryScreenWidget->BottomBackWeaponWidget->UI = this; + InventoryScreenWidget->BottomBackWeaponWidget->InventoryWidget = InventoryScreenWidget; + + InventoryScreenWidget->BottomBackWeaponWidget->LocalIndex = Item.GetLocalIndex(); + InventoryScreenWidget->BottomBackWeaponWidget->NetIndex = Item.GetNetIndex(); + + FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->BottomBackWeaponWidget, &UIFItemWidget::OnItemChanged); + Item.SetOnItemChanged(Event); + } + } + } + } } } @@ -84,30 +167,34 @@ void UARUIComponent::InitializeInventory() } void UARUIComponent::InitializeWeaponInventory() { - if (GetOwner()->GetNetMode() == ENetMode::NM_Client - || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) - { - AARPlayerController* MyPC = Cast(GetOwner()); - AARCharacter* Character = Cast(MyPC->GetPawn()); - if (WeaponInventoryWidgetClass && Character) - { - WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); - - WeaponInventoryWidget->SetInventory(Character->WeaponInventory); - WeaponInventoryWidget->CreateInventory(); - WeaponInventoryWidget->AddToViewport(); - - } - } + //if (GetOwner()->GetNetMode() == ENetMode::NM_Client + // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + //{ + // AARPlayerController* MyPC = Cast(GetOwner()); + // AARCharacter* Character = Cast(MyPC->GetPawn()); + // if (WeaponInventoryWidgetClass && Character) + // { + // InventoryScreenWidget->WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); + // + // InventoryScreenWidget->UI = this; + // InventoryScreenWidget->PC = MyPC; + // InventoryScreenWidget->Inventory = MyPC->MainInventory; + // InventoryScreenWidget->WeaponInventoryWidget->SetInventory(Character->WeaponInventory); + // InventoryScreenWidget->WeaponInventoryWidget->CreateInventory(); + // InventoryScreenWidget->WeaponInventoryWidget->InitializeWeaponItems(this); + // InventoryScreenWidget->WeaponInventoryWidget->AddToViewport(); + // + // } + //} } void UARUIComponent::ShowHideInventory() { - if (InventoryManagerWidget->GetVisibility() == ESlateVisibility::Collapsed) + if (InventoryScreenWidget->GetVisibility() == ESlateVisibility::Collapsed) { - InventoryManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + InventoryScreenWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); } - else if (InventoryManagerWidget->GetVisibility() == ESlateVisibility::SelfHitTestInvisible) + else if (InventoryScreenWidget->GetVisibility() == ESlateVisibility::SelfHitTestInvisible) { - InventoryManagerWidget->SetVisibility(ESlateVisibility::Collapsed); + InventoryScreenWidget->SetVisibility(ESlateVisibility::Collapsed); } } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index 65166b4..4b9d8ad 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -50,10 +50,17 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf WeaponInventoryWidgetClass; + TSubclassOf WeaponInventoryWidgetClass; + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf InventoryScreenWidgetClass; +public: + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf ItemWidgetClass; + +public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") - UIFItemContainerWidget* WeaponInventoryWidget; + UARInventoryScreenWidget* InventoryScreenWidget; public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") @@ -67,6 +74,7 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UARUIComponent(); protected: + virtual void InitializeComponent() override; // Called when the game starts virtual void BeginPlay() override; diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp new file mode 100644 index 0000000..574bcaa --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARInventoryScreenWidget.h" + +#include "Components/TextBlock.h" +#include "Components/WrapBox.h" + +#include "IFInventoryComponent.h" +#include "IFItemWidget.h" + +#include "UI/ARUIComponent.h" +#include "ARPlayerController.h" + +void UARInventoryScreenWidget::SetWeaponName(const FString& Name) +{ + SelectedWeapon->SetText(FText::FromString(Name)); +} + +void UARInventoryScreenWidget::UpdateItemList(const TArray& LocalIdxs) +{ + SelectedItemsContainer->ClearChildren(); + + for (uint8 Idx : LocalIdxs) + { + UIFItemBase* Item = Inventory->GetItem(Idx); + + if (Item) + { + const FIFItemData& Slot = Inventory->GetSlot(Idx); + UIFItemWidget* ItemWidget = CreateWidget(PC.Get(), UI->ItemWidgetClass); + ItemWidget->Inventory = Inventory; + ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); + ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex()); + + SelectedItemsContainer->AddChild(ItemWidget); + } + } + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h new file mode 100644 index 0000000..adc847f --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h @@ -0,0 +1,47 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARInventoryScreenWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase +{ + GENERATED_BODY() +public: + + TWeakObjectPtr Inventory; + TWeakObjectPtr UI; + TWeakObjectPtr PC; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UARItemWeaponWidget* RightWeaponWidget; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UARItemWeaponWidget* LeftWeaponWidget; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UARItemWeaponWidget* SideWeaponWidget; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UARItemWeaponWidget* BottomBackWeaponWidget; + + /* + Contains list of items compatibile with selected slot. + */ + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UWrapBox* SelectedItemsContainer; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UTextBlock* SelectedWeapon; + + void SetWeaponName(const FString& Name); + + void UpdateItemList(const TArray& LocalIdxs); + +}; diff --git a/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp new file mode 100644 index 0000000..38e1918 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponContainerWidget.h" + +#include "IFItemWidget.h" + +#include "ARPlayerController.h" +#include "ARCharacter.h" + +#include "UI/ARUIComponent.h" +#include "UI/Weapons/ARItemWeaponWidget.h" + + +void UARWeaponContainerWidget::InitializeWeaponItems(class UARUIComponent* UIComponent) +{ + for (UIFItemWidget* Widget : InventoryWidgets) + { + if (UARItemWeaponWidget* Weapon = Cast(Widget)) + { + AARPlayerController* PC = Cast(UIComponent->GetOwner()); + AARCharacter* Character = Cast(PC->GetPawn()); + + Weapon->WeaponInventory = Character->WeaponInventory; + Weapon->UI = UIComponent; + Weapon->InventoryWidget = UIComponent->InventoryScreenWidget; + } + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.h b/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.h new file mode 100644 index 0000000..bb9ba22 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFItemContainerWidget.h" +#include "ARWeaponContainerWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponContainerWidget : public UIFItemContainerWidget +{ + GENERATED_BODY() +public: + void InitializeWeaponItems(class UARUIComponent* UIComponent); + + +}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp new file mode 100644 index 0000000..d0a49ad --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemWeaponWidget.h" + +#include "IFInventoryComponent.h" + +#include "Weapons/ARItemWeapon.h" +#include "Weapons/ARWeaponInventoryComponent.h" + +#include "UI/Inventory/ARWeaponContainerWidget.h" +#include "UI/Inventory/ARInventoryScreenWidget.h" + +void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + TArray Items = Inventory->GetLocalItemIdxs(UARItemWeapon::StaticClass()); + + UARItemWeapon* CurrentItem = WeaponInventory->GetItem(LocalIndex); + + if (CurrentItem) + { + InventoryWidget->SetWeaponName(CurrentItem->GetName()); + } + InventoryWidget->UpdateItemList(Items); +} +void UARItemWeaponWidget::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) +{ + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.h new file mode 100644 index 0000000..a2d22f4 --- /dev/null +++ b/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFItemWidget.h" +#include "ARItemWeaponWidget.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARItemWeaponWidget : public UIFItemWidget +{ + GENERATED_BODY() +public: + TWeakObjectPtr WeaponInventory; + TWeakObjectPtr UI; + TWeakObjectPtr InventoryWidget; +public: + virtual void NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; + virtual void NativeOnMouseLeave(const FPointerEvent& InMouseEvent) override; + + +}; diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h index 624e38b..0bce8dd 100644 --- a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h @@ -14,9 +14,6 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem { GENERATED_BODY() public: - UPROPERTY(EditAnywhere) - UTexture2D* Icon; - UPROPERTY(EditAnywhere) TSoftClassPtr UpgradeEffect; }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h index 1836c4f..5d6b536 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h @@ -4,13 +4,14 @@ #include "CoreMinimal.h" #include "UObject/NoExportTypes.h" +#include "ARItemBase.h" #include "ARWeaponUpgradeItem.generated.h" /** * */ UCLASS(BlueprintType, Blueprintable) -class ACTIONRPGGAME_API UARWeaponUpgradeItem : public UObject +class ACTIONRPGGAME_API UARWeaponUpgradeItem : public UARItemBase { GENERATED_BODY() }; From de547d586cbf90e9b66e43a47ead478f2864b8a9 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 16 Apr 2018 23:58:50 +0200 Subject: [PATCH 134/187] removing duplicate/dead UI classes, in prepration for UI refactor --- .../Private/IFItemWidget.cpp | 42 --------- .../Public/IFItemWidget.h | 7 -- .../Abilities/ARAbilityManagerComponent.cpp | 29 ------ .../Abilities/ARAbilityManagerComponent.h | 19 ---- Source/ActionRPGGame/UI/ARAbilityWidget.cpp | 34 ------- Source/ActionRPGGame/UI/ARAbilityWidget.h | 26 ------ .../UI/ARCharacterEquipmentWidget.cpp | 7 -- .../ARAbilityDragVisual.cpp => ARHUD.cpp} | 2 +- .../ARAbilityManagerWidget.h => ARHUD.h} | 6 +- Source/ActionRPGGame/UI/ARUIComponent.cpp | 30 +------ Source/ActionRPGGame/UI/ARUIComponent.h | 16 +--- .../UI/ARWeaponActriveInfoWidget.cpp | 52 ----------- .../UI/ARWeaponActriveInfoWidget.h | 26 ------ .../ActionRPGGame/UI/ARWeaponInfoWidget.cpp | 63 ------------- Source/ActionRPGGame/UI/ARWeaponInfoWidget.h | 42 --------- .../UI/Abilities/ARAbilityCrosshairInfo.cpp | 35 -------- .../UI/Abilities/ARAbilityCrosshairInfo.h | 32 ------- .../UI/Abilities/ARAbilityDragVisual.h | 27 ------ .../UI/Abilities/ARAbilityInfoWidget.cpp | 22 ----- .../UI/Abilities/ARAbilityInfoWidget.h | 26 ------ .../Abilities/ARAbilityListSlotDragWidget.cpp | 60 ------------- .../Abilities/ARAbilityListSlotDragWidget.h | 37 -------- .../Abilities/ARAbilityListSlotDropWidget.cpp | 55 ------------ .../Abilities/ARAbilityListSlotDropWidget.h | 28 ------ .../UI/Abilities/ARAbilityListWidget.cpp | 15 ---- .../UI/Abilities/ARAbilityListWidget.h | 42 --------- .../UI/Abilities/ARAbilitySlotWidget.cpp | 88 ------------------- .../UI/Abilities/ARAbilitySlotWidget.h | 54 ------------ Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h | 26 +++--- .../UI/Inventory/ARInventoryScreenWidget.cpp | 5 -- .../UI/Inventory/ARInventoryScreenWidget.h | 30 +++++++ .../ARItemWeaponWidget.cpp | 4 +- .../ARItemWeaponWidget.h | 0 .../ARListItemWeaponWidget.cpp} | 2 +- .../ARListItemWeaponWidget.h} | 6 +- .../UI/Inventory/ARWeaponContainerWidget.cpp | 1 - .../UI/Weapons/ARMagazineUpgradeWidget.cpp | 13 --- .../UI/Weapons/ARMagazineUpgradeWidget.h | 21 ----- .../UI/Weapons/ARUpgradeBaseWidget.cpp | 7 -- .../UI/Weapons/ARUpgradeBaseWidget.h | 20 ----- .../UI/Weapons/ARWeaponBaseWidget.cpp | 27 ------ .../UI/Weapons/ARWeaponBaseWidget.h | 25 ------ .../UI/Weapons/ARWeaponSlotWidget.cpp | 26 ------ .../UI/Weapons/ARWeaponSlotWidget.h | 31 ------- .../UI/Weapons/ARWeaponUpgradeListWidget.cpp | 30 ------- .../UI/Weapons/ARWeaponUpgradeListWidget.h | 24 ----- .../Weapons/ARWeaponManagerComponent.cpp | 28 ------ .../Weapons/ARWeaponManagerComponent.h | 15 ---- 48 files changed, 59 insertions(+), 1204 deletions(-) delete mode 100644 Source/ActionRPGGame/UI/ARAbilityWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/ARAbilityWidget.h delete mode 100644 Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp rename Source/ActionRPGGame/UI/{Abilities/ARAbilityDragVisual.cpp => ARHUD.cpp} (71%) rename Source/ActionRPGGame/UI/{Abilities/ARAbilityManagerWidget.h => ARHUD.h} (53%) delete mode 100644 Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h delete mode 100644 Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/ARWeaponInfoWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h rename Source/ActionRPGGame/UI/{Weapons => Inventory}/ARItemWeaponWidget.cpp (83%) rename Source/ActionRPGGame/UI/{Weapons => Inventory}/ARItemWeaponWidget.h (100%) rename Source/ActionRPGGame/UI/{Abilities/ARAbilityManagerWidget.cpp => Inventory/ARListItemWeaponWidget.cpp} (70%) rename Source/ActionRPGGame/UI/{ARCharacterEquipmentWidget.h => Inventory/ARListItemWeaponWidget.h} (51%) delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp index cad2d6e..2067473 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp @@ -18,45 +18,3 @@ void UIFItemWidget::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex) const UIFItemBase* Item = Inventory->GetItem(InLocalIndex); BP_OnItemChanged(const_cast(Item)); } - -FReply UIFItemWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) -{ - const UIFItemBase* Item = Inventory->GetItem(LocalIndex); - if (Item) - { - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; - } - else - { - return FReply::Unhandled(); - } -} -void UIFItemWidget::NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) -{ - UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); - if (DragDropOp) - { - APlayerController* PC = GetOwningPlayer(); - - DragDropOp->Payload = this; - DragDropOp->DefaultDragVisual = DragVisual; - - OutOperation = DragDropOp; - } -} -bool UIFItemWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - UIFItemWidget* Payload = Cast(InOperation->Payload); - if (Payload->Inventory == Inventory) - { - Inventory->MoveItemInInventory(LocalIndex, Payload->LocalIndex); - } - else if (Payload->Inventory != Inventory) - { - Inventory->AddItemFromOtherInventory(Payload->Inventory.Get(), Payload->LocalIndex, LocalIndex); - } - return true; -} \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h index 73343a8..5af50e7 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -37,11 +37,4 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Changed")) void BP_OnItemChanged(class UIFItemBase* Item); - - virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) override; - virtual void NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; - virtual bool NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; }; diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp index e7cedd2..d4abf78 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp @@ -8,7 +8,6 @@ #include "DWBPFunctionLibrary.h" #include "SDraggableWindowWidget.h" #include "ARPlayerController.h" -#include "UI/Abilities/ARAbilityListWidget.h" // Sets default values for this component's properties UARAbilityManagerComponent::UARAbilityManagerComponent() @@ -30,21 +29,6 @@ void UARAbilityManagerComponent::BeginPlay() { APlayerController* OwnerPC = Cast(GetOwner()); // ... - if (ManagerWidgetClass) - { - ManagerWidget = CreateWidget(OwnerPC, ManagerWidgetClass); - ManagerWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); - ManagerWidget->ARPC = Cast(GetOwner()); - for (const FARAbilityItem& Ability : AvailableAbilities) - { - ManagerWidget->AddItem(DragWidgetClass, Ability.Ability); - } - - ManagerWindowHandle = UDWBPFunctionLibrary::CreateWindowWithContent(ManagerWidget, "Ability Manager"); - ManagerWindowHandle.Window.Pin()->bDestroyOnClose = false; - ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); - //ManagerWidget->AddToViewport(); - } } } @@ -59,19 +43,6 @@ void UARAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickT void UARAbilityManagerComponent::ShowHideAbilityManager() { - if (!ManagerWidget) - return; - - EVisibility Visibility = ManagerWindowHandle.Window.Pin()->GetVisibility(); - - if (Visibility == EVisibility::Collapsed) - { - ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::SelfHitTestInvisible); - } - else if (Visibility == EVisibility::SelfHitTestInvisible) - { - ManagerWindowHandle.Window.Pin()->SetVisibility(EVisibility::Collapsed); - } } void UARAbilityManagerComponent::SetCurrentSet(int32 SetIndex) diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h index 4f9e6d8..254e746 100644 --- a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h @@ -28,22 +28,8 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom { GENERATED_BODY() protected: - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf DragVisualClass; - - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf ManagerWidgetClass; - - UPROPERTY(EditAnywhere, Category = "Widget Config") - TSubclassOf DragWidgetClass; - - UPROPERTY() - class UARAbilityListWidget* ManagerWidget; - UPROPERTY(EditAnywhere) TArray AvailableAbilities; - - FDWWWindowHandle ManagerWindowHandle; public: UPROPERTY(BlueprintAssignable) FAROnAbilitySetChanged OnAbilitySetChanged; @@ -61,11 +47,6 @@ class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerCom void ShowHideAbilityManager(); - inline TSubclassOf GetDragVisualClass() - { - return DragVisualClass; - } - UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Ability Manager") void SetCurrentSet(int32 SetIndex); diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp b/Source/ActionRPGGame/UI/ARAbilityWidget.cpp deleted file mode 100644 index dac3b9f..0000000 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.cpp +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityWidget.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "AMAbilityManagerComponent.h" -#include "Abilities/GAAbilityBase.h" - -#include "ARAbilityBase.h" -#include "ARAbilityUIData.h" -#include "Input/Reply.h" -#include "Input/Events.h" -#include "Blueprint/WidgetBlueprintLibrary.h" -#include "../ARPlayerController.h" -#include "ARGlobals.h" - -void UARAbilityWidget::NativePreConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - UIComponent = MyPC->UIComponent; - AbilityManager = MyPC->AbilityManager; - } - Super::NativePreConstruct(); -} -void UARAbilityWidget::NativeConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - UIComponent = MyPC->UIComponent; - AbilityManager = MyPC->AbilityManager; - } - Super::NativeConstruct(); -} diff --git a/Source/ActionRPGGame/UI/ARAbilityWidget.h b/Source/ActionRPGGame/UI/ARAbilityWidget.h deleted file mode 100644 index 5d160c4..0000000 --- a/Source/ActionRPGGame/UI/ARAbilityWidget.h +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "ARUMGWidgetBase.h" -#include "GameplayTags.h" -#include "AssetRegistryModule.h" -#include "Engine/AssetManager.h" -#include "AMTypes.h" -#include "../Abilities/ARAbilityManagerComponent.h" -#include "ARAbilityWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityWidget : public UARUMGWidgetBase -{ - GENERATED_BODY() -public: - TWeakObjectPtr AbilityManager; - - virtual void NativePreConstruct() override; - virtual void NativeConstruct() override; -}; diff --git a/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp b/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp deleted file mode 100644 index d6ee0f6..0000000 --- a/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARCharacterEquipmentWidget.h" - - - - diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp b/Source/ActionRPGGame/UI/ARHUD.cpp similarity index 71% rename from Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp rename to Source/ActionRPGGame/UI/ARHUD.cpp index 2f7a4c2..c6f7d4e 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.cpp +++ b/Source/ActionRPGGame/UI/ARHUD.cpp @@ -1,6 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. -#include "ARAbilityDragVisual.h" +#include "ARHUD.h" diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h b/Source/ActionRPGGame/UI/ARHUD.h similarity index 53% rename from Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h rename to Source/ActionRPGGame/UI/ARHUD.h index b2e0ded..caa1819 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.h +++ b/Source/ActionRPGGame/UI/ARHUD.h @@ -3,14 +3,14 @@ #pragma once #include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "ARAbilityManagerWidget.generated.h" +#include "GameFramework/HUD.h" +#include "ARHUD.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARAbilityManagerWidget : public UUserWidget +class ACTIONRPGGAME_API AARHUD : public AHUD { GENERATED_BODY() diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 04a64a1..13e7bc4 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -8,9 +8,8 @@ #include "Inventory/ARInventoryManagerWidget.h" #include "Inventory/ARWeaponContainerWidget.h" - +#include "Inventory/ARItemWeaponWidget.h" #include "Inventory/ARInventoryScreenWidget.h" -#include "UI/Weapons/ARItemWeaponWidget.h" // Sets default values for this component's properties UARUIComponent::UARUIComponent() @@ -44,12 +43,6 @@ void UARUIComponent::BeginPlay() CrosshairWidget->SetVisibility(ESlateVisibility::HitTestInvisible); CrosshairWidget->AddToViewport(); } - /*if (InventoryManagerClass) - { - InventoryManagerWidget = CreateWidget(MyPC, InventoryManagerClass); - InventoryManagerWidget->SetVisibility(ESlateVisibility::Collapsed); - InventoryManagerWidget->AddToViewport(); - }*/ if (EnemyHealthBarClass) { @@ -64,12 +57,6 @@ void UARUIComponent::BeginPlay() HUDWidget->AddToViewport(); } - if (InventoryScreenWidgetClass) - { - InventoryScreenWidget = CreateWidget(MyPC, InventoryScreenWidgetClass); - InventoryScreenWidget->SetVisibility(ESlateVisibility::Collapsed); - InventoryScreenWidget->AddToViewport(); - } AARCharacter* Character = Cast(MyPC->GetPawn()); if (WeaponInventoryWidgetClass && Character) { @@ -114,7 +101,7 @@ void UARUIComponent::BeginPlay() InventoryScreenWidget->SideWeaponWidget->Inventory = MyPC->MainInventory; InventoryScreenWidget->SideWeaponWidget->WeaponInventory = WeapInv; InventoryScreenWidget->SideWeaponWidget->UI = this; - InventoryScreenWidget->RightWeaponWidget->InventoryWidget = InventoryScreenWidget; + InventoryScreenWidget->SideWeaponWidget->InventoryWidget = InventoryScreenWidget; InventoryScreenWidget->SideWeaponWidget->LocalIndex = Item.GetLocalIndex(); InventoryScreenWidget->SideWeaponWidget->NetIndex = Item.GetNetIndex(); @@ -152,18 +139,7 @@ void UARUIComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorC void UARUIComponent::InitializeInventory() { - if (GetOwner()->GetNetMode() == ENetMode::NM_Client - || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) - { - AARPlayerController* MyPC = Cast(GetOwner()); - if (InventoryWidgetClass) - { - InventoryWidget = CreateWidget(MyPC, InventoryWidgetClass); - InventoryWidget->SetInventory(MyPC->MainInventory); - InventoryWidget->CreateInventory(); - InventoryWidget->AddToViewport(); - } - } + } void UARUIComponent::InitializeWeaponInventory() { diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index 4b9d8ad..e56008e 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -27,12 +27,6 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY() UUserWidget* CrosshairWidget; - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf InventoryManagerClass; - UPROPERTY() - class UARInventoryManagerWidget* InventoryManagerWidget; - - UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf EnemyHealthBarClass; @@ -42,13 +36,6 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf HUDWidgetClass; - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf InventoryWidgetClass; - - UPROPERTY(BlueprintReadOnly, Category = "Widgets") - UIFItemContainerWidget* InventoryWidget; - - UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf WeaponInventoryWidgetClass; @@ -57,6 +44,9 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent public: UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf ItemWidgetClass; + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf ItemWeaponWidgetClass; + public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") diff --git a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp deleted file mode 100644 index 7770b2f..0000000 --- a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.cpp +++ /dev/null @@ -1,52 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponActriveInfoWidget.h" -#include "ARPlayerController.h" - -#include "ARAbilityBase.h" -#include "ARGunAttributes.h" -#include "../Weapons/ARWeaponManagerComponent.h" -#include "../Weapons/ARWeaponAbilityBase.h" - -float UARWeaponActriveInfoWidget::GetActiveMagazineAmmo() -{ - if (!WeaponEquipement.IsValid()) - return 0; - UGAAbilityBase* Ability = WeaponEquipement->GetCurrentWeapon(); - if (!Ability) - return 0; - - if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) - { - return Attributes->Magazine.GetCurrentValue(); - } - return 0; -} - -float UARWeaponActriveInfoWidget::GetActiveMagazineAmmoNormalized() -{ - if (!WeaponEquipement.IsValid()) - return 0; - UGAAbilityBase* Ability = WeaponEquipement->GetCurrentWeapon(); - if (!Ability) - return 0; - - if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) - { - float CurrentValue = Attributes->Magazine.GetCurrentValue(); - FVector2D Input(0, Attributes->Magazine.GetFinalValue()); - return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); - } - return 0; -} - -float UARWeaponActriveInfoWidget::GetReloadTimeNormalized() -{ - if (!WeaponEquipement.IsValid()) - return 0; - UGAAbilityBase* Ability = WeaponEquipement->GetCurrentWeapon(); - if (!Ability) - return 0; - - return Ability->GetCooldownRemainingTimeNormalized(); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h b/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h deleted file mode 100644 index c324325..0000000 --- a/Source/ActionRPGGame/UI/ARWeaponActriveInfoWidget.h +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/ARWeaponInfoWidget.h" -#include "ARWeaponActriveInfoWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponActriveInfoWidget : public UARWeaponInfoWidget -{ - GENERATED_BODY() - -public: - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") - float GetActiveMagazineAmmo(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") - float GetActiveMagazineAmmoNormalized(); - - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") - float GetReloadTimeNormalized(); - -}; diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp deleted file mode 100644 index 1c19fc8..0000000 --- a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.cpp +++ /dev/null @@ -1,63 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponInfoWidget.h" -#include "ARPlayerController.h" -#include "ARAbilityBase.h" -#include "ARGunAttributes.h" -#include "../Weapons/ARWeaponAbilityBase.h" -#include "../Weapons/ARWeaponManagerComponent.h" -void UARWeaponInfoWidget::NativePreConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - WeaponEquipement = MyPC->WeaponManager; - } -Super::NativePreConstruct(); -} -void UARWeaponInfoWidget::NativeConstruct() -{ - UARWeaponManagerComponent* WMC = nullptr; - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - WeaponEquipement = MyPC->WeaponManager; - WMC = MyPC->WeaponManager; - } - if (WeaponSlotTag.IsValid()) - { - // FAROnWeaponReady Delegate = FAROnWeaponReady::CreateUObject(this, &UARWeaponInfoWidget::OnWeaponChanged); - // WMC->AddOnWeaponChangedEvent(WeaponSlotTag, Delegate); - } - Super::NativeConstruct(); -} - -float UARWeaponInfoWidget::GetMagazineAmmo() -{ - UGAAbilityBase* Ability = WeaponEquipement->GetAbility(SlotIndex, EAMSlot::Slot001); - if (!Ability) - return 0; - - if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) - { - return Attributes->Magazine.GetCurrentValue(); - } - return 0; -} -float UARWeaponInfoWidget::GetMagazineAmmoNormalized() -{ - UGAAbilityBase* Ability = WeaponEquipement->GetAbility(SlotIndex, EAMSlot::Slot001); - if (!Ability) - return 0; - - if (UARGunAttributes* Attributes = Cast(Ability->Attributes)) - { - float CurrentValue = Attributes->Magazine.GetCurrentValue(); - FVector2D Input(0, Attributes->Magazine.GetFinalValue()); - return FMath::GetMappedRangeValueClamped(Input, FVector2D(0, 1), CurrentValue); - } - return 0; -} - -void UARWeaponInfoWidget::OnWeaponChanged(class UARWeaponAbilityBase* InAbility) -{ - -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h b/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h deleted file mode 100644 index d3eab88..0000000 --- a/Source/ActionRPGGame/UI/ARWeaponInfoWidget.h +++ /dev/null @@ -1,42 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "ARUMGWidgetBase.h" -#include "ARGunAttributes.h" -#include "GameplayTags.h" -#include "../Weapons/ARWeaponsTypes.h" -#include "AMTypes.h" -#include "ARWeaponInfoWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponInfoWidget : public UARUMGWidgetBase -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, BlueprintReadOnly) - EAMGroup SlotIndex; - - UPROPERTY(EditAnywhere, BlueprintReadOnly) - FGameplayTag WeaponSlotTag; - - TWeakObjectPtr Weapon; - - TWeakObjectPtr WeaponEquipement; -public: - - virtual void NativePreConstruct() override; - virtual void NativeConstruct() override; - - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") - float GetMagazineAmmo(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Weapon") - float GetMagazineAmmoNormalized(); - - UFUNCTION() - void OnWeaponChanged(class UARWeaponAbilityBase* InAbility); -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp deleted file mode 100644 index 41b86d0..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.cpp +++ /dev/null @@ -1,35 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityCrosshairInfo.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "Abilities/GAAbilityBase.h" -#include "ARPlayerController.h" -#include "Abilities/ARAbilityBase.h" -#include "Abilities/ARAbilityManagerComponent.h" - -void UARAbilityCrosshairInfo::NativePreConstruct() -{ - Super::NativePreConstruct(); - - CrosshairImage->SetBrushFromMaterial(CrosshairMaterial); -} -void UARAbilityCrosshairInfo::NativeConstruct() -{ - Super::NativeConstruct(); - - CrosshairImage->SetBrushFromMaterial(CrosshairMaterial); - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - MyPC->AbilityManager->OnAbilitySetChanged.AddDynamic(this, &UARAbilityCrosshairInfo::OnAbilityGroupChanged); - } -} - -void UARAbilityCrosshairInfo::NativeTick(const FGeometry& MyGeometry, float InDeltaTime) -{ - Super::NativeTick(MyGeometry, InDeltaTime); - - float CooldownRemaining = FMath::GetMappedRangeValueClamped(FVector2D(0, 1), FVector2D(1, 0), GetRemainingCooldown()); - - CrosshairImage->GetDynamicMaterial()->SetScalarParameterValue(TEXT("Percentage"), CooldownRemaining); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h deleted file mode 100644 index 22b46bf..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityCrosshairInfo.h +++ /dev/null @@ -1,32 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "ARUMGWidgetBase.h" -#include "GameplayTags.h" -#include "Abilities/GAAbilityBase.h" -#include "ARAbilityInfoWidget.h" -#include "ARAbilityCrosshairInfo.generated.h" -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityCrosshairInfo : public UARAbilityInfoWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Config") - UMaterialInterface* CrosshairMaterial; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* CrosshairImage; -public: - virtual void NativePreConstruct() override; - virtual void NativeConstruct() override; - virtual void NativeTick(const FGeometry& MyGeometry, float InDeltaTime) override; - - UFUNCTION(BlueprintImplementableEvent, Category = "ActionRPGGame|UI") - void OnAbilityGroupChanged(EAMGroup CurrentGroup); -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h deleted file mode 100644 index 209d342..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityDragVisual.h +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "AMTypes.h" -#include "ARAbilityDragVisual.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityDragVisual : public UUserWidget -{ - GENERATED_BODY() -public: - UPROPERTY() - class UARAbilityManagerComponent* AbilityManager; - UPROPERTY(EditAnywhere, Category = "Config") - EAMGroup Group; - UPROPERTY(EditAnywhere, Category = "Config") - EAMSlot AbilitySlot; - - - -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp deleted file mode 100644 index c1f877e..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityInfoWidget.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "Abilities/GAAbilityBase.h" -#include "ARPlayerController.h" -#include "Abilities/ARAbilityBase.h" -#include "Abilities/ARAbilityManagerComponent.h" - -float UARAbilityInfoWidget::GetRemainingCooldown() const -{ - if (!AbilityManager.IsValid()) - return 0; - - UGAAbilityBase* Ability = AbilityManager->GetAbility(AbilityGroup, AbilitySlot); - if (Ability) - { - return Ability->GetCooldownRemainingTimeNormalized(); - } - return 0; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h deleted file mode 100644 index 905b683..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityInfoWidget.h +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "ARUMGWidgetBase.h" -#include "GameplayTags.h" -#include "Abilities/GAAbilityBase.h" -#include "ARAbilityWidget.h" -#include "ARAbilityInfoWidget.generated.h" -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityInfoWidget : public UARAbilityWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Ability") - EAMSlot AbilitySlot; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Ability") - EAMGroup AbilityGroup; - - float GetRemainingCooldown() const; -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp deleted file mode 100644 index 192645e..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.cpp +++ /dev/null @@ -1,60 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityListSlotDragWidget.h" -#include "Blueprint/WidgetBlueprintLibrary.h" - -#include "ARAbilityDragVisual.h" -#include "Abilities/ARAbilityManagerComponent.h" -#include "Abilities/ARAbilityBase.h" -#include "Abilities/ARAbilityUIData.h" - -FReply UARAbilityListSlotDragWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) -{ - return UWidgetBlueprintLibrary::DetectDragIfPressed(InMouseEvent, this, EKeys::LeftMouseButton).NativeReply; - //return FReply::Unhandled(); -} - -void UARAbilityListSlotDragWidget::NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) -{ - UDragDropOperation* DragDropOp = NewObject(UDragDropOperation::StaticClass()); - if (DragDropOp) - { - APlayerController* MyPC = Cast(AbilityManager->GetOwner()); - //UARAbilityDragVisual* DragIcon = CreateWidget(MyPC, AbilityManager->GetDragVisualClass()); - //DragIcon->AbilityManager = AbilityManager; - - DragDropOp->Payload = this; - DragDropOp->DefaultDragVisual = IconImage; - - OutOperation = DragDropOp; - } -} - -void UARAbilityListSlotDragWidget::OnItemAdded() -{ - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UARAbilityListSlotDragWidget::OnItemLoaded, AbilityTag); - - Manager.RequestAsyncLoad(AbilityTag.ToSoftObjectPath() - , del); - } -} - -void UARAbilityListSlotDragWidget::OnItemLoaded(TSoftClassPtr InPrimaryAssetId) -{ - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - { - TSubclassOf AbilityClass = InPrimaryAssetId.Get(); - if (AbilityClass) - { - IconImage->SetBrushFromTexture(AbilityClass.GetDefaultObject()->UIData->Icon); - } - - { - Manager.Unload(InPrimaryAssetId.ToSoftObjectPath()); - } - } -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h deleted file mode 100644 index 21c4981..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDragWidget.h +++ /dev/null @@ -1,37 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/ARAbilityWidget.h" -#include "AMTypes.h" -#include "ARAbilityListSlotDragWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityListSlotDragWidget : public UARAbilityWidget -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Config") - TSoftClassPtr AbilityTag; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* IconImage; -public: - virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent) override; - virtual void NativeOnDragDetected(const FGeometry& InGeometry - , const FPointerEvent& InMouseEvent, UDragDropOperation*& OutOperation) override; - - inline const TSoftClassPtr& GetAbilityTag() const - { - return AbilityTag; - } - - void OnItemAdded(); -protected: - void OnItemLoaded(TSoftClassPtr InPrimaryAssetId); -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp deleted file mode 100644 index 28274c4..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.cpp +++ /dev/null @@ -1,55 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityListSlotDropWidget.h" - -#include "ARAbilityListSlotDragWidget.h" -#include "Abilities/ARAbilityManagerComponent.h" -#include "UI/ARUIComponent.h" - -bool UARAbilityListSlotDropWidget::NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) -{ - UARAbilityListSlotDragWidget* Payload = Cast(InOperation->Payload); - FSlateBrush brush = Payload->IconImage->Brush; - - AbilityManager->NativeEquipAbility(Payload->GetAbilityTag(), AbilityGroup, AbilitySlot); - - IconImage->SetBrush(brush); - if (AbilityGroup == EAMGroup::Group001) - { - switch (AbilitySlot) - { - case EAMSlot::Slot001: - //probabaly should just bind delgate from widget and track ability change. - UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot001->AbilityIcon->SetBrush(brush); //DAT BAD - break; - case EAMSlot::Slot002: - UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot002->AbilityIcon->SetBrush(brush); //DAT BAD - break; - case EAMSlot::Slot003: - UIComponent->HUDWidget->PlayerInfo->AbilityGroup001Slot003->AbilityIcon->SetBrush(brush); //DAT BAD - break; - default: - break; - } - } - else if (AbilityGroup == EAMGroup::Group002) - { - switch (AbilitySlot) - { - case EAMSlot::Slot001: - UIComponent->HUDWidget->PlayerInfo->AbilityGroup002Slot001->AbilityIcon->SetBrush(brush); //DAT BAD - break; - case EAMSlot::Slot002: - UIComponent->HUDWidget->PlayerInfo->AbilityGroup002Slot002->AbilityIcon->SetBrush(brush); //DAT BAD - break; - case EAMSlot::Slot003: - UIComponent->HUDWidget->PlayerInfo->AbilityGroup002Slot003->AbilityIcon->SetBrush(brush); //DAT BAD - break; - default: - break; - } - } - - return true; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h deleted file mode 100644 index a19830d..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListSlotDropWidget.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/ARAbilityWidget.h" -#include "AMTypes.h" -#include "ARAbilityListSlotDropWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityListSlotDropWidget : public UARAbilityWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Config") - EAMGroup AbilityGroup; - UPROPERTY(EditAnywhere, Category = "Config") - EAMSlot AbilitySlot; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* IconImage; -public: - virtual bool NativeOnDrop(const FGeometry& InGeometry - , const FDragDropEvent& InDragDropEvent, UDragDropOperation* InOperation) override; -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp deleted file mode 100644 index d6da4dc..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.cpp +++ /dev/null @@ -1,15 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityListWidget.h" -#include "ARAbilityListSlotDragWidget.h" - -#include "ARPlayerController.h" - -void UARAbilityListWidget::AddItem(TSubclassOf DragWidgetClass, const TSoftClassPtr& Ability) -{ - UARAbilityListSlotDragWidget* Item = CreateWidget(ARPC.Get(), DragWidgetClass); - Item->AbilityTag = Ability; - Items.Add(Item); - Item->OnItemAdded(); - ItemContainer->AddChild(Item); -} diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h deleted file mode 100644 index fecd6a4..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityListWidget.h +++ /dev/null @@ -1,42 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "Components/WrapBox.h" -#include "ARAbilityListWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilityListWidget : public UUserWidget -{ - GENERATED_BODY() -public: - TWeakObjectPtr ARPC; -protected: - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UWrapBox* ItemContainer; - - //Currently Equiped abilities - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARAbilityListSlotDropWidget* Ability001Group001; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARAbilityListSlotDropWidget* Ability002Group001; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARAbilityListSlotDropWidget* Ability003Group001; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARAbilityListSlotDropWidget* Ability001Group002; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARAbilityListSlotDropWidget* Ability002Group002; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - class UARAbilityListSlotDropWidget* Ability003Group002; - - UPROPERTY() - TArray Items; -public: - void AddItem(TSubclassOf DragWidgetClass, const TSoftClassPtr& Ability); -}; diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp deleted file mode 100644 index f734089..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.cpp +++ /dev/null @@ -1,88 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilitySlotWidget.h" - -#include "AMAbilityManagerComponent.h" -#include "Abilities/GAAbilityBase.h" - -#include "ARAbilityBase.h" -#include "ARAbilityUIData.h" - -void UARAbilitySlotWidget::NativeTick(const FGeometry& MyGeometry, float InDeltaTime) -{ - Super::NativeTick(MyGeometry, InDeltaTime); - - CooldownBar->SetPercent(GetCooldownRemainingTimeNormalized()); -} - -float UARAbilitySlotWidget::GetActivationRemainingTime() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationRemainingTime() : 0; -} -float UARAbilitySlotWidget::GetActivationRemainingTimeNormalized() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationRemainingTimeNormalized() : 0; -} -float UARAbilitySlotWidget::GetActivationCurrentTime() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationCurrentTime() : 0; -} -float UARAbilitySlotWidget::GetActivationCurrentTimeNormalized() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationCurrentTimeNormalized() : 0; -} -float UARAbilitySlotWidget::GetActivationEndTime() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetActivationEndTime() : 0; -} - -float UARAbilitySlotWidget::GetCooldownRemainingTime() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownRemainingTime() : 0; -} -float UARAbilitySlotWidget::GetCooldownRemainingTimeNormalized() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownRemainingTimeNormalized() : 0; -} -float UARAbilitySlotWidget::GetCooldownCurrentTime() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownCurrentTime() : 0; -} -float UARAbilitySlotWidget::GetCooldownCurrentTimeNormalized() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownCurrentTimeNormalized() : 0; -} -float UARAbilitySlotWidget::GetCooldownEndTime() -{ - if (!AbilityManager.IsValid()) - return 0; - UGAAbilityBase* Ability = AbilityManager->GetAbility(Group, AbilitySlot); - return Ability ? Ability->GetCooldownEndTime() : 0; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h b/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h deleted file mode 100644 index 05c2cff..0000000 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilitySlotWidget.h +++ /dev/null @@ -1,54 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/ARAbilityWidget.h" -#include "AMTypes.h" -#include "ARAbilitySlotWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARAbilitySlotWidget : public UARAbilityWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Config") - EAMGroup Group; - UPROPERTY(EditAnywhere, Category = "Config") - EAMSlot AbilitySlot; -public: - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UProgressBar* CooldownBar; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* AbilityIcon; -public: - - virtual void NativeTick(const FGeometry& MyGeometry, float InDeltaTime) override; - - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationRemainingTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationCurrentTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetActivationEndTime(); - - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownRemainingTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownCurrentTime(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, Category = "ActionRPGGame|UI|Abilities") - float GetCooldownEndTime(); - - -}; diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h index cbd6668..016e84c 100644 --- a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h +++ b/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h @@ -7,8 +7,6 @@ #include "Components/ProgressBar.h" #include "UI/ARUMGWidgetBase.h" -#include "UI/Weapons/ARWeaponSlotWidget.h" -#include "UI/Abilities/ARAbilitySlotWidget.h" #include "ARHUDPlayerInfo.generated.h" /** @@ -26,19 +24,19 @@ class ACTIONRPGGAME_API UARHUDPlayerInfo : public UARUMGWidgetBase UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UProgressBar* PlayerEnergy; public: - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARAbilitySlotWidget* AbilityGroup001Slot001; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARAbilitySlotWidget* AbilityGroup001Slot002; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARAbilitySlotWidget* AbilityGroup001Slot003; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARAbilitySlotWidget* AbilityGroup001Slot001; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARAbilitySlotWidget* AbilityGroup001Slot002; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARAbilitySlotWidget* AbilityGroup001Slot003; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARAbilitySlotWidget* AbilityGroup002Slot001; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARAbilitySlotWidget* AbilityGroup002Slot002; - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UARAbilitySlotWidget* AbilityGroup002Slot003; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARAbilitySlotWidget* AbilityGroup002Slot001; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARAbilitySlotWidget* AbilityGroup002Slot002; + //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + // UARAbilitySlotWidget* AbilityGroup002Slot003; //UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) // UARWeaponSlotWidget* Weapon001; diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp index 574bcaa..65160bf 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp @@ -3,12 +3,7 @@ #include "ARInventoryScreenWidget.h" #include "Components/TextBlock.h" -#include "Components/WrapBox.h" -#include "IFInventoryComponent.h" -#include "IFItemWidget.h" - -#include "UI/ARUIComponent.h" #include "ARPlayerController.h" void UARInventoryScreenWidget::SetWeaponName(const FString& Name) diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h index adc847f..9f12bc1 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h @@ -4,6 +4,14 @@ #include "CoreMinimal.h" #include "UI/ARUMGWidgetBase.h" + +#include "Components/WrapBox.h" + +#include "IFInventoryComponent.h" +#include "IFItemWidget.h" + +#include "UI/ARUIComponent.h" + #include "ARInventoryScreenWidget.generated.h" /** @@ -44,4 +52,26 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase void UpdateItemList(const TArray& LocalIdxs); + template + void UpdateItemList(const TArray& LocalIdxs, TSubclassOf WidgetClass) + { + SelectedItemsContainer->ClearChildren(); + + for (uint8 Idx : LocalIdxs) + { + ItemType* Item = Inventory->GetItem(Idx); + + if (Item) + { + const FIFItemData& Slot = Inventory->GetSlot(Idx); + WidgetType* ItemWidget = CreateWidget(PC.Get(), WidgetClass); + ItemWidget->Inventory = Inventory; + ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); + ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex()); + + SelectedItemsContainer->AddChild(ItemWidget); + } + } + } + }; diff --git a/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.cpp similarity index 83% rename from Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp rename to Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.cpp index d0a49ad..2328b3a 100644 --- a/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.cpp @@ -9,6 +9,8 @@ #include "UI/Inventory/ARWeaponContainerWidget.h" #include "UI/Inventory/ARInventoryScreenWidget.h" +#include "UI/Inventory/ARListItemWeaponWidget.h" + void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { @@ -20,7 +22,7 @@ void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const { InventoryWidget->SetWeaponName(CurrentItem->GetName()); } - InventoryWidget->UpdateItemList(Items); + InventoryWidget->UpdateItemList(Items, UI->ItemWeaponWidgetClass); } void UARItemWeaponWidget::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) { diff --git a/Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Weapons/ARItemWeaponWidget.h rename to Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.h diff --git a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.cpp similarity index 70% rename from Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp rename to Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.cpp index 576b0bd..e59c00e 100644 --- a/Source/ActionRPGGame/UI/Abilities/ARAbilityManagerWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.cpp @@ -1,6 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. -#include "ARAbilityManagerWidget.h" +#include "ARListItemWeaponWidget.h" diff --git a/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h b/Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.h similarity index 51% rename from Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h rename to Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.h index 64facea..30280f1 100644 --- a/Source/ActionRPGGame/UI/ARCharacterEquipmentWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.h @@ -3,14 +3,14 @@ #pragma once #include "CoreMinimal.h" -#include "UI/ARUMGWidgetBase.h" -#include "ARCharacterEquipmentWidget.generated.h" +#include "IFItemWidget.h" +#include "ARListItemWeaponWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARCharacterEquipmentWidget : public UARUMGWidgetBase +class ACTIONRPGGAME_API UARListItemWeaponWidget : public UIFItemWidget { GENERATED_BODY() diff --git a/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp index 38e1918..0bd947e 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp @@ -8,7 +8,6 @@ #include "ARCharacter.h" #include "UI/ARUIComponent.h" -#include "UI/Weapons/ARItemWeaponWidget.h" void UARWeaponContainerWidget::InitializeWeaponItems(class UARUIComponent* UIComponent) diff --git a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp deleted file mode 100644 index c83f6d7..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARMagazineUpgradeWidget.h" -#include "Weapons/ARWeaponManagerComponent.h" -#include "Weapons/ARItemWeapon.h" - - - -FReply UARMagazineUpgradeWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) -{ - WeaponManager->WeaponToModify->AddMagazineUpgrade(WeaponUpgrade); - return FReply::Unhandled(); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h b/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h deleted file mode 100644 index 6920324..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARMagazineUpgradeWidget.h +++ /dev/null @@ -1,21 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/Weapons/ARUpgradeBaseWidget.h" -#include "ARMagazineUpgradeWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARMagazineUpgradeWidget : public UARUpgradeBaseWidget -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UImage* Icon; - TSoftClassPtr WeaponUpgrade; - virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; -}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp deleted file mode 100644 index 284bcf9..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARUpgradeBaseWidget.h" - - - - diff --git a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h deleted file mode 100644 index 5a36e02..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARUpgradeBaseWidget.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/Weapons/ARWeaponBaseWidget.h" -#include "ARUpgradeBaseWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARUpgradeBaseWidget : public UARWeaponBaseWidget -{ - GENERATED_BODY() -public: - - - -}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp deleted file mode 100644 index 22d6008..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponBaseWidget.h" - -#include "../../ARPlayerController.h" -#include "../../Weapons/ARWeaponManagerComponent.h" - - - -void UARWeaponBaseWidget::NativePreConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - WeaponManager = MyPC->WeaponManager; - } - Super::NativePreConstruct(); -} -void UARWeaponBaseWidget::NativeConstruct() -{ - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - WeaponManager = MyPC->WeaponManager; - } - Super::NativeConstruct(); -} - - diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h deleted file mode 100644 index b56ab50..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponBaseWidget.h +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/ARUMGWidgetBase.h" -#include "ARWeaponBaseWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponBaseWidget : public UARUMGWidgetBase -{ - GENERATED_BODY() - public: - TWeakObjectPtr WeaponManager; - -public: - void NativePreConstruct(); - void NativeConstruct(); - - - -}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp deleted file mode 100644 index 78f94c0..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.cpp +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponSlotWidget.h" - - - - -float UARWeaponSlotWidget::GetCurrentReloadTime() const -{ - return 0; -} - -float UARWeaponSlotWidget::GetCurrentReloadTimeNormalized() const -{ - return 0; -} - -float UARWeaponSlotWidget::GetMagazineAmmo() const -{ - return 0; -} - -float UARWeaponSlotWidget::GetRemaningAmmo() const -{ - return 0; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h deleted file mode 100644 index 5f5d4c2..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponSlotWidget.h +++ /dev/null @@ -1,31 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UI/Weapons/ARWeaponBaseWidget.h" -#include "AMTypes.h" -#include "ARWeaponSlotWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponSlotWidget : public UARWeaponBaseWidget -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - EAMGroup WeaponSlot; - - - UFUNCTION(BlueprintPure, Category = "Weapon") - float GetCurrentReloadTime() const; - UFUNCTION(BlueprintPure, Category = "Weapon") - float GetCurrentReloadTimeNormalized() const; - UFUNCTION(BlueprintPure, Category = "Weapon") - float GetMagazineAmmo() const; - UFUNCTION(BlueprintPure, Category = "Weapon") - float GetRemaningAmmo() const; - -}; diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp b/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp deleted file mode 100644 index 1b6fe7e..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.cpp +++ /dev/null @@ -1,30 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponUpgradeListWidget.h" - -#include "ARPlayerController.h" -#include "Weapons/ARMagazineUpgradeItem.h" -#include "UI/Weapons/ARMagazineUpgradeWidget.h" -#include "Components/WrapBox.h" -#include "Components/Image.h" -#include "Weapons/ARWeaponManagerComponent.h" - - - -void UARWeaponUpgradeListWidget::OnShow() -{ - UpgradeList.Empty(); - ItemContainer->ClearChildren(); - - for (const TSubclassOf& Upgrade : WeaponManager->MagazineUpgradesClasses) - { - UARMagazineUpgradeItem* CDO = Upgrade->GetDefaultObject(); - - UARMagazineUpgradeWidget* Item = CreateWidget(Cast(WeaponManager->GetOwner()), WeaponManager->MagazineUpgradeClass); - Item->WeaponManager = WeaponManager; - Item->WeaponUpgrade = Upgrade; - Item->Icon->SetBrushFromTexture(CDO->Icon); - UpgradeList.Add(Item); - ItemContainer->AddChild(Item); - } -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h b/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h deleted file mode 100644 index 6056578..0000000 --- a/Source/ActionRPGGame/UI/Weapons/ARWeaponUpgradeListWidget.h +++ /dev/null @@ -1,24 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "ARWeaponBaseWidget.h" -#include "ARWeaponUpgradeListWidget.generated.h" - -/** - * Contains list of upgrades for weapon, for selected slot. - */ -UCLASS() -class ACTIONRPGGAME_API UARWeaponUpgradeListWidget : public UARWeaponBaseWidget -{ - GENERATED_BODY() -protected: - UPROPERTY() - TArray UpgradeList; - - UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) - UWrapBox* ItemContainer; -public: - void OnShow(); -}; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp index 89dbcc7..6dfde29 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp @@ -7,7 +7,6 @@ #include "ARItemWeapon.h" #include "ARCharacter.h" #include "ARPlayerController.h" -#include "UI/Weapons/ARWeaponUpgradeListWidget.h" #include "DWBPFunctionLibrary.h" #include "SDraggableWindowWidget.h" @@ -85,7 +84,6 @@ UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() void UARWeaponManagerComponent::AddToWeaponInventory(TSubclassOf InWeapon) { - WeaponClasses.Add(InWeapon); } void UARWeaponManagerComponent::BP_AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) @@ -94,32 +92,6 @@ void UARWeaponManagerComponent::BP_AddWeaponToManager(EAMGroup Group, EAMSlot Sl } void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) { - AARCharacter* Character = Cast(POwner); - UARItemWeapon* Item = DuplicateObject(WeaponClasses[Idx].GetDefaultObject(), Character); - if (Character) - { - ActiveGroup = EAMGroup::Group005; - } - NativeEquipAbility(WeaponClasses[Idx].GetDefaultObject()->Ability, - Group, EAMSlot::Slot001, POwner); - - if (IsClient()) - { - ServerAddWeaponToManager(Group, Slot, Idx); - } - else - { - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(POwner); - if (!ABInt) - return; - - ActiveGroup = EAMGroup::Group005; - } - } void UARWeaponManagerComponent::ServerAddWeaponToManager_Implementation(EAMGroup Group, EAMSlot Slot, int32 Idx) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h index 956441d..b84d576 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h @@ -45,24 +45,9 @@ class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComp protected: static constexpr int32 MAX_WEAPONS = 4; //maximum weapon + empty hands public: - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") - TArray> WeaponClasses; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Weapons") - TArray> MagazineUpgradesClasses; - UPROPERTY(EditAnywhere, Category = "Attachment Config") FName EquipSocketName; - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf MagazineUpgradeListClass; - - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf MagazineUpgradeClass; - - UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon|Widgets") - class UARWeaponUpgradeListWidget* MagazineUpgradeListWidget; - //maybe not reference directly ? TWeakObjectPtr WeaponToModify; From 34571f632d93c75f05f3f01e8b4d91f4033ddc1b Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 17 Apr 2018 00:04:20 +0200 Subject: [PATCH 135/187] move files --- Source/ActionRPGGame/UI/ARUIComponent.cpp | 5 ++--- .../UI/Inventory/ARInventoryManagerWidget.cpp | 7 ------- .../UI/Inventory/ARInventoryManagerWidget.h | 20 ------------------- .../{ => Weapons}/ARItemWeaponWidget.cpp | 4 ++-- .../{ => Weapons}/ARItemWeaponWidget.h | 0 .../{ => Weapons}/ARListItemWeaponWidget.cpp | 0 .../{ => Weapons}/ARListItemWeaponWidget.h | 0 .../{ => Weapons}/ARWeaponContainerWidget.cpp | 0 .../{ => Weapons}/ARWeaponContainerWidget.h | 0 9 files changed, 4 insertions(+), 32 deletions(-) delete mode 100644 Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp delete mode 100644 Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h rename Source/ActionRPGGame/UI/Inventory/{ => Weapons}/ARItemWeaponWidget.cpp (87%) rename Source/ActionRPGGame/UI/Inventory/{ => Weapons}/ARItemWeaponWidget.h (100%) rename Source/ActionRPGGame/UI/Inventory/{ => Weapons}/ARListItemWeaponWidget.cpp (100%) rename Source/ActionRPGGame/UI/Inventory/{ => Weapons}/ARListItemWeaponWidget.h (100%) rename Source/ActionRPGGame/UI/Inventory/{ => Weapons}/ARWeaponContainerWidget.cpp (100%) rename Source/ActionRPGGame/UI/Inventory/{ => Weapons}/ARWeaponContainerWidget.h (100%) diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index 13e7bc4..b631393 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -6,9 +6,8 @@ #include "ARCharacter.h" #include "ARPlayerController.h" -#include "Inventory/ARInventoryManagerWidget.h" -#include "Inventory/ARWeaponContainerWidget.h" -#include "Inventory/ARItemWeaponWidget.h" +#include "Inventory/Weapons/ARWeaponContainerWidget.h" +#include "Inventory/Weapons/ARItemWeaponWidget.h" #include "Inventory/ARInventoryScreenWidget.h" // Sets default values for this component's properties diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp deleted file mode 100644 index 88439ed..0000000 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARInventoryManagerWidget.h" - - - - diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h deleted file mode 100644 index 09d0e55..0000000 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryManagerWidget.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "ARInventoryManagerWidget.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UARInventoryManagerWidget : public UUserWidget -{ - GENERATED_BODY() - - - - -}; diff --git a/Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp similarity index 87% rename from Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.cpp rename to Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index 2328b3a..30f210a 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -7,9 +7,9 @@ #include "Weapons/ARItemWeapon.h" #include "Weapons/ARWeaponInventoryComponent.h" -#include "UI/Inventory/ARWeaponContainerWidget.h" #include "UI/Inventory/ARInventoryScreenWidget.h" -#include "UI/Inventory/ARListItemWeaponWidget.h" +#include "UI/Inventory/Weapons/ARWeaponContainerWidget.h" +#include "UI/Inventory/Weapons/ARListItemWeaponWidget.h" void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) diff --git a/Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.h b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARItemWeaponWidget.h rename to Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h diff --git a/Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.cpp rename to Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.h b/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARListItemWeaponWidget.h rename to Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h diff --git a/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.cpp rename to Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.h b/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARWeaponContainerWidget.h rename to Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.h From c9b879fdb0eb0eef172cec55737c04816c6ec35c Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 17 Apr 2018 22:37:38 +0200 Subject: [PATCH 136/187] working on player inventory screen --- .../Private/IFInventoryComponent.cpp | 80 +++++++--- .../Public/IFInventoryComponent.h | 38 +++-- .../Private/IFItemContainerWidget.cpp | 17 --- .../Private/IFItemWidget.cpp | 13 +- .../Public/IFItemWidget.h | 9 +- Source/ActionRPGGame/ARCharacter.cpp | 8 +- Source/ActionRPGGame/ARPlayerController.cpp | 7 +- Source/ActionRPGGame/UI/ARHUD.cpp | 20 ++- Source/ActionRPGGame/UI/ARHUD.h | 18 ++- Source/ActionRPGGame/UI/ARUIComponent.cpp | 102 ------------- Source/ActionRPGGame/UI/ARUIComponent.h | 19 --- .../UI/Inventory/ARInventoryScreenWidget.cpp | 40 ++--- .../UI/Inventory/ARInventoryScreenWidget.h | 39 ++++- .../ActionRPGGame/UI/Inventory/ARItemView.cpp | 20 +++ .../ActionRPGGame/UI/Inventory/ARItemView.h | 24 +++ .../UI/Inventory/ARListItemView.cpp | 20 +++ .../UI/Inventory/ARListItemView.h | 26 ++++ .../UI/Inventory/ARUIInventoryComponent.cpp | 137 ++++++++++++++++++ .../UI/Inventory/ARUIInventoryComponent.h | 54 +++++++ .../Inventory/Weapons/ARItemWeaponWidget.cpp | 35 +++-- .../UI/Inventory/Weapons/ARItemWeaponWidget.h | 12 +- .../Weapons/ARListItemWeaponWidget.cpp | 11 ++ .../Weapons/ARListItemWeaponWidget.h | 10 +- .../Weapons/ARWeaponContainerWidget.cpp | 11 -- 24 files changed, 517 insertions(+), 253 deletions(-) create mode 100644 Source/ActionRPGGame/UI/Inventory/ARItemView.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/ARItemView.h create mode 100644 Source/ActionRPGGame/UI/Inventory/ARListItemView.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/ARListItemView.h create mode 100644 Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 4b52320..9f91ee0 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -11,10 +11,6 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" -void FIFItemData::SetOnItemChanged(FIFOnItemChangedEvent& Event) -{ - OnItemChanged = Event; -} void FIFItemData::PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer) { if(Item) @@ -45,22 +41,23 @@ void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerial void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySerializer) { - InArraySerializer.IC->OnItemChangedEvent.Broadcast(NetIndex, LocalIndex); - OnItemChanged.ExecuteIfBound(NetIndex, LocalIndex); if (Item) { switch (ChangeType) { case EIFChangeType::Added: Item->OnItemAdded(LocalIndex); + InArraySerializer.IC->OnItemAddedEvent.Broadcast(NetIndex, LocalIndex, Item); InArraySerializer.IC->OnItemAdded(Item, LocalIndex); break; case EIFChangeType::Updated: Item->OnItemChanged(LocalIndex); + InArraySerializer.IC->OnItemUpdatedEvent.Broadcast(NetIndex, LocalIndex, Item); InArraySerializer.IC->OnItemChanged(Item, LocalIndex); break; case EIFChangeType::Removed: Item->OnItemRemoved(LocalIndex); + InArraySerializer.IC->OnItemRemovedEvent.Broadcast(NetIndex, LocalIndex, Item); InArraySerializer.IC->OnItemRemoved(LocalIndex); break; default: @@ -88,6 +85,7 @@ void FIFItemContainer::AddItem(class UIFItemBase* InItem, uint8 InNetIndex) Item.ChangeType = EIFChangeType::Added; Item.Item->OnItemAdded(LocalIndex); IC->OnItemAdded(Item.Item, Item.LocalIndex); + IC->OnItemAddedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); MarkItemDirty(Item); } @@ -98,10 +96,10 @@ void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) if (!Item.Item) { Item.Item = InItem; - //should be safe to call. On server it probabaly won't do anything and on standalone/clients will update widget. - Item.OnSlotChanged(); + Item.Item->OnItemAdded(Item.LocalIndex); IC->OnItemAdded(Item.Item, Item.LocalIndex); + IC->OnItemAddedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); Item.ChangeType = EIFChangeType::Added; MarkItemDirty(Item); break; @@ -139,17 +137,20 @@ void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) { NewItem.Item->OnItemChanged(NewItem.LocalIndex); IC->OnItemChanged(NewItem.Item, NewItem.LocalIndex); + IC->OnItemUpdatedEvent.Broadcast(NewItem.NetIndex, NewItem.LocalIndex, NewItem.Item); NewItem.ChangeType = EIFChangeType::Updated; } if (OldItem.Item) { OldItem.Item->OnItemChanged(OldItem.LocalIndex); IC->OnItemChanged(OldItem.Item, OldItem.LocalIndex); + IC->OnItemUpdatedEvent.Broadcast(OldItem.NetIndex, OldItem.LocalIndex, OldItem.Item); OldItem.ChangeType = EIFChangeType::Updated; } else { OldItem.ChangeType = EIFChangeType::Removed; + IC->OnItemRemovedEvent.Broadcast(OldItem.NetIndex, OldItem.LocalIndex, OldItem.Item); IC->OnItemRemoved(OldItem.LocalIndex); OldItem.Counter++; } @@ -180,7 +181,7 @@ void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source LocalItem.Counter++; IC->OnItemAdded(LocalItem.Item, LocalItem.LocalIndex); - LocalItem.OnSlotChanged(); + IC->OnItemAddedEvent.Broadcast(LocalItem.NetIndex, LocalItem.LocalIndex, LocalItem.Item); SourceItem.Item->MarkPendingKill(); SourceItem.Item = nullptr; @@ -198,11 +199,35 @@ void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source SourceItem.Counter++; Source->OnItemRemoved(SourceItem.LocalIndex); } - SourceItem.OnSlotChanged(); MarkItemDirty(LocalItem); Source->Inventory.MarkItemDirty(SourceItem); } +void FIFItemContainer::AddFromOtherInventoryAny(class UIFInventoryComponent* Source + , uint8 SourceNetIndex) +{ + + uint8 LocalIndex = NetToLocal[SourceNetIndex]; + FIFItemData& SourceItem = Source->Inventory.Items[LocalIndex]; + if (!SourceItem.Item) + return; + + for (FIFItemData& Item : Items) + { + if (!Item.Item) + { + Item.Item = DuplicateObject(SourceItem.Item, IC.Get()); + Item.Counter++; + Item.ChangeType = EIFChangeType::Added; + IC->OnItemAddedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); + + SourceItem.Item = nullptr; + SourceItem.ChangeType = EIFChangeType::Removed; + Source->OnItemRemovedEvent.Broadcast(SourceItem.NetIndex, SourceItem.LocalIndex, SourceItem.Item); + return; + } + } +} TArray FIFItemContainer::GetLocalItemIdxs(TSubclassOf ItemClass) { @@ -369,9 +394,6 @@ void UIFInventoryComponent::MoveItemInInventory(uint8 NewLocalPostion, uint8 Old const FIFItemData& NewSlot = GetSlot(NewLocalPostion); const FIFItemData& OldSlot = GetSlot(OldLocalPositin); - - NewSlot.OnSlotChanged(); - OldSlot.OnSlotChanged(); } void UIFInventoryComponent::ServerMoveItemInInventory_Implementation(uint8 NewNetPostion, uint8 OldNetPositin) @@ -456,6 +478,30 @@ bool UIFInventoryComponent::ServerAddItemFromOtherInventory_Validate(class UIFIn { return true; } + +void UIFInventoryComponent::AddItemFromOtherInventoryAny(class UIFInventoryComponent* Source + , uint8 SourceLocalIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + uint8 SourceLocalIdx = Inventory.NetToLocal[SourceLocalIndex]; + ServerAddItemFromOtherInventoryAny(Source, SourceLocalIdx); + return; + } + + uint8 SourceLocalIdx = Inventory.NetToLocal[SourceLocalIndex]; + Inventory.AddFromOtherInventoryAny(Source, SourceLocalIdx); +} +void UIFInventoryComponent::ServerAddItemFromOtherInventoryAny_Implementation(class UIFInventoryComponent* Source + , uint8 SourceNetIndex) +{ + Inventory.AddFromOtherInventoryAny(Source, SourceNetIndex); +} +bool UIFInventoryComponent::ServerAddItemFromOtherInventoryAny_Validate(class UIFInventoryComponent* Source + , uint8 SourceNetIndex) +{ + return true; +} void UIFInventoryComponent::AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex) { if (GetOwnerRole() < ENetRole::ROLE_Authority) @@ -518,15 +564,7 @@ void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); } -FSimpleMulticastDelegate& UIFInventoryComponent::GetOnInventoryRead() -{ - return OnInventoryReady; -} -FIFOnItemChanged& UIFInventoryComponent::GetItemChangedEvent() -{ - return OnItemChangedEvent; -} bool UIFInventoryComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) { bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index bfebe72..def07b3 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -7,9 +7,8 @@ #include "IFInventoryComponent.generated.h" //NetIndex, LocalIndex -DECLARE_MULTICAST_DELEGATE_TwoParams(FIFOnItemChanged, uint8, uint8); +DECLARE_MULTICAST_DELEGATE_ThreeParams(FIFItemEvent, uint8, uint8, class UIFItemBase*); DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); -DECLARE_DELEGATE_TwoParams(FIFOnItemChangedEvent, uint8, uint8); UENUM() enum class EIFChangeType : uint8 @@ -62,8 +61,6 @@ struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem UPROPERTY() uint8 Counter; - - FIFOnItemChangedEvent OnItemChanged; public: FIFItemData() @@ -90,13 +87,6 @@ struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem return LocalIndex; } - void OnSlotChanged() const - { - OnItemChanged.ExecuteIfBound(NetIndex, LocalIndex); - } - - void SetOnItemChanged(FIFOnItemChangedEvent& Event); - /** * Called right before deleting element during replication. * @@ -163,6 +153,9 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer , uint8 SourceNetIndex , uint8 InNetIndex); + void AddFromOtherInventoryAny(class UIFInventoryComponent* Source + , uint8 SourceNetIndex); + TArray GetLocalItemIdxs(TSubclassOf ItemClass); template @@ -219,7 +212,9 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UPROPERTY(Replicated) FIFItemContainer Inventory; - FIFOnItemChanged OnItemChangedEvent; + FIFItemEvent OnItemAddedEvent; + FIFItemEvent OnItemUpdatedEvent; + FIFItemEvent OnItemRemovedEvent; FIFOnInventoryChanged OnInventoryChanged; /* @@ -265,6 +260,10 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent inline FIFItemContainer& GetInventory() { return Inventory; } + inline FIFItemEvent& GetOnItemAdded() { return OnItemAddedEvent; } + inline FIFItemEvent& GetOnItemUpdated() { return OnItemUpdatedEvent; } + inline FIFItemEvent& GetOnItemRemoved() { return OnItemRemovedEvent; } + inline uint8 GetMaxSlots() { return MaxSlots; @@ -343,6 +342,17 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent , uint8 SourceNetIndex , uint8 InNetIndex); + + void AddItemFromOtherInventoryAny(class UIFInventoryComponent* Source + , uint8 SourceLocalIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItemFromOtherInventoryAny(class UIFInventoryComponent* Source + , uint8 SourceNetIndex); + void ServerAddItemFromOtherInventoryAny_Implementation(class UIFInventoryComponent* Source + , uint8 SourceNetIndex); + bool ServerAddItemFromOtherInventoryAny_Validate(class UIFInventoryComponent* Source + , uint8 SourceNetIndex); + /* Adds item from class. Realistically you should never call it on client. */ void AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); @@ -367,8 +377,6 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent void OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex); FSimpleMulticastDelegate& GetOnInventoryRead(); - - FIFOnItemChanged& GetItemChangedEvent(); - + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; }; diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp index c4f1651..03393f3 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemContainerWidget.cpp @@ -11,23 +11,6 @@ void UIFItemContainerWidget::SetInventory(UIFInventoryComponent* InInventory) void UIFItemContainerWidget::CreateInventory() { - APlayerController* PC = GetOwningPlayer(); - uint8 MaxSlots = Inventory->GetMaxSlots(); - - for (uint8 Idx = 0; Idx < MaxSlots; Idx++) - { - UIFItemWidget* Widget = CreateWidget(PC, ItemClass); - Widget->Inventory = Inventory; - - const FIFItemData& Slot = Inventory->GetSlot(Idx); - - FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(Widget, &UIFItemWidget::OnItemChanged); - const_cast(Slot).SetOnItemChanged(Event); - - Widget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); - - InventoryWidgets.Add(Widget); - } NativeOnInventoryCreated(); } diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp index 2067473..0276e27 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Private/IFItemWidget.cpp @@ -5,16 +5,19 @@ #include "IFInventoryComponent.h" -void UIFItemWidget::OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex) +void UIFItemWidget::OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) { NetIndex = InNetIndex; LocalIndex = InLocalIndex; - //const UIFItemBase* Item = Inventory->GetItem(InLocalIndex); - //BP_OnItemCreated(const_cast(Item)); + BP_OnItemCreated(Item); } -void UIFItemWidget::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex) +void UIFItemWidget::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) { - const UIFItemBase* Item = Inventory->GetItem(InLocalIndex); BP_OnItemChanged(const_cast(Item)); } + +void UIFItemWidget::OnItemRemoved(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) +{ + BP_OnItemRemoved(const_cast(Item)); +} \ No newline at end of file diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h index 5af50e7..001b1be 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -28,13 +28,18 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget UPROPERTY(BlueprintReadWrite, Category = "InventoryFramework") UWidget* DragVisual; public: - void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex); + void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); - void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex); + void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); + + void OnItemRemoved(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Created")) void BP_OnItemCreated(class UIFItemBase* Item); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Changed")) void BP_OnItemChanged(class UIFItemBase* Item); + + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Changed")) + void BP_OnItemRemoved(class UIFItemBase* Item); }; diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index b4ae7af..c94238e 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -565,12 +565,6 @@ void AARCharacter::OnRep_Controller() /* IIFInventoryInterface */ void AARCharacter::OnInventoryReplicated(class UIFInventoryComponent* Inventory) { - if (Cast(Inventory)) - { - if (AARPlayerController* PC = Cast(Controller)) - { - PC->UIComponent->InitializeWeaponInventory(); - } - } + } /* IIFInventoryInterface */ \ No newline at end of file diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 26b64a4..6ac44db 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -10,7 +10,7 @@ #include "Weapons/ARWeaponManagerComponent.h" #include "Abilities/ARAbilityManagerComponent.h" - +#include "UI/ARHUD.h" AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) @@ -144,7 +144,10 @@ void AARPlayerController::InputShowHideAbilityManager() } void AARPlayerController::InputShowHideInventory() { - UIComponent->ShowHideInventory(); + if (AARHUD* MyHUD = Cast(GetHUD())) + { + MyHUD->ShowHideInventory(); + } } void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag) { diff --git a/Source/ActionRPGGame/UI/ARHUD.cpp b/Source/ActionRPGGame/UI/ARHUD.cpp index c6f7d4e..e3bbfdb 100644 --- a/Source/ActionRPGGame/UI/ARHUD.cpp +++ b/Source/ActionRPGGame/UI/ARHUD.cpp @@ -1,7 +1,25 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARHUD.h" +#include "UI/Inventory/ARUIInventoryComponent.h" +#include "ARPlayerController.h" +AARHUD::AARHUD(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + UIInventoryComponent = ObjectInitializer.CreateDefaultSubobject(this, TEXT("UIInventoryComponent")); +} +void AARHUD::BeginPlay() +{ + Super::BeginPlay(); + if (AARPlayerController* PC = Cast(PlayerOwner)) + { + UIInventoryComponent->CreateInventoryView(PC); + } +} - +void AARHUD::ShowHideInventory() +{ + UIInventoryComponent->ShowHideInventory(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARHUD.h b/Source/ActionRPGGame/UI/ARHUD.h index caa1819..72f6116 100644 --- a/Source/ActionRPGGame/UI/ARHUD.h +++ b/Source/ActionRPGGame/UI/ARHUD.h @@ -13,8 +13,20 @@ UCLASS() class ACTIONRPGGAME_API AARHUD : public AHUD { GENERATED_BODY() +protected: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") + class UARUIInventoryComponent* UIInventoryComponent; - - - +public: + AARHUD(const FObjectInitializer& ObjectInitializer); + + virtual void BeginPlay() override; + + inline UARUIInventoryComponent* GetUIInventory() + { + return UIInventoryComponent; + } + + + void ShowHideInventory(); }; diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/UI/ARUIComponent.cpp index b631393..d21e789 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/UI/ARUIComponent.cpp @@ -55,75 +55,6 @@ void UARUIComponent::BeginPlay() HUDWidget = CreateWidget(MyPC, HUDWidgetClass); HUDWidget->AddToViewport(); } - - AARCharacter* Character = Cast(MyPC->GetPawn()); - if (WeaponInventoryWidgetClass && Character) - { - InventoryScreenWidget->UI = this; - InventoryScreenWidget->PC = MyPC; - InventoryScreenWidget->Inventory = MyPC->MainInventory; - - UARWeaponInventoryComponent* WeapInv = Character->WeaponInventory; - - for (FIFItemData& Item : WeapInv->GetInventory().GetItems()) - { - switch (Item.GetLocalIndex()) - { - case 0: - { - InventoryScreenWidget->RightWeaponWidget->Inventory = MyPC->MainInventory; - InventoryScreenWidget->RightWeaponWidget->WeaponInventory = WeapInv; - InventoryScreenWidget->RightWeaponWidget->UI = this; - InventoryScreenWidget->RightWeaponWidget->InventoryWidget = InventoryScreenWidget; - - InventoryScreenWidget->RightWeaponWidget->LocalIndex = Item.GetLocalIndex(); - InventoryScreenWidget->RightWeaponWidget->NetIndex = Item.GetNetIndex(); - - FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->RightWeaponWidget, &UIFItemWidget::OnItemChanged); - Item.SetOnItemChanged(Event); - } - case 1: - { - InventoryScreenWidget->LeftWeaponWidget->Inventory = MyPC->MainInventory; - InventoryScreenWidget->LeftWeaponWidget->WeaponInventory = WeapInv; - InventoryScreenWidget->LeftWeaponWidget->UI = this; - InventoryScreenWidget->LeftWeaponWidget->InventoryWidget = InventoryScreenWidget; - - InventoryScreenWidget->LeftWeaponWidget->LocalIndex = Item.GetLocalIndex(); - InventoryScreenWidget->LeftWeaponWidget->NetIndex = Item.GetNetIndex(); - - FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->LeftWeaponWidget, &UIFItemWidget::OnItemChanged); - Item.SetOnItemChanged(Event); - } - case 2: - { - InventoryScreenWidget->SideWeaponWidget->Inventory = MyPC->MainInventory; - InventoryScreenWidget->SideWeaponWidget->WeaponInventory = WeapInv; - InventoryScreenWidget->SideWeaponWidget->UI = this; - InventoryScreenWidget->SideWeaponWidget->InventoryWidget = InventoryScreenWidget; - - InventoryScreenWidget->SideWeaponWidget->LocalIndex = Item.GetLocalIndex(); - InventoryScreenWidget->SideWeaponWidget->NetIndex = Item.GetNetIndex(); - - FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->SideWeaponWidget, &UIFItemWidget::OnItemChanged); - Item.SetOnItemChanged(Event); - } - case 3: - { - InventoryScreenWidget->BottomBackWeaponWidget->Inventory = MyPC->MainInventory; - InventoryScreenWidget->BottomBackWeaponWidget->WeaponInventory = WeapInv; - InventoryScreenWidget->BottomBackWeaponWidget->UI = this; - InventoryScreenWidget->BottomBackWeaponWidget->InventoryWidget = InventoryScreenWidget; - - InventoryScreenWidget->BottomBackWeaponWidget->LocalIndex = Item.GetLocalIndex(); - InventoryScreenWidget->BottomBackWeaponWidget->NetIndex = Item.GetNetIndex(); - - FIFOnItemChangedEvent Event = FIFOnItemChangedEvent::CreateUObject(InventoryScreenWidget->BottomBackWeaponWidget, &UIFItemWidget::OnItemChanged); - Item.SetOnItemChanged(Event); - } - } - } - } } } @@ -140,36 +71,3 @@ void UARUIComponent::InitializeInventory() { } -void UARUIComponent::InitializeWeaponInventory() -{ - //if (GetOwner()->GetNetMode() == ENetMode::NM_Client - // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) - //{ - // AARPlayerController* MyPC = Cast(GetOwner()); - // AARCharacter* Character = Cast(MyPC->GetPawn()); - // if (WeaponInventoryWidgetClass && Character) - // { - // InventoryScreenWidget->WeaponInventoryWidget = CreateWidget(MyPC, WeaponInventoryWidgetClass); - // - // InventoryScreenWidget->UI = this; - // InventoryScreenWidget->PC = MyPC; - // InventoryScreenWidget->Inventory = MyPC->MainInventory; - // InventoryScreenWidget->WeaponInventoryWidget->SetInventory(Character->WeaponInventory); - // InventoryScreenWidget->WeaponInventoryWidget->CreateInventory(); - // InventoryScreenWidget->WeaponInventoryWidget->InitializeWeaponItems(this); - // InventoryScreenWidget->WeaponInventoryWidget->AddToViewport(); - // - // } - //} -} -void UARUIComponent::ShowHideInventory() -{ - if (InventoryScreenWidget->GetVisibility() == ESlateVisibility::Collapsed) - { - InventoryScreenWidget->SetVisibility(ESlateVisibility::SelfHitTestInvisible); - } - else if (InventoryScreenWidget->GetVisibility() == ESlateVisibility::SelfHitTestInvisible) - { - InventoryScreenWidget->SetVisibility(ESlateVisibility::Collapsed); - } -} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/UI/ARUIComponent.h index e56008e..cfb1668 100644 --- a/Source/ActionRPGGame/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/UI/ARUIComponent.h @@ -35,23 +35,6 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf HUDWidgetClass; - - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf WeaponInventoryWidgetClass; - - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf InventoryScreenWidgetClass; -public: - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf ItemWidgetClass; - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf ItemWeaponWidgetClass; - - -public: - UPROPERTY(BlueprintReadOnly, Category = "Widgets") - UARInventoryScreenWidget* InventoryScreenWidget; - public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") UARHUDWidget* HUDWidget; @@ -73,7 +56,5 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; void InitializeInventory(); - void InitializeWeaponInventory(); - void ShowHideInventory(); }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp index 65160bf..2b5a0b5 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp @@ -4,31 +4,33 @@ #include "Components/TextBlock.h" +#include "UI/Inventory/Weapons/ARItemWeaponWidget.h" + #include "ARPlayerController.h" +void UARInventoryScreenWidget::NativeConstruct() +{ + Super::NativeConstruct(); + WeaponSlots.Add(RightWeaponWidget); + WeaponSlots.Add(LeftWeaponWidget); + WeaponSlots.Add(SideWeaponWidget); + WeaponSlots.Add(BottomBackWeaponWidget); +} + void UARInventoryScreenWidget::SetWeaponName(const FString& Name) { SelectedWeapon->SetText(FText::FromString(Name)); } -void UARInventoryScreenWidget::UpdateItemList(const TArray& LocalIdxs) +void UARInventoryScreenWidget::OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) { - SelectedItemsContainer->ClearChildren(); - - for (uint8 Idx : LocalIdxs) - { - UIFItemBase* Item = Inventory->GetItem(Idx); - - if (Item) - { - const FIFItemData& Slot = Inventory->GetSlot(Idx); - UIFItemWidget* ItemWidget = CreateWidget(PC.Get(), UI->ItemWidgetClass); - ItemWidget->Inventory = Inventory; - ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); - ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex()); - - SelectedItemsContainer->AddChild(ItemWidget); - } - } - + WeaponSlots[NetIndex]->OnSlotCreated(NetIndex, LocalIndex, Item); +} +void UARInventoryScreenWidget::OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) +{ + WeaponSlots[NetIndex]->OnItemChanged(NetIndex, LocalIndex, Item); +} +void UARInventoryScreenWidget::OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) +{ + WeaponSlots[NetIndex]->OnItemRemoved(NetIndex, LocalIndex, Item); } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h index 9f12bc1..2c0b309 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h @@ -22,11 +22,6 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase { GENERATED_BODY() public: - - TWeakObjectPtr Inventory; - TWeakObjectPtr UI; - TWeakObjectPtr PC; - UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) class UARItemWeaponWidget* RightWeaponWidget; @@ -47,10 +42,12 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UTextBlock* SelectedWeapon; - - void SetWeaponName(const FString& Name); +protected: + TArray WeaponSlots; +public: + virtual void NativeConstruct() override; - void UpdateItemList(const TArray& LocalIdxs); + void SetWeaponName(const FString& Name); template void UpdateItemList(const TArray& LocalIdxs, TSubclassOf WidgetClass) @@ -74,4 +71,30 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase } } + template + void AddItems(const TArray& Items, TSubclassOf WidgetClass, class AARPlayerController* PC, class UARItemView* ForSlot) + { + SelectedItemsContainer->ClearChildren(); + + uint8 Idx = 0; + for (ItemType* Item : Items) + { + if (Item) + { + const FIFItemData& Slot = PC->MainInventory->GetSlot(Idx); + WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); + + ItemWidget->SetTarget(ForSlot); + ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + + SelectedItemsContainer->AddChild(ItemWidget); + } + Idx++; + } + } + + void OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); + void OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); + void OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARItemView.cpp b/Source/ActionRPGGame/UI/Inventory/ARItemView.cpp new file mode 100644 index 0000000..956954b --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARItemView.cpp @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemView.h" + +#include "UI/ARHUD.h" +#include "ARPlayerController.h" + + +void UARItemView::NativeConstruct() +{ + Super::NativeConstruct(); + + if (GetOwningPlayer()) + { + if (AARHUD* HUD = Cast(GetOwningPlayer()->GetHUD())) + { + InventoryComponent = HUD->GetUIInventory(); + } + } +} diff --git a/Source/ActionRPGGame/UI/Inventory/ARItemView.h b/Source/ActionRPGGame/UI/Inventory/ARItemView.h new file mode 100644 index 0000000..f72e929 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARItemView.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFItemWidget.h" +#include "ARItemView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARItemView : public UIFItemWidget +{ + GENERATED_BODY() +public: + TWeakObjectPtr InventoryComponent; + +public: + virtual void NativeConstruct() override; + + + +}; diff --git a/Source/ActionRPGGame/UI/Inventory/ARListItemView.cpp b/Source/ActionRPGGame/UI/Inventory/ARListItemView.cpp new file mode 100644 index 0000000..e6d8936 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARListItemView.cpp @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARListItemView.h" + +#include "UI/ARHUD.h" +#include "ARPlayerController.h" + + +void UARListItemView::NativeConstruct() +{ + Super::NativeConstruct(); + + if (GetOwningPlayer()) + { + if (AARHUD* HUD = Cast(GetOwningPlayer()->GetHUD())) + { + InventoryComponent = HUD->GetUIInventory(); + } + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARListItemView.h b/Source/ActionRPGGame/UI/Inventory/ARListItemView.h new file mode 100644 index 0000000..d283610 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARListItemView.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFItemWidget.h" +#include "ARListItemView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARListItemView : public UIFItemWidget +{ + GENERATED_BODY() + +protected: + TWeakObjectPtr Target; + TWeakObjectPtr InventoryComponent; +public: + virtual void NativeConstruct() override; + + inline void SetTarget(TWeakObjectPtr ForSlot) { Target = ForSlot; } + inline TWeakObjectPtr GetTarget() { return Target; } + +}; diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp new file mode 100644 index 0000000..6816533 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp @@ -0,0 +1,137 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARUIInventoryComponent.h" +#include "ARPlayerController.h" +#include "ARCharacter.h" + +#include "Weapons/ARItemWeapon.h" + +#include "UI/ARHUD.h" +#include "UI/Inventory/ARInventoryScreenWidget.h" +#include "UI/Inventory/Weapons/ARListItemWeaponWidget.h" + + +// Sets default values for this component's properties +UARUIInventoryComponent::UARUIInventoryComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UARUIInventoryComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UARUIInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +void UARUIInventoryComponent::CreateInventoryView(AARPlayerController* PC) +{ + if (InventoryViewClass) + { + InventoryView = CreateWidget(PC, InventoryViewClass); + + InventoryView->SetVisibility(ESlateVisibility::Collapsed); + InventoryView->AddToViewport(); + + if (AARCharacter* Character = Cast(PC->GetPawn())) + { + Character->WeaponInventory->GetOnItemAdded().AddUObject(this, &UARUIInventoryComponent::OnWeaponAdded); + Character->WeaponInventory->GetOnItemUpdated().AddUObject(this, &UARUIInventoryComponent::OnWeaponUpdated); + Character->WeaponInventory->GetOnItemRemoved().AddUObject(this, &UARUIInventoryComponent::OnWeaponRemoved); + } + } +} + +void UARUIInventoryComponent::ShowHideInventory() +{ + if (InventoryView->GetVisibility() == ESlateVisibility::Collapsed) + { + InventoryView->SetVisibility(ESlateVisibility::SelfHitTestInvisible); + } + else if (InventoryView->GetVisibility() == ESlateVisibility::SelfHitTestInvisible) + { + InventoryView->SetVisibility(ESlateVisibility::Collapsed); + } +} + +void UARUIInventoryComponent::OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) +{ + InventoryView->OnWeaponAdded(NetIndex, LocalIndex, Item); +} +void UARUIInventoryComponent::OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) +{ + InventoryView->OnWeaponUpdated(NetIndex, LocalIndex, Item); +} +void UARUIInventoryComponent::OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) +{ + InventoryView->OnWeaponRemoved(NetIndex, LocalIndex, Item); +} + +void UARUIInventoryComponent::ShowWeaponsForSlot(class UARItemView* ForSlot) +{ + TArray Items; + AARPlayerController* PC = nullptr; + if (AARHUD* HUD = Cast(GetOwner())) + { + PC = Cast(HUD->PlayerOwner); + if (PC) + { + Items = PC->MainInventory->GetItems(UARItemWeapon::StaticClass()); + } + } + + InventoryView->AddItems(Items, ListItemWeaponClass, PC, ForSlot); +} + +void UARUIInventoryComponent::AddWeaponToSlot(uint8 TargetNetIndex + , uint8 TargetLocalIndex + , uint8 SourceNetIndex + , uint8 SourceLocalIndex) +{ + AARHUD* HUD = Cast(GetOwner()); + if (!HUD) + return; + AARPlayerController* PC = Cast(HUD->PlayerOwner); + if (!PC) + return; + + AARCharacter* Character = Cast(PC->GetPawn()); + if (!Character) + return; + + Character->WeaponInventory->AddItemFromOtherInventory(PC->MainInventory, SourceLocalIndex, TargetLocalIndex); + +} + +void UARUIInventoryComponent::UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 SourceLocalIndex) +{ + AARHUD* HUD = Cast(GetOwner()); + if (!HUD) + return; + AARPlayerController* PC = Cast(HUD->PlayerOwner); + if (!PC) + return; + + AARCharacter* Character = Cast(PC->GetPawn()); + if (!Character) + return; + + PC->MainInventory->AddItemFromOtherInventoryAny(Character->WeaponInventory, SourceLocalIndex); + Character->WeaponInventory->Unequip(SourceLocalIndex); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h new file mode 100644 index 0000000..c777411 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h @@ -0,0 +1,54 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "ARUIInventoryComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Views") + TSubclassOf InventoryViewClass; + UPROPERTY(EditAnywhere, Category = "Views") + TSubclassOf ListItemWeaponClass; + + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") + class UARInventoryScreenWidget* InventoryView; +public: + // Sets default values for this component's properties + UARUIInventoryComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + void CreateInventoryView(AARPlayerController* PC); + void ShowHideInventory(); + +protected: + UFUNCTION() + void OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); + UFUNCTION() + void OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); + UFUNCTION() + void OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); + +public: + void ShowWeaponsForSlot(class UARItemView* ForSlot); + + void AddWeaponToSlot(uint8 TargetNetIndex + , uint8 TargetLocalIndex + , uint8 SourceNetIndex + , uint8 SourceLocalIndex); + + void UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 SourceLocalIndex); +}; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index 30f210a..6c967a1 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -7,24 +7,39 @@ #include "Weapons/ARItemWeapon.h" #include "Weapons/ARWeaponInventoryComponent.h" +#include "UI/ARHUD.h" +#include "UI/Inventory/ARUIInventoryComponent.h" #include "UI/Inventory/ARInventoryScreenWidget.h" #include "UI/Inventory/Weapons/ARWeaponContainerWidget.h" #include "UI/Inventory/Weapons/ARListItemWeaponWidget.h" - -void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +void UARItemWeaponWidget::NativeConstruct() { - TArray Items = Inventory->GetLocalItemIdxs(UARItemWeapon::StaticClass()); - - UARItemWeapon* CurrentItem = WeaponInventory->GetItem(LocalIndex); - - if (CurrentItem) + Super::NativeConstruct(); + if(GetOwningPlayer()) { - InventoryWidget->SetWeaponName(CurrentItem->GetName()); + if (AARHUD* HUD = Cast(GetOwningPlayer()->GetHUD())) + { + InventoryComponent = HUD->GetUIInventory(); + } } - InventoryWidget->UpdateItemList(Items, UI->ItemWeaponWidgetClass); +} + + +void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + InventoryComponent->ShowWeaponsForSlot(this); } void UARItemWeaponWidget::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) { -} \ No newline at end of file +} +FReply UARItemWeaponWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + FReply Handled = FReply::Unhandled(); + + InventoryComponent->UnequipWeaponFromSlot(NetIndex, LocalIndex); + Handled = FReply::Handled(); + + return Handled; +} diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h index a2d22f4..f53e848 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h @@ -3,23 +3,25 @@ #pragma once #include "CoreMinimal.h" -#include "IFItemWidget.h" +#include "UI/Inventory/ARItemView.h" #include "ARItemWeaponWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARItemWeaponWidget : public UIFItemWidget +class ACTIONRPGGAME_API UARItemWeaponWidget : public UARItemView { GENERATED_BODY() public: - TWeakObjectPtr WeaponInventory; - TWeakObjectPtr UI; - TWeakObjectPtr InventoryWidget; + TWeakObjectPtr InventoryComponent; + +public: + virtual void NativeConstruct() override; public: virtual void NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; virtual void NativeOnMouseLeave(const FPointerEvent& InMouseEvent) override; + virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp index e59c00e..e6d120d 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp @@ -1,7 +1,18 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARListItemWeaponWidget.h" +#include "UI/Inventory/ARUIInventoryComponent.h" +#include "UI/Inventory/ARItemView.h" +FReply UARListItemWeaponWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + FReply Handled = FReply::Unhandled(); + if (!Target.IsValid()) + return Handled; + InventoryComponent->AddWeaponToSlot(Target->NetIndex, Target->LocalIndex, NetIndex, LocalIndex); + Handled = FReply::Handled(); + return Handled; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h b/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h index 30280f1..6ecdf88 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h @@ -3,18 +3,16 @@ #pragma once #include "CoreMinimal.h" -#include "IFItemWidget.h" +#include "UI/Inventory/ARListItemView.h" #include "ARListItemWeaponWidget.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARListItemWeaponWidget : public UIFItemWidget +class ACTIONRPGGAME_API UARListItemWeaponWidget : public UARListItemView { GENERATED_BODY() - - - - +public: + virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp index 0bd947e..26e88f5 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp @@ -12,16 +12,5 @@ void UARWeaponContainerWidget::InitializeWeaponItems(class UARUIComponent* UIComponent) { - for (UIFItemWidget* Widget : InventoryWidgets) - { - if (UARItemWeaponWidget* Weapon = Cast(Widget)) - { - AARPlayerController* PC = Cast(UIComponent->GetOwner()); - AARCharacter* Character = Cast(PC->GetPawn()); - Weapon->WeaponInventory = Character->WeaponInventory; - Weapon->UI = UIComponent; - Weapon->InventoryWidget = UIComponent->InventoryScreenWidget; - } - } } \ No newline at end of file From e4c5a84888521933c72674ac4258a53f72c3ee83 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 18 Apr 2018 00:55:48 +0200 Subject: [PATCH 137/187] working on weapon upgrade ui --- .../Public/IFItemWidget.h | 2 +- .../UI/Inventory/ARInventoryScreenWidget.cpp | 7 +++ .../UI/Inventory/ARInventoryScreenWidget.h | 51 +++++++++++++++--- .../UI/Inventory/ARUIInventoryComponent.cpp | 54 +++++++++++++++++-- .../UI/Inventory/ARUIInventoryComponent.h | 12 +++++ .../Modifications/ARItemMagazineView.cpp | 12 +++++ .../Modifications/ARItemMagazineView.h | 20 +++++++ .../Modifications/ARListItemMagazineView.cpp | 7 +++ .../Modifications/ARListItemMagazineView.h | 20 +++++++ Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 1 + Source/ActionRPGGame/Weapons/ARItemWeapon.h | 4 ++ 11 files changed, 178 insertions(+), 12 deletions(-) create mode 100644 Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h create mode 100644 Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp create mode 100644 Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h index 001b1be..3844791 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -40,6 +40,6 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Changed")) void BP_OnItemChanged(class UIFItemBase* Item); - UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Changed")) + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Removed")) void BP_OnItemRemoved(class UIFItemBase* Item); }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp index 2b5a0b5..757a8d0 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp @@ -3,6 +3,7 @@ #include "ARInventoryScreenWidget.h" #include "Components/TextBlock.h" +#include "Components/Button.h" #include "UI/Inventory/Weapons/ARItemWeaponWidget.h" @@ -15,6 +16,7 @@ void UARInventoryScreenWidget::NativeConstruct() WeaponSlots.Add(LeftWeaponWidget); WeaponSlots.Add(SideWeaponWidget); WeaponSlots.Add(BottomBackWeaponWidget); + ModifySelectedWeapon->OnClicked.AddDynamic(this, &UARInventoryScreenWidget::OnModifyWeaponClicked); } void UARInventoryScreenWidget::SetWeaponName(const FString& Name) @@ -33,4 +35,9 @@ void UARInventoryScreenWidget::OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, void UARInventoryScreenWidget::OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) { WeaponSlots[NetIndex]->OnItemRemoved(NetIndex, LocalIndex, Item); +} + +void UARInventoryScreenWidget::OnModifyWeaponClicked() +{ + Inventory->ModifyWeapon(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h index 2c0b309..86c2092 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h @@ -34,14 +34,26 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) class UARItemWeaponWidget* BottomBackWeaponWidget; + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + UButton* ModifySelectedWeapon; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UARItemMagazineView* MagazineUpgrade; + + /* Contains list of items compatibile with selected slot. */ UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UWrapBox* SelectedItemsContainer; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UWrapBox* WeaponModificationContainer; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UTextBlock* SelectedWeapon; + + TWeakObjectPtr Inventory; protected: TArray WeaponSlots; public: @@ -50,21 +62,21 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase void SetWeaponName(const FString& Name); template - void UpdateItemList(const TArray& LocalIdxs, TSubclassOf WidgetClass) + void UpdateItemList(const TArray& LocalIdxs, TSubclassOf WidgetClass, class AARPlayerController* PC, class UARItemView* ForSlot) { SelectedItemsContainer->ClearChildren(); for (uint8 Idx : LocalIdxs) { - ItemType* Item = Inventory->GetItem(Idx); + ItemType* Item = PC->MainInventory->GetItem(Idx); if (Item) { - const FIFItemData& Slot = Inventory->GetSlot(Idx); - WidgetType* ItemWidget = CreateWidget(PC.Get(), WidgetClass); - ItemWidget->Inventory = Inventory; - ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex()); - ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex()); + const FIFItemData& Slot = PC->MainInventory->GetSlot(Idx); + WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); + ItemWidget->SetTarget(ForSlot); + ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); SelectedItemsContainer->AddChild(ItemWidget); } @@ -94,7 +106,32 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase } } + template + void AddWeaponMods(const TArray& Items, TSubclassOf WidgetClass, class AARPlayerController* PC, class UARItemView* ForSlot) + { + WeaponModificationContainer->ClearChildren(); + + for (uint8 Idx : Items) + { + ItemType* Item = PC->MainInventory->GetItem(Idx); + + if (Item) + { + const FIFItemData& Slot = PC->MainInventory->GetSlot(Idx); + WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); + + ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + + WeaponModificationContainer->AddChild(ItemWidget); + } + } + } + void OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); void OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); void OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); +protected: + UFUNCTION() + void OnModifyWeaponClicked(); }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp index 6816533..7619170 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp @@ -5,11 +5,14 @@ #include "ARCharacter.h" #include "Weapons/ARItemWeapon.h" +#include "Weapons/ARMagazineUpgradeItem.h" #include "UI/ARHUD.h" +#include "UI/Inventory/ARItemView.h" #include "UI/Inventory/ARInventoryScreenWidget.h" #include "UI/Inventory/Weapons/ARListItemWeaponWidget.h" - +#include "UI/Inventory/Weapons/Modifications/ARItemMagazineView.h" +#include "UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h" // Sets default values for this component's properties UARUIInventoryComponent::UARUIInventoryComponent() @@ -47,6 +50,7 @@ void UARUIInventoryComponent::CreateInventoryView(AARPlayerController* PC) InventoryView = CreateWidget(PC, InventoryViewClass); InventoryView->SetVisibility(ESlateVisibility::Collapsed); + InventoryView->Inventory = this; InventoryView->AddToViewport(); if (AARCharacter* Character = Cast(PC->GetPawn())) @@ -85,18 +89,19 @@ void UARUIInventoryComponent::OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, void UARUIInventoryComponent::ShowWeaponsForSlot(class UARItemView* ForSlot) { - TArray Items; + SelectedWeapon = ForSlot->LocalIndex; + TArray Items; AARPlayerController* PC = nullptr; if (AARHUD* HUD = Cast(GetOwner())) { PC = Cast(HUD->PlayerOwner); if (PC) { - Items = PC->MainInventory->GetItems(UARItemWeapon::StaticClass()); + Items = PC->MainInventory->GetLocalItemIdxs(UARItemWeapon::StaticClass()); } } - InventoryView->AddItems(Items, ListItemWeaponClass, PC, ForSlot); + InventoryView->UpdateItemList(Items, ListItemWeaponClass, PC, ForSlot); } void UARUIInventoryComponent::AddWeaponToSlot(uint8 TargetNetIndex @@ -134,4 +139,45 @@ void UARUIInventoryComponent::UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 PC->MainInventory->AddItemFromOtherInventoryAny(Character->WeaponInventory, SourceLocalIndex); Character->WeaponInventory->Unequip(SourceLocalIndex); +} + +void UARUIInventoryComponent::ShowUpgradesForWeapon(class UARItemMagazineView* For) +{ + TArray Items; + AARPlayerController* PC = nullptr; + if (AARHUD* HUD = Cast(GetOwner())) + { + PC = Cast(HUD->PlayerOwner); + if (PC) + { + Items = PC->MainInventory->GetLocalItemIdxs(UARMagazineUpgradeItem::StaticClass()); + } + } + + InventoryView->AddWeaponMods(Items, ListItemMagazinelass, PC, For); +} + +void UARUIInventoryComponent::ModifyWeapon() +{ + AARHUD* HUD = Cast(GetOwner()); + if (!HUD) + return; + AARPlayerController* PC = Cast(HUD->PlayerOwner); + if (!PC) + return; + + AARCharacter* Character = Cast(PC->GetPawn()); + if (!Character) + return; + + UARItemWeapon* Weapon = Character->WeaponInventory->GetItem(SelectedWeapon); + + if (!Weapon) + return; + + if (Weapon->MagazineModification.IsValid()) + { + TSubclassOf Magazine = Weapon->MagazineModification.LoadSynchronous(); + InventoryView->MagazineUpgrade->OnItemChanged(0, 0, Magazine->GetDefaultObject()); + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h index c777411..f3a3de5 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h @@ -17,8 +17,16 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Views") TSubclassOf ListItemWeaponClass; + UPROPERTY(EditAnywhere, Category = "Views") + TSubclassOf ListItemMagazinelass; + + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") class UARInventoryScreenWidget* InventoryView; + + /* NetIndex of selected Weapon. */ + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") + uint8 SelectedWeapon; public: // Sets default values for this component's properties UARUIInventoryComponent(); @@ -51,4 +59,8 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent , uint8 SourceLocalIndex); void UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 SourceLocalIndex); + + void ShowUpgradesForWeapon(class UARItemMagazineView* For); + + void ModifyWeapon(); }; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp new file mode 100644 index 0000000..8e9efc6 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp @@ -0,0 +1,12 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemMagazineView.h" +#include "UI/Inventory/ARUIInventoryComponent.h" + + + +FReply UARItemMagazineView::NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + InventoryComponent->ShowUpgradesForWeapon(this); + return FReply::Unhandled(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h new file mode 100644 index 0000000..db94349 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Inventory/ARItemView.h" +#include "ARItemMagazineView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARItemMagazineView : public UARItemView +{ + GENERATED_BODY() +public: + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; + + +}; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp new file mode 100644 index 0000000..d68f091 --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARListItemMagazineView.h" + + + + diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h new file mode 100644 index 0000000..e7fe23e --- /dev/null +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Inventory/ARListItemView.h" +#include "ARListItemMagazineView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARListItemMagazineView : public UARListItemView +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 232557a..75b165c 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -5,6 +5,7 @@ void UARItemWeapon::AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade) { + MagazineModification = InMagazineUpgrade; TSubclassOf clas = InMagazineUpgrade.LoadSynchronous(); MagazineEffect = clas->GetDefaultObject()->UpgradeEffect.LoadSynchronous(); OnMagazineUpdateAdded(); diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index 9739bac..73f799a 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -36,6 +36,10 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(EditAnywhere, Category = "Ability") UARWeaponAbilityBase* AbilityInstance; + UPROPERTY(EditAnywhere, Category = "Ability") + TSoftClassPtr MagazineModification; + + FAFPropertytHandle MagazineEffect; FGAEffectHandle MagazineEffectHandle; From 31c288d72770d0db08dc7e9a7b3ea64b37d2cae3 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 18 Apr 2018 23:50:04 +0200 Subject: [PATCH 138/187] prototype weapon upgrades --- .../Private/IFInventoryComponent.cpp | 15 ++++- .../Public/IFInventoryComponent.h | 3 + .../UI/Inventory/ARUIInventoryComponent.cpp | 67 +++++++++++++++++++ .../UI/Inventory/ARUIInventoryComponent.h | 2 + .../Inventory/Weapons/ARItemWeaponWidget.cpp | 17 ++++- .../UI/Inventory/Weapons/ARItemWeaponWidget.h | 3 +- .../Modifications/ARItemMagazineView.cpp | 13 +++- .../Modifications/ARItemMagazineView.h | 2 +- .../Modifications/ARListItemMagazineView.cpp | 10 +++ .../Modifications/ARListItemMagazineView.h | 3 +- Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 15 +++-- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 5 +- 12 files changed, 143 insertions(+), 12 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 9f91ee0..a372bd1 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -228,7 +228,19 @@ void FIFItemContainer::AddFromOtherInventoryAny(class UIFInventoryComponent* Sou } } } +void FIFItemContainer::RemoveItem(uint8 InNetIndex) +{ + uint8 LocalIndex = NetToLocal[InNetIndex]; + + FIFItemData& Item = Items[LocalIndex]; + if(Item.Item) + Item.Item->MarkPendingKill(); + Item.Item = nullptr; + Item.ChangeType = EIFChangeType::Removed; + + IC->OnItemRemovedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); +} TArray FIFItemContainer::GetLocalItemIdxs(TSubclassOf ItemClass) { TArray Indexes; @@ -541,7 +553,8 @@ void UIFInventoryComponent::BP_AddItemFromClass(TSoftClassPtr void UIFInventoryComponent::RemoveItem(uint8 InLocalIndex) { - + uint8 NetIndex = Inventory.LocalToNet[InLocalIndex]; + Inventory.RemoveItem(NetIndex); } void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index def07b3..fb1a560 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -158,6 +158,8 @@ struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer TArray GetLocalItemIdxs(TSubclassOf ItemClass); + void RemoveItem(uint8 InNetIndex); + template TArray GetItems(TSubclassOf ItemClass) { @@ -370,6 +372,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent void RemoveItem(uint8 InLocalIndex); + UFUNCTION() void OnItemLoadedFreeSlot(TSoftClassPtr InItem); diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp index 7619170..79b3d31 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp @@ -99,6 +99,14 @@ void UARUIInventoryComponent::ShowWeaponsForSlot(class UARItemView* ForSlot) { Items = PC->MainInventory->GetLocalItemIdxs(UARItemWeapon::StaticClass()); } + if (AARCharacter* Character = Cast(PC->GetPawn())) + { + UIFItemBase* Item = Character->WeaponInventory->GetItem(ForSlot->LocalIndex); + if (Item) + { + InventoryView->SetWeaponName(Item->GetName()); + } + } } InventoryView->UpdateItemList(Items, ListItemWeaponClass, PC, ForSlot); @@ -180,4 +188,63 @@ void UARUIInventoryComponent::ModifyWeapon() TSubclassOf Magazine = Weapon->MagazineModification.LoadSynchronous(); InventoryView->MagazineUpgrade->OnItemChanged(0, 0, Magazine->GetDefaultObject()); } +} + +void UARUIInventoryComponent::AddMagazineUpgrade(uint8 SourceNetIndex, uint8 SourceLocalIndex) +{ + //that's prototype. We should handle entire thing on server, either directly on item weapon, or trough WeaponInventory. + AARHUD* HUD = Cast(GetOwner()); + if (!HUD) + return; + AARPlayerController* PC = Cast(HUD->PlayerOwner); + if (!PC) + return; + + AARCharacter* Character = Cast(PC->GetPawn()); + if (!Character) + return; + + + UIFInventoryComponent* MainInventory = PC->MainInventory; + + UARMagazineUpgradeItem* MagazineUpgrade = MainInventory->GetItem(SourceLocalIndex); + + UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; + + UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); + + Weapon->AddMagazineUpgrade(MagazineUpgrade); // ??? + MainInventory->RemoveItem(SourceLocalIndex); + + if (Weapon->MagazineModification.IsValid()) + { + TSubclassOf Magazine = Weapon->MagazineModification.LoadSynchronous(); + InventoryView->MagazineUpgrade->OnItemChanged(0, 0, Magazine->GetDefaultObject()); + } +} + +void UARUIInventoryComponent::RemoveMagazineUpgrade() +{ + AARHUD* HUD = Cast(GetOwner()); + if (!HUD) + return; + AARPlayerController* PC = Cast(HUD->PlayerOwner); + if (!PC) + return; + + AARCharacter* Character = Cast(PC->GetPawn()); + if (!Character) + return; + + UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; + UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); + + TSoftClassPtr Item = Weapon->RemoveMagazineUpgrade(); + + + UIFInventoryComponent* MainInventory = PC->MainInventory; + + MainInventory->AddItemFromClass(Item, 0); + + InventoryView->MagazineUpgrade->OnItemChanged(0, 0, nullptr); } \ No newline at end of file diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h index f3a3de5..df1fab3 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h @@ -63,4 +63,6 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent void ShowUpgradesForWeapon(class UARItemMagazineView* For); void ModifyWeapon(); + void AddMagazineUpgrade(uint8 SourceNetIndex, uint8 SourceLocalIndex); + void RemoveMagazineUpgrade(); }; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index 6c967a1..7056fa6 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -4,6 +4,9 @@ #include "IFInventoryComponent.h" +#include "ARPlayerController.h" +#include "ARCharacter.h" + #include "Weapons/ARItemWeapon.h" #include "Weapons/ARWeaponInventoryComponent.h" @@ -18,17 +21,29 @@ void UARItemWeaponWidget::NativeConstruct() Super::NativeConstruct(); if(GetOwningPlayer()) { + if (AARPlayerController* PC = Cast(GetOwningPlayer())) + { + Inventory = PC->MainInventory; + } if (AARHUD* HUD = Cast(GetOwningPlayer()->GetHUD())) { InventoryComponent = HUD->GetUIInventory(); + if (AARCharacter* Character = Cast(GetOwningPlayer()->GetPawn())) + { + WeaponInventory = Character->WeaponInventory; + } } } } -void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +FReply UARItemWeaponWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { + UObject* Out = GetOuter(); + UARInventoryScreenWidget* MainView = Cast(Out); InventoryComponent->ShowWeaponsForSlot(this); + + return FReply::Handled(); } void UARItemWeaponWidget::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) { diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h index f53e848..9c00952 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h @@ -15,11 +15,12 @@ class ACTIONRPGGAME_API UARItemWeaponWidget : public UARItemView GENERATED_BODY() public: TWeakObjectPtr InventoryComponent; + TWeakObjectPtr WeaponInventory; public: virtual void NativeConstruct() override; public: - virtual void NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent); virtual void NativeOnMouseLeave(const FPointerEvent& InMouseEvent) override; virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp index 8e9efc6..4c0e397 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp @@ -9,4 +9,15 @@ FReply UARItemMagazineView::NativeOnMouseButtonDown(const FGeometry& InGeometry, { InventoryComponent->ShowUpgradesForWeapon(this); return FReply::Unhandled(); -} \ No newline at end of file +} + +FReply UARItemMagazineView::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + FReply Handled = FReply::Unhandled(); + + InventoryComponent->RemoveMagazineUpgrade(); + Handled = FReply::Handled(); + + return Handled; +} + diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h index db94349..f27f1b0 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h @@ -16,5 +16,5 @@ class ACTIONRPGGAME_API UARItemMagazineView : public UARItemView public: virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; - + virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp index d68f091..2030c3b 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp @@ -1,7 +1,17 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARListItemMagazineView.h" +#include "UI/Inventory/ARUIInventoryComponent.h" +#include "UI/Inventory/ARItemView.h" +FReply UARListItemMagazineView::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + FReply Handled = FReply::Unhandled(); + InventoryComponent->AddMagazineUpgrade(NetIndex, LocalIndex); + Handled = FReply::Handled(); + + return Handled; +} diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h index e7fe23e..e0bc2e3 100644 --- a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h +++ b/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h @@ -14,7 +14,8 @@ class ACTIONRPGGAME_API UARListItemMagazineView : public UARListItemView { GENERATED_BODY() - +public: + virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 75b165c..e2e47c5 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -3,17 +3,24 @@ #include "ARItemWeapon.h" #include "Weapons/ARMagazineUpgradeItem.h" -void UARItemWeapon::AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade) +void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade) { - MagazineModification = InMagazineUpgrade; - TSubclassOf clas = InMagazineUpgrade.LoadSynchronous(); - MagazineEffect = clas->GetDefaultObject()->UpgradeEffect.LoadSynchronous(); + MagazineModification = InMagazineUpgrade->GetClass()->GetPathName(); + MagazineEffect = InMagazineUpgrade->UpgradeEffect.LoadSynchronous(); OnMagazineUpdateAdded(); } void UARItemWeapon::OnMagazineUpdateAdded() { } + +TSoftClassPtr UARItemWeapon::RemoveMagazineUpgrade() +{ + TSoftClassPtr Copy = MagazineModification; + MagazineModification.Reset(); + return Copy; +} + void UARItemWeapon::OnItemAdded(uint8 LocalIndex) { diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index 73f799a..8d933e0 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -36,16 +36,17 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(EditAnywhere, Category = "Ability") UARWeaponAbilityBase* AbilityInstance; - UPROPERTY(EditAnywhere, Category = "Ability") + UPROPERTY(BlueprintReadOnly, Category = "Ability") TSoftClassPtr MagazineModification; FAFPropertytHandle MagazineEffect; FGAEffectHandle MagazineEffectHandle; - void AddMagazineUpgrade(const TSoftClassPtr& InMagazineUpgrade); + void AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade); void OnMagazineUpdateAdded(); + TSoftClassPtr RemoveMagazineUpgrade(); virtual void OnItemAdded(uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; From 6458d3bf1b89fce4b8d0b39e88341a65027befdc Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 20 Apr 2018 01:09:34 +0200 Subject: [PATCH 139/187] more work on item and weapons upgrades --- .../AbilityFramework/Effects/GAGameEffect.h | 2 +- .../InventoryFramework/Private/IFItemBase.cpp | 17 ++++++ .../InventoryFramework/Public/IFItemBase.h | 13 +++++ Source/ActionRPGGame/ARItemBase.h | 9 +++- .../UI/Inventory/ARUIInventoryComponent.cpp | 26 +++------- Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 33 +++++++++++- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 34 ++++++++++++ .../Weapons/ARMagazineUpgradeItem.h | 7 +++ .../Weapons/ARWeaponInventoryComponent.cpp | 52 +++++++++++++++++++ .../Weapons/ARWeaponInventoryComponent.h | 10 ++++ 10 files changed, 180 insertions(+), 23 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h index 31d62f3..3f15281 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h @@ -118,7 +118,7 @@ struct FAFConditionalEffectContainer Base effect class. You can derive your own specialized classes from it with preset customizations and values. You should never directly inherit blueprints from it. */ -UCLASS(Blueprintable, BlueprintType, Abstract) +UCLASS(Blueprintable, BlueprintType, Abstract, DefaultToInstanced, EditInlineNew) class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject { GENERATED_BODY() diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp index 8740edc..01d12e1 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFItemBase.cpp @@ -2,6 +2,23 @@ #include "IFItemBase.h" +#include "Engine/NetDriver.h" +#include "GameFramework/Actor.h" +#include "IFInventoryComponent.h" +bool UIFItemBase::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) +{ + check(!HasAnyFlags(RF_ClassDefaultObject)); + check(GetOuter() != NULL); + UIFInventoryComponent* Owner = CastChecked(GetOuter()); + UNetDriver* NetDriver = Owner->GetOwner()->GetNetDriver(); + if (NetDriver) + { + NetDriver->ProcessRemoteFunction(Owner->GetOwner(), Function, Parameters, OutParms, Stack, this); + return true; + } + + return false; +} diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 24d3095..4f24af4 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -3,9 +3,20 @@ #pragma once #include "CoreMinimal.h" +#include "UObject/Object.h" #include "UObject/NoExportTypes.h" #include "IFItemBase.generated.h" +/* + A Struct where the actuall item is contained (so it can be easy serialized/deserialized from json. + Also allows to easily embed a replicate itemsh within items. +*/ +USTRUCT() +struct FIFItemBaseData +{ + GENERATED_BODY() +}; + /** * */ @@ -24,6 +35,8 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject return true; } + bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + /* Called after item has been added to inventory. */ diff --git a/Source/ActionRPGGame/ARItemBase.h b/Source/ActionRPGGame/ARItemBase.h index 1423846..5b188d5 100644 --- a/Source/ActionRPGGame/ARItemBase.h +++ b/Source/ActionRPGGame/ARItemBase.h @@ -6,6 +6,14 @@ #include "IFItemBase.h" #include "ARItemBase.generated.h" +USTRUCT() +struct FIFItemBaseData : public FIFItemBaseData +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") + |TSoftObjectPtr Icon; +}; /** * */ @@ -18,5 +26,4 @@ class ACTIONRPGGAME_API UARItemBase : public UIFItemBase UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") UTexture2D* Icon; - }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp index 79b3d31..11730d4 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp @@ -204,23 +204,9 @@ void UARUIInventoryComponent::AddMagazineUpgrade(uint8 SourceNetIndex, uint8 Sou if (!Character) return; - - UIFInventoryComponent* MainInventory = PC->MainInventory; - - UARMagazineUpgradeItem* MagazineUpgrade = MainInventory->GetItem(SourceLocalIndex); - UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; - UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); - - Weapon->AddMagazineUpgrade(MagazineUpgrade); // ??? - MainInventory->RemoveItem(SourceLocalIndex); - - if (Weapon->MagazineModification.IsValid()) - { - TSubclassOf Magazine = Weapon->MagazineModification.LoadSynchronous(); - InventoryView->MagazineUpgrade->OnItemChanged(0, 0, Magazine->GetDefaultObject()); - } + WeaponInventory->AddMagazineMod(SelectedWeapon, SourceLocalIndex); } void UARUIInventoryComponent::RemoveMagazineUpgrade() @@ -237,14 +223,14 @@ void UARUIInventoryComponent::RemoveMagazineUpgrade() return; UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; - UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); + //UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); - TSoftClassPtr Item = Weapon->RemoveMagazineUpgrade(); + //TSoftClassPtr Item = Weapon->RemoveMagazineUpgrade(); - UIFInventoryComponent* MainInventory = PC->MainInventory; + //UIFInventoryComponent* MainInventory = PC->MainInventory; - MainInventory->AddItemFromClass(Item, 0); + //MainInventory->AddItemFromClass(Item, 0); - InventoryView->MagazineUpgrade->OnItemChanged(0, 0, nullptr); + //InventoryView->MagazineUpgrade->OnItemChanged(0, 0, nullptr); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index e2e47c5..5d5a67a 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -1,17 +1,30 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARItemWeapon.h" + +#include "ARCharacter.h" +#include "ARPlayerController.h" +#include "UI/ARHUD.h" +#include "UI/Inventory/ARUIInventoryComponent.h" + #include "Weapons/ARMagazineUpgradeItem.h" +#include "Weapons/ARWeaponInventoryComponent.h" + void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade) { MagazineModification = InMagazineUpgrade->GetClass()->GetPathName(); + MagazineModificationObj = DuplicateObject(InMagazineUpgrade, this); MagazineEffect = InMagazineUpgrade->UpgradeEffect.LoadSynchronous(); OnMagazineUpdateAdded(); } void UARItemWeapon::OnMagazineUpdateAdded() { - + //should be called only fropm server. + FARWeaponModInfo Info; + Info.Icon = MagazineModificationObj->Icon->GetPathName(); + Info.UpgradeType = EARWeaponUpgradeType::Magazine; + ClientOnMagazineAdded(Info); } TSoftClassPtr UARItemWeapon::RemoveMagazineUpgrade() @@ -21,6 +34,24 @@ TSoftClassPtr UARItemWeapon::RemoveMagazineUpgrade return Copy; } +void UARItemWeapon::ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& ModInfo) +{ + if (UARWeaponInventoryComponent* Inv = Cast(GetOuter())) + { + if (AARCharacter* Character = Cast(Inv->GetOwner())) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + if (AARHUD* HUD = Cast(PC->GetHUD())) + { + UARUIInventoryComponent* UIInc = HUD->GetUIInventory(); + + } + } + } + } +} + void UARItemWeapon::OnItemAdded(uint8 LocalIndex) { diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index 8d933e0..dfd12c3 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -9,6 +9,23 @@ #include "GameplayTags.h" #include "ARItemWeapon.generated.h" +UENUM() +enum class EARWeaponUpgradeType : uint8 +{ + Magazine +}; + +USTRUCT() +struct FARWeaponModInfo +{ + GENERATED_BODY(); +public: + UPROPERTY() + EARWeaponUpgradeType UpgradeType; + UPROPERTY() + TSoftObjectPtr Icon; +}; + /** * */ @@ -23,6 +40,13 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(EditAnywhere, Category = "Visual") TSoftClassPtr Weapon; + /* + Values from these attributes will be copied to ability, after ability is instanced. + It's here to allow random generation and easily store that information in Database instead of storing ability. + */ + UPROPERTY(EditAnywhere, Instanced, Category = "Attributes") + class UARGunAttributes* Attributes; + UPROPERTY(EditAnywhere, Category = "Transforms") FVector HolsteredPosition; UPROPERTY(EditAnywhere, Category = "Transforms") @@ -39,6 +63,12 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(BlueprintReadOnly, Category = "Ability") TSoftClassPtr MagazineModification; + /* + So it will actually actor as mini inventory with predefined slots. + That way we should be able to generate mods on the fly and store them as json in external database. + */ + UPROPERTY(BlueprintReadOnly, Category = "Ability") + class UARMagazineUpgradeItem* MagazineModificationObj; FAFPropertytHandle MagazineEffect; FGAEffectHandle MagazineEffectHandle; @@ -46,6 +76,10 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase void AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade); void OnMagazineUpdateAdded(); + UFUNCTION(Client, Reliable) + void ClientOnMagazineAdded(const FARWeaponModInfo& ModInfo); + void ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& ModInfo); + TSoftClassPtr RemoveMagazineUpgrade(); virtual void OnItemAdded(uint8 LocalIndex) override; diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h index 0bce8dd..b8dc67d 100644 --- a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h @@ -6,6 +6,13 @@ #include "Weapons/ARWeaponUpgradeItem.h" #include "ARMagazineUpgradeItem.generated.h" + +USTRUCT() +struct FARMagazineUpgradeItemData +{ + GENERATED_BODY() +}; + /** * */ diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index f0cf02a..a34f2d8 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -441,4 +441,56 @@ void UARWeaponInventoryComponent::AsynWeaponLoaded(UChildActorComponent* Compone Component->SetRelativeLocation(InWeapon.Position); Component->SetRelativeRotation(InWeapon.Rotation); +} +void UARWeaponInventoryComponent::AddMagazineMod(uint8 WeaponIdx, uint8 MagazineModIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerAddMagazineMod(WeaponIdx, MagazineModIndex); + return; + } + + if (AARCharacter* Character = Cast(GetOwner())) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + UIFInventoryComponent* MainInventory = PC->MainInventory; + + UARMagazineUpgradeItem* Magazine = MainInventory->GetItem(MagazineModIndex); + if (Magazine) + { + UARItemWeapon* Weapon = GetItem(WeaponIdx); + if (Weapon) + { + Weapon->AddMagazineUpgrade(Magazine); + MainInventory->RemoveItem(MagazineModIndex); + } + } + } + } +} +void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(uint8 WeaponIdx, uint8 MagazineModIndex) +{ + if (AARCharacter* Character = Cast(GetOwner())) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + UIFInventoryComponent* MainInventory = PC->MainInventory; + + UARMagazineUpgradeItem* Magazine = MainInventory->GetItem(MagazineModIndex); + if (Magazine) + { + UARItemWeapon* Weapon = GetItem(WeaponIdx); + if (Weapon) + { + Weapon->AddMagazineUpgrade(Magazine); + MainInventory->RemoveItem(MagazineModIndex); + } + } + } + } +} +bool UARWeaponInventoryComponent::ServerAddMagazineMod_Validate(uint8 WeaponIdx, uint8 MagazineModIndex) +{ + return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index dd0f46f..01aa3f1 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -136,4 +136,14 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone UFUNCTION() void AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon); + +public: + //Local Indexes + void AddMagazineMod(uint8 WeaponIdx, uint8 MagazineModIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddMagazineMod(uint8 WeaponIdx, uint8 MagazineModIndex); + + void ServerAddMagazineMod_Implementation(uint8 WeaponIdx, uint8 MagazineModIndex); + bool ServerAddMagazineMod_Validate(uint8 WeaponIdx, uint8 MagazineModIndex); + }; From 53d4f5eb8bb5b90ab4e5961b45720a8d3b3e0357 Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 20 Apr 2018 08:49:09 +0200 Subject: [PATCH 140/187] fixed compilation errors --- .../Source/InventoryFramework/Public/IFItemBase.h | 2 +- Source/ActionRPGGame/ARItemBase.h | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 4f24af4..ba28286 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -11,7 +11,7 @@ A Struct where the actuall item is contained (so it can be easy serialized/deserialized from json. Also allows to easily embed a replicate itemsh within items. */ -USTRUCT() +USTRUCT(BlueprintType) struct FIFItemBaseData { GENERATED_BODY() diff --git a/Source/ActionRPGGame/ARItemBase.h b/Source/ActionRPGGame/ARItemBase.h index 5b188d5..29fc70c 100644 --- a/Source/ActionRPGGame/ARItemBase.h +++ b/Source/ActionRPGGame/ARItemBase.h @@ -7,12 +7,12 @@ #include "ARItemBase.generated.h" USTRUCT() -struct FIFItemBaseData : public FIFItemBaseData +struct FARItemBaseData : public FIFItemBaseData { GENERATED_BODY() public: UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") - |TSoftObjectPtr Icon; + TSoftObjectPtr Icon; }; /** * From 6f08bd8fceca73b9c146d0360f51be89f54380eb Mon Sep 17 00:00:00 2001 From: "Lukasz \"iniside\" Baran" Date: Fri, 20 Apr 2018 09:00:37 +0200 Subject: [PATCH 141/187] modifying items to use struct data, for replication --- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 37 ++++++++++++++++++- .../Weapons/ARMagazineUpgradeItem.h | 9 ++++- 2 files changed, 44 insertions(+), 2 deletions(-) diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index dfd12c3..f372ac1 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -5,7 +5,8 @@ #include "CoreMinimal.h" #include "UObject/NoExportTypes.h" #include "Effects/GAGameEffect.h" -#include "ARItemBase.h" +#include "ARMagazineUpgradeItem.h" + #include "GameplayTags.h" #include "ARItemWeapon.generated.h" @@ -26,6 +27,37 @@ struct FARWeaponModInfo TSoftObjectPtr Icon; }; + +USTRUCT() +struct FARItemWeaponData : public FARItemBaseData +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Ability") + TSoftClassPtr Ability; + + UPROPERTY(EditAnywhere, Category = "Visual") + TSoftClassPtr Weapon; + + /* + Values from these attributes will be copied to ability, after ability is instanced. + It's here to allow random generation and easily store that information in Database instead of storing ability. + */ + UPROPERTY(EditAnywhere, Instanced, Category = "Attributes") + class UARGunAttributes* Attributes; + + UPROPERTY(EditAnywhere, Category = "Transforms") + FVector HolsteredPosition; + UPROPERTY(EditAnywhere, Category = "Transforms") + FRotator HolsteredRotation; + + UPROPERTY(EditAnywhere, Category = "Transforms") + FVector EquipedPosition; + UPROPERTY(EditAnywhere, Category = "Transforms") + FRotator EquipedRotation; +}; + + /** * */ @@ -69,6 +101,9 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase */ UPROPERTY(BlueprintReadOnly, Category = "Ability") class UARMagazineUpgradeItem* MagazineModificationObj; + + UPROPERTY() //replicated + FARMagazineUpgradeItemData MagazineUpgrade; FAFPropertytHandle MagazineEffect; FGAEffectHandle MagazineEffectHandle; diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h index b8dc67d..b862fa6 100644 --- a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h @@ -8,9 +8,14 @@ USTRUCT() -struct FARMagazineUpgradeItemData +struct FARMagazineUpgradeItemData : public FARItemBaseData { GENERATED_BODY() + /* + replace with instance, to make procedural generation easier. + */ + UPROPERTY(EditAnywhere) + TSoftClassPtr UpgradeEffect; }; /** @@ -21,6 +26,8 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem { GENERATED_BODY() public: + UPROPERTY(EditAnywhere) + FARMagazineUpgradeItemData Data; UPROPERTY(EditAnywhere) TSoftClassPtr UpgradeEffect; }; From 8524e31c772827f3d97dfc42362262efd9be762a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 20 Apr 2018 23:42:24 +0200 Subject: [PATCH 142/187] added empty function for creating item from JSON, added template function to create item of type with Data type --- .../InventoryFramework/Public/IFItemBase.h | 22 +++++++++++++++++++ .../UI/Inventory/ARUIInventoryComponent.h | 2 +- Source/ActionRPGGame/Weapons/ARItemWeapon.h | 3 +++ 3 files changed, 26 insertions(+), 1 deletion(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index ba28286..8f779fa 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -49,4 +49,26 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject Called after item has been removed from inventory; */ virtual void OnItemRemoved(uint8 LocalIndex) {}; + + virtual void PreItemLoad() {}; + + virtual void PostItemLoad() {}; + + static UIFItemBase* LoadFromJSON() { return nullptr; } + + template + static ItemType* CreateItemFromData(DataType InData, class UIFInventoryComponent* Owner) + { + ItemType* Item = NewObject(Owner, ItemType::StaticClass()); + Item->Data = InData; + return Item; + } + + template + static ItemType* CreateItemFromData(DataType InData, TSubclassOf ItemClass, class UIFInventoryComponent* Owner) + { + ItemType* Item = NewObject(Owner, ItemClass); + Item->Data = InData; + return Item; + } }; diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h index df1fab3..fec9534 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h @@ -38,7 +38,7 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - + inline UARInventoryScreenWidget* GetInventoryVieW() { return InventoryView; } void CreateInventoryView(AARPlayerController* PC); void ShowHideInventory(); diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Weapons/ARItemWeapon.h index f372ac1..a78ca66 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.h @@ -66,6 +66,9 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase { GENERATED_BODY() public: + UPROPERTY(EditAnywhere) + FARItemWeaponData Data; + UPROPERTY(EditAnywhere, Category = "Ability") TSoftClassPtr Ability; From eb7ef1ff1815c72587bdc49c162201ee37176aa1 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 22 Apr 2018 23:10:32 +0200 Subject: [PATCH 143/187] prototype json item serialization, for future integration with external backends/databases --- .../AbilityFramework/AFAbilityComponent.cpp | 2 +- .../InventoryFramework.Build.cs | 2 + .../Private/IFInventoryComponent.cpp | 86 ++++++++++++++++++- .../Public/IFInventoryComponent.h | 26 ++++++ .../InventoryFramework/Public/IFItemBase.h | 8 ++ Source/ActionRPGGame/ARPlayerController.cpp | 6 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 2 + .../UI/Inventory/ARUIInventoryComponent.h | 2 +- Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 5 +- 9 files changed, 131 insertions(+), 8 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index dafc2b3..39d1e81 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -127,7 +127,7 @@ void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickTyp void UAFAbilityComponent::BeginPlay() { Super::BeginPlay(); - FAFEffectTimerManager::Get(); + //FAFEffectTimerManager::Get(); } void UAFAbilityComponent::EndPlay(const EEndPlayReason::Type EndPlayReason) { diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs index 4debc05..d8dc3b9 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs +++ b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs @@ -40,6 +40,8 @@ public InventoryFramework(ReadOnlyTargetRules Target) : base(Target) "Engine", "Slate", "SlateCore", + "Json", + "JsonUtilities" // ... add private dependencies that you statically link with here ... } ); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index a372bd1..a87fcb3 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -11,6 +11,15 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" +#include "Json.h" +#include "JsonObjectConverter.h" + +#include "Policies/CondensedJsonPrintPolicy.h" +#include "Serialization/JsonTypes.h" +#include "Serialization/JsonReader.h" +#include "Policies/PrettyJsonPrintPolicy.h" +#include "Serialization/JsonSerializer.h" + void FIFItemData::PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer) { if(Item) @@ -301,6 +310,14 @@ void UIFInventoryComponent::InitializeInventory() { ENetMode NM = GetOwner()->GetNetMode(); ENetRole NR = GetOwnerRole(); + uint8 Counter = 0; + for (uint8 Idx = 0; Idx < MaxSlots; Idx++) + { + FIFItem NewItem; + NewItem.Index = Idx; + Counter++; + InventoryItems.Add(NewItem); + } //Preallocate inventory items. We are not going to add/remove struct items //but we are going to modify their internals later. @@ -436,6 +453,28 @@ void UIFInventoryComponent::AddAllItemsFromActor(class AIFItemActorBase* Source) } void UIFInventoryComponent::ServerAddAllItemsFromActor_Implementation(class AIFItemActorBase* Source) { + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + + TSharedPtr Obj = MakeShareable(new FJsonObject()); + TArray> Vals; + + TSharedPtr dupa = MakeShareable(new FJsonValueString("dupa string")); + Vals.Add(dupa); + + Obj->SetArrayField("TestData", Vals); + TSharedPtr dupaData = MakeShareable(new FJsonValueString("dupa asdasd string")); + Obj->SetField("DupaData", dupaData); + + FString OutputString; + TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); + check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + + FString asd; + + + + //ClientSendJsonData(OutputString); TArray> Items = Source->GetAllItems(); for (const TSoftClassPtr Item : Items) { @@ -561,11 +600,30 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr ItemClass = InItem.Get(); - UIFItemBase* Item = NewObject(this, ItemClass); - Inventory.AddItemToFreeSlot(Item); + FIFItem Item; + Item.Index = 0; + Item.Item = NewObject(this, ItemClass); + //Inventory.AddItemToFreeSlot(Item); + + + TSharedPtr Obj = MakeShareable(new FJsonObject()); + FJsonObjectConverter::UStructToJsonObject(Item.StaticStruct(), &Item, Obj.ToSharedRef(), 0, 0); + + FakeBackend.Add(Obj); + + InventoryItems[Item.Index] = Item; + + + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + + FString OutputString; + TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); + check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); + ClientSendJsonData(OutputString); } void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex) { @@ -574,6 +632,9 @@ void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem UIFItemBase* Item = NewObject(this, ItemClass); Inventory.AddItem(Item, InNetIndex); + + + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); } @@ -587,4 +648,25 @@ bool UIFInventoryComponent::ReplicateSubobjects(class UActorChannel *Channel, cl WroteSomething |= Channel->ReplicateSubobject(const_cast(Item.Item), *Bunch, *RepFlags); } return WroteSomething; +} + +void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Data) +{ + TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(Data); + + TSharedPtr Object = MakeShareable(new FJsonObject()); + + bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); + + TArray< TSharedPtr > Array; + bool bSuccessful2 = FJsonSerializer::Deserialize(Reader, Array); + + FIFItem Item; + FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), Item.StaticStruct(), &Item, 0, 0); + + if (Item.Item) + { + + } + } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index fb1a560..f01d60b 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -18,6 +18,18 @@ enum class EIFChangeType : uint8 Removed }; +USTRUCT(BlueprintType) +struct INVENTORYFRAMEWORK_API FIFItem +{ + GENERATED_BODY() +public: + UPROPERTY() + class UIFItemBase* Item; + + UPROPERTY(BlueprintReadOnly) + uint8 Index; +}; + USTRUCT(BlueprintType) struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem { @@ -219,6 +231,16 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent FIFItemEvent OnItemRemovedEvent; FIFOnInventoryChanged OnInventoryChanged; + /* Array faking an database backend (where data is stored as json like DynamoDB, GameSparks, CosmosDB, MongoDB */ + TArray> FakeBackend; + + /* Key is deserialized from Json and it stored in backend. */ + //UPROPERTY() + // TMap InventoryItems; + + + UPROPERTY() + TArray InventoryItems; /* Which items this inventory accept. */ @@ -382,4 +404,8 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent FSimpleMulticastDelegate& GetOnInventoryRead(); bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; + + UFUNCTION(Client, Reliable) + void ClientSendJsonData(const FString& Data); + void ClientSendJsonData_Implementation(const FString& Data); }; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 8f779fa..1bc1010 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -25,6 +25,14 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject { GENERATED_BODY() public: + + //Possibly just one index, if we are going to bypass unreal replication + //and just send items as json from server and then decode them and insert in map. + UPROPERTY() + uint8 LocalIndex; + UPROPERTY() + uint8 NetIndex; + bool IsNameStableForNetworking() const override { return false; diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 6ac44db..5e1f832 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -60,8 +60,7 @@ void AARPlayerController::Possess(APawn* aPawn) AbilityComp->BindAbilityToAction(InputComponent, InputHolsterWeapon); AbilityComp->BindAbilityToAction(InputComponent, InputSetAbilityGroup01); AbilityComp->BindAbilityToAction(InputComponent, InputSetAbilityGroup02); - InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); - InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); + AbilityManager->BindInputs(InputComponent, AbilityComp); WeaponManager->BindInputs(InputComponent, AbilityComp); @@ -132,7 +131,8 @@ void AARPlayerController::SetupInputComponent() { Super::SetupInputComponent(); InputComponent->BindAction("SwitchAbilitySet", IE_Pressed, this, &AARPlayerController::InputSwitchAbilitySet); - + InputComponent->BindAction("InputAbilityManager", IE_Pressed, this, &AARPlayerController::InputShowHideAbilityManager); + InputComponent->BindAction("InputInventory", IE_Pressed, this, &AARPlayerController::InputShowHideInventory); } void AARPlayerController::InputSwitchAbilitySet() diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 05d0442..237ef7d 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -51,6 +51,8 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "InputCore", "Slate", "SlateCore", + "Json", + "JsonUtilities", "UMG", "GameplayTags", "AbilityFramework", diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h index fec9534..ebf345f 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h @@ -38,7 +38,7 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent public: // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - inline UARInventoryScreenWidget* GetInventoryVieW() { return InventoryView; } + inline UARInventoryScreenWidget* GetInventoryView() { return InventoryView; } void CreateInventoryView(AARPlayerController* PC); void ShowHideInventory(); diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 5d5a67a..7424b54 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -6,6 +6,8 @@ #include "ARPlayerController.h" #include "UI/ARHUD.h" #include "UI/Inventory/ARUIInventoryComponent.h" +#include "UI/Inventory/ARInventoryScreenWidget.h" +#include "UI/Inventory/Weapons/Modifications/ARItemMagazineView.h" #include "Weapons/ARMagazineUpgradeItem.h" #include "Weapons/ARWeaponInventoryComponent.h" @@ -45,7 +47,8 @@ void UARItemWeapon::ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& if (AARHUD* HUD = Cast(PC->GetHUD())) { UARUIInventoryComponent* UIInc = HUD->GetUIInventory(); - + //not gonna work over network since we cant replicate uobject from uobject. + UIInc->GetInventoryView()->MagazineUpgrade->OnItemChanged(0, 0, MagazineModificationObj); } } } From 6f8962d7c4cff1f91989be94bd65596b7d9ebfb7 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 23 Apr 2018 21:50:59 +0200 Subject: [PATCH 144/187] prototyping json items --- .../Private/IFInventoryComponent.cpp | 108 +++++++++++------- .../Public/IFInventoryComponent.h | 31 +++-- Source/ActionRPGGame/ARCharacter.cpp | 9 +- Source/ActionRPGGame/ARPlayerController.cpp | 2 +- .../UI/Inventory/ARInventoryScreenWidget.h | 6 +- 5 files changed, 99 insertions(+), 57 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index a87fcb3..c50c709 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -289,6 +289,15 @@ void UIFInventoryComponent::BeginPlay() { Inventory.IC = this; Super::BeginPlay(); + uint8 Counter = 0; + for (uint8 Idx = 0; Idx < MaxSlots; Idx++) + { + FIFItem NewItem; + NewItem.Item = nullptr; + NewItem.Index = Idx; + Counter++; + InventoryItems.Add(NewItem); + } /* Further steps @@ -306,54 +315,69 @@ void UIFInventoryComponent::TickComponent(float DeltaTime, ELevelTick TickType, // ... } -void UIFInventoryComponent::InitializeInventory() +TArray UIFInventoryComponent::GetLocalItemIdxs(TSubclassOf ItemClass) { - ENetMode NM = GetOwner()->GetNetMode(); - ENetRole NR = GetOwnerRole(); - uint8 Counter = 0; - for (uint8 Idx = 0; Idx < MaxSlots; Idx++) - { - FIFItem NewItem; - NewItem.Index = Idx; - Counter++; - InventoryItems.Add(NewItem); - } - - //Preallocate inventory items. We are not going to add/remove struct items - //but we are going to modify their internals later. - if ((NM == ENetMode::NM_DedicatedServer) - || (NM == ENetMode::NM_ListenServer) - || (NM == ENetMode::NM_Standalone)) - { - uint8 AvailableCounter = 0; - for (uint8 Idx = 0; Idx < MaxSlots; Idx++) - { - FIFItemData NewItem(Idx, Idx); - if (AvailableCounter < AvailableSlots) - { - NewItem.bAvailable = true; - } - AvailableCounter++; - Inventory.AddData(NewItem); - } - OnInventoryReady.Broadcast(); - } - if (NM == ENetMode::NM_Standalone) + TArray Idxs; + for (uint8 Idx = 0; Idx < InventoryItems.Num(); Idx++) { - if (IIFInventoryInterface* Interface = Cast(GetOwner())) + if (InventoryItems[Idx].Item && InventoryItems[Idx].Item->IsA(ItemClass)) { - Interface->OnInventoryReplicated(this); + Idxs.Add(Idx); } } + + return Idxs; + //return Inventory.GetLocalItemIdxs(ItemClass); } -void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +void UIFInventoryComponent::InitializeInventory() { - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly replicate it to everyone - //to allow prediction for UI. - DOREPLIFETIME_CONDITION(UIFInventoryComponent, Inventory, COND_OwnerOnly); -} + ENetMode NM = GetOwner()->GetNetMode(); + ENetRole NR = GetOwnerRole(); + uint8 Counter = 0; + //for (uint8 Idx = 0; Idx < MaxSlots; Idx++) + //{ + // FIFItem NewItem; + // NewItem.Index = Idx; + // Counter++; + // InventoryItems.Add(NewItem); + //} + + //Preallocate inventory items. We are not going to add/remove struct items + //but we are going to modify their internals later. + //if ((NM == ENetMode::NM_DedicatedServer) + // || (NM == ENetMode::NM_ListenServer) + // || (NM == ENetMode::NM_Standalone)) + //{ + // uint8 AvailableCounter = 0; + // for (uint8 Idx = 0; Idx < MaxSlots; Idx++) + // { + // FIFItemData NewItem(Idx, Idx); + // if (AvailableCounter < AvailableSlots) + // { + // NewItem.bAvailable = true; + // } + // AvailableCounter++; + // Inventory.AddData(NewItem); + // } + // OnInventoryReady.Broadcast(); + //} + //if (NM == ENetMode::NM_Standalone) + //{ + // if (IIFInventoryInterface* Interface = Cast(GetOwner())) + // { + // Interface->OnInventoryReplicated(this); + // } + //} +} + +//void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +//{ +// Super::GetLifetimeReplicatedProps(OutLifetimeProps); +// //possibly replicate it to everyone +// //to allow prediction for UI. +// //DOREPLIFETIME_CONDITION(UIFInventoryComponent, Inventory, COND_OwnerOnly); +//} bool UIFInventoryComponent::AcceptItem(UIFItemBase* Item, uint8 InLocaLIndex) { @@ -666,7 +690,9 @@ void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Dat if (Item.Item) { - + InventoryItems[Item.Index] = Item; + OnItemAddedEvent.Broadcast(Item.Index, Item.Index, Item.Item); + OnItemUpdatedEvent.Broadcast(Item.Index, Item.Index, Item.Item); } } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index f01d60b..219411f 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -223,7 +223,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent friend struct FIFItemContainer; friend struct FIFItemData; protected: - UPROPERTY(Replicated) + //UPROPERTY(Replicated) FIFItemContainer Inventory; FIFItemEvent OnItemAddedEvent; @@ -298,25 +298,40 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent return Inventory.Items[Idx]; } + inline const FIFItem& GetIFItem(uint8 Idx) + { + return InventoryItems[Idx]; + + } inline UIFItemBase* GetItem(uint8 InLocalIndex) { - return Inventory.Items[InLocalIndex].Item; + return InventoryItems[InLocalIndex].Item; + //return Inventory.Items[InLocalIndex].Item; } template T* GetItem(uint8 InLocalIndex) { - return Cast(Inventory.Items[InLocalIndex].Item); + return Cast(InventoryItems[InLocalIndex].Item); + //return Cast(Inventory.Items[InLocalIndex].Item); } - TArray GetLocalItemIdxs(TSubclassOf ItemClass) - { - return Inventory.GetLocalItemIdxs(ItemClass); - } + TArray GetLocalItemIdxs(TSubclassOf ItemClass); template TArray GetItems(TSubclassOf ItemClass) { - return Inventory.GetItems(ItemClass); + TArray Items; + TArray Idxs; + for (uint8 Idx = 0; Idx < InventoryItems.Num(); Idx++) + { + if (InventoryItems[Idx].Item && InventoryItems[Idx].Item->IsA(ItemClass)) + { + Items.Add(Cast(InventoryItems[Idx].Item)); + } + } + + return Items; + //return Inventory.GetItems(ItemClass); } /* diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index c94238e..0d57676 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -156,6 +156,7 @@ void AARCharacter::BeginPlay() Super::BeginPlay(); WeaponInventory->SetIsReplicated(true); WeaponInventory->InitializeWeapons(this); + WeaponInventory->InitializeInventory(); } FString DirToString(EFourCardinalDirection dir) @@ -548,10 +549,10 @@ void AARCharacter::PossessedBy(AController* NewController) { Super::PossessedBy(NewController); ClientPossesedBy(NewController); - if (AARPlayerController* PC = Cast(Controller)) - { - WeaponInventory->InitializeInventory(); - } + //if (AARPlayerController* PC = Cast(Controller)) + //{ + // WeaponInventory->InitializeInventory(); + //} } void AARCharacter::ClientPossesedBy_Implementation(AController* NewController) { diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 5e1f832..3ce63d7 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -119,7 +119,7 @@ void AARPlayerController::Possess(APawn* aPawn) WeaponManager->POwner = aPawn; - MainInventory->InitializeInventory(); + //MainInventory->InitializeInventory(); } void AARPlayerController::ClientPossesed_Implementation(APawn* InPawn) diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h index 86c2092..e984f91 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h @@ -72,11 +72,11 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase if (Item) { - const FIFItemData& Slot = PC->MainInventory->GetSlot(Idx); + const FIFItem& Slot = PC->MainInventory->GetIFItem(Idx); WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); ItemWidget->SetTarget(ForSlot); - ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); - ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + ItemWidget->OnSlotCreated(Slot.Index, Slot.Index, Item); + ItemWidget->OnItemChanged(Slot.Index, Slot.Index, Item); SelectedItemsContainer->AddChild(ItemWidget); } From d658fe392fba5badc5f4ede3120b70429f87ac51 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 26 Apr 2018 00:32:15 +0200 Subject: [PATCH 145/187] reworking invetory plugin to work only with RPCs --- .../Private/IFInventoryComponent.cpp | 435 ++---------------- .../Public/IFInventoryComponent.h | 272 ++--------- Source/ActionRPGGame/ARCharacter.cpp | 1 - Source/ActionRPGGame/ARPlayerController.cpp | 2 - .../UI/Inventory/ARInventoryScreenWidget.h | 10 +- .../UI/Inventory/ARUIInventoryComponent.cpp | 4 - Source/ActionRPGGame/Weapons/ARItemWeapon.cpp | 3 - .../Weapons/ARWeaponInventoryComponent.cpp | 1 - 8 files changed, 76 insertions(+), 652 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index c50c709..c9ff386 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -20,249 +20,6 @@ #include "Policies/PrettyJsonPrintPolicy.h" #include "Serialization/JsonSerializer.h" -void FIFItemData::PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer) -{ - if(Item) - Item->OnItemRemoved(LocalIndex); -} - -void FIFItemData::PostReplicatedAdd(const struct FIFItemContainer& InArraySerializer) -{ - int32 Idx = InArraySerializer.Items.IndexOfByKey(*this); - - LocalIndex = static_cast(Idx); - const_cast(InArraySerializer).NetToLocal.Add(NetIndex, LocalIndex); - const_cast(InArraySerializer).LocalToNet.Add(LocalIndex, NetIndex); - if (InArraySerializer.IC.IsValid() && InArraySerializer.IC->MaxSlots == (NetIndex+1)) - { - InArraySerializer.IC->OnInventoryReady.Broadcast(); - if (IIFInventoryInterface* Interface = Cast(InArraySerializer.IC->GetOwner())) - { - Interface->OnInventoryReplicated(InArraySerializer.IC.Get()); - } - } - if (Item) - { - Item->OnItemAdded(LocalIndex); - InArraySerializer.IC->OnItemAdded(Item, LocalIndex); - } -} - -void FIFItemData::PostReplicatedChange(const struct FIFItemContainer& InArraySerializer) -{ - if (Item) - { - switch (ChangeType) - { - case EIFChangeType::Added: - Item->OnItemAdded(LocalIndex); - InArraySerializer.IC->OnItemAddedEvent.Broadcast(NetIndex, LocalIndex, Item); - InArraySerializer.IC->OnItemAdded(Item, LocalIndex); - break; - case EIFChangeType::Updated: - Item->OnItemChanged(LocalIndex); - InArraySerializer.IC->OnItemUpdatedEvent.Broadcast(NetIndex, LocalIndex, Item); - InArraySerializer.IC->OnItemChanged(Item, LocalIndex); - break; - case EIFChangeType::Removed: - Item->OnItemRemoved(LocalIndex); - InArraySerializer.IC->OnItemRemovedEvent.Broadcast(NetIndex, LocalIndex, Item); - InArraySerializer.IC->OnItemRemoved(LocalIndex); - break; - default: - break; - } - - } -} -void FIFItemContainer::PostReplicatedAdd(const TArrayView& AddedIndices, int32 FinalSize) -{ - -} -void FIFItemContainer::AddItem(uint8 InNetIndex) -{ - uint8 LocalIndex = NetToLocal.FindRef(InNetIndex); - FIFItemData& Item = Items[LocalIndex]; - - -} -void FIFItemContainer::AddItem(class UIFItemBase* InItem, uint8 InNetIndex) -{ - uint8 LocalIndex = NetToLocal.FindRef(InNetIndex); - FIFItemData& Item = Items[LocalIndex]; - Item.Item = InItem; - Item.ChangeType = EIFChangeType::Added; - Item.Item->OnItemAdded(LocalIndex); - IC->OnItemAdded(Item.Item, Item.LocalIndex); - IC->OnItemAddedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); - - MarkItemDirty(Item); -} -void FIFItemContainer::AddItemToFreeSlot(class UIFItemBase* InItem) -{ - for (FIFItemData& Item : Items) - { - if (!Item.Item) - { - Item.Item = InItem; - - Item.Item->OnItemAdded(Item.LocalIndex); - IC->OnItemAdded(Item.Item, Item.LocalIndex); - IC->OnItemAddedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); - Item.ChangeType = EIFChangeType::Added; - MarkItemDirty(Item); - break; - } - } -} -void FIFItemContainer::MoveItem(uint8 NewPosition, uint8 OldPosition) -{ - uint8 NewLocal = NetToLocal[NewPosition]; - uint8 OldLocal = NetToLocal[OldPosition]; - - FIFItemData& NewItem = Items[NewLocal]; - FIFItemData& OldItem = Items[OldLocal]; - if (!OldItem.Item) - { - return; - } - UIFItemBase* NewSlotBackup = nullptr; - - if (NewItem.Item) - { - NewSlotBackup = DuplicateObject(NewItem.Item, IC.Get()); - NewItem.Item->MarkPendingKill(); - Items[NewLocal].Item = nullptr; - } - - NewItem.Item = DuplicateObject(OldItem.Item, IC.Get()); - OldItem.Item->MarkPendingKill(); - OldItem.Item = nullptr; - if (NewSlotBackup) - { - OldItem.Item = NewSlotBackup; //duplicate ? - } - if (NewItem.Item) - { - NewItem.Item->OnItemChanged(NewItem.LocalIndex); - IC->OnItemChanged(NewItem.Item, NewItem.LocalIndex); - IC->OnItemUpdatedEvent.Broadcast(NewItem.NetIndex, NewItem.LocalIndex, NewItem.Item); - NewItem.ChangeType = EIFChangeType::Updated; - } - if (OldItem.Item) - { - OldItem.Item->OnItemChanged(OldItem.LocalIndex); - IC->OnItemChanged(OldItem.Item, OldItem.LocalIndex); - IC->OnItemUpdatedEvent.Broadcast(OldItem.NetIndex, OldItem.LocalIndex, OldItem.Item); - OldItem.ChangeType = EIFChangeType::Updated; - } - else - { - OldItem.ChangeType = EIFChangeType::Removed; - IC->OnItemRemovedEvent.Broadcast(OldItem.NetIndex, OldItem.LocalIndex, OldItem.Item); - IC->OnItemRemoved(OldItem.LocalIndex); - OldItem.Counter++; - } - - MarkItemDirty(NewItem); - MarkItemDirty(OldItem); - -} -void FIFItemContainer::AddFromOtherInventory(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InNetIndex) -{ - uint8 SourceLocalIdx = Source->Inventory.NetToLocal[SourceNetIndex]; - uint8 LocalIdx = NetToLocal[InNetIndex]; - - FIFItemData& SourceItem = const_cast(Source->GetSlot(SourceLocalIdx)); - FIFItemData& LocalItem = Items[LocalIdx]; - - UIFItemBase* LocalOld = nullptr; - if (LocalItem.Item) - { - LocalOld = LocalItem.Item; - } - - LocalItem.Item = DuplicateObject(SourceItem.Item, IC.Get()); - LocalItem.Item->OnItemAdded(LocalItem.LocalIndex); - LocalItem.ChangeType = EIFChangeType::Added; - LocalItem.Counter++; - - IC->OnItemAdded(LocalItem.Item, LocalItem.LocalIndex); - IC->OnItemAddedEvent.Broadcast(LocalItem.NetIndex, LocalItem.LocalIndex, LocalItem.Item); - - SourceItem.Item->MarkPendingKill(); - SourceItem.Item = nullptr; - if (LocalOld) - { - SourceItem.Item = DuplicateObject(LocalOld, Source); - LocalOld->MarkPendingKill(); - LocalOld = nullptr; - SourceItem.ChangeType = EIFChangeType::Added; - SourceItem.Counter++; - } - else - { - SourceItem.ChangeType = EIFChangeType::Removed; - SourceItem.Counter++; - Source->OnItemRemoved(SourceItem.LocalIndex); - } - - MarkItemDirty(LocalItem); - Source->Inventory.MarkItemDirty(SourceItem); -} -void FIFItemContainer::AddFromOtherInventoryAny(class UIFInventoryComponent* Source - , uint8 SourceNetIndex) -{ - - uint8 LocalIndex = NetToLocal[SourceNetIndex]; - FIFItemData& SourceItem = Source->Inventory.Items[LocalIndex]; - if (!SourceItem.Item) - return; - - for (FIFItemData& Item : Items) - { - if (!Item.Item) - { - Item.Item = DuplicateObject(SourceItem.Item, IC.Get()); - Item.Counter++; - Item.ChangeType = EIFChangeType::Added; - IC->OnItemAddedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); - - SourceItem.Item = nullptr; - SourceItem.ChangeType = EIFChangeType::Removed; - Source->OnItemRemovedEvent.Broadcast(SourceItem.NetIndex, SourceItem.LocalIndex, SourceItem.Item); - return; - } - } -} -void FIFItemContainer::RemoveItem(uint8 InNetIndex) -{ - uint8 LocalIndex = NetToLocal[InNetIndex]; - - FIFItemData& Item = Items[LocalIndex]; - if(Item.Item) - Item.Item->MarkPendingKill(); - - Item.Item = nullptr; - Item.ChangeType = EIFChangeType::Removed; - - IC->OnItemRemovedEvent.Broadcast(Item.NetIndex, Item.LocalIndex, Item.Item); -} -TArray FIFItemContainer::GetLocalItemIdxs(TSubclassOf ItemClass) -{ - TArray Indexes; - for (uint8 Idx = 0; Idx < Items.Num(); Idx++) - { - if (Items[Idx].Item && Items[Idx].Item->IsA(ItemClass)) - { - Indexes.Add(Items[Idx].LocalIndex); - } - } - return Indexes; -} - // Sets default values for this component's properties UIFInventoryComponent::UIFInventoryComponent() { @@ -281,18 +38,16 @@ UIFInventoryComponent::UIFInventoryComponent() void UIFInventoryComponent::InitializeComponent() { Super::InitializeComponent(); - Inventory.IC = this; } // Called when the game starts void UIFInventoryComponent::BeginPlay() { - Inventory.IC = this; Super::BeginPlay(); uint8 Counter = 0; for (uint8 Idx = 0; Idx < MaxSlots; Idx++) { - FIFItem NewItem; + FIFItemData NewItem; NewItem.Item = nullptr; NewItem.Index = Idx; Counter++; @@ -330,55 +85,6 @@ TArray UIFInventoryComponent::GetLocalItemIdxs(TSubclassOf I //return Inventory.GetLocalItemIdxs(ItemClass); } -void UIFInventoryComponent::InitializeInventory() -{ - ENetMode NM = GetOwner()->GetNetMode(); - ENetRole NR = GetOwnerRole(); - uint8 Counter = 0; - //for (uint8 Idx = 0; Idx < MaxSlots; Idx++) - //{ - // FIFItem NewItem; - // NewItem.Index = Idx; - // Counter++; - // InventoryItems.Add(NewItem); - //} - - //Preallocate inventory items. We are not going to add/remove struct items - //but we are going to modify their internals later. - //if ((NM == ENetMode::NM_DedicatedServer) - // || (NM == ENetMode::NM_ListenServer) - // || (NM == ENetMode::NM_Standalone)) - //{ - // uint8 AvailableCounter = 0; - // for (uint8 Idx = 0; Idx < MaxSlots; Idx++) - // { - // FIFItemData NewItem(Idx, Idx); - // if (AvailableCounter < AvailableSlots) - // { - // NewItem.bAvailable = true; - // } - // AvailableCounter++; - // Inventory.AddData(NewItem); - // } - // OnInventoryReady.Broadcast(); - //} - //if (NM == ENetMode::NM_Standalone) - //{ - // if (IIFInventoryInterface* Interface = Cast(GetOwner())) - // { - // Interface->OnInventoryReplicated(this); - // } - //} -} - -//void UIFInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -//{ -// Super::GetLifetimeReplicatedProps(OutLifetimeProps); -// //possibly replicate it to everyone -// //to allow prediction for UI. -// //DOREPLIFETIME_CONDITION(UIFInventoryComponent, Inventory, COND_OwnerOnly); -//} - bool UIFInventoryComponent::AcceptItem(UIFItemBase* Item, uint8 InLocaLIndex) { bool bAccept = false; @@ -435,15 +141,8 @@ void UIFInventoryComponent::MoveItemInInventory(uint8 NewLocalPostion, uint8 Old { if (GetOwnerRole() < ENetRole::ROLE_Authority) { - uint8 NewNetPosition = Inventory.GetNetIndex(NewLocalPostion); - uint8 OldNetPosition = Inventory.GetNetIndex(OldLocalPositin); - - ServerMoveItemInInventory(NewNetPosition, OldNetPosition); return; } - uint8 NewNetPosition = Inventory.GetNetIndex(NewLocalPostion); - uint8 OldNetPosition = Inventory.GetNetIndex(OldLocalPositin); - Inventory.MoveItem(NewNetPosition, OldNetPosition); const FIFItemData& NewSlot = GetSlot(NewLocalPostion); const FIFItemData& OldSlot = GetSlot(OldLocalPositin); @@ -451,7 +150,6 @@ void UIFInventoryComponent::MoveItemInInventory(uint8 NewLocalPostion, uint8 Old void UIFInventoryComponent::ServerMoveItemInInventory_Implementation(uint8 NewNetPostion, uint8 OldNetPositin) { - Inventory.MoveItem(NewNetPostion, OldNetPositin); } bool UIFInventoryComponent::ServerMoveItemInInventory_Validate(uint8 NewNetPostion, uint8 OldNetPositin) { @@ -515,80 +213,13 @@ bool UIFInventoryComponent::ServerAddAllItemsFromActor_Validate(class AIFItemAct } -void UIFInventoryComponent::AddItemFromOtherInventory(class UIFInventoryComponent* Source - , uint8 SourceLocalIndex - , uint8 InLocalIndex) -{ - UIFItemBase* ItemToCheck = Source->GetItem(SourceLocalIndex); - if (!AcceptItem(ItemToCheck, InLocalIndex)) - { - return; - } - - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - uint8 SourceNetIndex = Source->Inventory.GetNetIndex(SourceLocalIndex); - uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); - ServerAddItemFromOtherInventory(Source, SourceNetIndex, NetIndex); - return; - } - Inventory.AddFromOtherInventory(Source, SourceLocalIndex, InLocalIndex); -} -void UIFInventoryComponent::ServerAddItemFromOtherInventory_Implementation(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InNetIndex) -{ - uint8 SourceLocalIdx = Source->Inventory.NetToLocal[SourceNetIndex]; - uint8 LocalIdx = Inventory.NetToLocal[InNetIndex]; - UIFItemBase* ItemToCheck = Source->GetItem(SourceLocalIdx); - if (!AcceptItem(ItemToCheck, LocalIdx)) - { - return; - } - Inventory.AddFromOtherInventory(Source, SourceNetIndex, InNetIndex); -} -bool UIFInventoryComponent::ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InNetIndex) -{ - return true; -} - -void UIFInventoryComponent::AddItemFromOtherInventoryAny(class UIFInventoryComponent* Source - , uint8 SourceLocalIndex) -{ - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - uint8 SourceLocalIdx = Inventory.NetToLocal[SourceLocalIndex]; - ServerAddItemFromOtherInventoryAny(Source, SourceLocalIdx); - return; - } - uint8 SourceLocalIdx = Inventory.NetToLocal[SourceLocalIndex]; - Inventory.AddFromOtherInventoryAny(Source, SourceLocalIdx); -} -void UIFInventoryComponent::ServerAddItemFromOtherInventoryAny_Implementation(class UIFInventoryComponent* Source - , uint8 SourceNetIndex) -{ - Inventory.AddFromOtherInventoryAny(Source, SourceNetIndex); -} -bool UIFInventoryComponent::ServerAddItemFromOtherInventoryAny_Validate(class UIFInventoryComponent* Source - , uint8 SourceNetIndex) -{ - return true; -} void UIFInventoryComponent::AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex) { if (GetOwnerRole() < ENetRole::ROLE_Authority) { - uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); - ServerAddItemFromClass(Item.ToSoftObjectPath(), NetIndex); return; } - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - uint8 NetIndex = Inventory.GetNetIndex(InLocalIndex); - FStreamableDelegate Delegate = FStreamableDelegate::CreateUObject(this, &UIFInventoryComponent::OnItemLoaded, Item, NetIndex); - Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); } void UIFInventoryComponent::BP_AddAllItemsFromActor(class AIFItemActorBase* Source) { @@ -614,17 +245,56 @@ void UIFInventoryComponent::BP_AddItemFromClass(TSoftClassPtr AddItemFromClass(Item, InLocalIndex); } -void UIFInventoryComponent::RemoveItem(uint8 InLocalIndex) + +void UIFInventoryComponent::AddItemFromEquipment(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex) +{ + +} + +void UIFInventoryComponent::ServerAddItemFromEquipment_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex) +{ + +} +bool UIFInventoryComponent::ServerAddItemFromEquipment_Validate(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex) +{ + return true; +} +void UIFInventoryComponent::ClientAddItemFromEquipment_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex) +{ + +} + +void UIFInventoryComponent::RemoveItem(uint8 InIndex) +{ + + //remove from backend +} +void UIFInventoryComponent::ServerRemoveItem_Implementation(uint8 InIndex) { - uint8 NetIndex = Inventory.LocalToNet[InLocalIndex]; - Inventory.RemoveItem(NetIndex); + if (InventoryItems[InIndex].Item) + InventoryItems[InIndex].Item->MarkPendingKill(); + + InventoryItems[InIndex].Item = nullptr; + OnItemRemoved(InIndex); + ClientRemoveItem(InIndex); +} +bool UIFInventoryComponent::ServerRemoveItem_Validate(uint8 InIndex) +{ + return true; } +void UIFInventoryComponent::ClientRemoveItem_Implementation(uint8 InIndex) +{ + if (InventoryItems[InIndex].Item) + InventoryItems[InIndex].Item->MarkPendingKill(); + InventoryItems[InIndex].Item = nullptr; + OnItemRemoved(InIndex); +} void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem) { TSubclassOf ItemClass = InItem.Get(); - FIFItem Item; + FIFItemData Item; Item.Index = 0; Item.Item = NewObject(this, ItemClass); //Inventory.AddItemToFreeSlot(Item); @@ -654,26 +324,11 @@ void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem TSubclassOf ItemClass = InItem.Get(); UIFItemBase* Item = NewObject(this, ItemClass); - Inventory.AddItem(Item, InNetIndex); - - - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); } -bool UIFInventoryComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) -{ - bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); - for (const FIFItemData& Item : Inventory.Items) - { - if (Item.Item) - WroteSomething |= Channel->ReplicateSubobject(const_cast(Item.Item), *Bunch, *RepFlags); - } - return WroteSomething; -} - void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Data) { TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(Data); @@ -685,7 +340,7 @@ void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Dat TArray< TSharedPtr > Array; bool bSuccessful2 = FJsonSerializer::Deserialize(Reader, Array); - FIFItem Item; + FIFItemData Item; FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), Item.StaticStruct(), &Item, 0, 0); if (Item.Item) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 219411f..1a3724e 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -4,217 +4,15 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" +#include "IFTypes.h" #include "IFInventoryComponent.generated.h" //NetIndex, LocalIndex DECLARE_MULTICAST_DELEGATE_ThreeParams(FIFItemEvent, uint8, uint8, class UIFItemBase*); DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); -UENUM() -enum class EIFChangeType : uint8 -{ - Added, - Updated, - Removed -}; - -USTRUCT(BlueprintType) -struct INVENTORYFRAMEWORK_API FIFItem -{ - GENERATED_BODY() -public: - UPROPERTY() - class UIFItemBase* Item; - - UPROPERTY(BlueprintReadOnly) - uint8 Index; -}; - -USTRUCT(BlueprintType) -struct INVENTORYFRAMEWORK_API FIFItemData : public FFastArraySerializerItem -{ - GENERATED_BODY() - friend class UIFInventoryComponent; - friend struct FIFItemContainer; - -protected: - UPROPERTY() - class UIFItemBase* Item; - - /* - Indexes below are used to resolve item mapping between server and client, - because there is no guarnteed order of replication. - */ - /* - Index in Array of this item on Server. - */ - UPROPERTY(BlueprintReadOnly) - uint8 NetIndex; - - /* - LIndex in Array of this item on Client. - */ - UPROPERTY(NotReplicated, BlueprintReadOnly) - uint8 LocalIndex; - - /* Is slot currently available */ - UPROPERTY(BlueprintReadOnly) - uint8 bAvailable:1; - - /* - Do Not set Item to nullptr instead set this item to dirty, to indicate that items has been "removed", so we have a Chance - to call OnItemRemoved() on item on clients. - */ - UPROPERTY(BlueprintReadOnly) - uint8 bDirty : 1; - - UPROPERTY() - EIFChangeType ChangeType; - - UPROPERTY() - uint8 Counter; -public: - - FIFItemData() - : Item(nullptr) - , NetIndex(INDEX_NONE) - , LocalIndex(INDEX_NONE) - , bAvailable(false) - , Counter(0) - {} - - FIFItemData(uint8 InNetIndex, uint8 InLocalIndex) - : Item(nullptr) - , NetIndex(InNetIndex) - , LocalIndex(InLocalIndex) - , bAvailable(false) - , Counter(0) - {} - inline uint8 GetNetIndex() const - { - return NetIndex; - } - inline uint8 GetLocalIndex() const - { - return LocalIndex; - } - - /** - * Called right before deleting element during replication. - * - * @param InArraySerializer Array serializer that owns the item and has triggered the replication call - * - * NOTE: intentionally not virtual; invoked via templated code, @see FExampleItemEntry - */ - void PreReplicatedRemove(const struct FIFItemContainer& InArraySerializer); - /** - * Called after adding and serializing a new element - * - * @param InArraySerializer Array serializer that owns the item and has triggered the replication call - * - * NOTE: intentionally not virtual; invoked via templated code, @see FExampleItemEntry - */ - void PostReplicatedAdd(const struct FIFItemContainer& InArraySerializer); - /** - * Called after updating an existing element with new data - * - * @param InArraySerializer Array serializer that owns the item and has triggered the replication call - * NOTE: intentionally not virtual; invoked via templated code, @see FExampleItemEntry - */ - void PostReplicatedChange(const struct FIFItemContainer& InArraySerializer); - - bool operator==(const FIFItemData& Right) const - { - return NetIndex == Right.NetIndex; - } -}; - -USTRUCT() -struct INVENTORYFRAMEWORK_API FIFItemContainer : public FFastArraySerializer -{ - GENERATED_BODY() - friend class UIFInventoryComponent; - UPROPERTY() - TArray Items; - - TWeakObjectPtr IC; - /* NetIndex, LocalIndex */ - TMap NetToLocal; - TMap LocalToNet; - -protected: - void AddData(const FIFItemData& InItem) - { - - int32 Idx = Items.Add(InItem); - MarkItemDirty(Items[Idx]); - MarkArrayDirty(); - NetToLocal.Add(InItem.NetIndex, InItem.LocalIndex); - LocalToNet.Add(InItem.LocalIndex, InItem.NetIndex); - } - uint8 GetNetIndex(uint8 LocalIndex) - { - return LocalToNet.FindRef(LocalIndex); - } - void AddItem(uint8 InNetIndex); - void AddItem(class UIFItemBase* InItem, uint8 InNetIndex); - void AddItemToFreeSlot(class UIFItemBase* InItem); - void MoveItem(uint8 NewPosition, uint8 OldPosition); - - void AddFromOtherInventory(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InNetIndex); - - void AddFromOtherInventoryAny(class UIFInventoryComponent* Source - , uint8 SourceNetIndex); - - TArray GetLocalItemIdxs(TSubclassOf ItemClass); - - void RemoveItem(uint8 InNetIndex); - - template - TArray GetItems(TSubclassOf ItemClass) - { - TArray Indexes; - for (uint8 Idx = 0; Idx < Items.Num(); Idx++) - { - if (Items[Idx].Item && Items[Idx].Item->IsA(ItemClass)) - { - Indexes.Add(Cast(Items[Idx].Item)); - } - } - return Indexes; - } - -public: - inline TArray& GetItems() { return Items; } - - - void PostReplicatedAdd(const TArrayView& AddedIndices, int32 FinalSize); - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(Items, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FIFItemContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; -USTRUCT(BlueprintType) -struct FIFSlotAcceptedClasses -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray> AcceptedClasses; -}; UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent @@ -223,8 +21,6 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent friend struct FIFItemContainer; friend struct FIFItemData; protected: - //UPROPERTY(Replicated) - FIFItemContainer Inventory; FIFItemEvent OnItemAddedEvent; FIFItemEvent OnItemUpdatedEvent; @@ -240,7 +36,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UPROPERTY() - TArray InventoryItems; + TArray InventoryItems; /* Which items this inventory accept. */ @@ -281,9 +77,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; void InitializeInventory(); - - inline FIFItemContainer& GetInventory() { return Inventory; } - + inline FIFItemEvent& GetOnItemAdded() { return OnItemAddedEvent; } inline FIFItemEvent& GetOnItemUpdated() { return OnItemUpdatedEvent; } inline FIFItemEvent& GetOnItemRemoved() { return OnItemRemovedEvent; } @@ -295,14 +89,9 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent inline const FIFItemData& GetSlot(uint8 Idx) { - return Inventory.Items[Idx]; + return InventoryItems[Idx];; } - inline const FIFItem& GetIFItem(uint8 Idx) - { - return InventoryItems[Idx]; - - } inline UIFItemBase* GetItem(uint8 InLocalIndex) { return InventoryItems[InLocalIndex].Item; @@ -363,35 +152,6 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION(BlueprintCallable, Category = "InventoryFramework") void BP_AddAllItemsFromActor(class AIFItemActorBase* Source); - - /* - Moves item to this inventory from the source Inventory. If item already exist it will be swapped (if possible). - */ - void AddItemFromOtherInventory(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InLocalIndex); - UFUNCTION(Server, Reliable, WithValidation) - void ServerAddItemFromOtherInventory(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InLocalIndex); - void ServerAddItemFromOtherInventory_Implementation(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InNetIndex); - bool ServerAddItemFromOtherInventory_Validate(class UIFInventoryComponent* Source - , uint8 SourceNetIndex - , uint8 InNetIndex); - - - void AddItemFromOtherInventoryAny(class UIFInventoryComponent* Source - , uint8 SourceLocalIndex); - UFUNCTION(Server, Reliable, WithValidation) - void ServerAddItemFromOtherInventoryAny(class UIFInventoryComponent* Source - , uint8 SourceNetIndex); - void ServerAddItemFromOtherInventoryAny_Implementation(class UIFInventoryComponent* Source - , uint8 SourceNetIndex); - bool ServerAddItemFromOtherInventoryAny_Validate(class UIFInventoryComponent* Source - , uint8 SourceNetIndex); - /* Adds item from class. Realistically you should never call it on client. */ void AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); @@ -403,11 +163,32 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION(BlueprintCallable, Category = "InventoryFramework") void BP_AddItemFromClass(TSoftClassPtr Item, uint8 InLocalIndex); + + void AddItemFromEquipment(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItemFromEquipment(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + void ServerAddItemFromEquipment_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + bool ServerAddItemFromEquipment_Validate(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + /* + Confirm that change can be made and do the same change on client. + We do not predict inventory modifications. Clients MUST wait for server to make changes and send confirmation back. + */ + UFUNCTION(Client, Reliable) + void ClientAddItemFromEquipment(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + void ClientAddItemFromEquipment_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemRemoved(uint8 LocalIndex) {}; - void RemoveItem(uint8 InLocalIndex); + void RemoveItem(uint8 InIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerRemoveItem(uint8 InIndex); + void ServerRemoveItem_Implementation(uint8 InIndex); + bool ServerRemoveItem_Validate(uint8 InIndex); + UFUNCTION(Client, Reliable) + void ClientRemoveItem(uint8 Index); + void ClientRemoveItem_Implementation(uint8 InIndex); UFUNCTION() @@ -418,7 +199,6 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent FSimpleMulticastDelegate& GetOnInventoryRead(); - bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; UFUNCTION(Client, Reliable) void ClientSendJsonData(const FString& Data); diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/ARCharacter.cpp index 0d57676..ed544e1 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/ARCharacter.cpp @@ -156,7 +156,6 @@ void AARCharacter::BeginPlay() Super::BeginPlay(); WeaponInventory->SetIsReplicated(true); WeaponInventory->InitializeWeapons(this); - WeaponInventory->InitializeInventory(); } FString DirToString(EFourCardinalDirection dir) diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 3ce63d7..02d728a 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -118,8 +118,6 @@ void AARPlayerController::Possess(APawn* aPawn) } WeaponManager->POwner = aPawn; - - //MainInventory->InitializeInventory(); } void AARPlayerController::ClientPossesed_Implementation(APawn* InPawn) diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h index e984f91..db2dd11 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h @@ -72,7 +72,7 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase if (Item) { - const FIFItem& Slot = PC->MainInventory->GetIFItem(Idx); + const FIFItemData& Slot = PC->MainInventory->GetSlot(Idx); WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); ItemWidget->SetTarget(ForSlot); ItemWidget->OnSlotCreated(Slot.Index, Slot.Index, Item); @@ -97,8 +97,8 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); ItemWidget->SetTarget(ForSlot); - ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); - ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + ItemWidget->OnSlotCreated(Slot.Index, Slot.Index, Item); + ItemWidget->OnItemChanged(Slot.Index, Slot.Index, Item); SelectedItemsContainer->AddChild(ItemWidget); } @@ -120,8 +120,8 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase const FIFItemData& Slot = PC->MainInventory->GetSlot(Idx); WidgetType* ItemWidget = CreateWidget(PC, WidgetClass); - ItemWidget->OnSlotCreated(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); - ItemWidget->OnItemChanged(Slot.GetNetIndex(), Slot.GetLocalIndex(), Item); + ItemWidget->OnSlotCreated(Slot.Index, Slot.Index, Item); + ItemWidget->OnItemChanged(Slot.Index, Slot.Index, Item); WeaponModificationContainer->AddChild(ItemWidget); } diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp index 11730d4..65a189c 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp @@ -127,9 +127,6 @@ void UARUIInventoryComponent::AddWeaponToSlot(uint8 TargetNetIndex AARCharacter* Character = Cast(PC->GetPawn()); if (!Character) return; - - Character->WeaponInventory->AddItemFromOtherInventory(PC->MainInventory, SourceLocalIndex, TargetLocalIndex); - } void UARUIInventoryComponent::UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 SourceLocalIndex) @@ -145,7 +142,6 @@ void UARUIInventoryComponent::UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 if (!Character) return; - PC->MainInventory->AddItemFromOtherInventoryAny(Character->WeaponInventory, SourceLocalIndex); Character->WeaponInventory->Unequip(SourceLocalIndex); } diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp index 7424b54..f033716 100644 --- a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp @@ -46,9 +46,6 @@ void UARItemWeapon::ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& { if (AARHUD* HUD = Cast(PC->GetHUD())) { - UARUIInventoryComponent* UIInc = HUD->GetUIInventory(); - //not gonna work over network since we cant replicate uobject from uobject. - UIInc->GetInventoryView()->MagazineUpgrade->OnItemChanged(0, 0, MagazineModificationObj); } } } diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index a34f2d8..ed7fb3d 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -122,7 +122,6 @@ void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* MainHandWeapon.Weapon = InWeapon->Weapon; MainHandWeapon.Position = InWeapon->EquipedPosition; MainHandWeapon.Rotation = InWeapon->EquipedRotation; - MainHandWeapon.NetIndex = Inventory.LocalToNet[WeaponIndex]; MainHandWeapon.RepCounter++; WeaponHelper[WeaponIndex]->Weapon.Reset(); WeaponHelper[WeaponIndex]->RepCounter++; From 60e7cb5153aaadce8c513ec28db52784c2d8068f Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 26 Apr 2018 23:45:03 +0200 Subject: [PATCH 146/187] move more of inventory to use RPC --- .../Private/IFInventoryComponent.cpp | 8 +- .../Public/IFInventoryComponent.h | 8 +- .../UI/Inventory/ARUIInventoryComponent.cpp | 2 + .../Weapons/ARWeaponInventoryComponent.cpp | 184 +++++++++--------- .../Weapons/ARWeaponInventoryComponent.h | 70 ++++--- 5 files changed, 147 insertions(+), 125 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index c9ff386..0b19d93 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -266,7 +266,11 @@ void UIFInventoryComponent::ClientAddItemFromEquipment_Implementation(class UIFE void UIFInventoryComponent::RemoveItem(uint8 InIndex) { - + if(GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerRemoveItem(InIndex); + return; + } //remove from backend } void UIFInventoryComponent::ServerRemoveItem_Implementation(uint8 InIndex) @@ -275,7 +279,7 @@ void UIFInventoryComponent::ServerRemoveItem_Implementation(uint8 InIndex) InventoryItems[InIndex].Item->MarkPendingKill(); InventoryItems[InIndex].Item = nullptr; - OnItemRemoved(InIndex); + OnServerItemRemoved(InIndex); ClientRemoveItem(InIndex); } bool UIFInventoryComponent::ServerRemoveItem_Validate(uint8 InIndex) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 1a3724e..aa9130c 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -8,8 +8,7 @@ #include "IFInventoryComponent.generated.h" //NetIndex, LocalIndex -DECLARE_MULTICAST_DELEGATE_ThreeParams(FIFItemEvent, uint8, uint8, class UIFItemBase*); -DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); + @@ -181,6 +180,11 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemRemoved(uint8 LocalIndex) {}; + //these function are called on server. + virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; + virtual void OnServerItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; + virtual void OnServerItemRemoved(uint8 LocalIndex) {}; + void RemoveItem(uint8 InIndex); UFUNCTION(Server, Reliable, WithValidation) void ServerRemoveItem(uint8 InIndex); diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp index 65a189c..2431bd2 100644 --- a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp @@ -127,6 +127,8 @@ void UARUIInventoryComponent::AddWeaponToSlot(uint8 TargetNetIndex AARCharacter* Character = Cast(PC->GetPawn()); if (!Character) return; + + Character->WeaponInventory->AddItemFromInventory(PC->MainInventory, SourceNetIndex, TargetNetIndex); } void UARUIInventoryComponent::UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 SourceLocalIndex) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index ed7fb3d..ed9aac7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -14,10 +14,6 @@ UARWeaponInventoryComponent::UARWeaponInventoryComponent() // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; - WeaponHelper.Add(&Group001HolsteredAttachment); - WeaponHelper.Add(&Group002HolsteredAttachment); - WeaponHelper.Add(&Group003HolsteredAttachment); - WeaponHelper.Add(&Group004HolsteredAttachment); MaxSlots = 4; AvailableSlots = 4; @@ -53,7 +49,7 @@ void UARWeaponInventoryComponent::TickComponent(float DeltaTime, ELevelTick Tick // ... } -void UARWeaponInventoryComponent::SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component) +void UARWeaponInventoryComponent::SetWeapon(const FARWeaponRPC& InWeapon, UChildActorComponent* Component) { if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) { @@ -74,12 +70,13 @@ void UARWeaponInventoryComponent::SetWeapon(const FARWeapon& InWeapon, UChildAct void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) { UARItemWeapon* InWeapon = Cast(Item); - - WeaponHelper[LocalIndex]->Weapon.Reset(); - WeaponHelper[LocalIndex]->Weapon = InWeapon->Weapon; - WeaponHelper[LocalIndex]->RepCounter++; - - SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = InWeapon->HolsteredPosition; + Data.Rotation = InWeapon->HolsteredRotation; + Data.AttachSlot = static_cast(LocalIndex); + SetWeapon(Data, GroupToComponent[LocalIndex]); if (AARCharacter* Character = Cast(POwner)) { if (AARPlayerController* PC = Cast(Character->Controller)) @@ -97,65 +94,105 @@ void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) PC->WeaponManager->NativeRemoveAbility(TSoftClassPtr(), static_cast(LocalIndex), EAMSlot::Slot001); } } - WeaponHelper[LocalIndex]->Weapon.Reset(); - WeaponHelper[LocalIndex]->RepCounter++; - SetWeapon(*WeaponHelper[LocalIndex], GroupToComponent[LocalIndex]); + FARWeaponRPC Data; + Data.Weapon.Reset(); + //Data.SocketName = InWeapon->Socket; + Data.Position = FVector::ZeroVector; + Data.Rotation = FRotator::ZeroRotator; + Data.AttachSlot = static_cast(LocalIndex); + + SetWeapon(Data, GroupToComponent[LocalIndex]); if (LocalIndex == CurrentWeaponIndex) { Unequip(LocalIndex); } } -void UARWeaponInventoryComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) { - Super::GetLifetimeReplicatedProps(OutLifetimeProps); + UARItemWeapon* InWeapon = Cast(Item); + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = InWeapon->HolsteredPosition; + Data.Rotation = InWeapon->HolsteredRotation; + Data.AttachSlot = static_cast(LocalIndex); - DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group001HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group002HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group003HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, Group004HolsteredAttachment, COND_SkipOwner); - DOREPLIFETIME_CONDITION(UARWeaponInventoryComponent, MainHandWeapon, COND_SkipOwner); + MulticastAddWeapon(Data); } - -void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon) +void UARWeaponInventoryComponent::OnServerItemRemoved(uint8 LocalIndex) +{ +} +void UARWeaponInventoryComponent::MulticastAddWeapon_Implementation(const FARWeaponRPC& WeaponData) { - MainHandWeapon.Weapon = InWeapon->Weapon; - MainHandWeapon.Position = InWeapon->EquipedPosition; - MainHandWeapon.Rotation = InWeapon->EquipedRotation; - MainHandWeapon.RepCounter++; - WeaponHelper[WeaponIndex]->Weapon.Reset(); - WeaponHelper[WeaponIndex]->RepCounter++; if (AARCharacter* Character = Cast(POwner)) { - SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); - if (AARPlayerController* PC = Cast(Character->Controller)) + switch (WeaponData.AttachSlot) { - FSoftObjectPath Path = InWeapon->Ability.ToSoftObjectPath(); - TSoftClassPtr ab(Path); - PC->WeaponManager->EquipWeapon(ab); + case EARWeaponPosition::Right: + SetWeapon(WeaponData, Character->GetHolsteredRightWeapon()); + break; + case EARWeaponPosition::Left: + SetWeapon(WeaponData, Character->GetHolsteredLeftWeapon()); + break; + case EARWeaponPosition::BottomBack: + SetWeapon(WeaponData, Character->GetHolsteredBackDownWeapon()); + break; + case EARWeaponPosition::Side: + SetWeapon(WeaponData, Character->GetHolsteredSideLeftWeapon()); + break; + case EARWeaponPosition::Equiped: + break; + default: + break; } + } } +void UARWeaponInventoryComponent::MulticastRemoveWeapon_Implementation(const FARWeaponRPC& WeaponData) +{ + +} + +void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon) +{ + //MainHandWeapon.Weapon = InWeapon->Weapon; + //MainHandWeapon.Position = InWeapon->EquipedPosition; + //MainHandWeapon.Rotation = InWeapon->EquipedRotation; + //MainHandWeapon.RepCounter++; + //WeaponHelper[WeaponIndex]->Weapon.Reset(); + //WeaponHelper[WeaponIndex]->RepCounter++; + //if (AARCharacter* Character = Cast(POwner)) + //{ + // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + // GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + // if (AARPlayerController* PC = Cast(Character->Controller)) + // { + // FSoftObjectPath Path = InWeapon->Ability.ToSoftObjectPath(); + // TSoftClassPtr ab(Path); + // PC->WeaponManager->EquipWeapon(ab); + // } + //} +} void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) { - MainHandWeapon.Weapon.Reset(); - MainHandWeapon.Position = FVector(0,0,0); - MainHandWeapon.Rotation = FRotator(0,0,0); - MainHandWeapon.NetIndex = 0; - MainHandWeapon.RepCounter++; - WeaponHelper[WeaponIndex]->Weapon.Reset(); - WeaponHelper[WeaponIndex]->RepCounter++; + //MainHandWeapon.Weapon.Reset(); + //MainHandWeapon.Position = FVector(0,0,0); + //MainHandWeapon.Rotation = FRotator(0,0,0); + //MainHandWeapon.NetIndex = 0; + //MainHandWeapon.RepCounter++; + //WeaponHelper[WeaponIndex]->Weapon.Reset(); + //WeaponHelper[WeaponIndex]->RepCounter++; - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); - if (AARPlayerController* PC = Cast(Character->Controller)) - { - PC->WeaponManager->RemoveAbility(static_cast(WeaponIndex), EAMSlot::Slot001); - } - } + //if (AARCharacter* Character = Cast(POwner)) + //{ + // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); + // GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + // if (AARPlayerController* PC = Cast(Character->Controller)) + // { + // PC->WeaponManager->RemoveAbility(static_cast(WeaponIndex), EAMSlot::Slot001); + // } + //} } void UARWeaponInventoryComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) { @@ -388,50 +425,7 @@ UARItemWeapon* UARWeaponInventoryComponent::FindPreviousValid() return WeaponAbilityTag; } - -void UARWeaponInventoryComponent::OnRep_Group001HolsteredAttachment() -{ - ///if (Group001HolsteredAttachment.WeaponMesh.IsPending()) - ///{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group001HolsteredAttachment, Character->GetHolsteredRightWeapon()); - } - ///} -} -void UARWeaponInventoryComponent::OnRep_Group002HolsteredAttachment() -{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group002HolsteredAttachment, Character->GetHolsteredLeftWeapon()); - } -} -void UARWeaponInventoryComponent::OnRep_Group003HolsteredAttachment() -{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group003HolsteredAttachment, Character->GetHolsteredRightWeapon()); - } -} -void UARWeaponInventoryComponent::OnRep_Group004HolsteredAttachment() -{ - if (AARCharacter* Character = Cast(POwner)) - { - SetWeapon(Group004HolsteredAttachment, Character->GetHolsteredRightWeapon()); - } -} - -void UARWeaponInventoryComponent::OnRep_MainHandWeapon(FARWeapon OldWeapon) -{ - if (AARCharacter* Character = Cast(POwner)) - { - //SetWeapon(OldWeapon, GroupToComponent[OldWeapon.Group]); - SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - //GroupToComponent[MainHandWeapon.Group]->SetChildActorClass(nullptr); - } -} - -void UARWeaponInventoryComponent::AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon) +void UARWeaponInventoryComponent::AsynWeaponLoaded(UChildActorComponent* Component, FARWeaponRPC InWeapon) { Component->SetChildActorClass(InWeapon.Weapon.Get()); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index 01aa3f1..f7c05f8 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -8,6 +8,7 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" #include "IFInventoryComponent.h" +#include "IFEquipmentComponent.h" #include "AMTypes.h" #include "ARWeaponInventoryComponent.generated.h" @@ -36,24 +37,41 @@ struct FARWeapon uint8 RepCounter; }; +UENUM() +enum class EARWeaponPosition +{ + Right= 0, + Left = 1, + BottomBack = 2, + Side = 3, + Equiped = 4 +}; + +USTRUCT() +struct FARWeaponRPC +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Attachment Test") + TSoftClassPtr Weapon; + + UPROPERTY(EditAnywhere, Category = "Attachment Test") + FVector Position; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + FRotator Rotation; + UPROPERTY(EditAnywhere, Category = "Attachment Test") + EARWeaponPosition AttachSlot; +}; + + /* Manages currently equipped weapons (holstered and unholstered). */ UCLASS( ClassGroup=(Inventory), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryComponent +class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentComponent { GENERATED_BODY() protected: - UPROPERTY(ReplicatedUsing = OnRep_Group001HolsteredAttachment) - FARWeapon Group001HolsteredAttachment; - UPROPERTY(ReplicatedUsing = OnRep_Group002HolsteredAttachment) - FARWeapon Group002HolsteredAttachment; - UPROPERTY(ReplicatedUsing = OnRep_Group003HolsteredAttachment) - FARWeapon Group003HolsteredAttachment; - UPROPERTY(ReplicatedUsing = OnRep_Group004HolsteredAttachment) - FARWeapon Group004HolsteredAttachment; - UPROPERTY(ReplicatedUsing = OnRep_MainHandWeapon) - FARWeapon MainHandWeapon; UPROPERTY() class APawn* POwner; @@ -61,8 +79,6 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone TMap GroupToComponent; TMap GroupToItem; - TArray WeaponHelper; - uint8 CurrentWeaponIndex; public: @@ -79,6 +95,19 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; + + virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; + virtual void OnServerItemRemoved(uint8 LocalIndex) override; + + UFUNCTION(NetMulticast, Reliable) + void MulticastAddWeapon(const FARWeaponRPC& WeaponData); + void MulticastAddWeapon_Implementation(const FARWeaponRPC& WeaponData); + + UFUNCTION(NetMulticast, Reliable) + void MulticastRemoveWeapon(const FARWeaponRPC& WeaponData); + void MulticastRemoveWeapon_Implementation(const FARWeaponRPC& WeaponData); + + void Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon); void Unequip(uint8 WeaponIndex); void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); @@ -121,21 +150,10 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFInventoryCompone UARItemWeapon* FindPreviousValid(); protected: - void SetWeapon(const FARWeapon& InWeapon, UChildActorComponent* Component); - UFUNCTION() - void OnRep_Group001HolsteredAttachment(); - UFUNCTION() - void OnRep_Group002HolsteredAttachment(); - UFUNCTION() - void OnRep_Group003HolsteredAttachment(); - UFUNCTION() - void OnRep_Group004HolsteredAttachment(); - - UFUNCTION() - void OnRep_MainHandWeapon(FARWeapon OldWeapon); + void SetWeapon(const FARWeaponRPC& InWeapon, UChildActorComponent* Component); UFUNCTION() - void AsynWeaponLoaded(UChildActorComponent* Component, FARWeapon InWeapon); + void AsynWeaponLoaded(UChildActorComponent* Component, FARWeaponRPC InWeapon); public: //Local Indexes From aca173239a53657cbc57260b357912e57adfd665 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 28 Apr 2018 00:11:43 +0200 Subject: [PATCH 147/187] add RPC to Equip weapon and fixed ability equiping over network --- .../AbilityFramework/AFAbilityComponent.cpp | 16 ++-- .../AbilityFramework/AFAbilityComponent.h | 6 +- Source/ActionRPGGame/ARPlayerController.cpp | 28 +++---- .../Weapons/ARWeaponInventoryComponent.cpp | 74 ++++++++++++------- .../Weapons/ARWeaponInventoryComponent.h | 5 +- 5 files changed, 75 insertions(+), 54 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index 39d1e81..ad27d44 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -433,7 +433,7 @@ void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbili //FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeAddAbility(InAbility, InInputTag); + ServerNativeAddAbility(InAbility.ToSoftObjectPath(), InInputTag); /*if (AlreadyBound.IsValid()) { for (const FGameplayTag& Input : InInputTag) @@ -464,13 +464,13 @@ void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbili } -void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const TSoftClassPtr& InAbility, +void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, const TArray& InInputTag) { - NativeAddAbility(InAbility, InInputTag); + NativeAddAbility(TSoftClassPtr(InAbility), InInputTag); } -bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const TSoftClassPtr& InAbility, +bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, const TArray& InInputTag) { return true; @@ -508,16 +508,16 @@ void UAFAbilityComponent::NativeRemoveAbility(TSoftClassPtr InAb { if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeRemoveAbility(InAbilityTag); + ServerNativeRemoveAbility(InAbilityTag.ToSoftObjectPath()); } AbilityContainer.RemoveAbility(InAbilityTag); } -void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const TSoftClassPtr& InAbilityTag) +void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag) { - AbilityContainer.RemoveAbility(InAbilityTag); + AbilityContainer.RemoveAbility(TSoftClassPtr(InAbilityTag)); } -bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const TSoftClassPtr& InAbilityTag) +bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FSoftObjectPath InAbilityTag) { return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 426a40a..49f3cde 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -556,13 +556,13 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public const TArray& InInputTag); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeAddAbility(const TSoftClassPtr& InAbility, + void ServerNativeAddAbility(const FSoftObjectPath& InAbility, const TArray& InInputTag); - void ServerNativeAddAbility_Implementation(const TSoftClassPtr& InAbility, + void ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, const TArray& InInputTag); - bool ServerNativeAddAbility_Validate(const TSoftClassPtr& InAbility, + bool ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, const TArray& InInputTag); void OnFinishedLoad(TSoftClassPtr InAbility); diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/ARPlayerController.cpp index 02d728a..c9974f6 100644 --- a/Source/ActionRPGGame/ARPlayerController.cpp +++ b/Source/ActionRPGGame/ARPlayerController.cpp @@ -27,21 +27,8 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial void AARPlayerController::BeginPlay() { Super::BeginPlay(); - - MainInventory->SetIsReplicated(true); - -} -void AARPlayerController::SetPawn(APawn* InPawn) -{ - Super::SetPawn(InPawn); - - - //UIAbilityManagerComponent->BindInputs(); -} -void AARPlayerController::Possess(APawn* aPawn) -{ - Super::Possess(aPawn); ENetMode NetMode = GetNetMode(); + MainInventory->SetIsReplicated(true); if (NetMode == ENetMode::NM_Client || NetMode == ENetMode::NM_Standalone) { @@ -110,6 +97,19 @@ void AARPlayerController::Possess(APawn* aPawn) } } +} +void AARPlayerController::SetPawn(APawn* InPawn) +{ + Super::SetPawn(InPawn); + + + //UIAbilityManagerComponent->BindInputs(); +} +void AARPlayerController::Possess(APawn* aPawn) +{ + Super::Possess(aPawn); + ENetMode NetMode = GetNetMode(); + if (NetMode == ENetMode::NM_DedicatedServer || NetMode == ENetMode::NM_ListenServer) diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index ed9aac7..8031785 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -142,6 +142,7 @@ void UARWeaponInventoryComponent::MulticastAddWeapon_Implementation(const FARWea SetWeapon(WeaponData, Character->GetHolsteredSideLeftWeapon()); break; case EARWeaponPosition::Equiped: + SetWeapon(WeaponData, Character->GetEquipedMainWeapon()); break; default: break; @@ -154,25 +155,29 @@ void UARWeaponInventoryComponent::MulticastRemoveWeapon_Implementation(const FAR } -void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon) +void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(uint8 WeaponIndex, const FARWeaponRPC& WeaponData) { - //MainHandWeapon.Weapon = InWeapon->Weapon; - //MainHandWeapon.Position = InWeapon->EquipedPosition; - //MainHandWeapon.Rotation = InWeapon->EquipedRotation; - //MainHandWeapon.RepCounter++; - //WeaponHelper[WeaponIndex]->Weapon.Reset(); - //WeaponHelper[WeaponIndex]->RepCounter++; - //if (AARCharacter* Character = Cast(POwner)) - //{ - // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - // GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); - // if (AARPlayerController* PC = Cast(Character->Controller)) - // { - // FSoftObjectPath Path = InWeapon->Ability.ToSoftObjectPath(); - // TSoftClassPtr ab(Path); - // PC->WeaponManager->EquipWeapon(ab); - // } - //} + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(WeaponData, Character->GetEquipedMainWeapon()); + GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + } +} + +void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, const FARWeaponRPC& WeaponData) +{ + if (AARCharacter* Character = Cast(POwner)) + { + SetWeapon(WeaponData, Character->GetEquipedMainWeapon()); + GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); + if (AARPlayerController* PC = Cast(Character->Controller)) + { + UARItemWeapon* ItemWeapon = GetItem(WeaponIndex); + FSoftObjectPath Path = ItemWeapon->Ability.ToSoftObjectPath(); + TSoftClassPtr ab(Path); + PC->WeaponManager->EquipWeapon(ab); + } + } } void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) { @@ -222,12 +227,18 @@ void UARWeaponInventoryComponent::NextWeapon() } } - UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); - if (!NextWeaponAbility) + UARItemWeapon* InWeapon = GetItem(CurrentWeaponIndex); + if (!InWeapon) { - NextWeaponAbility = FindNextValid(); + InWeapon = FindNextValid(); } - Equip(CurrentWeaponIndex, NextWeaponAbility); + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = InWeapon->EquipedPosition; + Data.Rotation = InWeapon->EquipedRotation; + Data.AttachSlot = EARWeaponPosition::Equiped; + Equip(CurrentWeaponIndex, Data); if (GetOwnerRole() < ENetRole::ROLE_Authority) { ServerNextWeapon(CurrentWeaponIndex); @@ -296,12 +307,19 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIn CurrentWeaponIndex = CurrentIndex; } - UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); - if (!NextWeaponAbility) + UARItemWeapon* InWeapon = GetItem(CurrentWeaponIndex); + if (!InWeapon) { - NextWeaponAbility = FindNextValid(); + InWeapon = FindNextValid(); } - Equip(CurrentWeaponIndex, NextWeaponAbility); + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = InWeapon->EquipedPosition; + Data.Rotation = InWeapon->EquipedRotation; + Data.AttachSlot = EARWeaponPosition::Equiped; + + MulticastEquipWeapon(CurrentWeaponIndex, Data); if (WeaponIndex == CurrentWeaponIndex) { ClientNextWeapon(CurrentWeaponIndex, true); @@ -322,7 +340,7 @@ void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(uint8 WeaponIn CurrentWeaponIndex = WeaponIndex; UARItemWeapon* NextWeaponAbility = GetItem(WeaponIndex); - Equip(WeaponIndex, NextWeaponAbility); + //Equip(WeaponIndex, NextWeaponAbility); } void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 WeaponIndex) @@ -350,7 +368,7 @@ void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 Weap //situation where client can chage multiple weapons within second //should not have place, as there is animation and/or internal cooldown on weapon change. //since it will be done trough ability. - Equip(CurrentWeaponIndex, NextWeaponAbility); + //Equip(CurrentWeaponIndex, NextWeaponAbility); if (CurrentWeaponIndex != WeaponIndex) { ClientPreviousWeapon(CurrentWeaponIndex, false); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index f7c05f8..6161168 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -107,8 +107,11 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void MulticastRemoveWeapon(const FARWeaponRPC& WeaponData); void MulticastRemoveWeapon_Implementation(const FARWeaponRPC& WeaponData); + UFUNCTION(NetMulticast, Reliable) + void MulticastEquipWeapon(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); + void MulticastEquipWeapon_Implementation(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); - void Equip(uint8 WeaponIndex, class UARItemWeapon* InWeapon); + void Equip(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); void Unequip(uint8 WeaponIndex); void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); inline void SetPOwner(APawn* InPawn) From 334ff0db89232d2e7914e48477ab6a34ec064d4a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 28 Apr 2018 00:12:04 +0200 Subject: [PATCH 148/187] typo fix --- .../Source/AbilityFramework/AFAbilityComponent.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index ad27d44..a586ae5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -517,7 +517,7 @@ void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const FSoftOb AbilityContainer.RemoveAbility(TSoftClassPtr(InAbilityTag)); } -bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FSoftObjectPath InAbilityTag) +bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag) { return true; } From 5d2dcdd645f241e24132b44fb85f1b42327424c9 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 28 Apr 2018 00:16:11 +0200 Subject: [PATCH 149/187] missing changes --- .../Source/AbilityFramework/AFAbilityComponent.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index 49f3cde..a2b0eef 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -572,11 +572,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void NativeRemoveAbility(TSoftClassPtr InAbilityTag); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeRemoveAbility(const TSoftClassPtr& InAbilityTag); + void ServerNativeRemoveAbility(const FSoftObjectPath& InAbilityTag); - void ServerNativeRemoveAbility_Implementation(const TSoftClassPtr& InAbilityTag); + void ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag); - bool ServerNativeRemoveAbility_Validate(const TSoftClassPtr& InAbilityTag); + bool ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag); //TODO: Make it procted From 832e0e20e11ed2648572cd7dd65e7672c814dcb1 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 28 Apr 2018 02:07:25 +0200 Subject: [PATCH 150/187] added weapon holstering --- .../AbilityFramework/AFAbilityComponent.cpp | 17 +++++- .../AbilityFramework/AFAbilityComponent.h | 5 ++ .../AbilityFramework/AFAbilityTypes.cpp | 13 +++++ .../Source/AbilityFramework/AFAbilityTypes.h | 1 + .../Weapons/ARWeaponInventoryComponent.cpp | 55 +++++++++++-------- .../Weapons/ARWeaponInventoryComponent.h | 16 ++++-- 6 files changed, 77 insertions(+), 30 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp index a586ae5..4f1273d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp @@ -322,7 +322,22 @@ bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const TSoftClassPtr< { return true; } - +void UAFAbilityComponent::RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr) +{ + AbilityContainer.RemoveAbilityFromAction(InAbilityPtr); + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerRemoveAbilitiesFromActions(InAbilityPtr.ToSoftObjectPath()); + } +} +void UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr) +{ + AbilityContainer.RemoveAbilityFromAction(TSoftClassPtr(InAbilityPtr)); +} +bool UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr) +{ + return true; +} void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr) { NotifyOnAbilityInputReady(InAbilityPtr); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h index a2b0eef..30f8ae0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h @@ -518,6 +518,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); + void RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr); + UFUNCTION(Server, Reliable, WithValidation) + void ServerRemoveAbilitiesFromActions(const FSoftObjectPath& InAbilityPtr); + void ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr); + bool ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr); UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") void BP_InputPressed(FGameplayTag ActionName); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp index 95a306e..981b61a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp @@ -159,7 +159,20 @@ void FAFAbilityContainer::SetAbilityToAction(const TSoftClassPtr AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); } } +void FAFAbilityContainer::RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr) +{ + TArray* Inputs = AbilityToAction.Find(InAbiltyPtr); + if (Inputs) + { + for (const FGameplayTag& Input : *Inputs) + { + ActionToAbility.Remove(Input); + } + + AbilityToAction.Remove(InAbiltyPtr); + } +} UGAAbilityBase* FAFAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) { UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h index 4e7ef4b..a976afb 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h @@ -79,6 +79,7 @@ struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer void RemoveAbility(const TSoftClassPtr& AbilityIn); void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); + void RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr); TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp index 8031785..66dd993 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp @@ -162,6 +162,7 @@ void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(uint8 Weap SetWeapon(WeaponData, Character->GetEquipedMainWeapon()); GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); } + CurrentWeaponIndex = WeaponIndex; } void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, const FARWeaponRPC& WeaponData) @@ -177,6 +178,7 @@ void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, const FARWeaponRPC& W TSoftClassPtr ab(Path); PC->WeaponManager->EquipWeapon(ab); } + CurrentWeaponIndex = WeaponIndex; } } void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) @@ -199,9 +201,36 @@ void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) // } //} } -void UARWeaponInventoryComponent::Holster(EAMGroup Group, class UARItemWeapon* InWeapon) +void UARWeaponInventoryComponent::Holster() { - + UARItemWeapon* EquipedWeapon = GetItem(CurrentWeaponIndex); + if (!EquipedWeapon) + return; + if (AARCharacter* Character = Cast(POwner)) + { + Character->GetAbilityComp()->RemoveAbilitiesFromActions(EquipedWeapon->Ability); + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + } + FARWeaponRPC Data; + Data.Weapon = EquipedWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = EquipedWeapon->HolsteredPosition; + Data.Rotation = EquipedWeapon->HolsteredRotation; + Data.AttachSlot = static_cast(CurrentWeaponIndex); + SetWeapon(Data, GroupToComponent[CurrentWeaponIndex]); + ServerHolster(Data); +} +void UARWeaponInventoryComponent::ServerHolster_Implementation(const FARWeaponRPC& WeaponData) +{ + MulticastHolster(WeaponData); +} +bool UARWeaponInventoryComponent::ServerHolster_Validate(const FARWeaponRPC& WeaponData) +{ + return true; +} +void UARWeaponInventoryComponent::MulticastHolster_Implementation(const FARWeaponRPC& WeaponData) +{ + SetWeapon(WeaponData, GroupToComponent[CurrentWeaponIndex]); } void UARWeaponInventoryComponent::SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility) { @@ -268,27 +297,7 @@ void UARWeaponInventoryComponent::PreviousWeapon() void UARWeaponInventoryComponent::HolsterWeapon() { - //ActiveGroup = EAMGroup::Group005; - //if (AARCharacter* Character = Cast(POwner)) - //{ - // Character->GetWeapons()->HolsterActive(ActiveGroup); - //} - //if (GetOwnerRole() < ENetRole::ROLE_Authority) - //{ - // ServerHolsterWeapon(static_cast(ActiveGroup)); - //} -} -void UARWeaponInventoryComponent::ServerHolsterWeapon_Implementation(uint8 WeaponIndex) -{ - //ActiveGroup = EAMGroup::Group005; - //if (AARCharacter* Character = Cast(POwner)) - //{ - // Character->GetWeapons()->HolsterActive(ActiveGroup); - //} -} -bool UARWeaponInventoryComponent::ServerHolsterWeapon_Validate(uint8 WeaponIndex) -{ - return true; + Holster(); } void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIndex) { diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h index 6161168..b6fcbff 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h @@ -113,7 +113,16 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void Equip(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); void Unequip(uint8 WeaponIndex); - void Holster(EAMGroup Group, class UARItemWeapon* InWeapon); + void Holster(); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerHolster(const FARWeaponRPC& WeaponData); + void ServerHolster_Implementation(const FARWeaponRPC& WeaponData); + bool ServerHolster_Validate(const FARWeaponRPC& WeaponData); + UFUNCTION(NetMulticast, Reliable) + void MulticastHolster(const FARWeaponRPC& WeaponData); + void MulticastHolster_Implementation(const FARWeaponRPC& WeaponData); + inline void SetPOwner(APawn* InPawn) { POwner = InPawn; @@ -144,11 +153,6 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void ClientPreviousWeapon(uint8 WeaponIndex, bool bPredictionSuccess); void ClientPreviousWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess); - UFUNCTION(Server, Reliable, WithValidation) - void ServerHolsterWeapon(uint8 WeaponIndex); - void ServerHolsterWeapon_Implementation(uint8 WeaponIndex); - bool ServerHolsterWeapon_Validate(uint8 WeaponIndex); - UARItemWeapon* FindNextValid(); UARItemWeapon* FindPreviousValid(); From 26f820dbfe5df1d06af6904fef6e75f01ec8ef3d Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 29 Apr 2018 23:19:03 +0200 Subject: [PATCH 151/187] changed files organization, because of last changes in master branch --- .../AbilityFramework/AFAbilityComponent.cpp | 610 -------- .../AbilityFramework/AFAbilityComponent.h | 613 -------- .../AbilityFramework/AFAbilityInterface.cpp | 25 - .../AbilityFramework/AFAbilityInterface.h | 75 - .../AbilityFramework/AFAbilityTypes.cpp | 226 --- .../Source/AbilityFramework/AFAbilityTypes.h | 109 -- .../AbilityFramework/AFAttributeComponent.cpp | 35 - .../AbilityFramework/AFAttributeComponent.h | 29 - .../AFBlueprintFunctionLibrary.cpp | 46 - .../AFBlueprintFunctionLibrary.h | 17 - .../AbilityFramework/AFCueInterface.cpp | 7 - .../Source/AbilityFramework/AFCueInterface.h | 26 - .../Source/AbilityFramework/AFCueManager.cpp | 341 ----- .../Source/AbilityFramework/AFCueManager.h | 53 - .../AbilityFramework/AFEffectsComponent.cpp | 502 ------ .../AbilityFramework/AFEffectsComponent.h | 227 --- .../Abilities/AFAbilityActivationSpec.cpp | 13 - .../Abilities/AFAbilityActivationSpec.h | 21 - .../Abilities/AFAbilityCooldownSpec.cpp | 14 - .../Abilities/AFAbilityCooldownSpec.h | 20 - .../AFAbilityInfiniteDurationSpec.cpp | 13 - .../Abilities/AFAbilityInfiniteDurationSpec.h | 21 - .../Abilities/AFAbilityPeriodSpec.cpp | 13 - .../Abilities/AFAbilityPeriodSpec.h | 20 - .../AFAbilityPeriodicInfiniteSpec.cpp | 14 - .../Abilities/AFAbilityPeriodicInfiniteSpec.h | 18 - .../Abilities/GAAbilityBase.cpp | 950 ------------ .../Abilities/GAAbilityBase.h | 622 -------- .../Abilities/GAAbilityBlueprint.cpp | 33 - .../Abilities/GAAbilityBlueprint.h | 31 - .../Tasks/AFAbilityTask_SpawnProjectile.cpp | 30 - .../Tasks/AFAbilityTask_SpawnProjectile.h | 58 - .../Abilities/Tasks/GAAbilityTask.cpp | 12 - .../Abilities/Tasks/GAAbilityTask.h | 95 -- .../Tasks/GAAbilityTask_CreateObject.cpp | 64 - .../Tasks/GAAbilityTask_CreateObject.h | 32 - .../Tasks/GAAbilityTask_PlayMontage.cpp | 50 - .../Tasks/GAAbilityTask_PlayMontage.h | 45 - .../Abilities/Tasks/GAAbilityTask_Repeat.cpp | 15 - .../Abilities/Tasks/GAAbilityTask_Repeat.h | 24 - .../Tasks/GAAbilityTask_SpawnActor.cpp | 70 - .../Tasks/GAAbilityTask_SpawnActor.h | 34 - .../Tasks/GAAbilityTask_TargetData.cpp | 154 -- .../Tasks/GAAbilityTask_TargetData.h | 64 - .../Tasks/GAAbilityTask_TargetDataCircle.cpp | 64 - .../Tasks/GAAbilityTask_TargetDataCircle.h | 40 - .../GAAbilityTask_TargetDataLineTrace.cpp | 218 --- .../Tasks/GAAbilityTask_TargetDataLineTrace.h | 107 -- .../Tasks/GAAbilityTask_WaitForConfirm.cpp | 33 - .../Tasks/GAAbilityTask_WaitForConfirm.h | 30 - .../Tasks/GAAbilityTask_WaitTargetData.cpp | 84 - .../Tasks/GAAbilityTask_WaitTargetData.h | 34 - .../AbilityFramework.Build.cs | 19 - .../AbilityFramework/AbilityFramework.cpp | 213 --- .../AbilityFramework/AbilityFramework.h | 152 -- .../AnimNotify/AFAbilityNotifyState.cpp | 33 - .../AnimNotify/AFAbilityNotifyState.h | 28 - .../AnimNotify/AFAnimNotify.cpp | 19 - .../AnimNotify/AFAnimNotify.h | 23 - .../Attributes/GAAttributeBase.cpp | 248 --- .../Attributes/GAAttributeBase.h | 148 -- .../Attributes/GAAttributeExtension.cpp | 23 - .../Attributes/GAAttributeExtension.h | 32 - .../Attributes/GAAttributeGlobals.cpp | 5 - .../Attributes/GAAttributeGlobals.h | 15 - .../Attributes/GAAttributesBase.cpp | 297 ---- .../Attributes/GAAttributesBase.h | 136 -- .../GAAttributesBlueprintFunctionLibrary.cpp | 72 - .../GAAttributesBlueprintFunctionLibrary.h | 58 - .../Attributes/GAAttributesStats.cpp | 4 - .../Attributes/GAAttributesStats.h | 2 - .../AFEffectApplicationRequirement.cpp | 8 - .../Effects/AFEffectApplicationRequirement.h | 29 - .../Effects/AFEffectCustomApplication.cpp | 26 - .../Effects/AFEffectCustomApplication.h | 44 - .../Effects/AFEffectCustomStackingRule.cpp | 14 - .../Effects/AFEffectCustomStackingRule.h | 22 - .../Effects/AFEffectSpecFunctionLibrary.cpp | 50 - .../Effects/AFEffectSpecFunctionLibrary.h | 57 - .../AFAttributeStongerOverride.cpp | 39 - .../AFAttributeStongerOverride.h | 25 - .../AFEffectAlreadyApplied.cpp | 20 - .../AFEffectAlreadyApplied.h | 27 - .../AFAtributeDurationAdd.cpp | 25 - .../AFAtributeDurationAdd.h | 32 - .../AFAtributeDurationUnique.cpp | 38 - .../AFAtributeDurationUnique.h | 34 - .../AFAttributeDurationInfinite.cpp | 17 - .../AFAttributeDurationInfinite.h | 33 - .../AFAttributeDurationOverride.cpp | 27 - .../AFAttributeDurationOverride.h | 34 - .../AFPeriodApplicationAdd.cpp | 32 - .../AFPeriodApplicationAdd.h | 39 - .../AFPeriodApplicationExtend.cpp | 53 - .../AFPeriodApplicationExtend.h | 39 - .../AFPeriodApplicationInfiniteAdd.cpp | 24 - .../AFPeriodApplicationInfiniteAdd.h | 39 - .../AFPeriodApplicationOverride.cpp | 34 - .../AFPeriodApplicationOverride.h | 38 - .../AFPeriodicApplInfiniteOverride.cpp | 8 - .../AFPeriodicApplInfiniteOverride.h | 26 - .../Effects/EffectTasks/AFEffectTask.cpp | 8 - .../Effects/EffectTasks/AFEffectTask.h | 37 - .../AFEffectTask_AppliedEffectEvent.cpp | 82 - .../AFEffectTask_AppliedEffectEvent.h | 49 - .../AFEffectTask_AttributeChange.cpp | 70 - .../AFEffectTask_AttributeChange.h | 50 - .../AFEffectTask_EffectAppliedToSelf.cpp | 80 - .../AFEffectTask_EffectAppliedToSelf.h | 50 - .../AFEffectTask_EffectAppliedToTarget.cpp | 85 -- .../AFEffectTask_EffectAppliedToTarget.h | 50 - .../EffectTasks/AFEffectTask_EffectEvent.cpp | 84 - .../EffectTasks/AFEffectTask_EffectEvent.h | 48 - .../AFEffectTask_ExecutedEffectEvent.cpp | 84 - .../AFEffectTask_ExecutedEffectEvent.h | 49 - .../Effects/GABlueprintLibrary.cpp | 371 ----- .../Effects/GABlueprintLibrary.h | 111 -- .../Effects/GACustomCalculation.cpp | 11 - .../Effects/GACustomCalculation.h | 30 - .../Effects/GAEffectBlueprint.cpp | 33 - .../Effects/GAEffectBlueprint.h | 31 - .../AbilityFramework/Effects/GAEffectCue.cpp | 162 -- .../AbilityFramework/Effects/GAEffectCue.h | 85 -- .../GAEffectCueBlueprintGeneratedClass.cpp | 13 - .../GAEffectCueBlueprintGeneratedClass.h | 17 - .../Effects/GAEffectCueGlobals.cpp | 51 - .../Effects/GAEffectCueGlobals.h | 26 - .../Effects/GAEffectCueSequence.cpp | 130 -- .../Effects/GAEffectCueSequence.h | 69 - .../Effects/GAEffectExecution.cpp | 24 - .../Effects/GAEffectExecution.h | 22 - .../Effects/GAEffectExtension.cpp | 70 - .../Effects/GAEffectExtension.h | 79 - .../Effects/GAEffectField.cpp | 48 - .../AbilityFramework/Effects/GAEffectField.h | 60 - .../Effects/GAEffectGlobalTypes.cpp | 143 -- .../Effects/GAEffectGlobalTypes.h | 155 -- .../AbilityFramework/Effects/GAGameEffect.cpp | 847 ----------- .../AbilityFramework/Effects/GAGameEffect.h | 1346 ----------------- .../Source/AbilityFramework/GAGlobalTypes.cpp | 353 ----- .../Source/AbilityFramework/GAGlobalTypes.h | 790 ---------- .../AbilityFramework/GAHelperTemplates.cpp | 5 - .../AbilityFramework/GAHelperTemplates.h | 59 - .../AbilityFramework/GAPhysicalMaterial.cpp | 8 - .../AbilityFramework/GAPhysicalMaterial.h | 19 - .../Source/AbilityFramework/GAUIData.cpp | 8 - .../Source/AbilityFramework/GAUIData.h | 16 - .../AbilityFramework/IAbilityFramework.h | 37 - .../LatentActions/AFLatentInterface.cpp | 8 - .../LatentActions/AFLatentInterface.h | 25 - .../LatentActions/AFTaskBase.cpp | 100 -- .../LatentActions/AFTaskBase.h | 102 -- .../LatentActions/AFTaskManager.cpp | 25 - .../LatentActions/AFTaskManager.h | 17 - .../LatentActions/GAWaitAction.cpp | 51 - .../LatentActions/GAWaitAction.h | 42 - .../AbilityFramework/Mods/GAAttributeMod.cpp | 11 - .../AbilityFramework/Mods/GAAttributeMod.h | 32 - .../AFAbilityActionSpecDetails.cpp | 75 - .../AFAbilityActionSpecDetails.h | 31 - .../AFAbilityCooldownSpecDetails.cpp | 75 - .../AFAbilityCooldownSpecDetails.h | 30 - .../AFAbilityInfiniteDurationSpecDetails.cpp | 83 - .../AFAbilityInfiniteDurationSpecDetails.h | 31 - .../AFAbilityInfinitePeriodSpecDetails.cpp | 83 - .../AFAbilityInfinitePeriodSpecDetails.h | 31 - .../AFAbilityPeriodSpecDetails.cpp | 81 - .../AFAbilityPeriodSpecDetails.h | 31 - .../AFEK2Node_AsyncEffectTaskCall.cpp | 79 - .../AFEK2Node_AsyncEffectTaskCall.h | 20 - .../AFEffectCustomizationCommon.cpp | 111 -- .../AFEffectCustomizationCommon.h | 19 - .../AssetTypeActions_GAAbilityBlueprint.cpp | 57 - .../AssetTypeActions_GAAbilityBlueprint.h | 27 - .../GAAbilityBlueprintFactory.cpp | 334 ---- .../AbilityEditor/GAAbilityBlueprintFactory.h | 32 - .../AbilityEditor/GAAbilityEditor.cpp | 142 -- .../AbilityEditor/GAAbilityEditor.h | 64 - .../AbilityEditor/GAAbilityGraph.cpp | 16 - .../AbilityEditor/GAAbilityGraph.h | 15 - .../AbilityEditor/GAAbilityGraphSchema.cpp | 22 - .../AbilityEditor/GAAbilityGraphSchema.h | 38 - .../AbilityFrameworkEditor.Build.cs | 15 - .../AbilityFrameworkEditor.cpp | 161 -- .../AbilityFrameworkEditor.h | 60 - .../GACurveTableDetailCustomization.cpp | 28 - .../GACurveTableDetailCustomization.h | 23 - .../EffectCueEditor/AFEffectCueDetails.cpp | 353 ----- .../EffectCueEditor/AFEffectCueDetails.h | 36 - .../AssetTypeActions_GAEffectCueBlueprint.cpp | 57 - .../AssetTypeActions_GAEffectCueBlueprint.h | 27 - .../EffectCueEditor/GAEffectCueBlueprint.cpp | 33 - .../EffectCueEditor/GAEffectCueBlueprint.h | 32 - .../GAEffectCueBlueprintFactory.cpp | 334 ---- .../GAEffectCueBlueprintFactory.h | 32 - .../EffectCueEditor/GAEffectCueEditor.cpp | 210 --- .../EffectCueEditor/GAEffectCueEditor.h | 79 - .../EffectCueEditor/GAEffectCueGraph.cpp | 16 - .../EffectCueEditor/GAEffectCueGraph.h | 15 - .../GAEffectCueGraphSchema.cpp | 22 - .../EffectCueEditor/GAEffectCueGraphSchema.h | 38 - .../AssetTypeActions_GAEffectBlueprint.cpp | 57 - .../AssetTypeActions_GAEffectBlueprint.h | 27 - .../EffectEditor/GAEffectBlueprintFactory.cpp | 347 ----- .../EffectEditor/GAEffectBlueprintFactory.h | 32 - .../EffectEditor/GAEffectEditor.cpp | 124 -- .../EffectEditor/GAEffectEditor.h | 53 - .../EffectEditor/GAEffectGraph.cpp | 16 - .../EffectEditor/GAEffectGraph.h | 15 - .../EffectEditor/GAEffectGraphSchema.cpp | 22 - .../EffectEditor/GAEffectGraphSchema.h | 38 - .../GAAttributeDetailCustomization.cpp | 90 -- .../GAAttributeDetailCustomization.h | 33 - .../GAAttributePanelGraphPinFactory.cpp | 16 - .../GAAttributePanelGraphPinFactory.h | 23 - .../AbilityFrameworkEditor/GAAttributePin.cpp | 105 -- .../AbilityFrameworkEditor/GAAttributePin.h | 27 - .../GAEK2Node_LatentAbilityTaskCall.cpp | 79 - .../GAEK2Node_LatentAbilityTaskCall.h | 20 - .../GAEK2Node_LatentAction.cpp | 76 - .../GAEK2Node_LatentAction.h | 19 - .../GAEffectClassStructWidget.cpp | 856 ----------- .../GAEffectClassStructWidget.h | 58 - .../GAEffectDetails.cpp | 112 -- .../AbilityFrameworkEditor/GAEffectDetails.h | 32 - .../GAEffectPropertyStructCustomization.cpp | 96 -- .../GAEffectPropertyStructCustomization.h | 28 - .../GAGlobalTypesEditor.h | 35 - .../IAbilityFrameworkEditor.h | 36 - .../SGAAttributeWidget.cpp | 151 -- .../SGAAttributeWidget.h | 64 - .../AFDAbilityGiveTrigger.cpp | 107 -- .../AFDAbilityGiveTrigger.h | 83 - .../AFDBlueprintFunctionLibrary.cpp | 11 - .../AFDBlueprintFunctionLibrary.h | 20 - .../AbilityFrameworkDebugger/AFDManager.cpp | 41 - .../AbilityFrameworkDebugger/AFDManager.h | 38 - .../AbilityFrameworkDebugger.Build.cs | 8 - .../AbilityFrameworkDebugger.cpp | 45 - .../AbilityFrameworkDebugger.h | 22 - .../SAFDAttributes.cpp | 74 - .../AbilityFrameworkDebugger/SAFDAttributes.h | 39 - .../SAFDDesktopWidget.cpp | 203 --- .../SAFDDesktopWidget.h | 54 - .../SAFDEffectInspector.cpp | 16 - .../SAFDEffectInspector.h | 20 - .../AbilityFrameworkDebugger/SAFDEffects.cpp | 105 -- .../AbilityFrameworkDebugger/SAFDEffects.h | 82 - .../SAFDViewportMouseCapture.cpp | 22 - .../SAFDViewportMouseCapture.h | 24 - .../AMAbilityManagerComponent.cpp | 451 ------ .../AMAbilityManagerComponent.h | 201 --- .../Source/AbilityManager/AMTypes.cpp | 3 - .../Source/AbilityManager/AMTypes.h | 95 -- .../AbilityManager/AbilityManager.Build.cs | 12 - .../Source/AbilityManager/AbilityManager.cpp | 20 - .../Source/AbilityManager/AbilityManager.h | 15 - .../AMAbilityInputProperty.cpp | 36 - .../AMAbilityInputProperty.h | 18 - .../AbilityManagerEditor.Build.cs | 8 - .../AbilityManagerEditor.cpp | 20 - .../AbilityManagerEditor.h | 15 - .../DraggableWindow/DWBPFunctionLibrary.cpp | 14 - .../DraggableWindow/DWBPFunctionLibrary.h | 26 - .../Source/DraggableWindow/DWManager.cpp | 72 - .../Source/DraggableWindow/DWManager.h | 38 - .../Source/DraggableWindow/DWTypes.cpp | 3 - .../Source/DraggableWindow/DWTypes.h | 41 - .../DraggableWindow/DraggableWindow.Build.cs | 8 - .../DraggableWindow/DraggableWindow.cpp | 33 - .../Source/DraggableWindow/DraggableWindow.h | 21 - .../SDraggableWindowWidget.cpp | 706 --------- .../DraggableWindow/SDraggableWindowWidget.h | 195 --- .../InventoryFramework.Build.cs | 10 +- .../InventoryFrameworkUI.Build.cs | 10 +- .../AnimNode_BlendLocomotionFour.cpp | 548 ------- .../AnimNode_BlendLocomotionFour.h | 146 -- .../OrionAnimation/OrionAnimComponent.cpp | 34 - .../OrionAnimation/OrionAnimComponent.h | 29 - .../OrionAnimation/OrionAnimation.Build.cs | 8 - .../Source/OrionAnimation/OrionAnimation.cpp | 20 - .../Source/OrionAnimation/OrionAnimation.h | 15 - .../Source/OrionAnimation/OrionInterface.cpp | 6 - .../Source/OrionAnimation/OrionInterface.h | 42 - .../AnimGraphNode_BlendLocomotionFour.cpp | 130 -- .../AnimGraphNode_BlendLocomotionFour.h | 35 - .../OrionAnimationEditor.Build.cs | 10 +- .../OrionAnimationEditor.cpp | 20 - .../OrionAnimationEditor.h | 15 - .../Source/SpectrAI/SpectrAI.Build.cs | 8 - Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp | 20 - Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h | 15 - .../Source/SpectrAI/SpectrAIController.cpp | 12 - .../Source/SpectrAI/SpectrAIController.h | 48 - .../SpectrAI/Source/SpectrAI/SpectrAction.cpp | 60 - .../SpectrAI/Source/SpectrAI/SpectrAction.h | 94 -- .../Source/SpectrAI/SpectrBrainComponent.cpp | 175 --- .../Source/SpectrAI/SpectrBrainComponent.h | 323 ---- .../Source/SpectrAI/SpectrConsideration.cpp | 7 - .../Source/SpectrAI/SpectrConsideration.h | 20 - .../Source/SpectrAI/SpectrContext.cpp | 7 - .../SpectrAI/Source/SpectrAI/SpectrContext.h | 20 - .../Source/SpectrAI/SpectrEvaluator.cpp | 7 - .../Source/SpectrAI/SpectrEvaluator.h | 72 - .../SpectrAI/Source/SpectrAI/SpectrGoal.cpp | 7 - Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h | 63 - .../SpectrAIEditor/SpectrAIEditor.Build.cs | 9 - .../Source/SpectrAIEditor/SpectrAIEditor.cpp | 20 - .../Source/SpectrAIEditor/SpectrAIEditor.h | 15 - .../SpectrGoalCustomization.cpp | 12 - .../SpectrAIEditor/SpectrGoalCustomization.h | 17 - .../SpectrAITest/STestAIControllerBase.cpp | 7 - .../SpectrAITest/STestAIControllerBase.h | 20 - .../SpectrAITest/STestAction_ChopFirewood.cpp | 54 - .../SpectrAITest/STestAction_ChopFirewood.h | 36 - .../SpectrAITest/STestAction_ChopWood.cpp | 7 - .../SpectrAITest/STestAction_ChopWood.h | 20 - .../STestAction_CollectBranches.cpp | 7 - .../STestAction_CollectBranches.h | 20 - .../SpectrAITest/STestAction_CollectOre.cpp | 7 - .../SpectrAITest/STestAction_CollectOre.h | 20 - .../SpectrAITest/STestAction_DropFirewood.cpp | 52 - .../SpectrAITest/STestAction_DropFirewood.h | 36 - .../SpectrAITest/STestAction_DropOre.cpp | 7 - .../Source/SpectrAITest/STestAction_DropOre.h | 20 - .../SpectrAITest/STestAction_DropWood.cpp | 7 - .../SpectrAITest/STestAction_DropWood.h | 20 - .../Source/SpectrAITest/STestAction_GoTo.cpp | 7 - .../Source/SpectrAITest/STestAction_GoTo.h | 20 - .../SpectrAITest/STestAction_MakeAxe.cpp | 7 - .../Source/SpectrAITest/STestAction_MakeAxe.h | 20 - .../SpectrAITest/STestAction_MakePick.cpp | 7 - .../SpectrAITest/STestAction_MakePick.h | 20 - .../SpectrAITest/STestAction_MineOre.cpp | 7 - .../Source/SpectrAITest/STestAction_MineOre.h | 20 - .../SpectrAITest/STestAction_PickItemAxe.cpp | 52 - .../SpectrAITest/STestAction_PickItemAxe.h | 34 - .../SpectrAITest/STestAction_PickItemPick.cpp | 7 - .../SpectrAITest/STestAction_PickItemPick.h | 20 - .../Source/SpectrAITest/STestAxePickup.cpp | 27 - .../Source/SpectrAITest/STestAxePickup.h | 28 - .../Source/SpectrAITest/STestBranch.cpp | 27 - .../Source/SpectrAITest/STestBranch.h | 28 - .../Source/SpectrAITest/STestForge.cpp | 27 - .../Source/SpectrAITest/STestForge.h | 28 - .../Source/SpectrAITest/STestStorage.cpp | 27 - .../Source/SpectrAITest/STestStorage.h | 28 - .../Source/SpectrAITest/STestTree.cpp | 27 - .../Source/SpectrAITest/STestTree.h | 28 - .../Source/SpectrAITest/SpectrAITest.Build.cs | 8 - .../Source/SpectrAITest/SpectrAITest.cpp | 20 - .../Source/SpectrAITest/SpectrAITest.h | 15 - Source/ActionRPGGame/ActionRPGGame.Build.cs | 33 +- .../{ => Public}/AI/ARAICharacter.cpp | 0 .../{ => Public}/AI/ARAICharacter.h | 0 .../{ => Public}/AI/ARAIController.cpp | 0 .../{ => Public}/AI/ARAIController.h | 0 .../{ => Public}/ARCharacter.cpp | 49 +- .../ActionRPGGame/{ => Public}/ARCharacter.h | 11 + .../ARCharacterMovementComponent.cpp | 0 .../ARCharacterMovementComponent.h | 0 .../ActionRPGGame/{ => Public}/ARGameMode.cpp | 0 .../ActionRPGGame/{ => Public}/ARGameMode.h | 0 .../ActionRPGGame/{ => Public}/ARGlobals.cpp | 0 Source/ActionRPGGame/{ => Public}/ARGlobals.h | 0 .../ActionRPGGame/{ => Public}/ARItemBase.cpp | 0 .../ActionRPGGame/{ => Public}/ARItemBase.h | 0 .../{ => Public}/ARItemPickupBase.cpp | 0 .../{ => Public}/ARItemPickupBase.h | 0 .../{ => Public}/ARPlayerController.cpp | 0 .../{ => Public}/ARPlayerController.h | 0 .../{ => Public}/Abilities/ARAbilityBase.cpp | 0 .../{ => Public}/Abilities/ARAbilityBase.h | 0 .../Abilities/ARAbilityManagerComponent.cpp | 0 .../Abilities/ARAbilityManagerComponent.h | 0 .../Abilities/ARAbilityUIData.cpp | 0 .../{ => Public}/Abilities/ARAbilityUIData.h | 0 .../Abilities/ARAvailableAbilities.cpp | 0 .../Abilities/ARAvailableAbilities.h | 0 .../{ => Public}/ActionRPGGame.cpp | 0 .../{ => Public}/ActionRPGGame.h | 0 .../Attributes/ARAbilityAttributes.cpp | 0 .../Attributes/ARAbilityAttributes.h | 0 .../Attributes/ARCharacterAttributes.cpp | 0 .../Attributes/ARCharacterAttributes.h | 0 .../Attributes/ARGunAttributes.cpp | 0 .../{ => Public}/Attributes/ARGunAttributes.h | 0 .../Attributes/ARHealthExtension.cpp | 0 .../Attributes/ARHealthExtension.h | 0 .../Calculations/ARAmmoReloadCalculation.cpp | 0 .../Calculations/ARAmmoReloadCalculation.h | 0 .../ActionRPGGame/{ => Public}/UI/ARHUD.cpp | 0 Source/ActionRPGGame/{ => Public}/UI/ARHUD.h | 0 .../{ => Public}/UI/ARHUDWidget.cpp | 0 .../{ => Public}/UI/ARHUDWidget.h | 0 .../{ => Public}/UI/ARUIComponent.cpp | 0 .../{ => Public}/UI/ARUIComponent.h | 0 .../{ => Public}/UI/ARUMGWidgetBase.cpp | 0 .../{ => Public}/UI/ARUMGWidgetBase.h | 0 .../{ => Public}/UI/HUD/AREnemyHealthBar.cpp | 0 .../{ => Public}/UI/HUD/AREnemyHealthBar.h | 0 .../{ => Public}/UI/HUD/ARHUDCrosshair.cpp | 0 .../{ => Public}/UI/HUD/ARHUDCrosshair.h | 0 .../UI/HUD/ARHUDCrosshairInfo.cpp | 0 .../{ => Public}/UI/HUD/ARHUDCrosshairInfo.h | 0 .../{ => Public}/UI/HUD/ARHUDPlayerInfo.cpp | 0 .../{ => Public}/UI/HUD/ARHUDPlayerInfo.h | 0 .../UI/Inventory/ARInventoryScreenWidget.cpp | 0 .../UI/Inventory/ARInventoryScreenWidget.h | 0 .../{ => Public}/UI/Inventory/ARItemView.cpp | 0 .../{ => Public}/UI/Inventory/ARItemView.h | 0 .../UI/Inventory/ARListItemView.cpp | 0 .../UI/Inventory/ARListItemView.h | 0 .../UI/Inventory/ARUIInventoryComponent.cpp | 0 .../UI/Inventory/ARUIInventoryComponent.h | 0 .../Inventory/Weapons/ARItemWeaponWidget.cpp | 0 .../UI/Inventory/Weapons/ARItemWeaponWidget.h | 0 .../Weapons/ARListItemWeaponWidget.cpp | 0 .../Weapons/ARListItemWeaponWidget.h | 0 .../Weapons/ARWeaponContainerWidget.cpp | 0 .../Weapons/ARWeaponContainerWidget.h | 0 .../Modifications/ARItemMagazineView.cpp | 0 .../Modifications/ARItemMagazineView.h | 0 .../Modifications/ARListItemMagazineView.cpp | 0 .../Modifications/ARListItemMagazineView.h | 0 .../{ => Public}/UI/SARCrosshairBase.cpp | 0 .../{ => Public}/UI/SARCrosshairBase.h | 0 .../{ => Public}/UI/SARDrawTestWidget.cpp | 0 .../{ => Public}/UI/SARDrawTestWidget.h | 0 .../{ => Public}/Weapons/ARItemWeapon.cpp | 0 .../{ => Public}/Weapons/ARItemWeapon.h | 0 .../Weapons/ARMagazineUpgradeEffect.cpp | 0 .../Weapons/ARMagazineUpgradeEffect.h | 0 .../Weapons/ARMagazineUpgradeItem.cpp | 0 .../Weapons/ARMagazineUpgradeItem.h | 0 .../Weapons/ARWeaponAbilityBase.cpp | 0 .../Weapons/ARWeaponAbilityBase.h | 0 .../{ => Public}/Weapons/ARWeaponBase.cpp | 0 .../{ => Public}/Weapons/ARWeaponBase.h | 0 .../Weapons/ARWeaponInventoryComponent.cpp | 144 +- .../Weapons/ARWeaponInventoryComponent.h | 50 +- .../Weapons/ARWeaponManagerComponent.cpp | 0 .../Weapons/ARWeaponManagerComponent.h | 0 .../Weapons/ARWeaponUpgradeItem.cpp | 0 .../Weapons/ARWeaponUpgradeItem.h | 0 .../{ => Public}/Weapons/ARWeaponsTypes.cpp | 0 .../{ => Public}/Weapons/ARWeaponsTypes.h | 0 447 files changed, 188 insertions(+), 26966 deletions(-) delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AMTypes.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp delete mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h delete mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp delete mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp delete mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h rename Source/ActionRPGGame/{ => Public}/AI/ARAICharacter.cpp (100%) rename Source/ActionRPGGame/{ => Public}/AI/ARAICharacter.h (100%) rename Source/ActionRPGGame/{ => Public}/AI/ARAIController.cpp (100%) rename Source/ActionRPGGame/{ => Public}/AI/ARAIController.h (100%) rename Source/ActionRPGGame/{ => Public}/ARCharacter.cpp (96%) rename Source/ActionRPGGame/{ => Public}/ARCharacter.h (97%) rename Source/ActionRPGGame/{ => Public}/ARCharacterMovementComponent.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ARCharacterMovementComponent.h (100%) rename Source/ActionRPGGame/{ => Public}/ARGameMode.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ARGameMode.h (100%) rename Source/ActionRPGGame/{ => Public}/ARGlobals.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ARGlobals.h (100%) rename Source/ActionRPGGame/{ => Public}/ARItemBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ARItemBase.h (100%) rename Source/ActionRPGGame/{ => Public}/ARItemPickupBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ARItemPickupBase.h (100%) rename Source/ActionRPGGame/{ => Public}/ARPlayerController.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ARPlayerController.h (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAbilityBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAbilityBase.h (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAbilityManagerComponent.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAbilityManagerComponent.h (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAbilityUIData.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAbilityUIData.h (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAvailableAbilities.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Abilities/ARAvailableAbilities.h (100%) rename Source/ActionRPGGame/{ => Public}/ActionRPGGame.cpp (100%) rename Source/ActionRPGGame/{ => Public}/ActionRPGGame.h (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARAbilityAttributes.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARAbilityAttributes.h (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARCharacterAttributes.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARCharacterAttributes.h (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARGunAttributes.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARGunAttributes.h (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARHealthExtension.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Attributes/ARHealthExtension.h (100%) rename Source/ActionRPGGame/{ => Public}/Calculations/ARAmmoReloadCalculation.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Calculations/ARAmmoReloadCalculation.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARHUD.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARHUD.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARHUDWidget.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARHUDWidget.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARUIComponent.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARUIComponent.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARUMGWidgetBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/ARUMGWidgetBase.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/AREnemyHealthBar.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/AREnemyHealthBar.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/ARHUDCrosshair.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/ARHUDCrosshair.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/ARHUDCrosshairInfo.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/ARHUDCrosshairInfo.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/ARHUDPlayerInfo.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/HUD/ARHUDPlayerInfo.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARInventoryScreenWidget.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARInventoryScreenWidget.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARItemView.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARItemView.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARListItemView.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARListItemView.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARUIInventoryComponent.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/ARUIInventoryComponent.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/ARItemWeaponWidget.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/ARItemWeaponWidget.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/ARListItemWeaponWidget.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/ARWeaponContainerWidget.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/SARCrosshairBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/SARCrosshairBase.h (100%) rename Source/ActionRPGGame/{ => Public}/UI/SARDrawTestWidget.cpp (100%) rename Source/ActionRPGGame/{ => Public}/UI/SARDrawTestWidget.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARItemWeapon.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARItemWeapon.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARMagazineUpgradeEffect.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARMagazineUpgradeEffect.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARMagazineUpgradeItem.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARMagazineUpgradeItem.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponAbilityBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponAbilityBase.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponBase.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponBase.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponInventoryComponent.cpp (78%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponInventoryComponent.h (71%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponManagerComponent.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponManagerComponent.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponUpgradeItem.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponUpgradeItem.h (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponsTypes.cpp (100%) rename Source/ActionRPGGame/{ => Public}/Weapons/ARWeaponsTypes.h (100%) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp deleted file mode 100644 index 4f1273d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.cpp +++ /dev/null @@ -1,610 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" - -#include "Abilities/GAAbilityBase.h" -#include "Abilities/Tasks/GAAbilityTask.h" -#include "IAbilityFramework.h" - -#include "Net/UnrealNetwork.h" -#include "Engine/ActorChannel.h" -#include "Animation/AnimInstance.h" -#include "Animation/AnimMontage.h" -#include "Attributes/GAAttributesBase.h" -#include "AFAbilityInterface.h" -#include "Effects/GAEffectExecution.h" -#include "Effects/GAGameEffect.h" - -#include "Effects/GAEffectExtension.h" -#include "Effects/GAEffectCue.h" -#include "AFCueManager.h" -#include "Effects/GABlueprintLibrary.h" -#include "Async.h" - -#include "AFAbilityComponent.h" -#include "AFEffectsComponent.h" -#include "AFAbilityInterface.h" - -DEFINE_STAT(STAT_ApplyEffect); -DEFINE_STAT(STAT_ModifyAttribute); - - - -void FAFReplicatedAttributeItem::PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer) -{ - FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); - ArraySerializer.AttributeMap.Remove(AttributeTag); -} -void FAFReplicatedAttributeItem::PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer) -{ - FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); - UGAAttributesBase*& Attribute = ArraySerializer.AttributeMap.FindOrAdd(AttributeTag); - Attribute = Attributes; - InArraySerializer.OnAttributeReplicated(AttributeTag); -} -void FAFReplicatedAttributeItem::PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer) -{ - -} -UGAAttributesBase* FAFReplicatedAttributeContainer::Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter) -{ - UGAAttributesBase* AttributesDup = DuplicateObject(InAttributes, InOuter); - FAFReplicatedAttributeItem Item; - Item.AttributeTag = InTag; - Item.Attributes = AttributesDup; - Attributes.Add(Item); - MarkItemDirty(Item); - UGAAttributesBase*& Added = AttributeMap.FindOrAdd(InTag); - Added = AttributesDup; - return AttributesDup; -} -UAFAbilityComponent::UAFAbilityComponent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bWantsInitializeComponent = true; - bIsAnyAbilityActive = false; - bAutoActivate = true; - bAutoRegister = true; - PrimaryComponentTick.bCanEverTick = true; - PrimaryComponentTick.bStartWithTickEnabled = true; - PrimaryComponentTick.bRunOnAnyThread = false; - PrimaryComponentTick.bAllowTickOnDedicatedServer = true; - PrimaryComponentTick.TickGroup = ETickingGroup::TG_DuringPhysics; -} - -void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribute, - const FAFAttributeChangedData& InData) -{ - FAFAttributeChangedDelegate* Delegate = AttributeChanged.Find(InAttribute); - if (Delegate) - { - Delegate->Broadcast(InData); - } -} - -void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - ,FGAEffectProperty& InProperty) -{ - //OnAttributePreModifed.Broadcast(ModIn, 0); - //Add log. - if (!DefaultAttributes) - { - return; - } - float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); - FAFAttributeChangedData Data; - FGAEffectContext& Context = InProperty.GetContext(HandleIn).GetRef(); - Data.Mod = ModIn; - Data.Target = Context.Target; - Data.Location = Context.HitResult.Location; - OnAttributeModifed.Broadcast(Data); - NotifyInstigatorTargetAttributeChanged(Data, Context); - //add default replication (PropertyRep) that attribute changed. -}; -void UAFAbilityComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, - const FGAEffectContext& InContext) -{ - InContext.InstigatorComp->OnTargetAttributeModifed.Broadcast(InData); -} -void UAFAbilityComponent::GetAttributeStructTest(FGAAttribute Name) -{ - DefaultAttributes->GetAttribute(Name); -} - -void UAFAbilityComponent::OnRep_GameEffectContainer() -{ - float test = 0; -} -void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - UActorComponent::TickComponent(DeltaTime, TickType, ThisTickFunction); - if (DefaultAttributes) - { - DefaultAttributes->Tick(DeltaTime); - } -} - -void UAFAbilityComponent::BeginPlay() -{ - Super::BeginPlay(); - //FAFEffectTimerManager::Get(); -} -void UAFAbilityComponent::EndPlay(const EEndPlayReason::Type EndPlayReason) -{ - Super::EndPlay(EndPlayReason); - -} -void UAFAbilityComponent::DestroyComponent(bool bPromoteChildren) -{ - Super::DestroyComponent(bPromoteChildren); - -} - -void UAFAbilityComponent::OnAttributeModified(const FGAEffectMod& InMod, - const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) -{ - -} - -void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly replicate it to everyone - //to allow prediction for UI. - DOREPLIFETIME(UAFAbilityComponent, DefaultAttributes); - DOREPLIFETIME(UAFAbilityComponent, RepAttributes); - - DOREPLIFETIME(UAFAbilityComponent, ActiveCues); - DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); - DOREPLIFETIME_CONDITION(UAFAbilityComponent, RepMontage, COND_SkipOwner); -} -void UAFAbilityComponent::OnRep_ActiveEffects() -{ - -} -void UAFAbilityComponent::OnRep_ActiveCues() -{ - -} - -bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) -{ - bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); - - if (DefaultAttributes) - { - WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); - } - for (const FAFAbilityItem& Ability : AbilityContainer.AbilitiesItems) - { - //if (Set.InputOverride) - // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); - - if (Ability.Ability) - WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); - } - - for (const FAFReplicatedAttributeItem& Attribute : RepAttributes.Attributes) - { - //if (Set.InputOverride) - // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); - - if (Attribute.Attributes) - WroteSomething |= Channel->ReplicateSubobject(const_cast(Attribute.Attributes), *Bunch, *RepFlags); - } - - return WroteSomething; -} -void UAFAbilityComponent::GetSubobjectsWithStableNamesForNetworking(TArray& Objs) -{ - if (DefaultAttributes && DefaultAttributes->IsNameStableForNetworking()) - { - Objs.Add(const_cast(DefaultAttributes)); - } -} - -void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const -{ - if (IAFAbilityInterface* ABInterface = Cast(GetOwner())) - { - TagContainer = ABInterface->NativeGetEffectsComponent()->AppliedTags.AllTags; - } -} - - - -void UAFAbilityComponent::InitializeComponent() -{ - Super::InitializeComponent(); - //PawnInterface = Cast(GetOwner()); - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - AbilityContainer.AbilitiesComp = this; - //EffectTimerManager = MakeShareable(new FAFEffectTimerManager()); - - //EffectTimerManager.InitThread(); - if (DefaultAttributes) - { - DefaultAttributes->InitializeAttributes(this); - DefaultAttributes->InitializeAttributesFromTable(); - } - ActiveCues.OwningComp = this; - //ActiveCues.OwningComponent = this; - AppliedTags.AddTagContainer(DefaultTags); - InitializeInstancedAbilities(); - - AActor* MyOwner = GetOwner(); - if (!MyOwner || !MyOwner->IsTemplate()) - { - ULevel* ComponentLevel = (MyOwner ? MyOwner->GetLevel() : GetWorld()->PersistentLevel); - } -} -void UAFAbilityComponent::UninitializeComponent() -{ - Super::UninitializeComponent(); - //EffectTimerManager.Deinitialize(); - //EffectTimerManager.Reset(); - //GameEffectContainer -} -void UAFAbilityComponent::BindInputs(class UInputComponent* InputComponent) -{ - for (const FGameplayTag& Tag : AbilityInputs) - { - BindAbilityToAction(InputComponent, Tag); - } -} -void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) -{ - AbilityContainer.SetBlockedInput(InActionName, bBlock); -} -void UAFAbilityComponent::BP_BindAbilityToAction(FGameplayTag ActionName) -{ - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - check(InputComponent); - - BindAbilityToAction(InputComponent, ActionName); -} -void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName) -{ - check(InputComponent); - - if (!InputComponent) - return; - - { - FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); - AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputPressed, ActionName); - InputComponent->AddActionBinding(AB); - } - - // Released event - { - FInputActionBinding AB(ActionName.GetTagName(), IE_Released); - AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputReleased, ActionName); - InputComponent->AddActionBinding(AB); - } - SetBlockedInput(ActionName, false); -} -void UAFAbilityComponent::SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag - , const FAFOnAbilityReady& InputDelegate) -{ - AbilityContainer.SetAbilityToAction(InAbilityPtr, InInputTag); - ENetRole role = GetOwnerRole(); - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client - && role == ENetRole::ROLE_AutonomousProxy) - { - if (InputDelegate.IsBound()) - { - AddOnAbilityInputReadyDelegate(InAbilityPtr, InputDelegate); - } - ServerSetAbilityToAction(InAbilityPtr, InInputTag); - } -} - -TSoftClassPtr UAFAbilityComponent::IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) -{ - for (const FGameplayTag& Tag : InInputTag) - { - return AbilityContainer.IsAbilityBoundToAction(Tag); - break; - } - return TSoftClassPtr(); -} - -void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) -{ - if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - SetAbilityToAction(InAbilityPtr, InInputTag, FAFOnAbilityReady()); - } -} -bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) -{ - return true; -} -void UAFAbilityComponent::RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr) -{ - AbilityContainer.RemoveAbilityFromAction(InAbilityPtr); - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerRemoveAbilitiesFromActions(InAbilityPtr.ToSoftObjectPath()); - } -} -void UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr) -{ - AbilityContainer.RemoveAbilityFromAction(TSoftClassPtr(InAbilityPtr)); -} -bool UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr) -{ - return true; -} -void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr) -{ - NotifyOnAbilityInputReady(InAbilityPtr); - UGAAbilityBase* Ability = AbilityContainer.TagToAbility.FindRef(InAbilityPtr); - if (Ability) - { - Ability->OnAbilityInputReady(); - } -} - -void UAFAbilityComponent::SetAbilitiesToActions(const TArray& InAbilitiesActions - , const TArray& InputDelegate) -{ - for (const FAFAbilityActionSet& Set : InAbilitiesActions) - { - AbilityContainer.SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs); - } - ENetRole role = GetOwnerRole(); - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client - && role == ENetRole::ROLE_AutonomousProxy) - { - for (int32 Idx = 0; Idx < InAbilitiesActions.Num(); Idx++) - { - if (InputDelegate[Idx].IsBound()) - { - AddOnAbilityInputReadyDelegate(InAbilitiesActions[Idx].AbilityTag, InputDelegate[Idx]); - } - } - - ServerSetAbilitiesToActions(InAbilitiesActions); - } -} - -void UAFAbilityComponent::ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions) -{ - if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - for (const FAFAbilityActionSet& Set : InAbilitiesActions) - { - SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs, FAFOnAbilityReady()); - } - } -} -bool UAFAbilityComponent::ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions) -{ - return true; -} - -void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) -{ - NativeInputPressed(ActionName); -} -void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) -{ - FAFPredictionHandle PredHandle; - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - PredHandle = FAFPredictionHandle::GenerateClientHandle(this); - AbilityContainer.HandleInputPressed(ActionName, PredHandle); - } - ServerNativeInputPressed(ActionName, PredHandle); - -} - -void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) -{ - AbilityContainer.HandleInputPressed(ActionName, InPredictionHandle); - //NativeInputPressed(ActionName); -} -bool UAFAbilityComponent::ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) -{ - return true; -} - -void UAFAbilityComponent::BP_InputReleased(FGameplayTag ActionName) -{ - NativeInputReleased(ActionName); -} - -void UAFAbilityComponent::NativeInputReleased(FGameplayTag ActionName) -{ - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - AbilityContainer.HandleInputReleased(ActionName); - } - ServerNativeInputReleased(ActionName); -} - -void UAFAbilityComponent::ServerNativeInputReleased_Implementation(FGameplayTag ActionName) -{ - AbilityContainer.HandleInputReleased(ActionName); -} -bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag ActionName) -{ - return true; -} - -void UAFAbilityComponent::BP_AddAbility(TSoftClassPtr InAbility, - TArray InInputTag) -{ - NativeAddAbility(InAbility, InInputTag); -} - -void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbility, - const TArray& InInputTag) -{ - //FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNativeAddAbility(InAbility.ToSoftObjectPath(), InInputTag); - /*if (AlreadyBound.IsValid()) - { - for (const FGameplayTag& Input : InInputTag) - { - AbilityContainer.RemoveAbilityFromAction(AlreadyBound); - } - }*/ - } - else - { - /*if (AlreadyBound.IsValid()) - { - AbilityContainer.RemoveAbilityFromAction(AlreadyBound); - }*/ - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - FStreamableManager& StreamManager = UAssetManager::GetStreamableManager(); - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbility); - - StreamManager.RequestAsyncLoad(InAbility.ToSoftObjectPath() - , del); - } - } - } -} - - -void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, - const TArray& InInputTag) -{ - NativeAddAbility(TSoftClassPtr(InAbility), InInputTag); -} - -bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, - const TArray& InInputTag) -{ - return true; -} -void UAFAbilityComponent::OnFinishedLoad(TSoftClassPtr InAbility) -{ - if (AbilityContainer.AbilityExists(InAbility)) - { - return; - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - return; - } - - - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - - TSubclassOf cls = InAbility.Get(); - if (cls) - { - InstanceAbility(cls, InAbility); - } - - { - Manager.Unload(InAbility.ToSoftObjectPath()); - } -} - -void UAFAbilityComponent::BP_RemoveAbility(TSoftClassPtr TagIn) -{ - -} -void UAFAbilityComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag) -{ - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNativeRemoveAbility(InAbilityTag.ToSoftObjectPath()); - } - AbilityContainer.RemoveAbility(InAbilityTag); -} -void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag) -{ - AbilityContainer.RemoveAbility(TSoftClassPtr(InAbilityTag)); -} - -bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag) -{ - return true; -} - -UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(TSoftClassPtr TagIn) -{ - UGAAbilityBase* retVal = AbilityContainer.GetAbility(TagIn); - return retVal; -} -UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass - , TSoftClassPtr InClassPtr) -{ - if (AbilityClass) - { - UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InClassPtr); - AbilityContainer.MarkArrayDirty(); - return ability; - } - return nullptr; -} - -void UAFAbilityComponent::OnRep_InstancedAbilities() -{ -} -void UAFAbilityComponent::NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag) -{ - OnAbilityAdded.Broadcast(InAbilityTag); - -} -void UAFAbilityComponent::InitializeInstancedAbilities() -{ -} - -void UAFAbilityComponent::OnRep_PlayMontage() -{ - ACharacter* MyChar = Cast(GetOwner()); - if (MyChar) - { - UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); - AnimInst->Montage_Play(RepMontage.CurrentMontage); - if (RepMontage.SectionName != NAME_None) - { - AnimInst->Montage_JumpToSection(RepMontage.SectionName, RepMontage.CurrentMontage); - } - UE_LOG(AbilityFramework, Log, TEXT("OnRep_PlayMontage MontageName: %s SectionNAme: %s ForceRep: %s"), *RepMontage.CurrentMontage->GetName(), *RepMontage.SectionName.ToString(), *FString::FormatAsNumber(RepMontage.ForceRep)); - } -} - -void UAFAbilityComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) -{ - //if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - //Probabaly want to do something different here for client non authority montage plays. - //return; - } - ACharacter* MyChar = Cast(GetOwner()); - if (MyChar) - { - UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); - AnimInst->Montage_Play(MontageIn, Speed); - if (SectionName != NAME_None) - { - //AnimInst->Montage_JumpToSection(SectionName, MontageIn); - } - - UE_LOG(AbilityFramework, Log, TEXT("PlayMontage MontageName: %s SectionNAme: %s Where: %s"), *MontageIn->GetName(), *SectionName.ToString(), (GetOwnerRole() < ENetRole::ROLE_Authority ? TEXT("Client") : TEXT("Server"))); - RepMontage.SectionName = SectionName; - RepMontage.CurrentMontage = MontageIn; - RepMontage.ForceRep++; - } -} -void UAFAbilityComponent::MulticastPlayMontage_Implementation(UAnimMontage* MontageIn, FName SectionName, float Speed = 1) -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h deleted file mode 100644 index 30f8ae0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityComponent.h +++ /dev/null @@ -1,613 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "GameplayTags.h" -#include "AFAbilityTypes.h" - -#include "Attributes/GAAttributeBase.h" -#include "Attributes/GAAttributesBase.h" -#include "Effects/GAEffectCueGlobals.h" - -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" - -#include "GameplayTagAssetInterface.h" - -#include "AssetRegistryModule.h" -#include "Engine/AssetManager.h" - -#include "AFAbilityComponent.generated.h" - -DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); -DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); -DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); - -DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); - - -DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); - -DECLARE_DELEGATE(FAFOnAbilityReady); -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); -DECLARE_DELEGATE(FAFGenericAttributeDelegate); - - -//UAFAssetManager* GetAssetManager() -//{ -// return Cast(UAssetManager::GetIfValid()); -//}; - -USTRUCT() -struct FGAModifiedAttributeData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - TArray Mods; - UPROPERTY() - int32 ForceUpdate; - - FGAModifiedAttributeData() - : ForceUpdate(0) - {} -}; - -USTRUCT(BlueprintType) -struct FGAEffectUIData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(BlueprintReadOnly, Category = "UI") - float RemainingTime; - - FGAEffectUIData() - : RemainingTime(0) - {}; -}; -struct FGAContextSetup -{ -public: - UGAAttributesBase* IntigatorAttributes; - UGAAttributesBase* TargetAttributes; - UAFAbilityComponent* InstigatorComp; - UAFAbilityComponent* TargetComp; - - FGAContextSetup() - {}; - FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, - UAFAbilityComponent* InstigatorCompIn, UAFAbilityComponent* TargetCompIn) - : IntigatorAttributes(IntigatorAttributesIn), - TargetAttributes(TargetAttributesIn), - InstigatorComp(InstigatorCompIn), - TargetComp(TargetCompIn) - {}; -}; -DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); -DECLARE_DELEGATE_TwoParams(FAFMontageGenericDelegate, const FGameplayTag&, const FName&); -/* TODO:: Implement fast serialization for structs. */ -/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ -/**/ - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGASMontageRepData -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - UAnimMontage* CurrentMontage; - - UPROPERTY() - FName SectionName; - - UPROPERTY() - uint8 ForceRep; -}; - -USTRUCT() -struct FAFReplicatedAttributeItem : public FFastArraySerializerItem -{ - GENERATED_BODY() -public: - UPROPERTY() - FGameplayTag AttributeTag; - UPROPERTY() - UGAAttributesBase* Attributes; - - void PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer); - void PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer); - void PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer); -}; - -USTRUCT() -struct FAFReplicatedAttributeContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - UPROPERTY() - TArray Attributes; - - UPROPERTY() - TMap AttributeMap; - - - TMap AttributeReplicatedEvent; - - void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FSimpleDelegate& InDelegate) - { - if (!AttributeReplicatedEvent.Contains(InTag)) - return; - - AttributeReplicatedEvent.Add(InTag, InDelegate); - } - - void OnAttributeReplicated(const FGameplayTag& InTag) const - { - if (const FSimpleDelegate* Delegate = AttributeReplicatedEvent.Find(InTag)) - { - Delegate->Execute(); - //AttributeReplicatedEvent.Remove(InTag); - } - } - - UGAAttributesBase* Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter); - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(Attributes, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FAFReplicatedAttributeContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; - - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFAbilityActionSet -{ - GENERATED_BODY() -public: - UPROPERTY() - TSoftClassPtr AbilityTag; - UPROPERTY() - TArray AbilityInputs; -}; - -UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) -class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public IGameplayTagAssetInterface -{ - GENERATED_BODY() - /* Attributes handling */ -public: - //Only for base testing and prototyping cue application. - //will be removed when Cue Manager will be more functional. - - //FAFEffectTimerManager EffectTimerManager; - - UPROPERTY(EditAnywhere, Category = "Test") - FGameplayTag TagTest; - /* - Set attribute which will be considered for indicating whether or not actor is dead. - */ - UPROPERTY(EditAnywhere, Category = "Config") - FGAAttribute DeathAttribute; - - UPROPERTY(EditAnywhere, Category = "Input Config") - TArray AbilityInputs; - - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer DefaultTags; - - UPROPERTY() - FGACountedTagContainer AppliedTags; - - UPROPERTY() - FGACountedTagContainer ImmunityTags; - - UFUNCTION() - void OnRep_ActiveEffects(); - - UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) - FGameCueContainer ActiveCues; - UFUNCTION() - void OnRep_ActiveCues(); - /* - Could make it array. But realistically. How many times do you really need more, than one - attribute set for actor ? - - Of course array of attributes would allow to compose attributes from small discreete - attribute sets. On the other hand similiar funcionality can be achieved by using - inheritance. - - And I think that using inheritance in this case will be easier. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) - class UGAAttributesBase* DefaultAttributes; - - //probabaly replace FGameplayTag with FObjectKey - TMap AdditionalAttributes; - - UPROPERTY(Replicated) - FAFReplicatedAttributeContainer RepAttributes; - - UPROPERTY(BlueprintAssignable, Category = "Game Attributes") - FGAOnAttributeModifed OnAttributeModifed; - UPROPERTY(BlueprintAssignable, Category = "Game Attributes") - FGAOnAttributeModifed OnTargetAttributeModifed; - - - TMap AttributeChanged; - - - void BroadcastAttributeChange(const FGAAttribute& InAttribute, - const FAFAttributeChangedData& InData); - - UFUNCTION() - void OnRep_GameEffectContainer(); - - template - T* GetAttributes() - { - return CastChecked(DefaultAttributes); - } - - template - T* GetAttributeSet(FGameplayTag InOwner) - { - UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); - return Cast(AttributeSet); - } - UGAAttributesBase* AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) - { - if (!InAttributes) - return nullptr; - UGAAttributesBase* retVal = RepAttributes.Add(InOwner, InAttributes, this); - RepAttributes.MarkArrayDirty(); - - return retVal; - } - UFUNCTION(BlueprintCallable, Category = "Test") - void GetAttributeStructTest(FGAAttribute Name); - - /** UActorComponent Interface - Begin */ - virtual void BeginPlay() override; - virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; - virtual void DestroyComponent(bool bPromoteChildren = false) override; - virtual void InitializeComponent() override; - virtual void UninitializeComponent() override; - virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - /* UActorComponent Interface - End **/ -public: - ///////////////////////////////////////////////// - //////////// ATTRIBUTES HANDLING - - /* - Two functions, They will allow to apply any static numerical mods from player who - initiated attribute change, and from player who will be affected by change. - - Mods will be appiled by small objects, and changed against tags. - For example there might be physical armor mod, which will apply changes only - to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. - */ - - inline float GetFinalAttributeValue(const FGAAttribute& Name) - { - return DefaultAttributes->GetFinalAttributeValue(Name); - } - inline float GetCurrentAttributeValue(const FGAAttribute& Name) - { - return DefaultAttributes->GetCurrentAttributeValue(Name); - } - //////////// ATTRIBUTES HANDLING - ///////////////////////////////////////////////// - /* - Attribute replication. - */ - void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); - //Helper functions: -public: - /* - IGameplayTagAssetInterface Start - */ - /** - * Get any owned gameplay tags on the asset - * - * @param OutTags [OUT] Set of tags on the asset - */ - UFUNCTION(BlueprintCallable, Category = GameplayTags) - virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; - - /* - IGameplayTagAssetInterface End - */ - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; - - void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; - void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, - const FGAEffectContext& InContext); - FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; - void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; - float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; - -private: - class IAFAbilityInterface* AttributeInterface; - -public: - UAFAbilityComponent(const FObjectInitializer& ObjectInitializer); - - UFUNCTION() - void OnRep_InstancedAbilities(); - UPROPERTY(Replicated) - FAFAbilityContainer AbilityContainer; - UPROPERTY() - TArray AbilitiesRefs; - - UPROPERTY() - APlayerController* PCOwner; - - /* Ability which is currently being executed. */ - UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") - class UGAAbilityBase* ExecutingAbility; - - - - /*UFUNCTION(NetMulticast, Reliable) - MulticastExecuteEffect()*/ - - - - - /* - True if player is currently casting/channeling/activating(?) - any ability. - */ - bool bIsAnyAbilityActive; - - //AbilityTag, Delegate - TMap, FAFOnAbilityReady> OnAbilityReadyMap; - - void AddOnAbilityReadyDelegate(const TSoftClassPtr& InAbilityPtr, FAFOnAbilityReady& InDelegate) - { - if(InDelegate.IsBound()) - OnAbilityReadyMap.Add(InAbilityPtr, InDelegate); - } - - void NotifyOnAbilityReady(const TSoftClassPtr& InAbilityPtr) - { - if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityPtr)) - { - Ready->ExecuteIfBound(); - OnAbilityReadyMap.Remove(InAbilityPtr); - } - } - - TMap, FAFOnAbilityReady> OnAbilityInputReadyMap; - - void AddOnAbilityInputReadyDelegate(const TSoftClassPtr& InAbilityPtr, const FAFOnAbilityReady& InDelegate) - { - if(InDelegate.IsBound()) - OnAbilityInputReadyMap.Add(InAbilityPtr, InDelegate); - } - - void NotifyOnAbilityInputReady(const TSoftClassPtr& InAbilityPtr) - { - if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityPtr)) - { - Ready->ExecuteIfBound(); - OnAbilityInputReadyMap.Remove(InAbilityPtr); - } - } - - TMap> OnPreAttributeModifiedMap; - void AddOnPreAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) - { - TArray& delegates = OnPreAttributeModifiedMap.FindOrAdd(InAttribute); - delegates.Add(InDelegate); - } - - void NotifyOnPreAttributeModified(const FGAAttribute& InAttribute) - { - if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) - { - for(const FAFGenericAttributeDelegate& delegate : *Ready) - delegate.ExecuteIfBound(); - } - } - - void RemoveOnPreAttributeModified(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& Delegate) - { - if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) - { - //Ready->RemoveSingle(Delegate); - if (Ready->Num() <= 0) - { - OnPreAttributeModifiedMap.Remove(InAttribute); - } - } - } - - TMap> OnPostAttributeModifiedMap; - void AddOnPostAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) - { - TArray& delegates = OnPostAttributeModifiedMap.FindOrAdd(InAttribute); - delegates.Add(InDelegate); - } - - void NotifyOnPostAttributeModified(const FGAAttribute& InAttribute) - { - if (TArray* Ready = OnPostAttributeModifiedMap.Find(InAttribute)) - { - for (const FAFGenericAttributeDelegate& delegate : *Ready) - delegate.ExecuteIfBound(); - } - } - - - - FAFOnAbilityReady OnAbilityReady; - - UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") - FAFOnAbilityAdded OnAbilityAdded; - - FAFMontageGenericDelegate OnAbilityNotifyBegin; - FAFMontageGenericDelegate OnAbilityNotifyTick; - FAFMontageGenericDelegate OnAbilityNotifyEnd; - -private: - - - UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) - FGASMontageRepData RepMontage; - UFUNCTION() - void OnRep_PlayMontage(); - -public: - UFUNCTION(BlueprintCallable, Category = "AbilityFramework") - void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); - UFUNCTION(NetMulticast, Unreliable) - void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); -public: - inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) - { - return nullptr; - } - - TMap BlockedInput; - - - - void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - void BindInputs(class UInputComponent* InputComponent); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") - void BP_BindAbilityToAction(FGameplayTag ActionName); - void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); - - //need to be called on both client and server. - //Change InInputTag To Array, clear previous binds on the same tag. - void SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); - - TSoftClassPtr IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); - -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); - void ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); - bool ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); -public: - /* Called when ability action has been binded on server. */ - UFUNCTION(Client, Reliable) - void ClientNotifyAbilityInputReady(const TSoftClassPtr& InAbilityPtr); - void ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr); - - - void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); - UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilitiesToActions(const TArray& InAbilitiesActions); - void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); - bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); - - void RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr); - UFUNCTION(Server, Reliable, WithValidation) - void ServerRemoveAbilitiesFromActions(const FSoftObjectPath& InAbilityPtr); - void ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr); - bool ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr); - - UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") - void BP_InputPressed(FGameplayTag ActionName); - - void NativeInputPressed(FGameplayTag ActionName); -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - - -public: - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") - void BP_InputReleased(FGameplayTag ActionName); - - void NativeInputReleased(FGameplayTag ActionName); -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputReleased(FGameplayTag ActionName); - virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); - virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); -public: - /* - Finds ability using asset registry and then gives it to component. - Only valid on server. - Does not check if component can or can't have given ability. - So it must be checked before this function is called. - */ - - UFUNCTION(BlueprintCallable, meta=(DisplayName = "Add Ability"), Category = "AbilityFramework|Ability Component") - void BP_AddAbility(TSoftClassPtr InAbility, - TArray InInputTag); - - void NativeAddAbility(TSoftClassPtr InAbility, - const TArray& InInputTag); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeAddAbility(const FSoftObjectPath& InAbility, - const TArray& InInputTag); - - void ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, - const TArray& InInputTag); - - bool ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, - const TArray& InInputTag); - - void OnFinishedLoad(TSoftClassPtr InAbility); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") - void BP_RemoveAbility(TSoftClassPtr TagIn); - - void NativeRemoveAbility(TSoftClassPtr InAbilityTag); - UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeRemoveAbility(const FSoftObjectPath& InAbilityTag); - - void ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag); - - bool ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag); - - //TODO: Make it procted - - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") - UGAAbilityBase* BP_GetAbilityByTag(TSoftClassPtr TagIn); - - - bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; - void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; - - void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); -protected: - void InitializeInstancedAbilities(); - UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass - , TSoftClassPtr InClassPtr); - - -public: - /* - Latent Tasks Handling - */ - - UPROPERTY(Replicated) - TArray ReplicatedTasks; -}; - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp deleted file mode 100644 index 134412e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.cpp +++ /dev/null @@ -1,25 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "AFEffectsComponent.h" -#include "AFAttributeComponent.h" -UAFAbilityInterface::UAFAbilityInterface(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -//class UGAAttributesBase* IAFAbilityInterface::GetAttributes() -//{ -// return nullptr;// GetAbilityComp()->DefaultAttributes; -//} - -FGAEffectHandle IAFAbilityInterface::ApplyEffectToTarget( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, InHandle, Params, Modifier); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h deleted file mode 100644 index f5ede8f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityInterface.h +++ /dev/null @@ -1,75 +0,0 @@ -#pragma once -#include "GAGlobalTypes.h" -#include "Effects/GAGameEffect.h" -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypes.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.generated.h" - - -struct FAFAttributeBase; -struct FGAEffectHandle; -UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) -class ABILITYFRAMEWORK_API UAFAbilityInterface : public UInterface -{ - GENERATED_UINTERFACE_BODY() -}; - -class IAFAbilityInterface -{ - GENERATED_IINTERFACE_BODY() -public: - virtual FVector GetSocketLocation(FName SocketNameIn){ return FVector::ZeroVector; }; - - - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UAFAbilityComponent* GetAbilityComp() = 0; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual class UAFEffectsComponent* GetEffectsComponent() = 0; - - virtual class UAFEffectsComponent* NativeGetEffectsComponent() const = 0; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; - - virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) {}; - virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; - - virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; - - virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) {}; - //override to allow gathering tags from causer - //those tags will be merged into effect owned tags. - virtual FGameplayTagContainer GetCauserTags() { return FGameplayTagContainer(); } - - virtual FAFPredictionHandle GetPredictionHandle() { return FAFPredictionHandle(); } - - - FGAEffectHandle ApplyEffectToTarget( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual class UGAAttributesBase* GetAttributes() { return GetAbilityComp()->DefaultAttributes; }; - - template - T* GetAttributesTyped() - { - return Cast(GetAttributes()); - } - template - T* GetComponentTyped() - { - return Cast(GetAbilityComp()); - } - template - T* GetAttributeTyped(FGAAttribute InAttribute) - { - return static_cast(GetAttribute(InAttribute)); - } -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp deleted file mode 100644 index 981b61a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.cpp +++ /dev/null @@ -1,226 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityComponent.h" -#include "Abilities/GAAbilityBase.h" -#include "AFAbilityTypes.h" - -void FAFAbilityItem::PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer) -{ - if (InArraySerializer.AbilitiesComp.IsValid()) - { - FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); - //remove attributes - //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); - Ability->Attributes = nullptr; - InArraySerializerC.AbilityToAction.Remove(AbilityClass); - InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); - InArraySerializerC.TagToAbility.Remove(AbilityClass); - } -} -void FAFAbilityItem::PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer) -{ - if (InArraySerializer.AbilitiesComp.IsValid()) - { - //should be safe, since we only modify the non replicated part of struct. - FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); - Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); - if (InArraySerializer.AbilitiesComp.IsValid()) - { - APawn* POwner = Cast(InArraySerializer.AbilitiesComp->GetOwner()); - Ability->POwner = POwner; - Ability->PCOwner = Cast(POwner->Controller); - Ability->OwnerCamera = nullptr; - } - Ability->InitAbility(); - Ability->Attributes = nullptr; - - //TODO - CHANGE ATTRIBUTE HANDLING - UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); - Ability->Attributes = attr; - - InArraySerializerC.AbilitiesInputs.Add(AbilityClass, Ability); //.Add(Ability->AbilityTag, Ability); - InArraySerializerC.TagToAbility.Add(AbilityClass, Ability); - InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(AbilityClass); - } -} -void FAFAbilityItem::PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer) -{ - -} - - -void FAFAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) -{ - if (BlockedInput.Contains(InActionName)) - { - BlockedInput[InActionName] = bBlock; - } - else - { - BlockedInput.Add(InActionName, bBlock); - } -} -UGAAbilityBase* FAFAbilityContainer::AddAbility(TSubclassOf AbilityIn - , TSoftClassPtr InClassPtr) -{ - if (AbilityIn && AbilitiesComp.IsValid()) - { - - UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); - ability->AbilityComponent = AbilitiesComp.Get(); - if (AbilitiesComp.IsValid()) - { - APawn* POwner = Cast(AbilitiesComp->GetOwner()); - ability->POwner = POwner; - ability->PCOwner = Cast(POwner->Controller); - ability->OwnerCamera = nullptr; - } - ability->InitAbility(); - FGameplayTag Tag = ability->AbilityTag; - - AbilitiesInputs.Add(InClassPtr, ability); - FAFAbilityItem AbilityItem(ability, InClassPtr); - MarkItemDirty(AbilityItem); - AbilityItem.Ability = ability; - AbilitiesItems.Add(AbilityItem); - TagToAbility.Add(InClassPtr, ability); - - MarkArrayDirty(); - if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone - || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) - { - AbilitiesComp->NotifyOnAbilityReady(InClassPtr); - } - /* if (ActionName.IsValid()) - { - UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); - AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); - }*/ - return ability; - } - return nullptr; -} -void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& AbilityIn) -{ - int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); - - if (Index == INDEX_NONE) - return; - - UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); - - - for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) - { - AbilitiesComp->ReplicatedTasks.Remove(It->Value); - } - Ability->AbilityTasks.Reset(); - - AbilityToAction.Remove(AbilityIn); - AbilitiesInputs.Remove(AbilityIn); - TagToAbility.Remove(AbilityIn); - MarkItemDirty(AbilitiesItems[Index]); - AbilitiesItems.RemoveAt(Index); - MarkArrayDirty(); -} -TSoftClassPtr FAFAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) -{ - TSoftClassPtr Ability; - TSoftClassPtr* AbilityTag = ActionToAbility.Find(InInputTag); - if (AbilityTag) - { - Ability = *AbilityTag; - } - - return Ability; -} - -void FAFAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) -{ - for (const FGameplayTag& InputTag : InInputTag) - { - TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); - AbilityClassPtr = InAbiltyPtr; - TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); - ActionTag.Add(InputTag); - } - if (!AbilitiesComp.IsValid()) - return; - - UGAAbilityBase* Ability = TagToAbility.FindRef(InAbiltyPtr); - if (Ability) - { - Ability->OnAbilityInputReady(); - } - - if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); - } -} -void FAFAbilityContainer::RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr) -{ - TArray* Inputs = AbilityToAction.Find(InAbiltyPtr); - - if (Inputs) - { - for (const FGameplayTag& Input : *Inputs) - { - ActionToAbility.Remove(Input); - } - - AbilityToAction.Remove(InAbiltyPtr); - } -} -UGAAbilityBase* FAFAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) -{ - UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); - return retAbility; -} -void FAFAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) -{ - if (BlockedInput.FindRef(ActionName)) - { - return; - } - TSoftClassPtr AbiltyPtr = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(AbiltyPtr); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - ability->OnNativeInputPressed(ActionName, InPredictionHandle); - } -} -void FAFAbilityContainer::HandleInputReleased(FGameplayTag ActionName) -{ - if (BlockedInput.FindRef(ActionName)) - { - return; - } - TSoftClassPtr abilityTag = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); - if (ability) - { - ability->OnNativeInputReleased(ActionName); - } -} - -void FAFAbilityContainer::TriggerAbylityByTag(TSoftClassPtr InTag) -{ - UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - FAFPredictionHandle PredHandle = FAFPredictionHandle::GenerateClientHandle(AbilitiesComp.Get()); - ability->OnNativeInputPressed(FGameplayTag(), PredHandle); - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h deleted file mode 100644 index a976afb..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAbilityTypes.h +++ /dev/null @@ -1,109 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once -#include "Engine/NetSerialization.h" -#include "GameplayTags.h" -#include "AFAbilityTypes.generated.h" - -class UGAAbilityBase; - -USTRUCT() -struct ABILITYFRAMEWORK_API FAFAbilityItem : public FFastArraySerializerItem -{ - GENERATED_BODY() - -public: - UPROPERTY() - UGAAbilityBase* Ability; - UPROPERTY() - TSoftClassPtr AbilityClass; - - FAFAbilityItem() - {}; - - FAFAbilityItem(UGAAbilityBase* InAbility, TSoftClassPtr InAbilityClass) - : Ability(InAbility) - , AbilityClass(InAbilityClass) - {} - - void PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer); - void PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer); - void PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer); - - const bool operator==(const TSoftClassPtr& OtherAbility) const - { - return AbilityClass == OtherAbility; - } - - const bool operator==(UGAAbilityBase* OtherAbility) const - { - return Ability == OtherAbility; - } - const bool operator==(const FAFAbilityItem& OtherItem) const - { - return Ability == OtherItem.Ability; - } -}; - -USTRUCT() -struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - - UPROPERTY() - TArray AbilitiesItems; - - TWeakObjectPtr AbilitiesComp; - TMap BlockedInput; - - TMap, FGameplayTag> AbilityToInput; - - //Custom binding, for server side validation. - - //ActionInput, AbilityClassPtr - TMap> ActionToAbility; - - //AbilityTag, ActionInput - TMap, TArray> AbilityToAction; - - //abilityTag, Ability Ptr - TMap, UGAAbilityBase*> AbilitiesInputs; - - TMap, UGAAbilityBase*> TagToAbility; - - void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - UGAAbilityBase* AddAbility(TSubclassOf AbilityIn - , TSoftClassPtr InClassPtr); - - void RemoveAbility(const TSoftClassPtr& AbilityIn); - - void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); - void RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr); - TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); - - UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); - - void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); - void HandleInputReleased(FGameplayTag ActionName); - - void TriggerAbylityByTag(TSoftClassPtr InTag); - - bool AbilityExists(TSoftClassPtr InAbiltyPtr) const - { - return AbilityToInput.Contains(InAbiltyPtr); - } - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); - } -}; - -template<> -struct TStructOpsTypeTraits< FAFAbilityContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - }; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp deleted file mode 100644 index 3362503..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.cpp +++ /dev/null @@ -1,35 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAttributeComponent.h" - - -// Sets default values for this component's properties -UAFAttributeComponent::UAFAttributeComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - - // ... -} - - -// Called when the game starts -void UAFAttributeComponent::BeginPlay() -{ - Super::BeginPlay(); - - // ... - -} - - -// Called every frame -void UAFAttributeComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h deleted file mode 100644 index 1140809..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFAttributeComponent.h +++ /dev/null @@ -1,29 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "AFAttributeComponent.generated.h" - - -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ABILITYFRAMEWORK_API UAFAttributeComponent : public UActorComponent -{ - GENERATED_BODY() - -public: - // Sets default values for this component's properties - UAFAttributeComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp deleted file mode 100644 index 96bb5a8..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.cpp +++ /dev/null @@ -1,46 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" - -#include "Abilities/GAAbilityBase.h" -#include "Effects/GAEffectField.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "AFBlueprintFunctionLibrary.h" - -void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, - const FGameplayTag& AbilityTag, FGameplayTag ActionTag) -{ - IAFAbilityInterface* Interface = Cast(Target); - if (!Interface) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Invalid Target")); - return; - } - UAFAbilityComponent* Comp = Interface->GetAbilityComp(); - if (!Comp) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Target %s InvalidComponent"), *Target->GetName()); - return; - } - - Comp->NativeInputPressed(ActionTag); -} -void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, - const FGameplayTag& AbilityTag, FGameplayTag ActionTag) -{ - IAFAbilityInterface* Interface = Cast(Target); - if (!Interface) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Invalid Target")); - return; - } - UAFAbilityComponent* Comp = Interface->GetAbilityComp(); - if (!Comp) - { - UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Target %s InvalidComponent"), *Target->GetName()); - return; - } - - Comp->NativeInputReleased(ActionTag); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h deleted file mode 100644 index 700bfb5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFBlueprintFunctionLibrary.h +++ /dev/null @@ -1,17 +0,0 @@ -#pragma once -#include "GameplayTags.h" -#include "GameplayTagContainer.h" -#include "AFBlueprintFunctionLibrary.generated.h" -/* - Some static helper functions, to interact with Attribute system. -*/ -UCLASS() -class ABILITYFRAMEWORK_API UAFBlueprintFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_BODY() -public: - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - static void TriggerAbilityPressedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - static void TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp deleted file mode 100644 index 2fac5ab..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFCueInterface.h" - - -// Add default functionality here for any IAFCueInterface functions that are not pure virtual. diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h deleted file mode 100644 index 26baa08..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueInterface.h +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "AFCueInterface.generated.h" - -// This class does not need to be modified. -UINTERFACE(MinimalAPI) -class UAFCueInterface : public UInterface -{ - GENERATED_BODY() -}; - -/** - * - */ -class ABILITYFRAMEWORK_API IAFCueInterface -{ - GENERATED_BODY() - - // Add interface functions to this class. This is the class that will be inherited to implement this interface. -public: - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp deleted file mode 100644 index c988060..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.cpp +++ /dev/null @@ -1,341 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "Effects/GAEffectCue.h" -#include "AFCueManager.h" -#if WITH_EDITOR -#include "Editor.h" -#endif - -UAFCueManager* UAFCueManager::ManagerInstance = nullptr; -//UWorld* UAFCueManager::CurrentWorld = nullptr; - -UAFCueManager* UAFCueManager::Get() -{ - if (ManagerInstance) - { - return ManagerInstance; - } - ManagerInstance = NewObject(GEngine, UAFCueManager::StaticClass(), "UAFCueManagerInstance", - RF_MarkAsRootSet); - ManagerInstance->AddToRoot(); - ManagerInstance->Initialize(); - - return ManagerInstance; -} -void UAFCueManager::Initialize() -{ -#if WITH_EDITORONLY_DATA - FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); -#endif //WITH_EDITORONLY_DATA - FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); - FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); -} -#if WITH_EDITOR -void UAFCueManager::HandleOnPIEEnd(bool InVal) -{ - CurrentWorld = nullptr; - for (auto It = InstancedCues.CreateIterator(); It; ++It) - { - if (It->Value.IsValid()) - { - while (!It->Value->IsEmpty()) - { - AGAEffectCue* ToDestroy = nullptr; - It->Value->Dequeue(ToDestroy); - if (ToDestroy) - { - ToDestroy->Destroy(); - } - } - } - } - for (auto It = UsedCues.CreateIterator(); It; ++It) - { - if (It->Value.Num() <= 0) - { - UsedCues.Remove(It->Key); - } - for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) - { - if (QIt->Value.IsValid()) - { - while (!QIt->Value->IsEmpty()) - { - AGAEffectCue* ToDestroy = nullptr; - QIt->Value->Dequeue(ToDestroy); - if (ToDestroy) - { - ToDestroy->Destroy(); - } - } - } - if (It->Value.Num() <= 0) - { - UsedCues.Remove(It->Key); - } - } - - } - ActiveCues.Empty(); - InstancedCues.Empty(); - UsedCues.Empty(); -} -#endif //WITH_EDITOR -void UAFCueManager::HandlePreLoadMap(const FString& InMapName) -{ - CurrentWorld = nullptr; - - InstancedCues.Reset(); - InstancedCues.Compact(); - UsedCues.Reset(); - UsedCues.Compact(); - //for (auto It = InstancedCues.CreateIterator(); It; ++It) - //{ - // if (It->Value.IsValid()) - // { - // while (!It->Value->IsEmpty()) - // { - // AGAEffectCue* ToDestroy = nullptr; - // It->Value->Dequeue(ToDestroy); - // if (ToDestroy) - // { - // ToDestroy->Destroy(); - // } - // } - // } - //} - //for (auto It = UsedCues.CreateIterator(); It; ++It) - //{ - // if (It->Value.Num() <= 0) - // { - // UsedCues.Remove(It->Key); - // } - // for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) - // { - // if (QIt->Value.IsValid()) - // { - // while (!QIt->Value->IsEmpty()) - // { - // AGAEffectCue* ToDestroy = nullptr; - // QIt->Value->Dequeue(ToDestroy); - // if (ToDestroy) - // { - // ToDestroy->Destroy(); - // } - // } - // } - // if (It->Value.Num() <= 0) - // { - // UsedCues.Remove(It->Key); - // } - // } - - //} -} -void UAFCueManager::HandlePostLoadMap(UWorld* InWorld) -{ - CurrentWorld = InWorld; -} - - -void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) -{ - if (!CurrentWorld) - CurrentWorld = CueParams.Instigator->GetWorld(); - - - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - for (const FGameplayTag& CueTag : Tags) - { - - AGAEffectCue* actor = nullptr; - ENetRole mode = CueParams.Instigator->GetRemoteRole(); - TUniquePtr>& Cues = InstancedCues.FindOrAdd(CueTag); - if (Cues.IsValid()) - { - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(CueTag); - - if (!UseCuesQueue.IsValid()) - { - UseCuesQueue = MakeUnique>(); - } - { - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); - } - if (actor) - { - ActiveCues.Add(InHandle, actor); - actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.GetActor(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); - } - return;//don't try to load asset, we already have pooled instance. - } - - - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - - TArray AssetData; - FARFilter Filter; - Filter.TagsAndValues.Add("EffectCueTagSearch", CueTag.ToString()); - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("EffectCue"), AssetData[0].AssetName); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams, InHandle); - - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); - } - } - } -} -void UAFCueManager::HandleExecuteCue(FAFCueHandle InHandle) -{ - AGAEffectCue** Cue = ActiveCues.Find(InHandle); - if (Cue) - { - AGAEffectCue* cue = *Cue; - - cue->NativeOnExecuted(); - } -} -void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag - , FPrimaryAssetId InPrimaryAssetId - , FGAEffectCueParams CueParams - , FAFCueHandle InHandle) -{ - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); - TSubclassOf cls = Cast(loaded); - if (cls) - { - TSubclassOf CueClass = cls; - if (!CueClass) - return; - - ENetRole mode = CueParams.Instigator->GetRemoteRole(); - FString role; - switch (mode) - { - case ROLE_None: - role = "ROLE_None"; - break; - case ROLE_SimulatedProxy: - role = "ROLE_SimulatedProxy"; - break; - case ROLE_AutonomousProxy: - role = "ROLE_AutonomousProxy"; - break; - case ROLE_Authority: - role = "ROLE_Authority"; - break; - case ROLE_MAX: - role = "ROLE_MAX"; - break; - default: - break; - } - - FString prefix = ""; - //if (mode == ENetMode::NM_Client) - //{ - // prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - //} - - UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), - *prefix, - *InCueTag.ToString(), - CueParams.Instigator.IsValid() ? *CueParams.Instigator->GetName() : TEXT("Invalid Instigator"), - *CueParams.HitResult.Location.ToString(), - *CurrentWorld->GetName(), - *role - ); - - FActorSpawnParameters SpawnParams; - FVector Location = CueParams.HitResult.Location; - FRotator Rotation = FRotator::ZeroRotator; - AGAEffectCue* actor = nullptr; - - TUniquePtr>& Cues = InstancedCues.FindOrAdd(InCueTag); - if (!Cues.IsValid()) - { - Cues = MakeUnique>(); - } - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(InCueTag); - - if (!UseCuesQueue.IsValid()) - { - UseCuesQueue = MakeUnique>(); - } - - if (Cues->IsEmpty()) - { - actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); - Cues->Enqueue(actor); - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); - } - else - { - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); - } - - if (actor) - { - ActiveCues.Add(InHandle, actor); - actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - CueParams.Causer.Get(), CueParams.HitResult, CueParams); - } - } - - { - Manager->UnloadPrimaryAsset(InPrimaryAssetId); - } - } -} - -void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) -{ - if (!CurrentWorld) - CurrentWorld = CueParams.Instigator->GetWorld(); - for (const FGameplayTag& Tag : CueParams.CueTags) - { - AGAEffectCue* actor = nullptr; - TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); - if (!Cues.IsValid()) - { - Cues = MakeUnique>(); - } - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(Tag); - - if (!UseCuesQueue.IsValid()) - { - UseCuesQueue = MakeUnique>(); - } - - UseCuesQueue->Dequeue(actor); - - - if (actor) - { - ActiveCues.Remove(InHandle); - Cues->Enqueue(actor); - actor->NativeOnRemoved(); - } - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h deleted file mode 100644 index 86bb9c7..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFCueManager.h +++ /dev/null @@ -1,53 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "GameplayTags.h" -#include "GAGlobalTypes.h" -#include "Effects/GAEffectCue.h" -#include "AFCueManager.generated.h" - -/** - * - */ -UCLASS(config = Game) -class ABILITYFRAMEWORK_API UAFCueManager : public UObject -{ - GENERATED_BODY() -protected: - //UPROPERTY() - static UAFCueManager* ManagerInstance; - UWorld* CurrentWorld; - - //store per instigator ? Causer ? or global pool ? - //stores unused instanced cues. - TMap>> InstancedCues; - //store per instigator ? Causer ? - //stores used cues. - TMap>>> UsedCues; - - TMap ActiveCues; - -public: - void Initialize(); -#if WITH_EDITOR - //handle clearing up cache when PIE mode is ending. - void HandleOnPIEEnd(bool InVal); -#endif //WITH_EDITOR - void HandlePreLoadMap(const FString& InMapName); - void HandlePostLoadMap(UWorld* InWorld); -public: - static UAFCueManager* Get(); - void HandleCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); - void HandleExecuteCue(FAFCueHandle InHandle); - void HandleRemoveCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); -protected: - void OnFinishedLoad(FGameplayTag InCueTag - , FPrimaryAssetId InPrimaryAssetId - , FGAEffectCueParams CueParams - , FAFCueHandle InHandle); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp deleted file mode 100644 index 87b6110..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.cpp +++ /dev/null @@ -1,502 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFEffectsComponent.h" - -#include "Net/UnrealNetwork.h" -#include "Engine/ActorChannel.h" - -#include "AFAbilityInterface.h" -#include "Effects/GAEffectExecution.h" -#include "Effects/GAGameEffect.h" -#include "Effects/GAEffectExtension.h" -#include "Effects/GAEffectCue.h" -#include "AFCueManager.h" -#include "Effects/GABlueprintLibrary.h" - -// Sets default values for this component's properties -UAFEffectsComponent::UAFEffectsComponent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - - // ... -} - - -// Called when the game starts -void UAFEffectsComponent::BeginPlay() -{ - Super::BeginPlay(); - GameEffectContainer.OwningComponent = this; - // ... - -} -void UAFEffectsComponent::InitializeComponent() -{ - Super::InitializeComponent(); - - GameEffectContainer.OwningComponent = this; -} - -// Called every frame -void UAFEffectsComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} - -FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - FGAEffectProperty& InProperty = Params.GetProperty(); - const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; - - FAFEventData Data; - - for (const FGameplayTag& Tag : AppliedEventTags) - { - if (TArray* Events = EffectEvents.Find(Tag)) - { - for (const FAFEventDelegate& Event : *Events) - Event.Execute(Data); - } - - } - OnAppliedToSelf.Broadcast(Params.Context, Params.Property, Params.EffectSpec); - - if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) - { - Delegate->ExecuteIfBound(); - } - - FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InHandle, Params, Modifier); - GameEffectContainer.MarkArrayDirty(); - return Handle; -} - -FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - FGAEffectProperty& InProperty = Params.GetProperty(); - FGAEffectContext& InContext = Params.GetContext(); - if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) - { - Delegate->ExecuteIfBound(); - } - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - - FAFCueHandle CueHandle = FAFCueHandle::GenerateHandle(); - - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams(InContext, InProperty); - MulticastApplyEffectCue(CueParams, CueHandle); - } - - OnAppliedToTarget.Broadcast(Params.Context, Params.Property, Params.EffectSpec); - - if (InContext.TargetComp.IsValid()) - { - FGAEffectHandle Handle; - Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InHandle, Params, Modifier); - //if (!PropertyByHandle.Contains(Handle)) - // PropertyByHandle.Add(Handle, &InProperty); - - EffectToCue.Add(Handle, CueHandle); - - return Handle; - } - return FGAEffectHandle(); -} - - -/* Have to to copy handle around, because timer delegates do not support references. */ -void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn - , FAFEffectParams Params - , FAFFunctionModifier Modifier) -{ - FGAEffectContext& Context = Params.Context.GetRef(); - FGAEffectProperty& Property = Params.Property.GetRef(); - FAFEffectSpec& EffectSpec = Params.GetSpec(); - /* - this patth will give effects chance to do any replicated events, like applying cues. - WE do not make any replication at the ApplyEffect because some effect might want to apply cues - on periods on expiration etc, and all those will go trouch ExecuteEffect path. - */ - const FGameplayTagContainer& RequiredTags = Property.GetSpec()->RequiredTags; - if (RequiredTags.Num() > 0) - { - if (!HasAll(RequiredTags)) - { - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *Property.GetSpec()->GetName(), *RequiredTags.ToString()); - return; - } - } - - //apply execution events: - const FGameplayTagContainer& ExecuteEventTags = Property.GetSpec()->ExecuteEventTags; - FAFEventData Data(Params); - for (const FGameplayTag& Tag : ExecuteEventTags) - { - TriggerExecuteEvent(Tag, Data); - } - - //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *Property.GetSpec()->GetName()); - - FGAEffectMod Mod = FAFStatics::GetAttributeModifier(Property.GetAttributeModifier() - , Property.GetSpec() - , Context - , HandleIn); - - EffectSpec.OnExecuted(); - ExecuteEffectEvent(Property.GetSpec()->OnPeriodEvent); - - FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); - if (CueHandle) - MulticastExecuteEffectCue(*CueHandle); - - Property.ExecuteEffect(HandleIn, Mod, Params, Modifier); - PostExecuteEffect(); -} - -void UAFEffectsComponent::PostExecuteEffect() -{ - -} -/* ExpireEffect is used to remove existing effect naturally when their time expires. */ -void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn - , FAFEffectParams Params) -{ - //call effect internal delegate: - FGAEffectProperty& InProperty = Params.GetProperty(); - FGAEffectContext& InContext = Params.GetContext(); - FAFEffectSpec& EffectSpec = Params.GetSpec(); - FGAEffect* Effect = GameEffectContainer.GetEffect(HandleIn); - EffectSpec.OnExpired(); - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); - if (mode == ENetMode::NM_DedicatedServer - || mode == ENetMode::NM_ListenServer) - { - ClientExpireEffect(InProperty.GetPredictionHandle()); - } - - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams(InContext, InProperty); - - FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); - if (CueHandle) - { - MulticastRemoveEffectCue(CueParams, *CueHandle); - } - } - - TArray handles = GameEffectContainer.RemoveEffect(Params.Property); -} - -void UAFEffectsComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) -{ - -} - -void UAFEffectsComponent::RemoveEffect(const FAFPropertytHandle& InProperty - , const FGAEffectContext& InContext - , const FGAEffectHandle& InHandle) -{ - if (!InProperty.IsValid()) - { - UE_LOG(AFEffects, Log, TEXT("RemoveEffect - Trying to Remove invalid effect.")); - return; - } - //if (GetOwnerRole() == ENetRole::ROLE_Authority - // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) - { - InternalRemoveEffect(InProperty, InContext); - } - ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); - FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); - - FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); - if (CueHandle) - { - MulticastRemoveEffectCue(CueParams, *CueHandle); - } -} -void UAFEffectsComponent::InternalRemoveEffect(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext) -{ - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); - - //MulticastRemoveEffectCue(HandleIn); - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) - { - FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role >= ENetRole::ROLE_Authority) - { - //MulticastRemoveEffectCue(CueParams); - } - } - - TArray handles = GameEffectContainer.RemoveEffect(InProperty); -} - -void UAFEffectsComponent::AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) -{ - if (!InEventTag.IsValid()) - return; - if (!OnEffectEvent.Contains(InEventTag)) - { - UE_LOG(AbilityFramework, Log, TEXT("AddEffectEvent: %s"), *InEventTag.ToString()); - OnEffectEvent.Add(InEventTag, InEvent); - } -} -void UAFEffectsComponent::ExecuteEffectEvent(const FGameplayTag& InEventTag) -{ - if (!InEventTag.IsValid()) - return; - FSimpleDelegate* Delegate = OnEffectEvent.Find(InEventTag); - if (Delegate) - { - UE_LOG(AbilityFramework, Log, TEXT("ExecuteEffectEvent: %s"), *InEventTag.ToString()); - Delegate->ExecuteIfBound(); - } -} -void UAFEffectsComponent::RemoveEffectEvent(const FGameplayTag& InEventTag) -{ - if (!InEventTag.IsValid()) - return; - UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); - OnEffectEvent.Remove(InEventTag); -} -TArray& UAFEffectsComponent::GetTagEvent(FGameplayTag TagIn) -{ - TArray& Delegate = EffectEvents.FindChecked(TagIn); - return Delegate; -} - -void UAFEffectsComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) -{ - TArray* Delegate = EffectEvents.Find(TagIn); - if (Delegate) - { - for (const FAFEventDelegate& Event : *Delegate) - { - if (Event.IsBound()) - { - Event.Execute(InEventData); - } - } - } -} - -void UAFEffectsComponent::AddAppliedEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) -{ - TArray& Events = AppliedEvents.FindOrAdd(EventTag); - Events.Add(EventDelegate); -} -void UAFEffectsComponent::RemoveAppliedEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) -{ - TArray* Events = AppliedEvents.Find(EventTag); - if (Events) - { - int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) - { - return Other.GetHandle() == EventDelegate; - }); - - Events->RemoveAt(Idx, 1, true); - } -} -void UAFEffectsComponent::TriggerAppliedEvent(FGameplayTag TagIn, const FAFEventData& InEventData) -{ - TArray* Delegate = AppliedEvents.Find(TagIn); - if (Delegate) - { - for (const FAFEventDelegate& Event : *Delegate) - { - if (Event.IsBound()) - { - Event.Execute(InEventData); - } - } - } -} - -void UAFEffectsComponent::AddExecuteEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) -{ - TArray& Events = ExecutedEvents.FindOrAdd(EventTag); - Events.Add(EventDelegate); -} -void UAFEffectsComponent::RemoveExecuteEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) -{ - TArray* Events = ExecutedEvents.Find(EventTag); - if (Events) - { - int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) - { - return Other.GetHandle() == EventDelegate; - }); - - Events->RemoveAt(Idx, 1, true); - } -} -void UAFEffectsComponent::TriggerExecuteEvent(FGameplayTag TagIn, const FAFEventData& InEventData) -{ - TArray* Delegate = ExecutedEvents.Find(TagIn); - if (Delegate) - { - for (const FAFEventDelegate& Event : *Delegate) - { - if (Event.IsBound()) - { - Event.Execute(InEventData); - } - } - } -} - - -void UAFEffectsComponent::AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) -{ - TArray& Events = EffectEvents.FindOrAdd(EventTag); - Events.Add(EventDelegate); -} - -void UAFEffectsComponent::RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) -{ - TArray* Events = EffectEvents.Find(EventTag); - if (Events) - { - - int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) - { - return Other.GetHandle() == EventDelegate; - }); - - Events->RemoveAt(Idx, 1, true); - } -} - -bool UAFEffectsComponent::IsEffectActive(const FGAEffectHandle& InHandle) const -{ - return GameEffectContainer.IsEffectActive(InHandle); -} - -bool UAFEffectsComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) -{ - bool bDenyApplication = false; - if (InTags.Num() > 0) - { - bDenyApplication = HasAll(InTags); - } - return bDenyApplication; -} - -bool UAFEffectsComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) -{ - bool bAllowApplication = true; - if (InTags.Num() > 0) - { - bAllowApplication = HasAll(InTags); - } - return bAllowApplication; -} - -FGAEffect* UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) -{ - return *GameEffectContainer.ActiveEffects.Find(InHandle); -} - -/* -Need prediction for spawning effects on client, -and then on updateing them predicitvely on all other clients. -*/ -/* - -*/ -void UAFEffectsComponent::MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); - } -} -void UAFEffectsComponent::MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - UAFCueManager::Get()->HandleExecuteCue(InHandle); - } -} - -void UAFEffectsComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) -{ - ENetRole role = GetOwnerRole(); - ENetMode mode = GetOwner()->GetNetMode(); - if (mode == ENetMode::NM_Standalone - || role != ENetRole::ROLE_Authority) - { - UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams, InHandle); - } -} - -void UAFEffectsComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) -{ - -} - -void UAFEffectsComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) -{ - -} - -void UAFEffectsComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) -{ - -} - -void UAFEffectsComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) -{ - -} - - -/*Network Functions - BEGIN */ - -void UAFEffectsComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - - DOREPLIFETIME(UAFEffectsComponent, GameEffectContainer); - DOREPLIFETIME(UAFEffectsComponent, AppliedTags); - DOREPLIFETIME(UAFEffectsComponent, ImmunityTags); -} - -void UAFEffectsComponent::OnRep_GameEffectContainer() -{ - -} - -/*Network Functions - END */ \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h deleted file mode 100644 index 0a5c7b1..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AFEffectsComponent.h +++ /dev/null @@ -1,227 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "GameplayTags.h" -#include "GameplayTagAssetInterface.h" - -#include "Attributes/GAAttributeBase.h" -#include "Attributes/GAAttributesBase.h" -#include "Effects/GAEffectCueGlobals.h" -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" - -#include "AFEffectsComponent.generated.h" - -DECLARE_DELEGATE(FAFEffectEvent); -DECLARE_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); - -DECLARE_MULTICAST_DELEGATE_ThreeParams(FAFApplicationDelegate, FAFContextHandle, FAFPropertytHandle, FAFEffectSpecHandle); - -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent -{ - GENERATED_BODY() -private: - friend class UGAAbilityBase; - friend class IAFAbilityInterface; - friend class UAFAbilityComponent; - friend class UAFEffectTask_EffectEvent; - -private: - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer DefaultTags; - - UPROPERTY(Replicated) - FGACountedTagContainer AppliedTags; - - UPROPERTY(Replicated) - FGACountedTagContainer ImmunityTags; - - UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) - FGAEffectContainer GameEffectContainer; - - TMap OnEffectApplyToTarget; - TMap OnEffectApplyToSelf; - TMap> EffectEvents; - - TMap EffectToCue; - - TMap OnEffectEvent; - - TMap> AppliedEvents; - TMap> ExecutedEvents; -public: - FAFApplicationDelegate OnAppliedToTarget; - FAFApplicationDelegate OnAppliedToSelf; - FAFApplicationDelegate OnEffectExecuted; -public: - // Sets default values for this component's properties - UAFEffectsComponent(const FObjectInitializer& ObjectInitializer); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - - /** UActorComponent Interface - Begin */ - virtual void InitializeComponent() override; - /* UActorComponent Interface - End **/ - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - -protected: - - /* - * @call Order: - * Previous Function: UAFAbilityComponent::ApplyEffectToTarget - * Next Function: FGAEffectContainer::ApplyEffect - * Apply target to Me. Try to apply effect to container and launch Events in: - * TMap OnEffectEvent - event is called before application; - * TMap OnEffectApplyToSelf - event is called before application; - * - * @param EffectIn& - Effect to apply - * @param InProperty - cached effect information - * @param InContext - Context about effect application. Target, instigator, causer. - * @param Modifier - optional modifier which can be applied to effect. - * @return Handle to Effect; - */ - FGAEffectHandle ApplyEffectToSelf( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - /* - * @call Order: - * Previous Function: UGABlueprintLibrary::ApplyEffect - * Next Function: UAFAbilityComponent::ApplyEffectToSelf - * Apply effect to target provided inside Context. - * Try launch events: - * TMap OnEffectApplyToTarget - event is called before application - * - * @param EffectIn& - Effect to apply - * @param InProperty - cached effect information - * @param InContext - Context about effect application. Target, instigator, causer. - * @param Modifier - optional modifier which can be applied to effect. - * @return Handle to Effect; - */ - FGAEffectHandle ApplyEffectToTarget( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - -public: - /* Have to to copy handle around, because timer delegates do not support references. */ - void ExecuteEffect(FGAEffectHandle HandleIn - , FAFEffectParams Params - , FAFFunctionModifier Modifier); - - virtual void PostExecuteEffect(); - /* ExpireEffect is used to remove existing effect naturally when their time expires. */ -public: - void ExpireEffect(FGAEffectHandle HandleIn - , FAFEffectParams Params); - -protected: - UFUNCTION(Client, Reliable) - void ClientExpireEffect(FAFPredictionHandle PredictionHandle); - void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); - - /* RemoveEffect is used to remove effect by force. */ - void RemoveEffect(const FAFPropertytHandle& InProperty - , const FGAEffectContext& InContext - , const FGAEffectHandle& InHandle); - void InternalRemoveEffect(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext); - - void AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent); - void ExecuteEffectEvent(const FGameplayTag& InEventTag); - void RemoveEffectEvent(const FGameplayTag& InEventTag); - bool IsEffectActive(const FGAEffectHandle& InHandle) const; - -public: - void AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); - void RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); - TArray& GetTagEvent(FGameplayTag TagIn); - void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); - - void AddAppliedEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); - void RemoveAppliedEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); - void TriggerAppliedEvent(FGameplayTag TagIn, const FAFEventData& InEventData); - - - void AddExecuteEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); - void RemoveExecuteEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); - void TriggerExecuteEvent(FGameplayTag TagIn, const FAFEventData& InEventData); - -public: - bool DenyEffectApplication(const FGameplayTagContainer& InTags); - bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); -protected: - /* - - */ - UFUNCTION(NetMulticast, Unreliable) - void MulticastApplyEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastExecuteEffectCue(FAFCueHandle InHandle); - void MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastRemoveEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - void MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); - void MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); - void MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); - void MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); - - UFUNCTION(NetMulticast, Unreliable) - void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); - void MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); -public: - FGAEffect* GetEffect(const FGAEffectHandle& InHandle); - - /* Counted Tag Container Wrapper Start */ - inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; - inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; - inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; - inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; - inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } - inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; - inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; - inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; - inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; - inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; - inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } - /* Counted Tag Container Wrapper Start */ - - - /* Game Effect Container WRAPPER */ - bool IsEffectActive(TSubclassOf EffectClass) - { - return GameEffectContainer.IsEffectActive(EffectClass); - } - - /* Game Effect Container WRAPPER */ - - /*Network Functions - BEGIN */ -protected: - UFUNCTION() - void OnRep_GameEffectContainer(); - - /*Network Functions - END */ -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp deleted file mode 100644 index dbb9013..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../Effects/CustomApplications/AFAtributeDurationAdd.h" -#include "AFAbilityActivationSpec.h" - - - -UAFAbilityActivationSpec::UAFAbilityActivationSpec() - :Super() -{ - Application = UAFAtributeDurationAdd::StaticClass(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h deleted file mode 100644 index d9d6bfb..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityActivationSpec.h +++ /dev/null @@ -1,21 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityActivationSpec.generated.h" - -/** - * - */ -UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFAbilityActivationSpec : public UGAGameEffectSpec -{ - GENERATED_BODY() - -public: - UAFAbilityActivationSpec(); - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp deleted file mode 100644 index 045614d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.cpp +++ /dev/null @@ -1,14 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "Effects/CustomApplications/AFAtributeDurationAdd.h" -#include "AFAbilityCooldownSpec.h" - - - - -UAFAbilityCooldownSpec::UAFAbilityCooldownSpec() - : Super() -{ - Application = UAFAtributeDurationAdd::StaticClass(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h deleted file mode 100644 index 238e495..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityCooldownSpec.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityCooldownSpec.generated.h" - -/** - * - */ -UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFAbilityCooldownSpec : public UGAGameEffectSpec -{ - GENERATED_BODY() -public: - UAFAbilityCooldownSpec(); - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp deleted file mode 100644 index 19cf6ce..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "Effects/CustomApplications/AFAttributeDurationInfinite.h" -#include "AFAbilityInfiniteDurationSpec.h" - - - -UAFAbilityInfiniteDurationSpec::UAFAbilityInfiniteDurationSpec() - :Super() -{ - Application = UAFAttributeDurationInfinite::StaticClass(); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h deleted file mode 100644 index 89b59a2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityInfiniteDurationSpec.h +++ /dev/null @@ -1,21 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityInfiniteDurationSpec.generated.h" - -/** - * - */ -UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFAbilityInfiniteDurationSpec : public UGAGameEffectSpec -{ - GENERATED_BODY() -public: - UAFAbilityInfiniteDurationSpec(); - - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp deleted file mode 100644 index 49cb210..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityPeriodSpec.h" -#include "../Effects/CustomApplications/AFPeriodApplicationAdd.h" - - - -UAFAbilityPeriodSpec::UAFAbilityPeriodSpec() - :Super() -{ - Application = UAFPeriodApplicationAdd::StaticClass(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h deleted file mode 100644 index 7c6f1eb..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodSpec.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityPeriodSpec.generated.h" - -/** - * - */ -UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFAbilityPeriodSpec : public UGAGameEffectSpec -{ - GENERATED_BODY() -public: - UAFAbilityPeriodSpec(); - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp deleted file mode 100644 index a77c62a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.cpp +++ /dev/null @@ -1,14 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h" -#include "AFAbilityPeriodicInfiniteSpec.h" - - - - -UAFAbilityPeriodicInfiniteSpec::UAFAbilityPeriodicInfiniteSpec() - :Super() -{ - Application = UAFPeriodApplicationInfiniteAdd::StaticClass(); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h deleted file mode 100644 index 57158e4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/AFAbilityPeriodicInfiniteSpec.h +++ /dev/null @@ -1,18 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityPeriodicInfiniteSpec.generated.h" - -/** - * - */ -UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFAbilityPeriodicInfiniteSpec : public UGAGameEffectSpec -{ - GENERATED_BODY() -public: - UAFAbilityPeriodicInfiniteSpec(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp deleted file mode 100644 index 9b5a023..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.cpp +++ /dev/null @@ -1,950 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - - -#include "AbilityFramework.h" -#include "Tasks/GAAbilityTask.h" -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "Effects/GAEffectGlobalTypes.h" -#include "AFAbilityComponent.h" -#include "AFEffectsComponent.h" - -#include "GameplayTagContainer.h" -#include "Net/UnrealNetwork.h" -#include "Animation/AnimMontage.h" -#include "Effects/GABlueprintLibrary.h" -#include "Camera/CameraComponent.h" -#include "Kismet/KismetSystemLibrary.h" - -#include "GAAbilityBase.h" -FAFPredictionHandle UGAAbilityBase::GetPredictionHandle() { return PredictionHandle; } - -UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bReplicate = true; - bIsNameStable = false; -} - -void UGAAbilityBase::PostInitProperties() -{ - UpdateAssetRegistryInfo(); - Super::PostInitProperties(); -} - -void UGAAbilityBase::Serialize(FArchive& Ar) -{ - if (Ar.IsSaving()) - { - UpdateAssetRegistryInfo(); - } - - Super::Serialize(Ar); - - if (Ar.IsLoading()) - { - UpdateAssetRegistryInfo(); - } -} -#if WITH_EDITORONLY_DATA -void UGAAbilityBase::UpdateAssetBundleData() -{ - AssetBundleData.Reset(); - - // By default parse the metadata - if (UAssetManager::IsValid()) - { - UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); - } -} - -void UGAAbilityBase::PreSave(const class ITargetPlatform* TargetPlatform) -{ - Super::PreSave(TargetPlatform); - - UpdateAssetBundleData(); - - if (UAssetManager::IsValid()) - { - // Bundles may have changed, refresh - UAssetManager::Get().RefreshAssetData(this); - } -} -#endif - -FPrimaryAssetId UGAAbilityBase::GetPrimaryAssetId() const -{ - //FName Name = GetFName(); - //FName clsNam = GetClass()->GetFName(); - FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); - //FName dupa2 = FPackageName::GetShortFName(GetFName()); - const UGAAbilityBase* A = this; - return FPrimaryAssetId(FPrimaryAssetType("Ability"), dupa1); - //if (HasAnyFlags(RF_ClassDefaultObject)) - { - UClass* SearchNativeClass = GetClass(); - - while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) - { - SearchNativeClass = SearchNativeClass->GetSuperClass(); - } - - if (SearchNativeClass && SearchNativeClass != GetClass()) - { - // If blueprint, return native class and asset name - - } - - // Native CDO, return nothing - return FPrimaryAssetId(); - } - - // Data assets use Class and ShortName by default, there's no inheritance so class works fine - //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); -} - -void UGAAbilityBase::PostLoad() -{ - Super::PostLoad(); - -#if WITH_EDITORONLY_DATA - FAssetBundleData OldData = AssetBundleData; - - UpdateAssetBundleData(); - - if (UAssetManager::IsValid() && OldData != AssetBundleData) - { - // Bundles changed, refresh - UAssetManager::Get().RefreshAssetData(this); - } -#endif -} -#if WITH_EDITOR -void UGAAbilityBase::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) -{ - Super::PostEditChangeProperty(PropertyChangedEvent); -} -#endif // WITH_EDITOR - -void UGAAbilityBase::UpdateAssetRegistryInfo() -{ - AbilityTagSearch = AbilityTag.GetTagName(); -} - -void UGAAbilityBase::InitAbility() -{ - //still want to initialize, as Spec is used in multiple places. - DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); - ActivationEffect.InitializeIfNotInitialized(DefaultContext); - CooldownEffect.InitializeIfNotInitialized(DefaultContext); - for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) - { - AttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); - } - AttributeCostHandle.AddZeroed(AttributeCost.Num()); - - for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) - { - AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); - } - AbilityAttributeCostHandle.AddZeroed(AbilityAttributeCost.Num()); - if (AbilityComponent) - { - World = AbilityComponent->GetWorld(); - } - - if (!AbilityComponent) - { - AbilityComponent = GetAbilityComp(); - } - if (Attributes) - { - Attributes->InitializeAttributes(GetAbilityComp()); - Attributes->InitializeAttributesFromTable(); - } - - ENetRole role = AbilityComponent->GetOwnerRole(); - ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); - - if (role < ENetRole::ROLE_Authority) - { - FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); - AbilityComponent->RepAttributes.RegisterAttributeRepEvent(AbilityTag, Delegate); - } - - //AbilityComponent->RepAttributes.AttributeMap.Add(AbilityTag, Attributes); - if (role == ENetRole::ROLE_Authority || - mode == ENetMode::NM_Standalone) - { - if (AbilityComponent && Attributes) - { - UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes);; - Attributes = nullptr; - Attributes = NewAttributes; - } - } - - if (!OwnerCamera) - { - OwnerCamera = POwner->FindComponentByClass(); - } - - OnAbilityInited(); -} -void UGAAbilityBase::OnAttributeSetReplicated() -{ - UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); - Attributes = attributes; -} - -void UGAAbilityBase::OnAbilityInited() -{ - -} -void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) -{ - { - UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); - PredictionHandle = InPredictionHandle; - OnInputPressed(ActionName); - OnInputPressedDelegate.Broadcast(); - } -} - -void UGAAbilityBase::OnNativeInputReleased(FGameplayTag ActionName) -{ - { - UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputReleased in ability %s"), *GetName()); - OnInputReleased(ActionName); - OnInputReleasedDelegate.Broadcast(); - } -} - -void UGAAbilityBase::StartActivation(bool bApplyActivationEffect) -{ - if (!CanUseAbility()) - { - UE_LOG(AbilityFramework, Log, TEXT("Cannot use Ability: %s"), *GetName()); - return; - } - //AbilityComponent->ExecutingAbility = this; - AbilityState = EAFAbilityState::Activating; - NativeOnBeginAbilityActivation(bApplyActivationEffect); -} - -void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) -{ - UE_LOG(AbilityFramework, Log, TEXT("Begin Executing Ability: %s"), *GetName()); - - if (OnConfirmCastingEndedDelegate.IsBound()) - { - OnConfirmCastingEndedDelegate.Broadcast(); - } - //ActivationInfo.SetActivationInfo(); - ApplyActivationEffect(bApplyActivationEffect); - OnActivate(); - OnActivateBeginDelegate.Broadcast(); - AbilityComponent->AppliedTags.AddTagContainer(ActivationAddedTags); - //OnAbilityExecuted(); -} - -void UGAAbilityBase::OnCooldownEffectExpired() -{ - UE_LOG(AFAbilities, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); - - if (CooldownEffectHandle.IsValid()) - { - //CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); - } -} -/* Functions for activation effect delegates */ -void UGAAbilityBase::NativeOnAbilityActivationFinish(FGAEffectHandle InHandle) -{ - UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); - OnActivationFinished(); - OnActivationFinishedDelegate.Broadcast(); -} -void UGAAbilityBase::NativeOnAbilityActivationCancel() -{ - //OnAbilityExecutedNative(); - //this works under assumption that current state == activation state. - UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Removed In Ability: %s"), *GetName()); - //AbilityComponent->ExecutingAbility = nullptr; - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); - - OnActivationCancel(); - //AbilityActivatedCounter++; -} -void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) -{ - UE_LOG(AFAbilities, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); - - OnPeriod(); -} -void UGAAbilityBase::FinishAbility() -{ - UE_LOG(AFAbilities, Log, TEXT("FinishExecution in ability %s"), *GetName()); - OnAbilityFinished(); - NativeFinishAbility(); - AbilityState = EAFAbilityState::Waiting; - GetEffectsComponent()->AppliedTags.RemoveTagContainer(ActivationAddedTags); -} -void UGAAbilityBase::NativeFinishAbility() -{ - UE_LOG(AFAbilities, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); - AbilityComponent->ExecutingAbility = nullptr; - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); - if (!ActivationEffectHandle.IsValid()) - { - GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); - ActivationEffectHandle.Reset(); - } - //remove effect. -} -/* Functions for activation effect delegates */ -void UGAAbilityBase::CancelActivation() -{ - NativeCancelActivation(); -} -void UGAAbilityBase::NativeCancelActivation() -{ - if (!ActivationEffectHandle.IsValid()) - return; - - UAFAbilityComponent* AttrComp = DefaultContext.InstigatorComp.Get(); - AbilityComponent->ExecutingAbility = nullptr; - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); - if (GetEffectsComponent()) - { - GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); - AbilityState = EAFAbilityState::Waiting; - ActivationEffectHandle.Reset(); - } - OnActivationCancel(); -} - -bool UGAAbilityBase::IsWaitingForConfirm() -{ - if (OnConfirmDelegate.IsBound()) - return true; - else - return false; -} -void UGAAbilityBase::ConfirmAbility() -{ - if (OnConfirmDelegate.IsBound()) - OnConfirmDelegate.Broadcast(); - OnConfirmDelegate.Clear(); - OnConfirmDelegate.RemoveAll(this); -} - -bool UGAAbilityBase::ApplyCooldownEffect() -{ - if (!CooldownEffect.GetSpec()) - { - return false; - } - FAFFunctionModifier Modifier; - - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); - GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); - - CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( - CooldownEffect - , CooldownEffectHandle - , this - , POwner - , this - , Modifier); - ENetMode nm = AbilityComponent->GetOwner()->GetNetMode(); - ENetRole role = AbilityComponent->GetOwnerRole(); - - if (role >= ENetRole::ROLE_Authority) - { - ClientSetCooldownHandle(CooldownEffectHandle); - } - OnCooldownStart(); - - //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); - return false; -} -void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) -{ - //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); - OnCooldownEnd(InHandle); - CooldownEffectHandle.Reset(); -} -void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) -{ - //CooldownEffectHandle = InCooldownHandle; -} -bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) -{ - if (!ActivationEffect.GetSpec()) - return false; - FHitResult Hit(ForceInit); - - UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); - float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); - float PeriodCheck = Spec->Period.GetFloatValue(DefaultContext); - if (DurationCheck > 0 || PeriodCheck > 0) - { - bApplyActivationEffect = true; - } - - if (bApplyActivationEffect) - { - FHitResult HitIn; - if (ActivationEffectHandle.IsValid()) - ActivationEffectHandle.Reset(); - - FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); - GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); - - FAFFunctionModifier Modifier; - ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( - ActivationEffect - , ActivationEffectHandle - , this - , POwner - , this - , Modifier); - - //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) - // ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); - - - if (PeriodCheck > 0) - { - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); - GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); - //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) - // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); - } - } - else - { - NativeOnAbilityActivationFinish(FGAEffectHandle()); - } - return false; -} - -bool UGAAbilityBase::CanUseAbility() -{ - bool CanUse = true; - bool bIsOnCooldown = IsOnCooldown(); - bool bIsActivating = IsActivating(); - //if (!AbilityComponent->ExecutingAbility) - // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); - - CanUse = !bIsOnCooldown && !bIsActivating; - UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility Ability, Cooldown: %s, Activating: %s \n"), bIsOnCooldown ? TEXT("true") : TEXT("false"), bIsActivating ? TEXT("true") : TEXT("false") ); - //now Lets check tags - if (CanUse) - { - if (GetEffectsComponent()->HasAll(ActivationRequiredTags)) - { - CanUse = true; - } - //blocking takes precedence. - if (GetEffectsComponent()->HasAny(ActivationBlockedTags)) - { - CanUse = false; - } - } - - return CanUse; -} -bool UGAAbilityBase::BP_CanUseAbility() -{ - return CanUseAbility(); -} -bool UGAAbilityBase::CanReleaseAbility() -{ - bool bCanUse = true; - /*if (AbilityComponent->ExecutingAbility == this) - { - bCanUse = true; - }*/ - if (IsOnCooldown()) - { - bCanUse = false; - UE_LOG(AbilityFramework, Log, TEXT("CanReleaseAbility can't release ability is on cooldown")); - } - return bCanUse; -} - -class UGAAttributesBase* UGAAbilityBase::GetAttributes() -{ - return Attributes; -} -UAFAbilityComponent* UGAAbilityBase::GetAbilityComp() -{ - IAFAbilityInterface* OwnerAttributes = Cast(POwner); - if (OwnerAttributes) - { - return OwnerAttributes->GetAbilityComp(); - } - return nullptr; -} - -UAFEffectsComponent* UGAAbilityBase::GetEffectsComponent() -{ - IAFAbilityInterface* OwnerAttributes = Cast(POwner); - if (OwnerAttributes) - { - return OwnerAttributes->GetEffectsComponent(); - } - return nullptr; -} -UAFEffectsComponent* UGAAbilityBase::NativeGetEffectsComponent() const -{ - IAFAbilityInterface* OwnerAttributes = Cast(POwner); - if (OwnerAttributes) - { - return OwnerAttributes->NativeGetEffectsComponent(); - } - return nullptr; -} -float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const -{ - return NativeGetAttributeValue(AttributeIn); -} -float UGAAbilityBase::NativeGetAttributeValue(const FGAAttribute AttributeIn) const -{ - return Attributes->GetCurrentAttributeValue(AttributeIn); -} -float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const -{ - return Attributes->GetCurrentAttributeValue(AttributeIn); -} - -bool UGAAbilityBase::ApplyAttributeCost() -{ - FAFFunctionModifier Modifier; - if (CheckAttributeCost()) - { - for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) - { - AttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( - AttributeCost[Idx] - , AttributeCostHandle[Idx] - , POwner - , POwner - , this - , Modifier); - } - return true; - } - return false; -} -bool UGAAbilityBase::ApplyAbilityAttributeCost() -{ - //add checking if attribute goes below zero - //maybe let game specific code handle it.. - FAFFunctionModifier Modifier; - - if (CheckAbilityAttributeCost()) - { - for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) - { - AbilityAttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( - AbilityAttributeCost[Idx] - , AbilityAttributeCostHandle[Idx] - , this - , POwner - , this - , Modifier); - } - return true; - } - return false; -} -bool UGAAbilityBase::BP_ApplyAttributeCost() -{ - return ApplyAttributeCost(); -} -bool UGAAbilityBase::BP_CheckAttributeCost() -{ - return CheckAttributeCost(); -} - -bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() -{ - return ApplyAbilityAttributeCost(); -} -bool UGAAbilityBase::BP_CheckAbilityAttributeCost() -{ - return CheckAbilityAttributeCost(); -} -bool UGAAbilityBase::CheckAbilityAttributeCost() -{ - for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) - { - float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Attributes->GetFloatValue(Attribute); - if (ModValue > AttributeVal) - return false; - } - return true; -} -bool UGAAbilityBase::CheckAttributeCost() -{ - IAFAbilityInterface* Interface = Cast(POwner); - - for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) - { - float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Interface->GetAttributes()->GetFloatValue(Attribute); - if (ModValue > AttributeVal) - return false; - } - return true; -} -bool UGAAbilityBase::IsOnCooldown() -{ - bool bOnCooldown = false; - bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle); - if (bOnCooldown) - { - OnNotifyOnCooldown.Broadcast(); - } - return bOnCooldown; //temp -} -bool UGAAbilityBase::IsActivating() -{ - bool bAbilityActivating = false; - bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffect.GetHandle(this)); - bool bInActivatingState = AbilityState == EAFAbilityState::Activating; - UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); - bAbilityActivating = bHaveEffect || bInActivatingState; - - return bAbilityActivating; //temp -} -bool UGAAbilityBase::BP_IsOnCooldown() -{ - return IsOnCooldown(); -} -void UGAAbilityBase::BP_ApplyCooldown() -{ - ApplyCooldownEffect(); -} - -float UGAAbilityBase::GetCurrentActivationTime() -{ - if (ActivationEffectHandle.IsValid()) - { - if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) - { - FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); - if (Effect) - { - return Effect->GetCurrentDuration(); - } - } - //return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); - } - return 0; -} - -float UGAAbilityBase::CalculateAnimationSpeed(UAnimMontage* MontageIn) -{ - float ActivationTime = MontageIn->GetPlayLength(); - UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); - float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); - if (DurationCheck > 0) - { - ActivationTime = DurationCheck; - } - float Duration = MontageIn->GetPlayLength(); - - float PlaySpeed = Duration / ActivationTime; - return PlaySpeed; -} - - -bool UGAAbilityBase::IsNameStableForNetworking() const -{ - return bIsNameStable; -} - -void UGAAbilityBase::SetNetAddressable() -{ - bIsNameStable = true; -} - -class UWorld* UGAAbilityBase::GetWorld() const -{ - return World; -} -void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) -{ - AbilityComponent->PlayMontage(MontageIn, SectionName, Speed); -} - -//replication -void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly can be infered upon replication. - //does other players need info about this ? - DOREPLIFETIME(UGAAbilityBase, POwner); - DOREPLIFETIME(UGAAbilityBase, PCOwner); - DOREPLIFETIME(UGAAbilityBase, AICOwner); - DOREPLIFETIME(UGAAbilityBase, AvatarActor); - //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. - -} -int32 UGAAbilityBase::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) -{ - if (HasAnyFlags(RF_ClassDefaultObject)) - { - return FunctionCallspace::Local; - } - check(POwner != NULL); - return POwner->GetFunctionCallspace(Function, Parameters, Stack); -} -bool UGAAbilityBase::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) -{ - check(!HasAnyFlags(RF_ClassDefaultObject)); - check(POwner != NULL); - - - UNetDriver* NetDriver = POwner->GetNetDriver(); - if (NetDriver) - { - NetDriver->ProcessRemoteFunction(POwner, Function, Parameters, OutParms, Stack, this); - return true; - } - - return false; -} - -void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) -{ - AbilityComponent->NativeInputPressed(ActionName); -} -void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) -{ - AbilityComponent->NativeInputReleased(ActionName); -} - -bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) -{ - bool bHaveTag = false; - if (IAFAbilityInterface* Interface = Cast(Target)) - { - if (UAFEffectsComponent* Comp = GetEffectsComponent()) - { - if (Comp->HasTag(Tag)) - { - bHaveTag = true; - } - } - } - return bHaveTag; -} -bool UGAAbilityBase::HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag) -{ - bool bHaveTag = false; - if (IAFAbilityInterface* Interface = Cast(Target)) - { - if (UAFEffectsComponent* Comp = GetEffectsComponent()) - { - if (Comp->HasAny(Tag)) - { - bHaveTag = true; - } - } - } - return bHaveTag; -} -/* Tracing Helpers Start */ -bool UGAAbilityBase::LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit) -{ - ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); - static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); - FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); - - bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); - return bHit; -} -bool UGAAbilityBase::LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) -{ - FVector Start = FVector::ZeroVector; - if (OwnerCamera) - { - Start = OwnerCamera->GetComponentLocation(); - } - else - { - FRotator UnusedRot; - POwner->GetActorEyesViewPoint(Start, UnusedRot); - } - FVector End = (POwner->GetBaseAimRotation().Vector() * Range) + Start; - ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); - static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); - FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); - bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); -#if ENABLE_DRAW_DEBUG - if (DrawDebugType != EDrawDebugTrace::None) - { - bool bPersistent = DrawDebugType == EDrawDebugTrace::Persistent; - float LifeTime = (DrawDebugType == EDrawDebugTrace::ForDuration) ? DrawTime : 0.f; - - // @fixme, draw line with thickness = 2.f? - if (bHit && OutHit.bBlockingHit) - { - // Red up to the blocking hit, green thereafter - ::DrawDebugLine(World, Start, OutHit.ImpactPoint, TraceColor.ToFColor(true), bPersistent, LifeTime); - ::DrawDebugLine(World, OutHit.ImpactPoint, End, TraceHitColor.ToFColor(true), bPersistent, LifeTime); - ::DrawDebugPoint(World, OutHit.ImpactPoint, 16, TraceColor.ToFColor(true), bPersistent, LifeTime); - } - else - { - // no hit means all red - ::DrawDebugLine(World, Start, End, TraceColor.ToFColor(true), bPersistent, LifeTime); - } - } -#endif - return bHit; -} -bool UGAAbilityBase::LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) -{ - return false; -} -bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) -{ - return false; -} -/* Tracing Helpers End */ - -//Helpers -float UGAAbilityBase::GetActivationRemainingTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationRemainingTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationCurrentTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationCurrentTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); -} -float UGAAbilityBase::GetActivationEndTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle); -} -float UGAAbilityBase::BP_GetActivationRemainingTime() -{ - return GetActivationRemainingTime(); -} -float UGAAbilityBase::BP_GetActivationRemainingTimeNormalized() -{ - return GetActivationRemainingTimeNormalized(); -} -float UGAAbilityBase::BP_GetActivationCurrentTime() -{ - return GetActivationCurrentTime(); -} -float UGAAbilityBase::BP_GetActivationCurrentTimeNormalized() -{ - return GetActivationCurrentTimeNormalized(); -} -float UGAAbilityBase::BP_GetActivationEndTime() -{ - return GetActivationEndTime(); -} - - -float UGAAbilityBase::GetCooldownRemainingTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownCurrentTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); -} -float UGAAbilityBase::GetCooldownEndTime() const -{ - return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle); -} -float UGAAbilityBase::BP_GetCooldownRemainingTime() -{ - return GetCooldownRemainingTime(); -} -float UGAAbilityBase::BP_GetCooldownRemainingTimeNormalized() -{ - return GetCooldownRemainingTimeNormalized(); -} -float UGAAbilityBase::BP_GetCooldownCurrentTime() -{ - return GetCooldownCurrentTime(); -} -float UGAAbilityBase::BP_GetCooldownCurrentTimeNormalized() -{ - return GetCooldownCurrentTimeNormalized(); -} -float UGAAbilityBase::BP_GetCooldownEndTime() -{ - return GetCooldownEndTime(); -} - -AActor* UGAAbilityBase::BP_GetAvatar() -{ - return AvatarActor; -} - - -void UGAAbilityBase::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) -{ - if (!InstanceName.IsNone()) - { - AbilityTasks.Add(InstanceName, TaskIn); - } -}; -void UGAAbilityBase::AddReplicatedTask(class UAFTaskBase* TaskIn) -{ - AbilityComponent->ReplicatedTasks.Add(TaskIn); -} -void UGAAbilityBase::OnLatentTaskRemoved(class UAFTaskBase* TaskIn) -{ -}; - -void UGAAbilityBase::OnLatentTaskActivated(class UAFTaskBase* TaskIn) -{ -}; -void UGAAbilityBase::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) -{ -}; - -class UAFTaskBase* UGAAbilityBase::GetCachedLatentAction(FName TaskName) -{ - return AbilityTasks.FindRef(TaskName); -} -class UGAAbilityTask* UGAAbilityBase::GetAbilityTask(const FName& InName) -{ - UAFTaskBase* result = AbilityTasks.FindRef(InName); - return Cast(result); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h deleted file mode 100644 index 91519ad..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBase.h +++ /dev/null @@ -1,622 +0,0 @@ -#pragma once -#include "GAGlobalTypes.h" -#include "Effects/GAGameEffect.h" -#include "GameplayTasksComponent.h" -#include "GameplayTask.h" -#include "GameplayTaskOwnerInterface.h" -#include "Attributes/GAAttributesBase.h" -#include "AFAbilityInterface.h" -#include "AFAbilityActivationSpec.h" -#include "AssetBundleData.h" -#include "SubclassOf.h" -#include "LatentActions/AFLatentInterface.h" - -#include "GAAbilityBase.generated.h" - -/* - TODO:: - 1. Add virtual functions, for default behaviours inside ability. - And figure out some clever names for them. Functions like: - ExecuteAbility() - Possibly default input functions. - The interface for it, is not yet fully determined. - It would be best if the functions and names of them, made sense.. For both AI and player - pawns. - 2. Add linked abilities. I'm not 100% sure if it really should be default functionality, - but the idea is that after first ability is executed, it will automatically set next, ability - for execution in chain, and so on, until last ability. Last ability will, simply back to first. - This can be implement as very simple linked list (though I'm not sure about nice BP workflow), - at ability level, OR it can be implemented at component level as queue. - But, from game design perspective implementation on ability level makes more sense. - - Moar TODO: (idk, if the above is still relevelant). - 1. Add simple tracing directly inside ability. Aside from targeting tasks. - - 2. Add caching for effects, so we don;'t create new ones every time, just reference handle. -*/ -/* - Base class for abilities. It will only implement few generic virtual functions, needed by all - abilities. - - Ability is what actor can do, not nessesarly, how actor will go about doing it. - For example we can have jump ability, which is nothing else, than object encapsulating, - access jump function inside Movement Component. - - This way you can give actors, certain abilities, which they can then used based on - some critera (for example defined in Blackboard and Behaviour tree), and if it is - possible for actor to perform ability, he will do it (though, one must be careful to - give abilities, which can be performed by actors, an ordinary actor, can't jump). - - More complicated abilities, can be actions in their own right. Like spells. - - Abilities are using state machine, combined with effects, to perform actions, like - casting, channeling etc. - It needs to be better explained on how each state makes use of effect parameters (Duration, Period). -*/ -DECLARE_MULTICAST_DELEGATE(FGASSimpleAbilityDynamicDelegate); - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASGenericAbilityDelegate); - -USTRUCT() -struct FGAActiationInfo -{ - GENERATED_USTRUCT_BODY(); - - UPROPERTY() - float TimeStamp; - UPROPERTY() - float Duration; - UPROPERTY() - float Period; - UPROPERTY() - bool bApplyActivationEffect; - - inline void SetActivationInfo(float TimeStampIn, float DurationIn, float PeriodIn, - bool bApplyActivationEffectIn) - { - TimeStamp = TimeStampIn; - Duration = DurationIn; - Period = PeriodIn; - bApplyActivationEffect = bApplyActivationEffectIn; - //always increment to make sure it is replicated. - ForceReplication++; - } - - UPROPERTY() - int8 ForceReplication; -}; - -enum EAFAbilityState -{ - Waiting, - Activating -}; - -UCLASS(BlueprintType, Blueprintable) -class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInterface, public IAFLatentInterface -{ - GENERATED_BODY() -public: - - /* - Since each ability is instanced per owner, and cannot be activated multiple times (ie, to run in background), - we can assume that PredictionHandle will always be unique per activation. - */ - FAFPredictionHandle PredictionHandle; - /* By default all abilities are considered to be replicated. */ - UPROPERTY(EditAnywhere, Category = "Replication") - bool bReplicate; - - bool bIsNameStable; - - //possibly map TMap ? - UPROPERTY() - TSet ActiveTasks; - /* List of tasks, this ability have. */ - UPROPERTY() - TMap AbilityTasks; - - /* - Delegate is used to confirm ability execution. - After confirming ability will proceed to activation state and either casts instatly or start - casting effect. - */ - FGASSimpleAbilityDynamicDelegate OnConfirmDelegate; - /* - Delegate which is called after ability is confirmed and then cast time ended. - */ - FGASSimpleAbilityDynamicDelegate OnConfirmCastingEndedDelegate; - FSimpleDelegate ConfirmDelegate; - - /* Attributes specific to ability. */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "AbilityFramework|Abilities") - UGAAttributesBase* Attributes; - - UPROPERTY() - class UWorld* World; - /* - Replicated to everyone because we will need it, to determine cosmetic stuff on clients. - */ - /* - */ - UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") - APawn* POwner; - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") - APlayerController* PCOwner; - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") - class AAIController* AICOwner; - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") - class UAFAbilityComponent* AbilityComponent; - - /* - Physical reprsentation of ability in game world. It might be sword, gun, or character. - What differs it from pawn or controller is that Avatar is actually used by ability to perform actions. - - It will need some common interfaces for getting data out. - */ - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") - class AActor* AvatarActor; - - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") - UCameraComponent* OwnerCamera; - - FGAEffectContext DefaultContext; - - /* - Tags applied to instigator of this ability, for duration of cooldown. - Duration of this effect equals cooldown of ability. - */ - UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") - FAFPropertytHandle CooldownEffect; - FGAEffectHandle CooldownEffectHandle; - /* - Tags applied to the time of activation ability. - Only applies to abilities, which are not instant (for now). - Though even instant abilities have animation time, - they probabaly never apply activation tags, since - main usecase for those tags is to make other abilities - being able to interrupt them. - All abilities with casting/channeling time use it. - - Add Periodic Effect ? (For abilities with period). - */ - UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") - FAFPropertytHandle ActivationEffect; - FGAEffectHandle ActivationEffectHandle; - - /* - These attributes will be reduced by specified amount when ability is activated. - Attribute cost from Ability Owner attributes - */ - UPROPERTY(EditAnywhere, Category = "Config") - TArray AttributeCost; - TArray AttributeCostHandle; - /* - Attribute cost from ability own attributes - */ - UPROPERTY(EditAnywhere, Category = "Config") - TArray AbilityAttributeCost; - TArray AbilityAttributeCostHandle; - - UPROPERTY(AssetRegistrySearchable) - FName AbilityTagSearch; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTag AbilityTag; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer OwnedTags; - /* - These tags are added to owner while ability is activating (or channeled). - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer ActivationAddedTags; - /* - These tags must be present on onwer to activate this ability. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer ActivationRequiredTags; - /* - If any of these tags is present ability activation is blocked. - */ - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") - FGameplayTagContainer ActivationBlockedTags; - -public: //because I'm to lazy to write all those friend states.. - UFUNCTION() - void OnActivationEffectPeriod(FGAEffectHandle InHandle); - - /* Replication counters for above events. */ - - - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnInputPressedDelegate; - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnInputReleasedDelegate; - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnActivateBeginDelegate; - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnActivationFinishedDelegate; - - UPROPERTY(BlueprintAssignable) - FGASGenericAbilityDelegate OnNotifyOnCooldown; - - /* Stub, I think replicating montage directly from ability will be better, as abilities are replicated regardless. */ - UPROPERTY() - UAnimMontage* RepMontage; -protected: - EAFAbilityState AbilityState; - -public: - UGAAbilityBase(const FObjectInitializer& ObjectInitializer); - - virtual void PostInitProperties() override; - - virtual void Serialize(FArchive& Ar) override; - // UObject interface - virtual FPrimaryAssetId GetPrimaryAssetId() const override; - virtual void PostLoad() override; - -#if WITH_EDITORONLY_DATA - /** This scans the class for AssetBundles metadata on asset properties and initializes the AssetBundleData with InitializeAssetBundlesFromMetadata */ - virtual void UpdateAssetBundleData(); - - /** Updates AssetBundleData */ - virtual void PreSave(const class ITargetPlatform* TargetPlatform) override; - -protected: - /** Asset Bundle data computed at save time. In cooked builds this is accessible from AssetRegistry */ - UPROPERTY() - FAssetBundleData AssetBundleData; -#endif -public: -#if WITH_EDITOR - virtual void PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) override; -#endif // WITH_EDITOR - - void UpdateAssetRegistryInfo(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); - - void InitAbility(); -public: - UFUNCTION() - void OnAttributeSetReplicated(); - //called on both server and client after InitAbility(); - virtual void OnAbilityInited(); - - /* - Called on server and client, after ability has been bound to some input. - */ - virtual void OnAbilityInputReady() {}; - - /* - * @call Order: - * Previous Function: FGASAbilityContainer::HandleInputPressed - * Next Function: UGAAbilityBase::OnInputPressed - * - * Called on both Client and Server. - * - * @param ActionName - Name of action which tirggered this ability - * @param InPredictionHandle - Prediction Handle Generate By Client - */ - void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); - /* - * @call Order: - * Previous Function: UGAAbilityBase::OnNativeInputPressed - * Next Function: Multiple Choices. Next function is usually called from within Ability Blueprint - * Default Choices: - * UGAAbilityBase::StartActivation - * UGAAbilityBase::CanUseAbility - * Custom Function - * - * Called on both Client and Server. - * - * @param ActionName - Name of action which tirggered this ability - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnInputPressed(FGameplayTag ActionName); - - void OnNativeInputReleased(FGameplayTag ActionName); - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnInputReleased(FGameplayTag ActionName); - - - - - void NativeOnAbilityConfirmed(); - - - - /* - * @call Order: - * Previous Function: UGAAbilityBase::StartActivation - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - * - * Called on both Client and Server to indicate that ability is finished. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivationFinished(); - - /* - * @call Order: - * Previous Function: (Blueprint) UGAAbilityBase::OnInputPressed - * Next Function: UGAAbilityBase::NativeOnBeginAbilityActivation - * - * Called on both Client and Server. - * - * @param bApplyActivationEffect - Should apply activation effect to Owner. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void StartActivation(bool bApplyActivationEffect); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::StartActivation - * Next Function: UGAAbilityBase::ApplyActivationEffect - * Next Function: (Blueprint) UGAAbilityBase::OnActivate - * - * Called on both Client and Server. - * - * @param bApplyActivationEffect - Should apply activation effect to Owner. - */ - virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - - * called when activation effect finishes (or immedietly, if there was no activation effect applied). - * Next Function: (Blueprint) Custom Functions - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point - * finish ability. - * - * Called on both Client and Server. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivate(); - - /* Event called when ability activation has been canceled. */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnActivationCancel(); - /* - * @call Order: - * Previous Function: Called if Periodic effect has been applied and is active. Otherwise inactive. - * called when activation effect finishes (or immedietly, if there was no activation effect applied). - * Next Function: (Blueprint) Custom Functions - * - * Called on both Client and Server. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnPeriod(); - - - - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnCooldownStart(); - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnCooldownEnd(FGAEffectHandle InHandle); - - void NativeOnCooldownEnd(FGAEffectHandle InHandle); - - UFUNCTION() - void OnCooldownEffectExpired(); - UFUNCTION() - void NativeOnAbilityActivationFinish(FGAEffectHandle InHandle); - UFUNCTION() - void NativeOnAbilityActivationCancel(); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - - * called when activation effect finishes (or immedietly, if there was no activation effect applied). - * Next Function: (Blueprint) Custom Functions - * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point - * finish ability. - * - * Called to finish ability and start clean up. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void FinishAbility(); - /* - * @call Order: - * Previous Function: UGAAbilityBase::FinishAbility - * Next Function: (Blueprint) UGAAbilityBase::OnAbilityFinished - * - * Called to finish ability and start clean up. - */ - void NativeFinishAbility(); - - /* - * @call Order: - * Previous Function: UGAAbilityBase::NativeFinishAbility - * Next Function: (Blueprint) Custom Functions - * - * Called when ability is finished. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnAbilityFinished(); - /* - Stop effect activation and remove activation effect. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void CancelActivation(); - void NativeCancelActivation(); - - bool IsWaitingForConfirm(); - void ConfirmAbility(); - - bool CanUseAbility(); - bool CanReleaseAbility(); - - UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") - bool BP_CanUseAbility(); - - /** IAFAbilityInterface Begin */ - virtual class UGAAttributesBase* GetAttributes() override; - virtual class UAFAbilityComponent* GetAbilityComp() override; - virtual class UAFEffectsComponent* GetEffectsComponent() override; - virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") - virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; - virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; - virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; - virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; - virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - , FGAEffectProperty& InProperty) override - { - if (!Attributes) - { - UE_LOG(AFAbilities, Log, TEXT("ModifyAttribute Ability Attributes INVALID")); - return; - } - Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); - }; - virtual FAFPredictionHandle GetPredictionHandle() override; - /* IAFAbilityInterface End **/ - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") - virtual float GetAttributeVal(FGAAttribute AttributeIn) const; - -public: //protected ? - bool ApplyCooldownEffect(); - UFUNCTION(Client, Reliable) - void ClientSetCooldownHandle(FGAEffectHandle InCooldownHandle); - void ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle); - - bool ApplyActivationEffect(bool bApplyActivationEffect); - bool ApplyAttributeCost(); - bool ApplyAbilityAttributeCost(); - bool CheckAbilityAttributeCost(); - bool CheckAttributeCost(); - bool IsOnCooldown(); - bool IsActivating(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Is On Cooldown"), Category = "AbilityFramework|Abilities") - bool BP_IsOnCooldown(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Cooldown"), Category = "AbilityFramework|Abilities") - void BP_ApplyCooldown(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_ApplyAttributeCost(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_CheckAttributeCost(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_ApplyAbilityAttributeCost(); - - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Ability Attribute Cost"), Category = "AbilityFramework|Abilities") - bool BP_CheckAbilityAttributeCost(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - float GetCurrentActivationTime(); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - float CalculateAnimationSpeed(UAnimMontage* MontageIn); - - /* Replication */ - bool IsNameStableForNetworking() const override; - - bool IsSupportedForNetworking() const override - { - return bReplicate; - } - void SetNetAddressable(); - -public: - int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; - virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") - void ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); - - virtual class UWorld* GetWorld() const override; - - inline void AddAbilityTask(FName InName, class UAFTaskBase* InTask) - { - if (!AbilityTasks.Contains(InName)) - { - AbilityTasks.Add(InName, InTask); - } - } - class UGAAbilityTask* GetAbilityTask(const FName& InName); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") - bool HaveGameplayTag(AActor* Target, const FGameplayTag& Tag); - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") - bool HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag); - - /* Tracing Helpers Start */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit); - /* Traces location from owner camera position if no camera available traces from eyes */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); - /* Traces from ability avatar socket. */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); - /* Make first trace from camera location and then second trace from avatar socket in direction of first trace. */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") - bool LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, - EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); - /* Tracing Helpers End */ - - - //Helpers - float GetActivationRemainingTime() const; - float GetActivationRemainingTimeNormalized() const; - float GetActivationCurrentTime() const; - float GetActivationCurrentTimeNormalized() const; - float GetActivationEndTime() const; - - UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationRemainingTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationCurrentTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetActivationEndTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetActivationEndTime(); - - - float GetCooldownRemainingTime() const; - float GetCooldownRemainingTimeNormalized() const; - float GetCooldownCurrentTime() const; - float GetCooldownCurrentTimeNormalized() const; - float GetCooldownEndTime() const; - - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownRemainingTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownRemainingTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownCurrentTime(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownCurrentTimeNormalized(); - UFUNCTION(BlueprintPure, DisplayName = "GetCooldownEndTime", Category = "AbilityFramework|Abilities|Helpers") - float BP_GetCooldownEndTime(); - - UFUNCTION(BlueprintCallable, DisplayName = "Get Avatar", Category = "AbilityFramework|Abilities|Helpers") - AActor* BP_GetAvatar(); - - virtual void OnAvatarReady() {}; - - - /* IAFLatentInterface */ - virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn); - virtual void AddReplicatedTask(class UAFTaskBase* TaskIn); - virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn); - - virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn); - virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn); - - virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); - /* IAFLatentInterface */ -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp deleted file mode 100644 index 71133ea..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GAAbilityBlueprint.h" - -////////////////////////////////////////////////////////////////////////// -// UGameplayAbilityBlueprint - -UGAAbilityBlueprint::UGAAbilityBlueprint(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#if WITH_EDITOR - -/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ -UGAAbilityBlueprint* UGAAbilityBlueprint::FindRootGameplayAbilityBlueprint(UGAAbilityBlueprint* DerivedBlueprint) -{ - UGAAbilityBlueprint* ParentBP = NULL; - - // Determine if there is a gameplay ability blueprint in the ancestry of this class - for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) - { - if (UGAAbilityBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) - { - ParentBP = TestBP; - } - } - - return ParentBP; -} - -#endif diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h deleted file mode 100644 index e1c6fef..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/GAAbilityBlueprint.h +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Engine/Blueprint.h" -#include "GAAbilityBlueprint.generated.h" - -/** - * Game Ability Blueprint - */ - -UCLASS(BlueprintType) -class ABILITYFRAMEWORK_API UGAAbilityBlueprint : public UBlueprint -{ - GENERATED_UCLASS_BODY() - -#if WITH_EDITOR - - // UBlueprint interface - virtual bool SupportedByDefaultBlueprintFactory() const override - { - return false; - } - // End of UBlueprint interface - - /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ - static UGAAbilityBlueprint* FindRootGameplayAbilityBlueprint(UGAAbilityBlueprint* DerivedBlueprint); - -#endif -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp deleted file mode 100644 index dee0062..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp +++ /dev/null @@ -1,30 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityTask_SpawnProjectile.h" - - - - -UAFAbilityTask_SpawnProjectile* UAFAbilityTask_SpawnProjectile::Ability_SpawnProjectile(UGAAbilityBase* WorldContextObject, - FName InTaskName, - FVector InStartLocation, - FVector InEndLocation, - float InLaunchSpeed, - float InOverrideGravityZ, - EAFPRojectileSpawnTraceOption InTraceOption, - float InCollisionRadius, - bool InbFavorHighArc, - bool InbDrawDebug) -{ - auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); - MyObj->StartLocation = InStartLocation; - MyObj->EndLocation = InEndLocation; - MyObj->LaunchSpeed = InLaunchSpeed; - MyObj->OverrideGravityZ = InOverrideGravityZ; - MyObj->TraceOption = InTraceOption; - MyObj->CollisionRadius = InCollisionRadius; - MyObj->bFavorHighArc = InbFavorHighArc; - MyObj->bDrawDebug = InbDrawDebug; - return MyObj; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h deleted file mode 100644 index 5d3e7ae..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h +++ /dev/null @@ -1,58 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Abilities/Tasks/GAAbilityTask.h" -#include "AFAbilityTask_SpawnProjectile.generated.h" - -UENUM() -enum class EAFPRojectileSpawnTraceOption : uint8 -{ - DoNotTrace, - TraceFullPath, - OnlyTraceWhileAscending, -}; - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FAFOnPRojectileSpawned); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFAbilityTask_SpawnProjectile : public UGAAbilityTask -{ - GENERATED_BODY() -public: - UPROPERTY() - FVector StartLocation; - UPROPERTY() - FVector EndLocation; - UPROPERTY() - float LaunchSpeed; - UPROPERTY() - float OverrideGravityZ; - UPROPERTY() - EAFPRojectileSpawnTraceOption TraceOption; - UPROPERTY() - float CollisionRadius; - UPROPERTY() - bool bFavorHighArc; - UPROPERTY() - bool bDrawDebug; - - UPROPERTY(BlueprintAssignable) - FAFOnPRojectileSpawned Played; -public: - static UAFAbilityTask_SpawnProjectile* Ability_SpawnProjectile(UGAAbilityBase* WorldContextObject, - FName InTaskName, - FVector InStartLocation, - FVector InEndLocation, - float InLaunchSpeed, - float InOverrideGravityZ, - EAFPRojectileSpawnTraceOption InTraceOption, - float InCollisionRadius, - bool InbFavorHighArc, - bool InbDrawDebug); - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp deleted file mode 100644 index 190da1a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.cpp +++ /dev/null @@ -1,12 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../../AbilityFramework.h" -#include "../GAAbilityBase.h" -#include "GAAbilityTask.h" - -UGAAbilityTask::UGAAbilityTask(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - bIsReplicated = false; - SetFlags(RF_StrongRefOnFrame); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h deleted file mode 100644 index b989524..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask.h +++ /dev/null @@ -1,95 +0,0 @@ -#pragma once -#include "GameplayTask.h" -#include "GAAbilityBase.h" -#include "AFAbilityComponent.h" - -#include "LatentActions/AFTaskBase.h" - -#include "GAAbilityTask.generated.h" -/* - AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and - the should be activated from ability. - Then can perform tasks, like spawn tagetting helpers (splines, circles), spawn actors, - gather targeting data etc. - - Should they be activated automatically after ability is initialized, (it'e ability enterted in - active state, which means it's ready to be fired and display helpers, but did not yet received input, - or should designer in blueprint decide when to launch actions ?). -*/ - -UCLASS(BlueprintType, Blueprintable, Within=GAAbilityBase) -class ABILITYFRAMEWORK_API UGAAbilityTask : public UAFTaskBase -{ - GENERATED_BODY() - friend struct FAFAbilityTaskMessageTick; -public: - uint8 bIsReplicated : 1; - /* Ability owning this task */ - TWeakObjectPtr Ability; - /* Ability owning this task */ - TWeakObjectPtr AbilityComponent; -public: - - template - static T* NewAbilityTask(UGAAbilityBase* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) - { - check(WorldContextObject); - - T* MyObj = nullptr; - UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); - MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); - - MyObj->Ability = ThisAbility; - MyObj->AbilityComponent = ThisAbility->AbilityComponent; - - return MyObj; - } - UGAAbilityTask(const FObjectInitializer& ObjectInitializer); - bool IsReplicated() - { - return bIsReplicated; - } - -protected: - bool IsClient() - { - APawn* POwner = Ability->POwner; - if (POwner->GetNetMode() == ENetMode::NM_Client) - { - return true; - } - return false; - } - - bool IsServer() - { - APawn* POwner = Ability->POwner; - if (POwner->GetNetMode() == ENetMode::NM_DedicatedServer - || POwner->GetNetMode() == ENetMode::NM_ListenServer) - { - return true; - } - return false; - } - bool IsServerOrStandalone() - { - APawn* POwner = Ability->POwner; - if (POwner->GetNetMode() == ENetMode::NM_DedicatedServer - || POwner->GetNetMode() == ENetMode::NM_ListenServer - || POwner->GetNetMode() == ENetMode::NM_Standalone) - { - return true; - } - return false; - } - - bool IsAuthority() - { - APawn* POwner = Ability->POwner; - if (POwner->Role >= ENetRole::ROLE_Authority) - { - return true; - } - return false; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp deleted file mode 100644 index c82011a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.cpp +++ /dev/null @@ -1,64 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "GAAbilityTask_CreateObject.h" - -UGAAbilityTask_CreateObject* UGAAbilityTask_CreateObject::CreateObject(UGAAbilityBase* WorldContextObject, - FName InTaskName, TSubclassOf Class, UObject* Outer) -{ - auto MyObj = NewAbilityTask(WorldContextObject); - //if(MyObj) - // MyObj->SpawnObject(WorldContextObject, InClass, Outer); - //MyObj->CachedTargetDataHandle = TargetData; - return MyObj; -} - -// --------------------------------------------------------------------------------------- - -bool UGAAbilityTask_CreateObject::BeginSpawningActor(UGAAbilityBase* WorldContextObject, - TSubclassOf Class, UObject*& SpawnedActor) -{ - //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) - //{ - //UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject); - //if (World) - //{ - SpawnedActor = NewObject(WorldContextObject, Class); - //} - //} - - if (SpawnedActor == nullptr) - { - Failure.Broadcast(nullptr); - return false; - } - UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); - return true; -} - -void UGAAbilityTask_CreateObject::FinishSpawningActor(UGAAbilityBase* WorldContextObject, UObject* SpawnedActor) -{ - if (SpawnedActor) - { - FTransform SpawnTransform;// = AbilitySystemComponent->GetOwner()->GetTransform(); - - //if (FGameplayAbilityTargetData* LocationData = CachedTargetDataHandle.Get(0)) //Hardcode to use data 0. It's OK if data isn't useful/valid. - //{ - // //Set location. Rotation is unaffected. - // if (LocationData->HasHitResult()) - // { - // SpawnTransform.SetLocation(LocationData->GetHitResult()->Location); - // } - // else if (LocationData->HasEndPoint()) - // { - // SpawnTransform.SetLocation(LocationData->GetEndPoint()); - // } - //} - - //SpawnedActor->FinishSpawning(SpawnTransform); - - Success.Broadcast(SpawnedActor); - } - UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); - EndTask(); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h deleted file mode 100644 index 3fbdd2c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_CreateObject.h +++ /dev/null @@ -1,32 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_CreateObject.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASSpawnObjectDelegate, class UObject*, SpawnedObject); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_CreateObject : public UGAAbilityTask -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FGASSpawnObjectDelegate Success; - UPROPERTY(BlueprintAssignable) - FGASSpawnObjectDelegate Failure; - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_CreateObject* CreateObject(UGAAbilityBase* WorldContextObject, - FName InTaskName, TSubclassOf Class, UObject* Outer); - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - bool BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, class UObject*& SpawnedActor); - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - void FinishSpawningActor(UGAAbilityBase* WorldContextObject, class UObject* SpawnedActor); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp deleted file mode 100644 index 3ab4e2e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp +++ /dev/null @@ -1,50 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "../../AFAbilityComponent.h" -#include "GAAbilityTask_PlayMontage.h" - -UGAAbilityTask_PlayMontage* UGAAbilityTask_PlayMontage::AbilityPlayMontage(UGAAbilityBase* WorldContextObject, - FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, - bool bInUseActivationTime) -{ - auto MyObj = NewAbilityTask(WorldContextObject); - MyObj->Montage = MontageIn; - MyObj->SectionName = SectionNameIn; - MyObj->PlayRate = PlayRateIn; - MyObj->bUseActivationTime = bInUseActivationTime; - return MyObj; -} - -void UGAAbilityTask_PlayMontage::Activate() -{ - AbilityComponent->OnAbilityNotifyBegin.Unbind(); - AbilityComponent->OnAbilityNotifyTick.Unbind(); - AbilityComponent->OnAbilityNotifyEnd.Unbind(); - - AbilityComponent->OnAbilityNotifyBegin.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastStartNotifyState); - AbilityComponent->OnAbilityNotifyTick.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastTickNotifyState); - AbilityComponent->OnAbilityNotifyEnd.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastEndNotifyState); - if (bUseActivationTime) - { - PlayRate = Ability->CalculateAnimationSpeed(Montage); - Ability->PlayMontage(Montage, SectionName, PlayRate); - } - else - { - Ability->PlayMontage(Montage, SectionName, PlayRate); - } -} - -void UGAAbilityTask_PlayMontage::BroadcastStartNotifyState(const FGameplayTag& InTag, const FName& InName) -{ - NotifyBegin.Broadcast(InTag, InName); -} -void UGAAbilityTask_PlayMontage::BroadcastEndNotifyState(const FGameplayTag& InTag, const FName& InName) -{ - NotifyTick.Broadcast(InTag, InName); -} -void UGAAbilityTask_PlayMontage::BroadcastTickNotifyState(const FGameplayTag& InTag, const FName& InName) -{ - NotifyEnd.Broadcast(InTag, InName); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h deleted file mode 100644 index 1c33398..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_PlayMontage.h +++ /dev/null @@ -1,45 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "AFAbilityTypes.h" -#include "GAAbilityTask_PlayMontage.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGASGenericMontageDelegate, FGameplayTag, Tag, FName, NotifyName); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_PlayMontage : public UGAAbilityTask -{ - GENERATED_BODY() - -public: - UPROPERTY(BlueprintReadOnly, meta = (ExposeOnSpawn = true)) - UAnimMontage* Montage; - FName SectionName; - float PlayRate; - bool bUseActivationTime; - - UPROPERTY(BlueprintAssignable) - FGASGenericMontageDelegate Played; - UPROPERTY(BlueprintAssignable) - FGASGenericMontageDelegate NotifyBegin; - UPROPERTY(BlueprintAssignable) - FGASGenericMontageDelegate NotifyTick; - UPROPERTY(BlueprintAssignable) - FGASGenericMontageDelegate NotifyEnd; - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_PlayMontage* AbilityPlayMontage(UGAAbilityBase* WorldContextObject, - FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, - bool bInUseActivationTime); - - virtual void Activate() override; - - void BroadcastStartNotifyState(const FGameplayTag& InTag, const FName& InName); - void BroadcastEndNotifyState(const FGameplayTag& InTag, const FName& InName); - void BroadcastTickNotifyState(const FGameplayTag& InTag, const FName& InName); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp deleted file mode 100644 index 1ee4cbb..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.cpp +++ /dev/null @@ -1,15 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "GAAbilityTask_Repeat.h" - - - - -UGAAbilityTask_Repeat* UGAAbilityTask_Repeat::CreateRepeatTask(UGAAbilityBase* WorldContextObject, - FName InTaskName) -{ - auto MyObj = NewAbilityTask(WorldContextObject); - //MyObj->CachedTargetDataHandle = TargetData; - return MyObj; -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h deleted file mode 100644 index 914bf6a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_Repeat.h +++ /dev/null @@ -1,24 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_Repeat.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnTaskRepeated); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_Repeat : public UGAAbilityTask -{ - GENERATED_BODY() - - UPROPERTY(BlueprintAssignable) - FGASOnTaskRepeated OnTaskRepeated; - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_Repeat* CreateRepeatTask(UGAAbilityBase* WorldContextObject, - FName InTaskName); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp deleted file mode 100644 index a075365..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp +++ /dev/null @@ -1,70 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "GAAbilityTask_SpawnActor.h" - - - - - -UGAAbilityTask_SpawnActor* UGAAbilityTask_SpawnActor::SpawnActor(UGAAbilityBase* WorldContextObject, - FName InTaskName, TSubclassOf InClass) -{ - auto MyObj = NewAbilityTask(WorldContextObject); - //MyObj->CachedTargetDataHandle = TargetData; - return MyObj; -} - -// --------------------------------------------------------------------------------------- -void UGAAbilityTask_SpawnActor::Activate() -{ - UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); - //EndTask(); -} - -bool UGAAbilityTask_SpawnActor::BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf InClass, AActor*& SpawnedActor) -{ - //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) - //{ - UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); - if (World) - { - SpawnedActor = World->SpawnActorDeferred(InClass, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); - } - //} - - if (SpawnedActor == nullptr) - { - Failure.Broadcast(nullptr); - return false; - } - UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); - return true; -} - -void UGAAbilityTask_SpawnActor::FinishSpawningActor(UGAAbilityBase* WorldContextObject, AActor* SpawnedActor) -{ - if (SpawnedActor) - { - FTransform SpawnTransform;// = AbilitySystemComponent->GetOwner()->GetTransform(); - - //if (FGameplayAbilityTargetData* LocationData = CachedTargetDataHandle.Get(0)) //Hardcode to use data 0. It's OK if data isn't useful/valid. - //{ - // //Set location. Rotation is unaffected. - // if (LocationData->HasHitResult()) - // { - // SpawnTransform.SetLocation(LocationData->GetHitResult()->Location); - // } - // else if (LocationData->HasEndPoint()) - // { - // SpawnTransform.SetLocation(LocationData->GetEndPoint()); - // } - //} - - SpawnedActor->FinishSpawning(SpawnTransform); - - Success.Broadcast(SpawnedActor); - } - UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); - //EndTask(); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h deleted file mode 100644 index af30e2f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_SpawnActor.h +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_SpawnActor.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASSpawnActorDelegate, AActor*, SpawnedActor); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_SpawnActor : public UGAAbilityTask -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FGASSpawnActorDelegate Success; - UPROPERTY(BlueprintAssignable) - FGASSpawnActorDelegate Failure; - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_SpawnActor* SpawnActor(UGAAbilityBase* WorldContextObject, - FName InTaskName, TSubclassOf Class); - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - bool BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, AActor*& SpawnedActor); - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - void FinishSpawningActor(UGAAbilityBase* WorldContextObject, AActor* SpawnedActor); - - virtual void Activate() override; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp deleted file mode 100644 index 9221e99..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.cpp +++ /dev/null @@ -1,154 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "../GAAbilityBase.h" -#include "GAAbilityTask_TargetData.h" - - -UGAAbilityTask_TargetData* UGAAbilityTask_TargetData::CreateTargetDataTask(UGAAbilityBase* WorldContextObject, - FName InTaskName, - bool bDrawDebug, - bool bDrawCorrectedDebug, - bool bUseCorrectedTrace, - EGASConfirmType ConfirmTypeIn, - float Range) -{ - auto MyObj = NewAbilityTask(WorldContextObject); - - if (MyObj) - { - MyObj->Range = Range; - MyObj->ConfirmType = ConfirmTypeIn; - MyObj->bIsTickable = false; - MyObj->bDrawDebug = bDrawDebug; - MyObj->bDrawCorrectedDebug = bDrawCorrectedDebug; - MyObj->bUseCorrectedTrace = bUseCorrectedTrace; - } - return MyObj; -} - -void UGAAbilityTask_TargetData::Activate() -{ - switch (ConfirmType) - { - case EGASConfirmType::Instant: - { - FHitResult Hit = LineTrace(); - OnReceiveTargetData.Broadcast(Hit); - EndTask(); - break; - } - case EGASConfirmType::WaitForConfirm: - { - if (Ability.IsValid()) - { - if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) - { - Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetData::OnConfirm); - bIsTickable = true; - } - if (!Ability->OnConfirmCastingEndedDelegate.IsBoundToObject(this)) - { - Ability->OnConfirmCastingEndedDelegate.AddUObject(this, &UGAAbilityTask_TargetData::OnCastEndedConfirm); - } - } - break; - } - } -} - -// --------------------------------------------------------------------------------------- - -void UGAAbilityTask_TargetData::OnConfirm() -{ - FHitResult Hit(ForceInit);// = LineTrace(); - OnConfirmed.Broadcast(Hit); - Ability->OnConfirmDelegate.RemoveAll(this); -} -void UGAAbilityTask_TargetData::OnCastEndedConfirm() -{ - FHitResult Hit = LineTrace(); - OnReceiveTargetData.Broadcast(Hit); - bIsTickable = false; - EndTask(); -} -void UGAAbilityTask_TargetData::Tick(float DeltaTime) -{ - //FHitResult HitOut = LineTrace(); -} - -FHitResult UGAAbilityTask_TargetData::LineTrace() -{ - FHitResult HitOut; - APlayerController* PC = Ability->PCOwner; - APawn* P = Ability->POwner; - UCameraComponent* Camera = Ability->OwnerCamera; - FVector TraceStart; - FRotator UnusedRot; - if (PC) - { - PC->PlayerCameraManager->GetCameraViewPoint(TraceStart, UnusedRot); -// TraceStart = Camera->GetComponentLocation(); - } - else - { - UnusedRot = P->GetBaseAimRotation(); - TraceStart = P->GetPawnViewLocation(); - } - - FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; - UWorld* World = GetWorld(); - FCollisionQueryParams ColParams; - ColParams.AddIgnoredActor(P); - FCollisionResponseParams ColResp; - World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); - if (HitOut.bBlockingHit) - { - FHitResult NewHit; - FVector Start = P->GetPawnViewLocation(); - FVector NewDir = (HitOut.Location - Start).GetSafeNormal(); - float Distance = FVector::Dist(Start, HitOut.Location); - FVector End = Start + (NewDir * Range); - World->LineTraceSingleByChannel(NewHit, Start, End, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); - - if (bDrawCorrectedDebug) - { - DrawDebugLine(GetWorld(), Start, End, FColor::Green, true, 2);// GetWorld()->DeltaTimeSeconds); - if (NewHit.bBlockingHit) - { - DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); - DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); - } - } - } - else - { - FHitResult NewHit; - FVector Start = P->GetPawnViewLocation(); - FVector NewDir = (TraceEnd - Start).GetSafeNormal(); - float Distance = Range - FVector::Dist(TraceStart, Start); - FVector End = Start + (NewDir * Distance); - - World->LineTraceSingleByChannel(NewHit, Start, End, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); - - if (bDrawCorrectedDebug) - { - DrawDebugLine(GetWorld(), Start, End, FColor::Green, true, 2);//GetWorld()->DeltaTimeSeconds); - if (NewHit.bBlockingHit) - { - DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); - DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); - } - } - } - if (bDrawDebug) - { - if (HitOut.bBlockingHit) - { - DrawDebugLine(GetWorld(), TraceStart, HitOut.ImpactPoint, FColor::Red, true, 2);//GetWorld()->DeltaTimeSeconds); - DrawDebugPoint(GetWorld(), HitOut.Location, 8, FColor::Red, true, 2);//GetWorld()->DeltaTimeSeconds); - } - DrawDebugLine(GetWorld(), TraceStart, TraceEnd, FColor::Green, true, 2);//GetWorld()->DeltaTimeSeconds); - } - return HitOut; -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h deleted file mode 100644 index 2ce9ab4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetData.h +++ /dev/null @@ -1,64 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_TargetData.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASOnReceiveTargetData, const FHitResult&, HitResult); - -UENUM() -enum class EGASConfirmType : uint8 -{ - Instant, - WaitForConfirm -}; - - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_TargetData : public UGAAbilityTask, public FTickableGameObject -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FGASOnReceiveTargetData OnConfirmed; - UPROPERTY(BlueprintAssignable) - FGASOnReceiveTargetData OnReceiveTargetData; - - EGASConfirmType ConfirmType; - - float Range; - bool bIsTickable; - bool bDrawDebug; - bool bDrawCorrectedDebug; - bool bUseCorrectedTrace; -public: - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_TargetData* CreateTargetDataTask(UGAAbilityBase* WorldContextObject, - FName InTaskName, - bool bDrawDebug, - bool bDrawCorrectedDebug, - bool bUseCorrectedTrace, - EGASConfirmType ConfirmTypeIn, - float Range); - - virtual void Activate() override; - - UFUNCTION() - void OnConfirm(); - - UFUNCTION() - void OnCastEndedConfirm(); - - /* FTickableGameObject Begin */ - virtual void Tick(float DeltaTime) override; - virtual bool IsTickable() const override { return bIsTickable; } - virtual TStatId GetStatId() const override { RETURN_QUICK_DECLARE_CYCLE_STAT(UGAAbilityTask_TargetData, STATGROUP_Tickables); }; - /* FTickableGameObject End */ - -protected: - FHitResult LineTrace(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp deleted file mode 100644 index 1d539b4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp +++ /dev/null @@ -1,64 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "../GAAbilityBase.h" -#include "GAAbilityTask_TargetDataCircle.h" - - -UGAAbilityTask_TargetDataCircle* UGAAbilityTask_TargetDataCircle::TargetCircleDataTask(UGAAbilityBase* WorldContextObject, - FName InTaskName, EGASConfirmType ConfirmTypeIn) -{ - auto MyObj = NewAbilityTask(WorldContextObject); - - if (MyObj) - { - MyObj->ConfirmType = ConfirmTypeIn; - } - return MyObj; -} - -void UGAAbilityTask_TargetDataCircle::Activate() -{ - switch (ConfirmType) - { - case EGASConfirmType::Instant: - { - - } - case EGASConfirmType::WaitForConfirm: - { - if (Ability.IsValid()) - { - if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) - { - Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetDataCircle::OnConfirm); - } - } - } - } - //EndTask(); -} - -// --------------------------------------------------------------------------------------- - -//bool UGAAbilityTask_TargetDataCircle::BeginSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject*& SpawnedActor) -//{ -// SpawnedActor = Class.GetDefaultObject();//NewObject(WorldContext -// return true; -//} -// -//void UGAAbilityTask_TargetDataCircle::FinishSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject* SpawnedActor) -//{ -// if (SpawnedActor) -// { -// //Success.Broadcast(SpawnedActor); -// } -// UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); -// ReadyForActivation(); -//} - -void UGAAbilityTask_TargetDataCircle::OnConfirm() -{ - //TargetObj2->GetTarget(); - EndTask(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h deleted file mode 100644 index ea39110..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h +++ /dev/null @@ -1,40 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_TargetData.h" -#include "GAAbilityTask_TargetDataCircle.generated.h" - -//DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASOnReceiveTargetData, const FHitResult&, HitResult); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataCircle : public UGAAbilityTask_TargetData -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FGASOnReceiveTargetData OnReceiveTargetDataCircle; - - EGASConfirmType ConfirmType; - -public: - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_TargetDataCircle* TargetCircleDataTask(UGAAbilityBase* WorldContextObject, - FName InTaskName, EGASConfirmType ConfirmTypeIn); - - virtual void Activate() override; - - //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - // bool BeginSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject*& SpawnedActor); - - //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - // void FinishSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject* SpawnedActor); - // - - UFUNCTION() - void OnConfirm(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp deleted file mode 100644 index 38115e5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp +++ /dev/null @@ -1,218 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "Abilities/GAAbilityBase.h" -#include "GAAbilityTask_TargetDataLineTrace.h" - - -UGAAbilityTask_TargetDataLineTrace* UGAAbilityTask_TargetDataLineTrace::CreateTargetDataLineTrace(UGAAbilityBase* WorldContextObject - , FName InTaskName - , ETraceTypeQuery InTraceChannel - , USkeletalMeshComponent* InSocketComponent - , FName InSocketName - , bool bDrawDebug - , EAFConfirmType ConfirmTypeIn - , float Range) -{ - auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); - - if (MyObj) - { - MyObj->TraceChannel = InTraceChannel; - MyObj->Range = Range; - MyObj->ConfirmType = ConfirmTypeIn; - MyObj->SocketComponent = InSocketComponent; - MyObj->SocketName = InSocketName; - MyObj->bIsTickable = false; - MyObj->bDrawDebug = bDrawDebug; - } - return MyObj; -} -UGAAbilityTask_TargetDataLineTrace::UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bIsReplicated = true; -} -void UGAAbilityTask_TargetDataLineTrace::Activate() -{ - LocalHitResult.Reset(1, false); - FHitResult HitData; - switch (ConfirmType) - { - case EAFConfirmType::Instant: - { - HitData = LineTrace(); - LocalHitResult = HitData; - //OnClient... Is called on both Client and server and is result of local simulation - //unconfirmed by server. This result might get overrided when data from server arrive to client - //it's good to spawn some cosmetic effects, but shouldn't be used to actually confirm hit result on client. - - //OnServer.. is confirmed by server that we got hit (or not), and should be used to show client confirmation - //for hits. - if (IsServerOrStandalone()) - { - OnClientReceiveTargetData.Broadcast(HitData); - OnServerReceiveTargetData.Broadcast(HitData); - EndTask(); - } - else - { - OnClientReceiveTargetData.Broadcast(HitData); - } - break; - } - case EAFConfirmType::WaitForConfirm: - { - if (Ability.IsValid()) - { - if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) - { - Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetDataLineTrace::OnConfirm); - bIsTickable = true; - } - if (!Ability->OnConfirmCastingEndedDelegate.IsBoundToObject(this)) - { - Ability->OnConfirmCastingEndedDelegate.AddUObject(this, &UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm); - } - } - break; - } - } - if (HitData.IsValidBlockingHit()) - { - if (AbilityComponent->GetOwnerRole() < ROLE_Authority) - { - APlayerController* PC = Ability->PCOwner; - APawn* P = Ability->POwner; - - PC->PlayerState->RecalculateAvgPing(); - float ExactPing = PC->PlayerState->ExactPing; - - FAFLineTraceData TraceData; - TraceData.ExactPing = ExactPing; - TraceData.HitActor = HitData.GetActor(); - TraceData.HitLocation = HitData.Location; - - ServerConfirmHitInfo(TraceData); - } - } -} - -void UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData) -{ - int test = 0; - FAFLineTraceConfirmData ConfirmData; - ConfirmData.bConfirmed = true; - ConfirmData.HitActor = LocalHitResult.GetActor(); - ConfirmData.HitLocation = LocalHitResult.Location; - ClientConfirmHitInfo(ConfirmData); -} -bool UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Validate(FAFLineTraceData TraceData) -{ - return true; -} - -void UGAAbilityTask_TargetDataLineTrace::ClientConfirmHitInfo_Implementation(FAFLineTraceConfirmData ConfirmData) -{ - if (ConfirmData.bConfirmed) - { - OnServerReceiveTargetData.Broadcast(LocalHitResult); - } - else - { - LocalHitResult.Actor = ConfirmData.HitActor; - LocalHitResult.Location = ConfirmData.HitLocation; - LocalHitResult.ImpactPoint = ConfirmData.HitLocation; - OnServerReceiveTargetData.Broadcast(LocalHitResult); - } -} - -// --------------------------------------------------------------------------------------- - -void UGAAbilityTask_TargetDataLineTrace::OnConfirm() -{ - FHitResult Hit = LineTrace(); - OnConfirmed.Broadcast(Hit); - Ability->OnConfirmDelegate.RemoveAll(this); -} -void UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm() -{ - FHitResult Hit = LineTrace(); - OnClientReceiveTargetData.Broadcast(Hit); - bIsTickable = false; - EndTask(); -} -void UGAAbilityTask_TargetDataLineTrace::Tick(float DeltaTime) -{ - //FHitResult HitOut = LineTrace(); -} - -FHitResult UGAAbilityTask_TargetDataLineTrace::LineTrace() -{ - FHitResult HitOut; - APlayerController* PC = Ability->PCOwner; - APawn* P = Ability->POwner; - - - UCameraComponent* Camera = Ability->OwnerCamera; - FVector TraceStart; - FRotator UnusedRot; - if (PC) - { - PC->PlayerCameraManager->GetCameraViewPoint(TraceStart, UnusedRot); -// TraceStart = Camera->GetComponentLocation(); - } - else - { - UnusedRot = P->GetBaseAimRotation(); - TraceStart = P->GetPawnViewLocation(); - } - - FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; - UWorld* World = GetWorld(); - FCollisionQueryParams ColParams; - ColParams.AddIgnoredActor(P); - FCollisionResponseParams ColResp; - ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); - World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, CollisionChannel, ColParams, ColResp); - if (HitOut.bBlockingHit) - { - FHitResult NewHit; - FVector Start = SocketComponent->GetSocketLocation(SocketName); - FVector NewDir = (HitOut.Location - Start).GetSafeNormal(); - float Distance = FVector::Dist(Start, HitOut.Location); - FVector End = Start + (NewDir * Range); - World->LineTraceSingleByChannel(NewHit, Start, End, CollisionChannel, ColParams, ColResp); - UE_LOG(AbilityFramework, Log, TEXT("UGAAbilityTask_TargetDataLineTrace::LineTrace Corrected")); - if (bDrawDebug) - { - DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1.0f); - if (NewHit.bBlockingHit) - { - DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, false, 1.0f); - DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, false, 1.0f); - } - } - } - else - { - FHitResult NewHit; - FVector Start = SocketComponent->GetSocketLocation(SocketName); - FVector NewDir = (TraceEnd - Start).GetSafeNormal(); - float Distance = Range - FVector::Dist(TraceStart, Start); - FVector End = Start + (NewDir * Distance); - - World->LineTraceSingleByChannel(NewHit, Start, End, CollisionChannel, ColParams, ColResp); - UE_LOG(AbilityFramework, Log, TEXT("UGAAbilityTask_TargetDataLineTrace::LineTrace")); - if (bDrawDebug) - { - DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1.0f); - if (NewHit.bBlockingHit) - { - DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, false, 1.0f); - DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, false, 1.0f); - } - } - } - return HitOut; -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h deleted file mode 100644 index bf137c2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h +++ /dev/null @@ -1,107 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "Components/SkeletalMeshComponent.h" -#include "GAAbilityTask_TargetDataLineTrace.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnTargetReceived, const FHitResult&, HitResult); - -UENUM() -enum class EAFConfirmType : uint8 -{ - Instant, - WaitForConfirm -}; - -USTRUCT() -struct FAFLineTraceData -{ - GENERATED_BODY() - UPROPERTY() - float ExactPing; - UPROPERTY() - AActor* HitActor; - UPROPERTY() - FVector HitLocation; -}; -USTRUCT() -struct FAFLineTraceConfirmData -{ - GENERATED_BODY() - - UPROPERTY() - uint8 bConfirmed : 1; - UPROPERTY() - AActor* HitActor; - UPROPERTY() - FVector HitLocation; -}; -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataLineTrace : public UGAAbilityTask, public FTickableGameObject -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FAFOnTargetReceived OnConfirmed; - - UPROPERTY(BlueprintAssignable) - FAFOnTargetReceived OnClientReceiveTargetData; - - UPROPERTY(BlueprintAssignable) - FAFOnTargetReceived OnServerReceiveTargetData; - - ETraceTypeQuery TraceChannel; - USkeletalMeshComponent* SocketComponent; - FName SocketName; - EAFConfirmType ConfirmType; - - float Range; - bool bIsTickable; - bool bDrawDebug; - - //Result of trace from either server or client simulation - FHitResult LocalHitResult; -public: - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_TargetDataLineTrace* CreateTargetDataLineTrace(UGAAbilityBase* WorldContextObject - , FName InTaskName - , ETraceTypeQuery InTraceChannel - , USkeletalMeshComponent* InSocketComponent - , FName InSocketName - , bool bDrawDebug - , EAFConfirmType ConfirmTypeIn - , float Range); - - UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer); - - virtual void Activate() override; - - UFUNCTION(Server, Reliable, WithValidation) - void ServerConfirmHitInfo(FAFLineTraceData TraceData); - void ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData); - bool ServerConfirmHitInfo_Validate(FAFLineTraceData TraceData); - - UFUNCTION(Client, Reliable) - void ClientConfirmHitInfo(FAFLineTraceConfirmData ConfirmData); - void ClientConfirmHitInfo_Implementation(FAFLineTraceConfirmData ConfirmData); - - UFUNCTION() - void OnConfirm(); - - UFUNCTION() - void OnCastEndedConfirm(); - - /* FTickableGameObject Begin */ - virtual void Tick(float DeltaTime) override; - virtual bool IsTickable() const override { return bIsTickable; } - virtual TStatId GetStatId() const override { RETURN_QUICK_DECLARE_CYCLE_STAT(UGAAbilityTask_TargetData, STATGROUP_Tickables); }; - /* FTickableGameObject End */ - -protected: - FHitResult LineTrace(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp deleted file mode 100644 index 58e48ce..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "../GAAbilityBase.h" -#include "GAAbilityTask_WaitForConfirm.h" - - - - -UGAAbilityTask_WaitForConfirm* UGAAbilityTask_WaitForConfirm::CreateWaitConfirmTask(UGAAbilityBase* WorldContextObject, - FName InTaskName) -{ - auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); - return MyObj; -} -void UGAAbilityTask_WaitForConfirm::Activate() -{ - if (AbilityComponent.IsValid() && Ability.IsValid()) - { - GetOuterUGAAbilityBase()->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_WaitForConfirm::OnConfirm); - } -} -void UGAAbilityTask_WaitForConfirm::Initialize() -{ - -} - -void UGAAbilityTask_WaitForConfirm::OnConfirm() -{ - Ability->OnConfirmDelegate.Clear(); - OnConfirmed.Broadcast(); - EndTask(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h deleted file mode 100644 index e81c18a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h +++ /dev/null @@ -1,30 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_WaitForConfirm.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnConfirmed); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAbilityTask_WaitForConfirm : public UGAAbilityTask -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FGASOnConfirmed OnConfirmed; - - UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") - static UGAAbilityTask_WaitForConfirm* CreateWaitConfirmTask(UGAAbilityBase* WorldContextObject, - FName InTaskName); - - virtual void Activate() override; - virtual void Initialize() override; - - UFUNCTION() - void OnConfirm(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp deleted file mode 100644 index 38f2151..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp +++ /dev/null @@ -1,84 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "GAAbilityTask_WaitTargetData.h" - - -UGAAbilityTask_WaitTargetData::UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - - -//UGAAbilityTask_WaitTargetData* UGAAbilityTask_WaitTargetData::WaitTargetData(UObject* WorldContextObject, -// FName InTaskName, TSubclassOf InClass, float InRange, ETraceTypeQuery InTraceChannel) -//{ -// auto MyObj = NewAbilityTask(WorldContextObject, "UGAAbilityTask_WaitTargetData"); -// MyObj->Range = InRange; -// MyObj->TraceChannel = InTraceChannel; -// return MyObj; -//} - -// --------------------------------------------------------------------------------------- -void UGAAbilityTask_WaitTargetData::Activate() -{ - UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); - if (Ability.IsValid()) - { - if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) - Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_WaitTargetData::OnConfirm); - //Ability->ConfirmDelegate.CreateUObject(this, &UGAAbilityTask_WaitForConfirm::OnConfirm); - } -} - -//bool UGAAbilityTask_WaitTargetData::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AGATargetingActor*& SpawnedActor) -//{ -// UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); -// if (World) -// { -// SpawnedActor = World->SpawnActorDeferred(Class, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); -// } -// -// if (SpawnedActor == nullptr) -// { -// return false; -// } -// UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); -// return true; -//} -// -//void UGAAbilityTask_WaitTargetData::FinishSpawningActor(UObject* WorldContextObject, AGATargetingActor* SpawnedActor) -//{ -// if (SpawnedActor) -// { -// FTransform SpawnTransform; -// SpawnedActor->FinishSpawning(SpawnTransform); -// TargetActor = SpawnedActor; -// } -// ReadyForActivation(); -// UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); -//} -void UGAAbilityTask_WaitTargetData::TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) -{ - //if (TargetActor && Ability.IsValid()) - //{ - // FHitResult OutHit; - // bool bHit = Ability->LineTraceSingleByChannelFromCamera(Range, TraceChannel, false, OutHit, - // EDrawDebugTrace::Type::None, true, FLinearColor::Green, FLinearColor::Red, 2); - // if (bHit) - // { - // TargetActor->SetActorLocation(OutHit.Location); - // } - // else - // { - // TargetActor->SetActorLocation(OutHit.TraceEnd); - // } - //} -} - -void UGAAbilityTask_WaitTargetData::OnConfirm() -{ - Ability->OnConfirmDelegate.Clear(); - OnConfirmed.Broadcast(); - EndTask(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h deleted file mode 100644 index d50f96e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Abilities/Tasks/GAAbilityTask_WaitTargetData.h +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GAAbilityTask.h" -#include "GAAbilityTask_WaitTargetData.generated.h" -DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnTargetingTaskConfimred); - -/** - * - */ -UCLASS(meta = (ExposedAsyncProxy)) -class ABILITYFRAMEWORK_API UGAAbilityTask_WaitTargetData : public UGAAbilityTask -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FGASOnTargetingTaskConfimred OnConfirmed; - - UPROPERTY() - float Range; - ETraceTypeQuery TraceChannel; - - virtual void Activate() override; - - virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; - - - UFUNCTION() - void OnConfirm(); - -public: - UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs index d76f8a6..3230335 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.Build.cs @@ -6,27 +6,8 @@ public class AbilityFramework : ModuleRules { public AbilityFramework(ReadOnlyTargetRules Target) : base(Target) { - PublicIncludePaths.AddRange( - new string[] { - "AbilityFramework", - "AbilityFramework/Abilities", - "AbilityFramework/Attributes", - "AbilityFramework/Effects", - "AbilityFramework/Effects/ApplicationRequirement", - "AbilityFramework/Effects/CustomApplications", - "AbilityFramework/Public" - // ... add public include paths required here ... - } - ); - PrivateIncludePaths.AddRange( new string[] { - "AbilityFramework", - "AbilityFramework/Abilities", - "AbilityFramework/Attributes", - "AbilityFramework/Effects", - "AbilityFramework/LatentActions", - "AbilityFramework/Private", // ... add other private include paths required here ... } ); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp deleted file mode 100644 index 25f3d4f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.cpp +++ /dev/null @@ -1,213 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "AbilityFramework.h" - -DEFINE_LOG_CATEGORY(AbilityFramework); -DEFINE_LOG_CATEGORY(GameAttributesGeneral); -DEFINE_LOG_CATEGORY(GameAttributes); -DEFINE_LOG_CATEGORY(GameAttributesEffects); - -DEFINE_LOG_CATEGORY(AFAttributes); -DEFINE_LOG_CATEGORY(AFEffects); -DEFINE_LOG_CATEGORY(AFAbilities); - -FAFEffectTimerManager* FAFEffectTimerManager::Instance = nullptr; - -DECLARE_CYCLE_STAT(TEXT("EffectTimer.Run"), STAT_EffectTimerRun, STATGROUP_EffectTimer); -FAFEffectTimer::FAFEffectTimer() -{ - -} -FAFEffectTimerWorker::FAFEffectTimerWorker() -{ - bActive = true; - Timers.Reset(); - Timers.SetNumZeroed(0); - InternalTime = FPlatformTime::ToSeconds64(FPlatformTime::Cycles64()); - for (int Idx = 0; Idx < 10000; Idx++) - { - float Duration = FMath::RandRange(15, 25); - AddTimer(Duration, 0.2); - } -} -FAFEffectTimerManager::FAFEffectTimerManager() -{ - TimerWorker = new FAFEffectTimerWorker(); - TimerThread = FRunnableThread::Create(TimerWorker, TEXT("EffectTimerThread"), 512*1024, TPri_Normal); - - check(TimerWorker != nullptr); -} -FAFEffectTimerManager::~FAFEffectTimerManager() -{ - //if (TimerThread) - //{ - // TimerThread->Kill(); - // delete TimerThread; - // TimerThread = nullptr; - //} -} -uint32 FAFEffectTimerWorker::Run() -{ - while (1) - { - SCOPE_CYCLE_COUNTER(STAT_EffectTimerRun); - InternalTime = FPlatformTime::ToSeconds64(FPlatformTime::Cycles64()); - //while (Timers.Num() > 0) - { -//#if UE_BUILD_DEVELOPTMENT || UE_BUILD_DEBUG - -//#endif // UE_BUILD_DEVELOPTMENT || UE_BUILD_DEBUG - - //for (FAFEffectTimer& Timer : Timers) - { - //auto It = Timers.CreateIterator(); - //for (; It; ++It) - //{ - - // if (It->bHavePeriod && (InternalTime > It->NextPeriodTime)) - // { - // double asdasd = It->ExpireTime - InternalTime; - // double FinalTime = InternalTime - It->StartTime; - // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Period TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); - - // It->NextPeriodTime = InternalTime + It->PeriodTime; - // //It->PeriodDelegate.ExecuteIfBound(); - - // } - // if (It->bHaveDuration && (InternalTime > It->ExpireTime)) - // { - // double asdasd = It->ExpireTime - InternalTime; - // double FinalTime = InternalTime - It->StartTime; - // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); - // //It->ExpireDelegate.ExecuteIfBound(); - - // //FAFEffectTimer Out; - // //Timers.Remove(*It); - // //Timers.Shrink(); - // } - //} - for (FAFEffectTimer& Timer : Timers) - { - if (!Timer.bActive) - continue; - - if (Timer.bHavePeriod && (InternalTime > Timer.NextPeriodTime)) - { - double asdasd = Timer.ExpireTime - InternalTime; - double FinalTime = InternalTime - Timer.StartTime; - //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Period TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); - - Timer.NextPeriodTime = InternalTime + Timer.PeriodTime; - //Timer.PeriodDelegate.ExecuteIfBound(); - - } - if (Timer.bHaveDuration && (InternalTime > Timer.ExpireTime)) - { - double asdasd = Timer.ExpireTime - InternalTime; - double FinalTime = InternalTime - Timer.StartTime; - //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); - //Timer.ExpireDelegate.ExecuteIfBound(); - //Timer.bActive = false; - //FAFEffectTimer Out; - //Timers.Remove(*It); - //Timers.Shrink(); - } - } - //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer TimeRemaining: %f"), asdasd); - //FAFEffectTimer& Top = Timers.HeapTop(); - - //if (Timer.bActive) - //{ - // if (Top.bHaveDuration && (InternalTime > Top.ExpireTime)) - // { - // double asdasd = Top.ExpireTime - InternalTime; - // double FinalTime = InternalTime - Top.StartTime; - // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); - // Top.ExpireDelegate.ExecuteIfBound(); - - // FAFEffectTimer Out; - // Timers.HeapPop(Out); - // Timers.Shrink(); - // } - //} - } - } - FPlatformProcess::Sleep(0.01); - } - return 0; -} -bool FAFEffectTimerWorker::Init() -{ - return true; -} -void FAFEffectTimerWorker::Stop() -{ - bActive = false; -} - -/** -* Exits the runnable object. -* -* Called in the context of the aggregating thread to perform any cleanup. -* @see Init, Run, Stop -*/ -void FAFEffectTimerWorker::Exit() -{ - //Timers.Empty(); - //bActive = false; -} - -FAFEffectTimeHandle FAFEffectTimerWorker::AddTimer(double InDuration, double InPeriod) -{ - FScopeLock lock(&CS); - //bActive = false; - FAFEffectTimer Timer; - Timer.Duration = InDuration; - Timer.PeriodTime = InPeriod; - Timer.bHaveDuration = InDuration <= 0 ? false : true; - Timer.bHavePeriod = InPeriod <= 0 ? false : true; - Timer.StartTime = InternalTime; // FPlatformTime::ToSeconds64(FPlatformTime::Cycles64());// InternalTime; - - Timer.ExpireTime = InternalTime + Timer.Duration; - Timer.NextPeriodTime = InternalTime + Timer.PeriodTime; - Timer.bActive = true; - Timers.Add(Timer); - int32 idx = Timers.Num() - 1; - //Timers.Push(Timer); - //Timers.Heapify(); - FAFEffectTimeHandle Handle; - Handle.Index = idx; - Timers[idx].Handle = Handle; - UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Start TimeDifference: %f"), (Timer.ExpireTime - InternalTime)); - - //since there is at least one timer, set timer manager to be active. - - bActive = true; - return Handle; -} - -FAFEffectTimeHandle FAFEffectTimerManager::AddTimer(double InDuration, double InPeriod) -{ - - return TimerWorker->AddTimer(InDuration, InPeriod); -} - -void FAbilityFramework::StartupModule() -{ -#if WITH_EDITOR - //FModuleManager::Get().LoadModule(TEXT("AbilityFrameworkEditor")); -#endif //WITH_EDITOR - //FAFEffectTimerManager::Get(); - // This code will execute after your module is loaded into memory (but after global variables are initialized, of course.) -} - - -void FAbilityFramework::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - - - -IMPLEMENT_MODULE(FAbilityFramework, AbilityFramework) \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h deleted file mode 100644 index eca4711..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AbilityFramework.h +++ /dev/null @@ -1,152 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "Engine.h" -#include "IAbilityFramework.h" -#include "InputCoreTypes.h" - -#include "Runtime/UMG/Public/UMG.h" -#include "Runtime/UMG/Public/UMGStyle.h" -#include "Runtime/UMG/Public/Slate/SObjectWidget.h" -#include "Runtime/UMG/Public/IUMGModule.h" -#include "Runtime/UMG/Public/Blueprint/UserWidget.h" -//#include "GameTrace.h" - -enum class EAFEffectTimerStatus : uint8 -{ - Pending, - Active, - Executing, - Paused -}; - -struct FAFEffectTimeHandle -{ - int32 Index; - bool operator==(const FAFEffectTimeHandle& Other) const - { - return Index == Other.Index; - } -}; - -struct FAFEffectTimer -{ - double StartTime; //when started - double ExpireTime; - double NextPeriodTime; - double PeriodTime; - double Duration; //how often timer is executed - - bool bHaveDuration; //does it loop - bool bHavePeriod; - bool bActive; - - EAFEffectTimerStatus Status; - - FSimpleDelegate ExpireDelegate; - FSimpleDelegate PeriodDelegate; - - FAFEffectTimeHandle Handle; - - FAFEffectTimer(); - - bool operator<(const FAFEffectTimer& Other) const - { - return ExpireTime < Other.ExpireTime; - } - bool operator==(const FAFEffectTimer& Other) const - { - return Handle == Other.Handle; - } -}; - -DECLARE_STATS_GROUP(TEXT("EffectTimer"), STATGROUP_EffectTimer, STATCAT_Advanced); -class FAFEffectTimerWorker : public FRunnable -{ - FCriticalSection CS; - TArray Timers; - TArray ActiveTimers; - UWorld* World; - double InternalTime; - bool bActive; -public: - FAFEffectTimerWorker(); - virtual bool Init() override; - - /** - * Runs the runnable object. - * - * This is where all per object thread work is done. This is only called if the initialization was successful. - * - * @return The exit code of the runnable object - * @see Init, Stop, Exit - */ - virtual uint32 Run() override; - - /** - * Stops the runnable object. - * - * This is called if a thread is requested to terminate early. - * @see Init, Run, Exit - */ - virtual void Stop() override; - - /** - * Exits the runnable object. - * - * Called in the context of the aggregating thread to perform any cleanup. - * @see Init, Run, Stop - */ - virtual void Exit() override; - - FAFEffectTimeHandle AddTimer(double InDuration, double InPeriod); -}; - -class FAFEffectTimerManager -{ - FRunnableThread* TimerThread; - FAFEffectTimerWorker* TimerWorker; - - -public: - static FAFEffectTimerManager* Instance; - static FAFEffectTimerManager* Get() - { - //static FAFEffectTimerManager Obj;// = nullptr; - //return Obj; - if (!Instance) - Instance = new FAFEffectTimerManager(); - - return Instance; - - } - - FAFEffectTimerManager(); - - ~FAFEffectTimerManager(); - - void TickTimer(float InDeltaTime); - FAFEffectTimeHandle AddTimer(double InDuration, double InPeriod); -}; - -class FAbilityFramework : public IAbilityFramework -{ - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; - - -DECLARE_LOG_CATEGORY_EXTERN(AbilityFramework, Log, All); - -DECLARE_LOG_CATEGORY_EXTERN(GameAttributesGeneral, Log, All); - -DECLARE_LOG_CATEGORY_EXTERN(GameAttributes, Log, All); - -DECLARE_LOG_CATEGORY_EXTERN(GameAttributesEffects, Log, All); - - - -DECLARE_LOG_CATEGORY_EXTERN(AFAttributes, Log, All); -DECLARE_LOG_CATEGORY_EXTERN(AFEffects, Log, All); -DECLARE_LOG_CATEGORY_EXTERN(AFAbilities, Log, All); \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp deleted file mode 100644 index 10e8534..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "AFAbilityNotifyState.h" - - - - -void UAFAbilityNotifyState::NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) -{ - IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); - if (IAbilities) - { - CachedAbilitiesComp = IAbilities->GetAbilityComp(); - CachedAbilitiesComp->OnAbilityNotifyBegin.ExecuteIfBound(Tag, Name); - } -} -void UAFAbilityNotifyState::NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) -{ - if (CachedAbilitiesComp) - { - CachedAbilitiesComp->OnAbilityNotifyTick.ExecuteIfBound(Tag, Name); - } -} -void UAFAbilityNotifyState::NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) -{ - if (CachedAbilitiesComp) - { - CachedAbilitiesComp->OnAbilityNotifyEnd.ExecuteIfBound(Tag, Name); - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h deleted file mode 100644 index d2a949a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAbilityNotifyState.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Animation/AnimNotifies/AnimNotifyState.h" -#include "GameplayTags.h" -#include "AFAbilityNotifyState.generated.h" - -/** - * - */ -UCLASS(meta = (DisplayName = "Ability Notify State")) -class ABILITYFRAMEWORK_API UAFAbilityNotifyState : public UAnimNotifyState -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere) - FGameplayTag Tag; - UPROPERTY(EditAnywhere) - FName Name; - UPROPERTY() - class UAFAbilityComponent* CachedAbilitiesComp; -public: - virtual void NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) override; - virtual void NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) override; - virtual void NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) override; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp deleted file mode 100644 index 26e0f2d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.cpp +++ /dev/null @@ -1,19 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.h" -#include "AFAnimNotify.h" - - - - -void UAFAnimNotify::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) -{ - IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); - if (!IAbilities) - return; - - UAFAbilityComponent* Comp = IAbilities->GetAbilityComp(); - Comp->OnAbilityNotifyBegin.ExecuteIfBound(Tag, Name); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h b/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h deleted file mode 100644 index b6e0390..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/AnimNotify/AFAnimNotify.h +++ /dev/null @@ -1,23 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Animation/AnimNotifies/AnimNotify.h" -#include "GameplayTags.h" -#include "AFAnimNotify.generated.h" - -/** - * - */ -UCLASS(meta=(DisplayName = "Ability Notify")) -class ABILITYFRAMEWORK_API UAFAnimNotify : public UAnimNotify -{ - GENERATED_BODY() - - virtual void Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) override; - - UPROPERTY(EditAnywhere) - FGameplayTag Tag; - UPROPERTY(EditAnywhere) - FName Name; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp deleted file mode 100644 index 77ff541..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.cpp +++ /dev/null @@ -1,248 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GameplayTagContainer.h" -#include "../AFAbilityComponent.h" -#include "GAAttributesBase.h" -#include "../AFAbilityInterface.h" -#include "GAAttributeExtension.h" - -#include "GAAttributeBase.h" -DEFINE_STAT(STAT_CalculateBonus); -DEFINE_STAT(STAT_CurrentBonusByTag); -DEFINE_STAT(STAT_FinalBonusByTag); -//UGAAttributeBase::UGAAttributeBase(const FObjectInitializer& ObjectInitializer) -// : Super(ObjectInitializer) -//{ -// -//} -FAFAttributeBase::FAFAttributeBase() - : CurrentValue(0), - BonusValue(0) -{ - Modifiers.AddDefaulted(7); -}; -FAFAttributeBase::FAFAttributeBase(float BaseValueIn) - : BaseValue(BaseValueIn), - CurrentValue(BaseValue), - BonusValue(0) -{ - Modifiers.AddDefaulted(7); -}; - - -void FAFAttributeBase::InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName) -{ - CurrentValue = BaseValue; - CalculateBonus(); - CurrentValue = GetFinalValue(); - Modifiers.Empty(); - Modifiers.AddDefaulted(7);// static_cast(EGAAttributeMod::Invalid)); - //Modifiers.AddDefaulted(static_cast(EGAAttributeMod::Invalid)); - if (ExtensionClass) - { - ExtensionClass.GetDefaultObject()->Initialize(InComponent, InAttributeName); - } -} - -void FAFAttributeBase::CalculateBonus() -{ - SCOPE_CYCLE_COUNTER(STAT_CalculateBonus); - float AdditiveBonus = 0; - float SubtractBonus = 0; - float MultiplyBonus = 1; - float DivideBonus = 1; - //auto ModIt = Modifiers.CreateConstIterator(); - TMap& Additive = Modifiers[static_cast(EGAAttributeMod::Add)]; - TMap& Subtractive = Modifiers[static_cast(EGAAttributeMod::Subtract)]; - TMap& Multiplicative = Modifiers[static_cast(EGAAttributeMod::Multiply)]; - TMap& Divide = Modifiers[static_cast(EGAAttributeMod::Divide)]; - for (auto ModIt = Additive.CreateConstIterator(); ModIt; ++ModIt) - { - AdditiveBonus += ModIt->Value.Value; - } - for (auto ModIt = Subtractive.CreateConstIterator(); ModIt; ++ModIt) - { - SubtractBonus += ModIt->Value.Value; - } - for (auto ModIt = Multiplicative.CreateConstIterator(); ModIt; ++ModIt) - { - MultiplyBonus += ModIt->Value.Value; - } - for (auto ModIt = Divide.CreateConstIterator(); ModIt; ++ModIt) - { - DivideBonus += ModIt->Value.Value; - } - //for (ModIt; ModIt; ++ModIt) - //{ - // const FGAEffectMod& mod = ModIt->Value; - // switch (mod.AttributeMod) - // { - // case EGAAttributeMod::Add: - // AdditiveBonus += mod.Value; - // break; - // case EGAAttributeMod::Subtract: - // SubtractBonus += mod.Value; - // break; - // case EGAAttributeMod::Multiply: - // MultiplyBonus += mod.Value; - // break; - // case EGAAttributeMod::Divide: - // DivideBonus += mod.Value; - // break; - // default: - // break; - // } - //} - float OldBonus = BonusValue; - //calculate final bonus from modifiers values. - //we don't handle stacking here. It's checked and handled before effect is added. - BonusValue = (AdditiveBonus - SubtractBonus); - BonusValue = (BonusValue * MultiplyBonus); - BonusValue = (BonusValue / DivideBonus); - //this is absolute maximum (not clamped right now). - float addValue = BonusValue - OldBonus; - //reset to max = 200 - CurrentValue = CurrentValue + addValue; - /* - BaseValue = 200; - CurrentValue = 200; - BonusValue = 50; - CurrentValue = 200 + 50; - CurentValue == 250; - - Damage taken. - CurrentValue = 250 - 25; - CurrentValue == 225; - Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; - Expected Result : 175; (225 - 50) - OldBonusValue = 50; - BonusValue = 0; - CurrentValue == 225; - BonusValue - OldBonusValue = -50; - CurrentValue = CurrentValue + (-50); ?? - - TwoBonuses 50 + 50; - CurrentValue = 300 - 25; - CurrentValue == 275; - Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; - Expected Result : 225; (275 - 50) - OldBonusValue = 100; - BonusValue = 50; - CurrentValue == 225; - BonusValue - OldBonusValue = -50; - CurrentValue = CurrentValue + (-50); ?? - - Inverse Bonus is going to be Increased: - TwoBonuses 50 + 50; - CurrentValue = 300 - 25; - CurrentValue == 275; - Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; - Expected Result : 325; (275 + 50) - OldBonusValue = 100; - new BonusValue = 150; (new bonus gives +50) - CurrentValue == 275; - BonusValue - OldBonusValue = 50; (150 - 100) = 50 - CurrentValue = CurrentValue + (50); ?? - */ -} - -bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) -{ - TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; - auto It = mods.CreateConstIterator(); - for (; It; ++It) - { - if (InMod > It->Value) - { - return true; - } - } - if (mods.Num() <= 0) - { - return true; - } - return false; -} -float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - FGAEffectProperty& InProperty) -{ - //FString name = GetTypeName(); - if (ExtensionClass) - { - ExtensionClass.GetDefaultObject()->OnPreAttributeModify(CurrentValue); - } - float returnValue = -1; - bool isPeriod = InProperty.GetPeriod() > 0; - bool IsDuration = InProperty.GetDuration() > 0; - if ( !InProperty.GetIsInstant()) - { - FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); - AttrMod.Tags.AppendTags(InProperty.GetSpec()->AttributeTags); - AddBonus(ModIn, HandleIn); - return ModIn.Value; - } - else - { - switch (ModIn.AttributeMod) - { - case EGAAttributeMod::Add: - { - float OldCurrentValue = CurrentValue; - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: OldCurrentValue: %f"), OldCurrentValue); - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: AddValue: %f"), ModIn.Value); - float Val = CurrentValue - (OldCurrentValue + ModIn.Value); - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: ActuallAddVal: %f"), Val); - CurrentValue -= Val; - CurrentValue = FMath::Clamp(CurrentValue, 0, GetFinalValue()); - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: CurrentValue: %f"), CurrentValue); - returnValue = CurrentValue; - break; - } - case EGAAttributeMod::Subtract: - { - float OldCurrentValue = CurrentValue; - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: OldCurrentValue: %f"), OldCurrentValue); - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: SubtractValue: %f"), ModIn.Value); - float Val = CurrentValue - (OldCurrentValue - ModIn.Value); - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: ActuallSubtractVal: %f"), Val); - CurrentValue -= Val; - CurrentValue = FMath::Clamp(CurrentValue, 0, GetFinalValue()); - UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: CurrentValue: %f"), CurrentValue); - - returnValue = CurrentValue; - break; - } - case EGAAttributeMod::Multiply: - { - returnValue = -1; - break; - } - case EGAAttributeMod::Divide: - { - returnValue = -1; - break; - } - } - } - if (ExtensionClass) - { - ExtensionClass.GetDefaultObject()->OnPreAttributeModify(returnValue); - } - return returnValue; -} - -void FAFAttributeBase::AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle) -{ - TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; - FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); - modsTemp = ModIn; - CalculateBonus(); -} -void FAFAttributeBase::RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod) -{ - TMap& mods = Modifiers[static_cast(InMod)]; - mods.Remove(Handle); - //Modifiers.Remove(Handle); - CalculateBonus(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h deleted file mode 100644 index 650b95c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeBase.h +++ /dev/null @@ -1,148 +0,0 @@ -#pragma once -#include "../GAGlobalTypes.h" -#include "./Effects/GAGameEffect.h" -#include "../Effects/GAEffectGlobalTypes.h" - -// Messaging -//#include "Messaging.h" - -#include "GAAttributeBase.generated.h" - -DECLARE_MULTICAST_DELEGATE(FGAGenericAttributeDelegate); - -DECLARE_STATS_GROUP(TEXT("Attribute"), STATGROUP_Attribute, STATCAT_Advanced); -DECLARE_CYCLE_STAT_EXTERN(TEXT("CalculateBonus"), STAT_CalculateBonus, STATGROUP_Attribute, ); -DECLARE_CYCLE_STAT_EXTERN(TEXT("CurrentBonusByTag"), STAT_CurrentBonusByTag, STATGROUP_Attribute, ); -DECLARE_CYCLE_STAT_EXTERN(TEXT("FinalBonusByTag"), STAT_FinalBonusByTag, STATGROUP_Attribute, ); - - -struct QueuedAttributeMods -{ -public: - FGAEffectHandle Handle; - FGAEffectMod Mod; - - void operator=(const QueuedAttributeMods& Other) - { - Handle = Other.Handle; - Mod = Other.Mod; - } -}; - -//wrapper for multi-precision attribute. -//works like any numeric type, but depending on preprocessor flag it can int16,in32, float or double. - -typedef int16 AttributeReal; - -struct FNumericAttribute -{ - AttributeReal Value; -}; - -class UAFAbilityComponent; -/* - I probabaly should chaange attribute to use int's instead of floats. Stable, accurate and - I can still have decimal values with them. -*/ -/* - Base data structure describing Attribute: - 1. Base Value - the base value attribute has been initialized with. - 2. Current value - current value of attribute. - 3. Bonuses value. - 4. One bonus value (if need be attribute can take care of calculating it's own bonus value). - - As for now it's made to in mind to use it as meta attribute. Meta attributes, have always - 0 value and are used to change other attributes. Like Damage is used to subtract health. - LifeSteal is used to transfer health from target to instigator etc. - - We could extend attributes, to also support tags, so their bonus can be recalculated, - based on on tags requiremnts from effect asking for this particular attribute. -*/ -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFAttributeBase -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - float BaseValue; - UPROPERTY(EditAnywhere) - float MinValue; - UPROPERTY(EditAnywhere) - float MaxValue; - UPROPERTY() - float CurrentValue; - UPROPERTY() - float BonusValue; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") - TSubclassOf ExtensionClass; - - TArray> Modifiers; - FAFAttributeBase(); - FAFAttributeBase(float BaseValueIn); - void InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName); - /* You should never use those tree function to set attributes. - Only use them for testing/debugging and setting initial values for attributes. */ - inline void SetBaseValue(float ValueIn) { BaseValue = ValueIn; } - inline void SetMinValue(float ValueIn) { MinValue = ValueIn; } - inline void SetMaxValue(float ValueIn) { MaxValue = ValueIn; } - //used internally. NEver call it directly. - inline void SetCurrentValue(float ValueIn) { CurrentValue = ValueIn; } - - inline float GetFinalValue() - { - return FMath::Clamp(BaseValue + BonusValue, MinValue, MaxValue); - }; - inline float GetCurrentValue() { return CurrentValue; }; - void CalculateBonus(); - bool CheckIfStronger(const FGAEffectMod& InMod); - float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); - void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); - void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); - void SetExtensionClass(TSubclassOf InExtensionClass) { ExtensionClass = InExtensionClass; }; -}; -template<> -struct TStructOpsTypeTraits : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithCopy = false - }; -}; -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAModifiedAttribute -{ - GENERATED_USTRUCT_BODY() -public: - /** - * Always increment it, to make sure it will replicate. - */ - UPROPERTY() - int8 ReplicationCounter; - - /** - * Attribute we have modified. - */ - UPROPERTY() - FGAAttribute Attribute; - - /** - * Final value by which we modified attribute. - */ - UPROPERTY(BlueprintReadOnly, Category = "UI") - float ModifiedByValue; - - /** - * Final tags appiled by this change. - */ - UPROPERTY() - FGameplayTagContainer Tags; - - UPROPERTY(BlueprintReadOnly, Category = "UI") - FVector TargetLocation; //change to vector, we need only position. - UPROPERTY(BlueprintReadOnly, Category = "UI") - FVector InstigatorLocation; - - UPROPERTY() - TWeakObjectPtr Causer; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp deleted file mode 100644 index 6066955..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.cpp +++ /dev/null @@ -1,23 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../AbilityFramework.h" -#include "../AFAbilityComponent.h" -#include "GAAttributeExtension.h" - - - - -void UGAAttributeExtension::Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName) -{ - AbilityComponent = InAbilityComponent; - Attribute = FGAAttribute(InAttributeName); -} - -void UGAAttributeExtension::OnPreAttributeModify(float InValue) -{ - AbilityComponent->NotifyOnPreAttributeModified(Attribute); -} -void UGAAttributeExtension::OnPostAttributeModify(float InValue) -{ - AbilityComponent->NotifyOnPostAttributeModified(Attribute); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h deleted file mode 100644 index 34b4b7c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeExtension.h +++ /dev/null @@ -1,32 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "UObject/NoExportTypes.h" -#include "../GAGlobalTypes.h" -#include "GAAttributeExtension.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAAttributeExtension : public UObject -{ - GENERATED_BODY() -public: - UPROPERTY() - class UAFAbilityComponent* AbilityComponent; - UPROPERTY() - FGAAttribute Attribute; - void Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName); - - void OnPreAttributeModify(float InValue); - void OnPostAttributeModify(float InValue); - - virtual void PreAttributeModify() {}; - virtual void PostAttributeModify() {}; - virtual float CalculateBonusValueByTags(const FGAIndividualMods& Mods) { return 0; } - virtual float CalculateCurentValue() { return 0; } - virtual bool CanModifyAttribute() { return true; } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp deleted file mode 100644 index de1a982..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.cpp +++ /dev/null @@ -1,5 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../AbilityFramework.h" -#include "GAAttributeGlobals.h" - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h deleted file mode 100644 index e82dfdf..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributeGlobals.h +++ /dev/null @@ -1,15 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once -#include "Engine/NetSerialization.h" -#include "GameplayTags.h" -#include "GAAttributeGlobals.generated.h" -/** - * - */ - -USTRUCT() -struct FDumbStruct -{ - GENERATED_BODY() -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp deleted file mode 100644 index 4a59378..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.cpp +++ /dev/null @@ -1,297 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "../GAGlobalTypes.h" -#include "../AFAbilityComponent.h" -#include "Net/UnrealNetwork.h" -#include "GAAttributesBase.h" - -UGAAttributesBase::UGAAttributesBase(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - bNetAddressable = false; - LastAttributeProp = nullptr; - CachedFloatPropety = nullptr; -} -UGAAttributesBase::~UGAAttributesBase() -{ - LastAttributeProp = nullptr; //make sure we clear this pointer. - CachedFloatPropety = nullptr; -} -//void UGAAttributesBase::PostNetReceive() -//{ -// Super::PostNetReceive(); -//} -void UGAAttributesBase::InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) -{ - OwningAttributeComp = InOwningAttributeComp; - for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) - { - FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); - if (attr) - { - attr->InitializeAttribute(InOwningAttributeComp, StrIt->GetFName()); - TickableAttributes.Add(attr); - } - } - /* - Bind Delegates to map > For each attribute, so we don't store them inside attribute - but in this class. - */ - /*for (TFieldIterator PropIt(GetClass(), EFieldIteratorFlags::IncludeSuper); PropIt; ++PropIt) - { - int32 FoundIndex = -1; - FoundIndex = PropIt->GetName().Find("PostAttribute"); - FAFAttributeBase* attrPtr = GetAttribute(FGAAttribute(PropIt->GetFName())); - if (attrPtr) - { - return attrPtr->InitializeAttribute(); - } - }*/ - BP_InitializeAttributes(); -} - -void UGAAttributesBase::InitializeAttributesFromTable() -{ - if (!AttributeValues) - return; - - for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) - { - FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); - if (attr) - { - FName fieldName = StrIt->GetFName(); - FString OutString; - FAFAtributeRowData* row = AttributeValues->FindRow(fieldName, OutString); - if (row) - { - attr->SetBaseValue(row->BaseValue); - attr->SetMaxValue(row->MaxValue); - attr->SetMinValue(row->MinValue); - attr->SetCurrentValue(row->CurrentValue); - attr->SetExtensionClass(row->Extension); - attr->InitializeAttribute(OwningAttributeComp, StrIt->GetFName()); - } - //TickableAttributes.Add(attr); - } - } -} - -void UGAAttributesBase::Tick(float DeltaTime) -{ - for (FAFAttributeBase* Attribute : TickableAttributes) - { - } -} - - -UProperty* UGAAttributesBase::FindProperty(const FGAAttribute& AttributeIn) -{ - //if new attribute name is the same as last attribute name and pointer to last property - //is not null, then we just return last pointer instead of performing new search. - if ((AttributeIn.AttributeName == LastAttributeName) && LastAttributeProp) - return LastAttributeProp; - - LastAttributeName = AttributeIn.AttributeName; - LastAttributeProp = FindFieldChecked(this->GetClass(), LastAttributeName); - return LastAttributeProp; - return nullptr; -} -UStructProperty* UGAAttributesBase::GetStructAttribute(const FGAAttribute& Name) -{ - return FindField(this->GetClass(), Name.AttributeName); -} -FAFAttributeBase* UGAAttributesBase::GetAttribute(const FGAAttribute& Name) -{ - if (!Name.IsValid()) - { - UE_LOG(GameAttributesEffects, Log, TEXT("GetAttribute INVALID NAME")); - return nullptr; - } - UStructProperty* tempStruct = FindField(this->GetClass(), Name.AttributeName); - - FAFAttributeBase* attr = nullptr; - if (tempStruct) - { - attr = tempStruct->ContainerPtrToValuePtr(this); - return attr; - } - return attr; -} -void UGAAttributesBase::SetAttribute(const FGAAttribute& NameIn, UObject* NewVal) -{ - //UStructProperty* tempStruct = FindField(this->GetClass(), NameIn.AttributeName); -} -void UGAAttributesBase::SetAttributeAdditiveBonus(const FGAAttribute& NameIn, float NewValue) -{ - UStructProperty* tempStruct = FindField(this->GetClass(), NameIn.AttributeName); - UScriptStruct* scriptStruct = tempStruct->Struct; - - uint8* StructData = tempStruct->ContainerPtrToValuePtr(this); - - //omg figured it out! - //for (TFieldIterator It(scriptStruct); It; ++It) - //{ - // if (UProperty* Prop = *It) - // { - // if (Prop->GetFName() == "AdditiveBonus") - // { - // if (Prop->IsA(UFloatProperty::StaticClass())) - // { - // float testValue = NewValue; - // Cast(Prop)->SetPropertyValue_InContainer(StructData, testValue); - // break; - // } - // } - // } - //} -} - -float UGAAttributesBase::GetFinalAttributeValue(const FGAAttribute& Name) -{ - FAFAttributeBase* attrPtr = GetAttribute(Name); - if (attrPtr) - { - return attrPtr->GetFinalValue(); - } - return 0; -} -float UGAAttributesBase::GetCurrentAttributeValue(const FGAAttribute& Name) -{ - FAFAttributeBase* attrPtr = GetAttribute(Name); - if (attrPtr) - { - return attrPtr->GetCurrentValue(); - } - return 0; -} -float UGAAttributesBase::GetFloatValue(const FGAAttribute& AttributeIn) -{ - FAFAttributeBase* Attribute = GetAttribute(AttributeIn); - - if (!Attribute) - return 0; - return Attribute->GetCurrentValue(); -} - -float UGAAttributesBase::SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn) -{ - if ((AttributeIn.AttributeName == LastAttributeName)) - { - if (CachedFloatPropety) - { - void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); - CachedFloatPropety->SetFloatingPointPropertyValue(ValuePtr, ValueIn); - return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); - } - } - //LastAttributeName = AttributeIn.AttributeName; - UNumericProperty* NumericProperty = CastChecked(FindProperty(AttributeIn)); - CachedFloatPropety = NumericProperty; - void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); - NumericProperty->SetFloatingPointPropertyValue(ValuePtr, ValueIn); - return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); - return 0; -} - -float UGAAttributesBase::AttributeOperation(const FGAAttribute& AttributeIn, float ValueIn, EGAAttributeMod Operation) -{ - switch (Operation) - { - case EGAAttributeMod::Add: - return AddAttributeFloat(GetFloatValue(AttributeIn), ValueIn); //don't want to set. - case EGAAttributeMod::Subtract: - return SubtractAttributeFloat(GetFloatValue(AttributeIn), ValueIn); - case EGAAttributeMod::Multiply: - return MultiplyAttributeFloat(GetFloatValue(AttributeIn), ValueIn); - case EGAAttributeMod::Divide: - return DivideAttributeFloat(GetFloatValue(AttributeIn), ValueIn); - case EGAAttributeMod::Set: - return SetFloatValue(AttributeIn, ValueIn); - default: - return 0; - } - return 0; -} - -float UGAAttributesBase::AddAttributeFloat(float ValueA, float ValueB) -{ - return ValueA + ValueB; -} -float UGAAttributesBase::SubtractAttributeFloat(float ValueA, float ValueB) -{ - return ValueA - ValueB; -} -float UGAAttributesBase::MultiplyAttributeFloat(float ValueA, float ValueB) -{ - return ValueA * ValueB; -} -float UGAAttributesBase::DivideAttributeFloat(float ValueA, float ValueB) -{ - return ValueA / ValueB; -} - -bool UGAAttributesBase::IsNameStableForNetworking() const -{ - /** - * IsNameStableForNetworking means an attribute set can be referred to its path name (relative to owning AActor*) over the network - * - * Attribute sets are net addressable if: - * -They are Default Subobjects (created in C++ constructor) - * -They were loaded directly from a package (placed in map actors) - * -They were explicitly set to bNetAddressable - */ - - return bNetAddressable;// || Super::IsNameStableForNetworking(); -} - - -void UGAAttributesBase::SetNetAddressable() -{ - bNetAddressable = true; -} -void UGAAttributesBase::ModifyAttribute(const FGAEffect& EffectIn) -{ - -} - -float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn, - const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty) -{ - FAFAttributeBase* attr = nullptr; - - attr = GetAttribute(ModIn.Attribute); - float OutVal = -1; - if (attr) - { - OutVal = attr->Modify(ModIn, HandleIn, InProperty); - } - OnAttributeModified(ModIn, HandleIn); - return OutVal; -} - -void UGAAttributesBase::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) -{ - FAFAttributeBase* attr = nullptr; - - attr = GetAttribute(AttributeIn); - if (attr) - { - return attr->RemoveBonus(HandleIn, InMod); - } -} - -void UGAAttributesBase::OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle) -{ - OwningAttributeComp->OnAttributeModified(InMod, InHandle, this); - FAFAttributeChangedData Data; - OwningAttributeComp->BroadcastAttributeChange(InMod.Attribute, Data); -} -void UGAAttributesBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const -{ - Super::GetLifetimeReplicatedProps(OutLifetimeProps); - //possibly replicate it to everyone - //to allow prediction for UI. - DOREPLIFETIME(UGAAttributesBase, OwningAttributeComp); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h deleted file mode 100644 index b5786b6..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBase.h +++ /dev/null @@ -1,136 +0,0 @@ -#pragma once -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "UObject/Object.h" -#include "UObject/Class.h" -#include "Templates/SubclassOf.h" -#include "UObject/UnrealType.h" -#include "UObject/CoreNet.h" -#include "../Effects/GAGameEffect.h" -#include "../GAGlobalTypes.h" -#include "GAAttributeBase.h" -#include "GAAttributesBase.generated.h" - -/* - What I need. - Easy way to create Targeted modifications. - For Example, we have ability Fireball, which have cast time 3s, and recharge time 5 seconds. - Targeted modification, will only affect this one ability! - - So we want attribute which will decrease recharge time of this ability by 2 seconds (or decrease recharge time by 25% - or increase recharge speed). How to do it ? - - Path of least resistance is to create special object, which will be instanced, which will listen for abilities - which are activated, and you can cast to your particular ability (or check for tags), and just modify it's - properties directly. - - Second way, (??) would be to create small objects, contained within array (structs), which would do the same thing. - Except they would only be able to catch something like ability activation by tag. They wouldn't know, what kind of - properties are on ability. - - The ability in this case would be needed to be treated as source of incoming attribute, and that object would check - for this attribute and modify it. - Well kind of. - - The same problems exist for any kind of abilities more broad (like Hex), more narrow (only Necromancer Hex), - or for weapons (we want to increase fire rate, if you have equiped machine gun). - - Though on the very base level attribute system have no idea, what kind of properties you might have on - your machine gun. - - - This bring us to the core issue. How to create system like Traits/Feats/Talents, which can contain - myriads of possible combinations of those tree systems. We would need to mix some instanced/non-instanced UObjects - along with plain structs. Which is probabaly going to be total mess. -*/ -UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInlineNew) -class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject -{ - GENERATED_BODY() -public: - - UPROPERTY(EditAnywhere, BlueprintReadOnly, meta=(ExposeOnSpawn)) - UDataTable* AttributeValues; - UGAAttributesBase(const FObjectInitializer& ObjectInitializer); - ~UGAAttributesBase(); - //virtual void PostNetReceive() override; - virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp); - void InitializeAttributesFromTable(); - UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) - bool BP_InitializeAttributes(); - /* - Updates attributes. - @param AttributeIn - attribute which changed value. - - You can use this function to update other attributes (for example derived ones), - based on the primary attribute, if the primary attribute (AttributeIn), changed. - - I have yet to fully figure out how do I want it to work. But one thing for certain is - that it must be fully functional from within blueprint. - */ - UPROPERTY(Replicated) - class UAFAbilityComponent* OwningAttributeComp; -protected: - UProperty* FindProperty(const FGAAttribute& AttributeIn); - -public: - /* - Ticked called from owning component. - */ - virtual void Tick(float DeltaTime);// {}; - /* - Helper C++ functions. Shouldn't ever be exposed or called from blueprint. Also never - try to override them. - - probabaly could also add support for int32 values. - */ - UStructProperty* GetStructAttribute(const FGAAttribute& Name); - /* - Gets pointer to compelx attribute. - */ - FAFAttributeBase* GetAttribute(const FGAAttribute& Name); - /* - Deprecated. I'm going to remove it, since it does not work as intended! - */ - void SetAttribute(const FGAAttribute& NameIn, UObject* NewVal); - - void SetAttributeAdditiveBonus(const FGAAttribute& NameIn, float NewValue); - - /* - Gets value from complex attribute (FAFAttributeBase). - */ - float GetFinalAttributeValue(const FGAAttribute& Name); - float GetCurrentAttributeValue(const FGAAttribute& Name); - - float GetFloatValue(const FGAAttribute& AttributeIn); - float SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn); - float AttributeOperation(const FGAAttribute& AttributeIn, float ValueIn, EGAAttributeMod Operation); - - bool IsNameStableForNetworking() const override; - - bool IsSupportedForNetworking() const override - { - return true; - } - void SetNetAddressable(); - - void ModifyAttribute(const FGAEffect& EffectIn); - float ModifyAttribute(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); - void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod); -protected: - bool bNetAddressable; - -private: - TArray TickableAttributes; - UProperty* LastAttributeProp; - FName LastAttributeName; - // cached numeric property. WEll we probabaly don't need UProperty cache then.. - UNumericProperty* CachedFloatPropety; - - float AddAttributeFloat(float ValueA, float ValueB); - float SubtractAttributeFloat(float ValueA, float ValueB); - float MultiplyAttributeFloat(float ValueA, float ValueB); - float DivideAttributeFloat(float ValueA, float ValueB); - - void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp deleted file mode 100644 index 3a194a8..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.cpp +++ /dev/null @@ -1,72 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" - -#include "../AFAbilityInterface.h" -#include "GAAttributesBase.h" -#include "../AFAbilityComponent.h" -#include "GABlueprintLibrary.h" -#include "GAAttributesBlueprintFunctionLibrary.h" - - - -UGAAttributesBlueprintFunctionLibrary::UGAAttributesBlueprintFunctionLibrary(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} - -bool UGAAttributesBlueprintFunctionLibrary::EqualAttribute(const FGAAttribute& Compare, FGAAttribute Against) -{ - return Compare == Against; -} -FName UGAAttributesBlueprintFunctionLibrary::GetAttribute(FGAAttribute AttributeIn) -{ - return AttributeIn.AttributeName; -} -float UGAAttributesBlueprintFunctionLibrary::GetFinalAttributeValue(AActor* Target, FGAAttribute Name) -{ - IAFAbilityInterface* attributeInt = Cast(Target); - if (!attributeInt) - return 0; - if (!attributeInt->GetAttributes()) - return 0; - - return attributeInt->GetAttributes()->GetFinalAttributeValue(Name); -} -float UGAAttributesBlueprintFunctionLibrary::GetCurrentAttributeValue(AActor* Target, FGAAttribute Name) -{ - IAFAbilityInterface* attributeInt = Cast(Target); - if (!attributeInt) - return 0; - return attributeInt->GetAttributes()->GetCurrentAttributeValue(Name); -} -float UGAAttributesBlueprintFunctionLibrary::GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn) -{ - IAFAbilityInterface* attributeInt = Cast(Target); - if (!attributeInt) - return 0; - - return attributeInt->GetAttributes()->GetFloatValue(AttributeIn); -} - -void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues( - APawn* Instigator - , UObject* Causer - , FAFPropertytHandle From - , FGAEffectHandle FromHandle - , UObject* FromTarget - , FAFPropertytHandle To - , FGAEffectHandle ToHandle - , UObject* ToTarget) -{ - IAFAbilityInterface* FromInterface = Cast(FromTarget); - IAFAbilityInterface* ToInterface = Cast(ToTarget); - - if (!FromInterface || !ToInterface) - return; - - FAFFunctionModifier ModF; - UGABlueprintLibrary::ApplyGameEffectToObject(From, FromHandle, FromTarget, Instigator, Causer, ModF); - UGABlueprintLibrary::ApplyGameEffectToObject(To, ToHandle, ToTarget, Instigator, Causer, ModF); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h deleted file mode 100644 index 6a9cf15..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesBlueprintFunctionLibrary.h +++ /dev/null @@ -1,58 +0,0 @@ -#pragma once -#include "../GAGlobalTypes.h" -#include "GAGameEffect.h" -#include "GAAttributesBlueprintFunctionLibrary.generated.h" -/* - Some static helper functions, to interact with Attribute system. -*/ -UCLASS() -class ABILITYFRAMEWORK_API UGAAttributesBlueprintFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_UCLASS_BODY() -public: - UFUNCTION(BlueprintPure, meta=(DisplayName="Equal"), Category = "AbilityFramework|Attributes") - static bool EqualAttribute(const FGAAttribute& Compare, FGAAttribute Against); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - static FName GetAttribute(FGAAttribute AttributeIn); - - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") - static float GetFinalAttributeValue(AActor* Target, FGAAttribute Name); - - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") - static float GetCurrentAttributeValue(AActor* Target, FGAAttribute Name); - - /** - * Takes actor, and return value of specified attribute. - * - * @param Target - Actrom from which take attribute - * @param AttributeIn - Attribute from which we want to get value - * - * @return value of attribute from actor. - */ - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") - static float GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn); - /** - * Subtracts value specified by From effect - * and adds it by effect specified by To. - * - * @param Instigator - Who Insigated effects. - * @param Causer - Who Caused Effects - * @param From - effect which will subtract Value - * @param FromTarget - from whose attributes value will be subtracted - * @param To - Effect specifing where attribute should be added. - * @param ToTarget - Target to which attributes will be added. - * - * @return value of attribute from actor. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") - static void ExchangeAttributesValues( - APawn* Instigator - , UObject* Causer - , FAFPropertytHandle From - , FGAEffectHandle FromHandle - , UObject* FromTarget - , FAFPropertytHandle To - , FGAEffectHandle ToHandle - , UObject* ToTarget); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp deleted file mode 100644 index 110fd10..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.cpp +++ /dev/null @@ -1,4 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GAAttributesStats.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h b/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h deleted file mode 100644 index 3f59c93..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Attributes/GAAttributesStats.h +++ /dev/null @@ -1,2 +0,0 @@ -#pragma once - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp deleted file mode 100644 index a6e6ad6..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFEffectApplicationRequirement.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h deleted file mode 100644 index 3225e76..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectApplicationRequirement.h +++ /dev/null @@ -1,29 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "../GAGlobalTypes.h" -#include "GAGameEffect.h" -#include "AFEffectApplicationRequirement.generated.h" - -/** - * Default requirment always passes. - */ -UCLASS(meta=(DisplayName = "No Requirement")) -class ABILITYFRAMEWORK_API UAFEffectApplicationRequirement : public UObject -{ - GENERATED_BODY() - -public: - virtual bool CanApply( - const FGAEffect& EffectIn - , const FAFEffectParams& Params - , const FGAEffectHandle& InHandle - , struct FGAEffectContainer* InContainer) - { - return true; - } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp deleted file mode 100644 index 8f04be7..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.cpp +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../AFAbilityComponent.h" -#include "AFEffectCustomApplication.h" - - - - -bool UAFEffectCustomApplication::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - return true; -} - -void UAFEffectCustomApplication::ApplyExecute( - const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - Params.GetContext().GetTargetEffectsComponent()->ExecuteEffect(InHandle, Params, Modifier); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h deleted file mode 100644 index 24fd308..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomApplication.h +++ /dev/null @@ -1,44 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "../GAGlobalTypes.h" -#include "GAGameEffect.h" -#include "AFEffectCustomApplication.generated.h" - -/** - * Default application used for instant effects. - */ -UCLASS(meta = (DisplayName = "Default Application")) -class ABILITYFRAMEWORK_API UAFEffectCustomApplication : public UObject -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual void ApplyExecute( - const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual bool CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) - { - return true; - } - - virtual bool ShowPeriod() - { - return false; - } - virtual bool ShowDuration() - { - return false; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp deleted file mode 100644 index bc4b54b..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.cpp +++ /dev/null @@ -1,14 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFEffectCustomStackingRule.h" - - - - -bool UAFEffectCustomStackingRule::CanStack(class UAFAbilityComponent* InComp, struct FGAEffectContainer* InContainer, - const FGAEffectHandle& InHandle) -{ - //InHandle.GetContext().TargetComp->ExecuteEffect(InHandle); - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h deleted file mode 100644 index ba364d2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectCustomStackingRule.h +++ /dev/null @@ -1,22 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "../GAGlobalTypes.h" -#include "AFEffectCustomStackingRule.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectCustomStackingRule : public UObject -{ - GENERATED_BODY() - -public: - virtual bool CanStack(class UAFAbilityComponent* InComp, struct FGAEffectContainer* InContainer, - const FGAEffectHandle& InHandle); - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp deleted file mode 100644 index 5d1704c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.cpp +++ /dev/null @@ -1,50 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFEffectSpecFunctionLibrary.h" - - - -void UAFEffectSpecFunctionLibrary::AppendOwnedTags(FAFEffectSpecHandle Spec, const FGameplayTagContainer& InTags) -{ - Spec.GetPtr()->OwnedTags.AppendTags(InTags); -} - -void UAFEffectSpecFunctionLibrary::CompareOwnedTags(FAFEffectSpecHandle Spec - , EAFTagContainerCompare Mode - , const FGameplayTagContainer& InTags - , EAFTagCompareResult& Result) -{ - switch (Mode) - { - case EAFTagContainerCompare::HasAny: - Spec.GetPtr()->OwnedTags.HasAny(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; - break; - case EAFTagContainerCompare::HasAnyExact: - Spec.GetPtr()->OwnedTags.HasAnyExact(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; - break; - case EAFTagContainerCompare::HasAll: - Spec.GetPtr()->OwnedTags.HasAll(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; - break; - case EAFTagContainerCompare::HasAllExact: - Spec.GetPtr()->OwnedTags.HasAllExact(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; - default: - break; - } -} - -void UAFEffectSpecFunctionLibrary::CompareOwnedTag(FAFEffectSpecHandle Spec - , EAFTagCompare Mode - , FGameplayTag InTag - , EAFTagCompareResult& Result) -{ - switch (Mode) - { - case EAFTagCompare::HasTag: - Spec.GetPtr()->OwnedTags.HasTag(InTag) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; - break; - case EAFTagCompare::HasTagExact: - Spec.GetPtr()->OwnedTags.HasTagExact(InTag) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; - break; - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h deleted file mode 100644 index 7a9aa21..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/AFEffectSpecFunctionLibrary.h +++ /dev/null @@ -1,57 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Kismet/BlueprintFunctionLibrary.h" -#include "Effects/GAGameEffect.h" -#include "AFEffectSpecFunctionLibrary.generated.h" -UENUM(BlueprintType) -enum class EAFTagCompareResult : uint8 -{ - Match, - NoMatch, -}; -UENUM() -enum class EAFTagContainerCompare : uint8 -{ - HasAny, - HasAnyExact, - HasAll, - HasAllExact, -}; - -UENUM() -enum class EAFTagCompare : uint8 -{ - HasTag, - HasTagExact -}; - - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectSpecFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_BODY() - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Spec") - static void AppendOwnedTags(FAFEffectSpecHandle Spec, const FGameplayTagContainer& InTags); - - - UFUNCTION(BlueprintCallable, meta = (ExpandEnumAsExecs = "Result"), Category = "AbilityFramework|Effects|Spec") - static void CompareOwnedTags(FAFEffectSpecHandle Spec - , EAFTagContainerCompare Mode - , const FGameplayTagContainer& InTags - , EAFTagCompareResult& Result); - - - UFUNCTION(BlueprintCallable, meta = (ExpandEnumAsExecs = "Result"), Category = "AbilityFramework|Effects|Spec") - static void CompareOwnedTag(FAFEffectSpecHandle Spec - , EAFTagCompare Mode - , FGameplayTag InTag - , EAFTagCompareResult& Result); - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp deleted file mode 100644 index 46e7ee3..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp +++ /dev/null @@ -1,39 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../../Attributes/GAAttributeBase.h" -#include "../../AFAbilityInterface.h" -#include "AFAttributeStongerOverride.h" - - - - -bool UAFAttributeStongerOverride::CanApply( - const FGAEffect& EffectIn - , const FAFEffectParams& Params - , const FGAEffectHandle& InHandle - , struct FGAEffectContainer* InContainer) -{ - bool bCanApply = true; - FGAAttribute Attribute = Params.GetProperty().GetSpec()->AtributeModifier.Attribute; - FAFAttributeBase* AttributePtr = Params.GetContext().TargetInterface->GetAttribute(Attribute); - FGAEffectProperty& InProperty = Params.GetProperty(); - - if (AttributePtr) - { - FGAEffectMod mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() - , InProperty.GetSpec() - , Params.GetContext() - , InHandle); - - if (AttributePtr->CheckIfStronger(mod)) - { - bCanApply = true; - } - else - { - bCanApply = false; - } - } - return bCanApply; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h deleted file mode 100644 index f2e18f5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFAttributeStongerOverride.h +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectApplicationRequirement.h" -#include "AFAttributeStongerOverride.generated.h" - -/** - * USe only with Duration Based application. - * Effect will be applied if the attribute modifier is stronger than the current one on Attribute. - */ -UCLASS(BlueprintType, meta = (DisplayName = "Attribute Stronger")) -class ABILITYFRAMEWORK_API UAFAttributeStongerOverride : public UAFEffectApplicationRequirement -{ - GENERATED_BODY() -public: - virtual bool CanApply( - const FGAEffect& EffectIn - , const FAFEffectParams& Params - , const FGAEffectHandle& InHandle - , struct FGAEffectContainer* InContainer) override; - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp deleted file mode 100644 index 9e44f37..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFEffectAlreadyApplied.h" - - - - -bool UAFEffectAlreadyApplied::CanApply( - const FGAEffect& EffectIn - , const FAFEffectParams& Params - , const FGAEffectHandle& InHandle - , struct FGAEffectContainer* InContainer) -{ - if (InContainer->ContainsEffectOfClass(Params.Property)) - { - return false; - } - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h deleted file mode 100644 index 13b21b5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectApplicationRequirement.h" -#include "AFEffectAlreadyApplied.generated.h" - -/** - * If effect of the same type is already applied, it will be skipped. - */ -UCLASS(meta = (DisplayName = "Only One Of Type")) -class ABILITYFRAMEWORK_API UAFEffectAlreadyApplied : public UAFEffectApplicationRequirement -{ - GENERATED_BODY() -public: - virtual bool CanApply( - const FGAEffect& EffectIn - , const FAFEffectParams& Params - , const FGAEffectHandle& InHandle - , struct FGAEffectContainer* InContainer) override; - - - - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp deleted file mode 100644 index a96c24c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.cpp +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFAtributeDurationAdd.h" - - - - -bool UAFAtributeDurationAdd::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, - Params.GetProperty().GetDuration(), false); - - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h deleted file mode 100644 index 04eca4b..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationAdd.h +++ /dev/null @@ -1,32 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFAtributeDurationAdd.generated.h" - -/** - * Adds New duration Effect. - */ -UCLASS(meta = (DisplayName = "Duration Add")) -class ABILITYFRAMEWORK_API UAFAtributeDurationAdd : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual bool ShowPeriod() override - { - return false; - } - virtual bool ShowDuration() override - { - return true; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp deleted file mode 100644 index d38c4e1..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.cpp +++ /dev/null @@ -1,38 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFAbilityInterface.h" -#include "AFAtributeDurationUnique.h" - - - - -bool UAFAtributeDurationUnique::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - if (InContainer->IsEffectActive(Params.GetSpec().GetEffectClass())) - { - return false; - } - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, - Params.GetProperty().GetDuration(), false); - - return true; -} - -bool UAFAtributeDurationUnique::CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) -{ - if (!Target) - return false; - - return !Target->GetEffectsComponent()->IsEffectActive(EffectClass); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h deleted file mode 100644 index be69075..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAtributeDurationUnique.h +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFAtributeDurationUnique.generated.h" - -/** - * Adds New Unique duration Effect. If effect of the same class is already applied to target, new effect will be ignored. - */ -UCLASS(meta = (DisplayName = "Duration Add Unique")) -class ABILITYFRAMEWORK_API UAFAtributeDurationUnique : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual bool CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) override; - - virtual bool ShowPeriod() override - { - return false; - } - virtual bool ShowDuration() override - { - return true; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp deleted file mode 100644 index 373b41c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.cpp +++ /dev/null @@ -1,17 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAttributeDurationInfinite.h" - - - - -bool UAFAttributeDurationInfinite::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h deleted file mode 100644 index 7707eda..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationInfinite.h +++ /dev/null @@ -1,33 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFAttributeDurationInfinite.generated.h" - -/** - * Adds infinite duration effect. - */ -UCLASS(meta = (DisplayName = "Duration Infinite Add")) -class ABILITYFRAMEWORK_API UAFAttributeDurationInfinite : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual bool ShowPeriod() override - { - return false; - } - virtual bool ShowDuration() override - { - return false; - } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp deleted file mode 100644 index 145e7bf..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFAttributeDurationOverride.h" - - - - -bool UAFAttributeDurationOverride::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - InContainer->RemoveEffect(Params.Property); - - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, - Params.GetProperty().GetDuration(), false); - - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h deleted file mode 100644 index 158d374..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFAttributeDurationOverride.h +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFAttributeDurationOverride.generated.h" - -/** - * If effect of the same class is already applied it will be removed, and new one will be applied. - */ -UCLASS(meta = (DisplayName = "Duration Override")) -class ABILITYFRAMEWORK_API UAFAttributeDurationOverride : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - - virtual bool ShowPeriod() override - { - return false; - } - virtual bool ShowDuration() override - { - return true; - } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp deleted file mode 100644 index a7bab63..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.cpp +++ /dev/null @@ -1,32 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFPeriodApplicationAdd.h" - - -bool UAFPeriodApplicationAdd::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, - Params.GetProperty().GetDuration(), false); - - FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); - PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, - Params.GetProperty().GetPeriod(), true); - - //InContainer->AddEffect(InProperty, InHandle); - - return true; -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h deleted file mode 100644 index 00a1e2a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationAdd.h +++ /dev/null @@ -1,39 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFPeriodApplicationAdd.generated.h" - -/** - * Adds new periodic effect. - */ -UCLASS(meta = (DisplayName = "Periodic Add")) -class ABILITYFRAMEWORK_API UAFPeriodApplicationAdd : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) override; - - virtual void ExecuteEffect( - const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) - {}; - - virtual bool ShowPeriod() override - { - return true; - } - virtual bool ShowDuration() override - { - return true; - } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp deleted file mode 100644 index c6b461d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ /dev/null @@ -1,53 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAGlobalTypes.h" -#include "Effects/GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFPeriodApplicationExtend.h" - - - - -bool UAFPeriodApplicationExtend::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - TSet handles = InContainer->GetHandlesByClass(Params.GetProperty(), Params.GetContext()); - for (const FGAEffectHandle& handle : handles) - { - FGAEffect& ExtEffect = *InContainer->GetEffect(handle); - FGAEffect& Effect = const_cast(EffectIn); - - FGAEffectContext& ExtContext = const_cast(Params).GetProperty().GetContext(handle).GetRef(); - - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - float RemainingTime = DurationTimer.GetTimerRemaining(ExtEffect.DurationTimerHandle); - float NewDuration = RemainingTime + Effect.GetDurationTime(); - DurationTimer.ClearTimer(ExtEffect.DurationTimerHandle); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(ExtContext.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(ExtEffect.DurationTimerHandle, delDuration, - NewDuration, false); - } - if (handles.Num() <= 0) - { - FGAEffect& Effect = const_cast(EffectIn);; - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(Effect.DurationTimerHandle, delDuration, - Params.GetProperty().GetDuration(), false); - - FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); - PeriodTimer.SetTimer(Effect.PeriodTimerHandle, PeriodDuration, - Params.GetProperty().GetPeriod(), true); - } - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h deleted file mode 100644 index e5efa4e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationExtend.h +++ /dev/null @@ -1,39 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFPeriodApplicationExtend.generated.h" - -/** - * If periodic effect of the same class already exists it duration will be extended. If not new effect - * will be applied. - */ -UCLASS(meta = (DisplayName = "Periodic Extend")) -class ABILITYFRAMEWORK_API UAFPeriodApplicationExtend : public UAFEffectCustomApplication -{ - GENERATED_BODY() - -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual void ExecuteEffect( - const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) - {}; - virtual bool ShowPeriod() override - { - return true; - } - virtual bool ShowDuration() override - { - return true; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp deleted file mode 100644 index 7fc9e0a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp +++ /dev/null @@ -1,24 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFPeriodApplicationInfiniteAdd.h" - - -bool UAFPeriodApplicationInfiniteAdd::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); - PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, - Params.GetProperty().GetPeriod(), true); - - return true; -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h deleted file mode 100644 index 745850a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h +++ /dev/null @@ -1,39 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFPeriodApplicationInfiniteAdd.generated.h" - -/** - * Periodic effect will be applied for infinite amount of time. - */ -UCLASS(meta = (DisplayName = "Periodic Infinite Add")) -class ABILITYFRAMEWORK_API UAFPeriodApplicationInfiniteAdd : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual void ExecuteEffect( - const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) - {}; - - virtual bool ShowPeriod() override - { - return true; - } - virtual bool ShowDuration() override - { - return false; - } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp deleted file mode 100644 index db10dbe..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../GAGameEffect.h" -#include "AFEffectsComponent.h" -#include "AFPeriodApplicationOverride.h" - - - - -bool UAFPeriodApplicationOverride::ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - - InContainer->RemoveEffect(Params.Property); - - FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); - DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, - Params.GetProperty().GetDuration(), false); - - FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); - - FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); - PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, - Params.GetProperty().GetPeriod(), true); - - return true; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h deleted file mode 100644 index 6f7e271..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodApplicationOverride.h +++ /dev/null @@ -1,38 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFPeriodApplicationOverride.generated.h" - -/** - * If effect of the same class already exist it will be removed and new effect will be appllied. - */ -UCLASS(meta = (DisplayName = "Periodic Override")) -class ABILITYFRAMEWORK_API UAFPeriodApplicationOverride : public UAFEffectCustomApplication -{ - GENERATED_BODY() -public: - virtual bool ApplyEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - virtual void ExecuteEffect( - const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) - {}; - virtual bool ShowPeriod() override - { - return true; - } - virtual bool ShowDuration() override - { - return true; - } - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp deleted file mode 100644 index 4585496..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFPeriodicApplInfiniteOverride.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h deleted file mode 100644 index 8d613d5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFPeriodicApplInfiniteOverride.generated.h" - -/** - * Adds infinite periodic effect. If effect of the same class already exists, it will be removed first. - */ -UCLASS(meta=(DisplayName = "Periodic Infinite Override")) -class ABILITYFRAMEWORK_API UAFPeriodicApplInfiniteOverride : public UAFEffectCustomApplication -{ - GENERATED_BODY() - - - virtual void ExecuteEffect( - const FGAEffectHandle& InHandle - , const FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) - {}; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp deleted file mode 100644 index d24b545..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../../AbilityFramework.h" -#include "AFEffectTask.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h deleted file mode 100644 index 67a5429..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask.h +++ /dev/null @@ -1,37 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "LatentActions/AFTaskBase.h" -#include "GAEffectExtension.h" -#include "GAGlobalTypes.h" -#include "AFAbilityComponent.h" -#include "AFEffectTask.generated.h" - -/** - * - */ -UCLASS(BlueprintType, meta = (ExposedAsyncProxy = "true") ) -class ABILITYFRAMEWORK_API UAFEffectTask : public UAFTaskBase -{ - GENERATED_BODY() -public: - UPROPERTY() - class UGAEffectExtension* Effect; - UPROPERTY() - class UAFEffectsComponent* EffectsComponent; - -public: - template - static T* NewEffectTask(UGAEffectExtension* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) - { - T* MyObj = nullptr; - UGAEffectExtension* EffectExtension = WorldContextObject; - MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); - - MyObj->Effect = EffectExtension; - MyObj->EffectsComponent = EffectExtension->OwningComponent; - - return MyObj; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp deleted file mode 100644 index df86500..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp +++ /dev/null @@ -1,82 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityInterface.h" -#include "AFEffectsComponent.h" -#include "AFEffectTask_AppliedEffectEvent.h" - - - - -UAFEffectTask_AppliedEffectEvent::UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - -} - -UAFEffectTask_AppliedEffectEvent* UAFEffectTask_AppliedEffectEvent::ListenAppliedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) -{ - auto MyObj = NewEffectTask(OwningExtension, TaskName); - MyObj->Tag = Tag; - MyObj->SetExternalTarget(OptionalExternalTarget); - MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - - return MyObj; -} - -void UAFEffectTask_AppliedEffectEvent::Activate() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - //(this, &UAFEffectTask_AppliedEffectEvent::GameplayEventCallback - FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_AppliedEffectEvent::GameplayEventCallback); - MyHandle = Delegate.GetHandle(); - ASC->AddAppliedEvent(Tag, Delegate); - } - - Super::Activate(); -} - -void UAFEffectTask_AppliedEffectEvent::GameplayEventCallback(FAFEventData Payload) -{ - //if (ShouldBroadcastAbilityTaskDelegates()) - { - OnEvent.Broadcast(Payload); - } - if (OnlyTriggerOnce) - { - EndTask(); - } -} -void UAFEffectTask_AppliedEffectEvent::OnTaskEnded() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - ASC->RemoveAppliedEvent(Tag, MyHandle); - } -} -void UAFEffectTask_AppliedEffectEvent::SetExternalTarget(AActor* Actor) -{ - if (Actor) - { - - if (IAFAbilityInterface* interface = Cast(Actor)) - { - UseExternalTarget = true; - OptionalExternalTarget = interface->GetEffectsComponent(); - } - - } -} - -UAFEffectsComponent* UAFEffectTask_AppliedEffectEvent::GetTargetASC() -{ - if (UseExternalTarget) - { - return OptionalExternalTarget; - } - - return EffectsComponent; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h deleted file mode 100644 index 3393112..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h +++ /dev/null @@ -1,49 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "../../GAGlobalTypes.h" -#include "AFEffectTask_AppliedEffectEvent.generated.h" - - - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTask -{ - GENERATED_BODY() -public: - DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); - UPROPERTY(BlueprintAssignable) - FAFEffectEventDelegate OnEvent; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_AppliedEffectEvent* ListenAppliedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); - - UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer); - - void SetExternalTarget(AActor* Actor); - - class UAFEffectsComponent* GetTargetASC(); - - virtual void Activate() override; - - virtual void GameplayEventCallback(FAFEventData Payload); - - virtual void OnTaskEnded() override; - - FGameplayTag Tag; - - UPROPERTY() - UAFEffectsComponent* OptionalExternalTarget; - - bool UseExternalTarget; - bool OnlyTriggerOnce; - - FDelegateHandle MyHandle; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp deleted file mode 100644 index 1e91f68..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp +++ /dev/null @@ -1,70 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFEffectTask_AttributeChange.h" - - -UAFEffectTask_AttributeChange::UAFEffectTask_AttributeChange(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - -} - -UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeChanged(UGAEffectExtension* OwningExtension, - FGAAttribute InAttribute, - AActor* OptionalExternalTarget, - bool OnlyTriggerOnce) -{ - auto MyObj = NewEffectTask(OwningExtension); - MyObj->Attribute = InAttribute; - MyObj->SetExternalTarget(OptionalExternalTarget); - MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - - return MyObj; -} - -void UAFEffectTask_AttributeChange::Activate() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - // MyHandle = ASC->AttributeChanged.FindOrAdd(Attribute).AddUObject(this, &UAFEffectTask_AttributeChange::AttributeChangedCallback); - } - - Super::Activate(); -} - -void UAFEffectTask_AttributeChange::AttributeChangedCallback(FAFAttributeChangedData Payload) -{ - //if (ShouldBroadcastAbilityTaskDelegates()) - { - OnEvent.Broadcast(Payload); - } - if (OnlyTriggerOnce) - { - EndTask(); - } -} - -void UAFEffectTask_AttributeChange::SetExternalTarget(AActor* Actor) -{ - if (Actor) - { - if (IAFAbilityInterface* interface = Cast(Actor)) - { - UseExternalTarget = true; - OptionalExternalTarget = interface->GetEffectsComponent(); - } - - } -} - -UAFEffectsComponent* UAFEffectTask_AttributeChange::GetTargetASC() -{ - if (UseExternalTarget) - { - return OptionalExternalTarget; - } - - return EffectsComponent; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h deleted file mode 100644 index 1952d19..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_AttributeChange.h +++ /dev/null @@ -1,50 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "AFEffectTask_AttributeChange.generated.h" -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFTaskAttributeChangedDelegate, FAFAttributeChangedData, Payload); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FAFTaskAttributeChangedDelegate OnEvent; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_AttributeChange* ListenAttributeChanged(UGAEffectExtension* OwningExtension, - FGAAttribute InAttribute, - AActor* OptionalExternalTarget = nullptr, - bool OnlyTriggerOnce = false); - - UAFEffectTask_AttributeChange(const FObjectInitializer& ObjectInitializer); - - void SetExternalTarget(AActor* Actor); - - class UAFEffectsComponent* GetTargetASC(); - - virtual void Activate() override; - - void AttributeChangedCallback(FAFAttributeChangedData Payload); - - FGAAttribute Attribute; - - UPROPERTY() - UAFEffectsComponent* OptionalExternalTarget; - - bool UseExternalTarget; - bool OnlyTriggerOnce; - - FDelegateHandle MyHandle; - - - - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp deleted file mode 100644 index 584eaed..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp +++ /dev/null @@ -1,80 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityInterface.h" -#include "AFEffectsComponent.h" -#include "AFEffectTask_EffectAppliedToSelf.h" - - - - -UAFEffectTask_EffectAppliedToSelf::UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - -} - -UAFEffectTask_EffectAppliedToSelf* UAFEffectTask_EffectAppliedToSelf::ListenEffectAppliedToSelf(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) -{ - auto MyObj = NewEffectTask(OwningExtension, TaskName); - MyObj->SetExternalTarget(OptionalExternalTarget); - MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - - return MyObj; -} - -void UAFEffectTask_EffectAppliedToSelf::Activate() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - MyHandle = ASC->OnAppliedToSelf.AddUObject(this, &UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback);//AddExecuteEvent(Tag, Delegate); - } - - Super::Activate(); -} - -void UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback(FAFContextHandle Context - , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec) -{ - //if (ShouldBroadcastAbilityTaskDelegates()) - { - OnEvent.Broadcast(Context, Property, Spec); - } - if (OnlyTriggerOnce) - { - EndTask(); - } -} -void UAFEffectTask_EffectAppliedToSelf::OnTaskEnded() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - ASC->OnAppliedToSelf.Remove(MyHandle); - } -} -void UAFEffectTask_EffectAppliedToSelf::SetExternalTarget(AActor* Actor) -{ - if (Actor) - { - - if (IAFAbilityInterface* interface = Cast(Actor)) - { - UseExternalTarget = true; - OptionalExternalTarget = interface->GetEffectsComponent(); - } - - } -} - -UAFEffectsComponent* UAFEffectTask_EffectAppliedToSelf::GetTargetASC() -{ - if (UseExternalTarget) - { - return OptionalExternalTarget; - } - - return EffectsComponent; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h deleted file mode 100644 index 81ac081..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h +++ /dev/null @@ -1,50 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "AFEffectTask_EffectAppliedToSelf.generated.h" - - - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectTask -{ - GENERATED_BODY() -public: - DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); - UPROPERTY(BlueprintAssignable) - FAFEffectEventDelegate OnEvent; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectAppliedToSelf* ListenEffectAppliedToSelf(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); - - UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer); - - void SetExternalTarget(AActor* Actor); - - class UAFEffectsComponent* GetTargetASC(); - - virtual void Activate() override; - - virtual void GameplayEventCallback(FAFContextHandle Context - , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec); - - virtual void OnTaskEnded() override; - - UPROPERTY() - UAFEffectsComponent* OptionalExternalTarget; - - bool UseExternalTarget; - bool OnlyTriggerOnce; - - FDelegateHandle MyHandle; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp deleted file mode 100644 index 9c8b566..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp +++ /dev/null @@ -1,85 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityInterface.h" -#include "AFEffectsComponent.h" -#include "AFEffectTask_EffectAppliedToTarget.h" - - - - -UAFEffectTask_EffectAppliedToTarget::UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - -} - -UAFEffectTask_EffectAppliedToTarget* UAFEffectTask_EffectAppliedToTarget::ListenEffectAppliedToTarget(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) -{ - auto MyObj = NewEffectTask(OwningExtension, TaskName); - MyObj->SetExternalTarget(OptionalExternalTarget); - MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - - return MyObj; -} - -void UAFEffectTask_EffectAppliedToTarget::Activate() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - //(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback - //FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback); - //MyHandle = Delegate.GetHandle(); - MyHandle = ASC->OnAppliedToTarget.AddUObject(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback);//AddExecuteEvent(Tag, Delegate); - } - - Super::Activate(); -} - -void UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback(FAFContextHandle Context - , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec) -{ - //if (ShouldBroadcastAbilityTaskDelegates()) - { - OnEvent.Broadcast(Context, Property, Spec); - } - if (OnlyTriggerOnce) - { - EndTask(); - } -} - -void UAFEffectTask_EffectAppliedToTarget::OnTaskEnded() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - ASC->OnAppliedToTarget.Remove(MyHandle); - } -} - -void UAFEffectTask_EffectAppliedToTarget::SetExternalTarget(AActor* Actor) -{ - if (Actor) - { - - if (IAFAbilityInterface* interface = Cast(Actor)) - { - UseExternalTarget = true; - OptionalExternalTarget = interface->GetEffectsComponent(); - } - - } -} - -UAFEffectsComponent* UAFEffectTask_EffectAppliedToTarget::GetTargetASC() -{ - if (UseExternalTarget) - { - return OptionalExternalTarget; - } - - return EffectsComponent; -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h deleted file mode 100644 index 665f5a4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h +++ /dev/null @@ -1,50 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "AFEffectTask_EffectAppliedToTarget.generated.h" - - - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffectTask -{ - GENERATED_BODY() -public: - DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); - UPROPERTY(BlueprintAssignable) - FAFEffectEventDelegate OnEvent; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectAppliedToTarget* ListenEffectAppliedToTarget(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); - - UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer); - - void SetExternalTarget(AActor* Actor); - - class UAFEffectsComponent* GetTargetASC(); - - virtual void Activate() override; - - virtual void GameplayEventCallback(FAFContextHandle Context - , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec); - - virtual void OnTaskEnded() override; - - UPROPERTY() - UAFEffectsComponent* OptionalExternalTarget; - - bool UseExternalTarget; - bool OnlyTriggerOnce; - - FDelegateHandle MyHandle; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp deleted file mode 100644 index c59cda4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp +++ /dev/null @@ -1,84 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "../../AFAbilityInterface.h" -#include "AFEffectsComponent.h" -#include "AFEffectTask_EffectEvent.h" - - - - -UAFEffectTask_EffectEvent::UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - -} - -UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) -{ - auto MyObj = NewEffectTask(OwningExtension, TaskName); - MyObj->Tag = Tag; - MyObj->SetExternalTarget(OptionalExternalTarget); - MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - - return MyObj; -} - -void UAFEffectTask_EffectEvent::Activate() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - //(this, &UAFEffectTask_EffectEvent::GameplayEventCallback - FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); - MyHandle = Delegate.GetHandle(); - ASC->AddEvent(Tag, Delegate); - } - - Super::Activate(); -} - -void UAFEffectTask_EffectEvent::GameplayEventCallback(FAFEventData Payload) -{ - //if (ShouldBroadcastAbilityTaskDelegates()) - { - OnEvent.Broadcast(Payload); - } - if (OnlyTriggerOnce) - { - EndTask(); - } -} - -void UAFEffectTask_EffectEvent::OnTaskEnded() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - ASC->RemoveEvent(Tag, MyHandle); - } -} - -void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) -{ - if (Actor) - { - - if (IAFAbilityInterface* interface = Cast(Actor)) - { - UseExternalTarget = true; - OptionalExternalTarget = interface->GetEffectsComponent(); - } - - } -} - -UAFEffectsComponent* UAFEffectTask_EffectEvent::GetTargetASC() -{ - if (UseExternalTarget) - { - return OptionalExternalTarget; - } - - return EffectsComponent; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h deleted file mode 100644 index 52f79d4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_EffectEvent.h +++ /dev/null @@ -1,48 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "../../GAGlobalTypes.h" -#include "AFEffectTask_EffectEvent.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintAssignable) - FAFEffectEventDelegate OnEvent; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_EffectEvent* ListenEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); - - UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer); - - void SetExternalTarget(AActor* Actor); - - class UAFEffectsComponent* GetTargetASC(); - - virtual void Activate() override; - - virtual void GameplayEventCallback(FAFEventData Payload); - - virtual void OnTaskEnded() override; - - FGameplayTag Tag; - - UPROPERTY() - UAFEffectsComponent* OptionalExternalTarget; - - bool UseExternalTarget; - bool OnlyTriggerOnce; - - FDelegateHandle MyHandle; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp deleted file mode 100644 index cdeaaa0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp +++ /dev/null @@ -1,84 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "AFAbilityInterface.h" -#include "AFEffectsComponent.h" -#include "AFEffectTask_ExecutedEffectEvent.h" - - - - -UAFEffectTask_ExecutedEffectEvent::UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - -} - -UAFEffectTask_ExecutedEffectEvent* UAFEffectTask_ExecutedEffectEvent::ListenExecutedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) -{ - auto MyObj = NewEffectTask(OwningExtension, TaskName); - MyObj->Tag = Tag; - MyObj->SetExternalTarget(OptionalExternalTarget); - MyObj->OnlyTriggerOnce = OnlyTriggerOnce; - - return MyObj; -} - -void UAFEffectTask_ExecutedEffectEvent::Activate() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - //(this, &UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback - FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback); - MyHandle = Delegate.GetHandle(); - ASC->AddExecuteEvent(Tag, Delegate); - } - - Super::Activate(); -} - -void UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback(FAFEventData Payload) -{ - //if (ShouldBroadcastAbilityTaskDelegates()) - { - OnEvent.Broadcast(Payload); - } - if (OnlyTriggerOnce) - { - EndTask(); - } -} - -void UAFEffectTask_ExecutedEffectEvent::OnTaskEnded() -{ - UAFEffectsComponent* ASC = GetTargetASC(); - if (ASC) - { - ASC->RemoveExecuteEvent(Tag, MyHandle); - } -} - -void UAFEffectTask_ExecutedEffectEvent::SetExternalTarget(AActor* Actor) -{ - if (Actor) - { - - if (IAFAbilityInterface* interface = Cast(Actor)) - { - UseExternalTarget = true; - OptionalExternalTarget = interface->GetEffectsComponent(); - } - - } -} - -UAFEffectsComponent* UAFEffectTask_ExecutedEffectEvent::GetTargetASC() -{ - if (UseExternalTarget) - { - return OptionalExternalTarget; - } - - return EffectsComponent; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h deleted file mode 100644 index c4253e3..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h +++ /dev/null @@ -1,49 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "../../GAGlobalTypes.h" -#include "AFEffectTask_ExecutedEffectEvent.generated.h" - - - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORK_API UAFEffectTask_ExecutedEffectEvent : public UAFEffectTask -{ - GENERATED_BODY() -public: - DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); - UPROPERTY(BlueprintAssignable) - FAFEffectEventDelegate OnEvent; - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) - static UAFEffectTask_ExecutedEffectEvent* ListenExecutedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); - - UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer); - - void SetExternalTarget(AActor* Actor); - - class UAFEffectsComponent* GetTargetASC(); - - virtual void Activate() override; - - virtual void GameplayEventCallback(FAFEventData Payload); - - virtual void OnTaskEnded() override; - - FGameplayTag Tag; - - UPROPERTY() - UAFEffectsComponent* OptionalExternalTarget; - - bool UseExternalTarget; - bool OnlyTriggerOnce; - - FDelegateHandle MyHandle; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp deleted file mode 100644 index b8c4ed5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.cpp +++ /dev/null @@ -1,371 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "AFAbilityComponent.h" - - -#include "GABlueprintLibrary.h" - -#include "AFAbilityInterface.h" -#include "GAGameEffect.h" -#include "AFEffectCustomApplication.h" - -#include "GAEffectExtension.h" - -UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} - - -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToObject( - UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier) -{ - return ApplyEffectToObject(InEffect, Handle, Target, Instigator, Causer, Modifier); -} - -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToActor( - UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle - , class AActor* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier) -{ - return ApplyEffectToActor(InEffect, Handle, Target, Instigator, Causer, Modifier); -} - -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation( - UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle - , const FHitResult& Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier) -{ - return ApplyEffectFromHit(InEffect, Handle, Target, Instigator, Causer, Modifier); -} - -FGAEffectHandle UGABlueprintLibrary::ApplyEffect( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FHitResult& HitIn - , const FAFFunctionModifier& Modifier) -{ - IAFAbilityInterface* Ability = Cast(Causer); - if (!Ability) - { - UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); - return FGAEffectHandle(); - } - - IAFAbilityInterface* TargetInterface = Cast(Target); - if (!InEffect.GetClass().GetDefaultObject()->Application.GetDefaultObject()->CanApply(TargetInterface, InEffect.GetClass())) - { - return FGAEffectHandle(); - } - bool bReusedParams = false; - bool bPeriodicEffect = false; - bool bReusedSpec = false; - if (Handle.IsValid() && (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) - { - bPeriodicEffect = true; - } - - FAFContextHandle Context; - FAFEffectSpecHandle EffectSpecHandle; - - //only reused Spec and Context if effect is instant ? - if (Handle.IsValid() && !bPeriodicEffect) - { - FAFContextHandle ExistingContext = InEffect.GetContext(Handle); - if (ExistingContext.IsValid()) - { - Context = ExistingContext; - Context.SetTarget(Target); - bReusedParams = true; - } - FAFEffectSpecHandle SpecHandle = InEffect.GetEffectSpec(Handle); - EffectSpecHandle = SpecHandle; - bReusedParams = true; - bReusedSpec = true; - } - else - { - Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - } - - InEffect.InitializeIfNotInitialized(Context.GetRef()); - UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); - - - if ((InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) - { - bPeriodicEffect = true; - } - - if (!InEffect.IsInitialized()) - { - UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); - return FGAEffectHandle(); - } - - - if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) - { - return FGAEffectHandle(); - } - if (Target2->DenyEffectApplication(InEffect.GetSpec()->DenyTags)) - { - return FGAEffectHandle(); - } - UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); - - FGAEffect effect; - effect.World = Instigator->GetWorld(); - if (Ability) - { - //InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); - - effect.PredictionHandle = Ability->GetPredictionHandle(); - } - IAFAbilityInterface* InstigatorInterface = Cast(Instigator); - - FAFEffectParams Params(InEffect); - - if (!bReusedSpec) - { - FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); - AddTagsToEffect(EffectSpec); - Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); - } - else - { - Params.EffectSpec = EffectSpecHandle; - } - Params.bRecreated = bReusedParams; - Params.bPeriodicEffect = bPeriodicEffect; - Params.Context = Context; - - FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); - - return NewHandle; -} -FGAEffectHandle UGABlueprintLibrary::ApplyEffect( - FGAEffectProperty* InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FHitResult& HitIn - , const FAFFunctionModifier& Modifier) -{ - //IAFAbilityInterface* Ability = Cast(Causer); - //if (!Ability) - //{ - // UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); - // return FGAEffectHandle(); - //} - //bool bReusedParams = false; - //bool bPeriodicEffect = false; - //bool bReusedSpec = false; - //if (Handle.IsValid() && (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0)) - //{ - // bPeriodicEffect = true; - //} - - //FAFContextHandle Context; - //FAFEffectSpecHandle EffectSpecHandle; - - //if (Handle.IsValid()) - //{ - // if (bPeriodicEffect) - // { - // FAFContextHandle* ExistingContext = InEffect->GetContext(Handle); - // if (ExistingContext) - // { - // Context = *ExistingContext; - // Context.SetTarget(Target); - // bReusedParams = true; - // } - // FAFEffectSpecHandle* SpecHandle = InEffect->GetEffectSpec(Handle); - // EffectSpecHandle = *SpecHandle; - // bReusedSpec = true; - // } - // else - // { - // Context = InEffect->GetInstantContext(); - // Context.SetTarget(Target); - - // EffectSpecHandle = InEffect->GetInstantEffectSpec(); - // bReusedParams = true; - // bReusedSpec = true; - // } - //} - //else - //{ - // Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - //} - - //InEffect->InitializeIfNotInitialized(Context.GetRef()); - - //if (!InEffect->IsInitialized()) - //{ - // UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); - // return FGAEffectHandle(); - //} - - //UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); - //if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) - //{ - // return FGAEffectHandle(); - //} - //if (Target2->DenyEffectApplication(InEffect->GetSpec()->DenyTags)) - //{ - // return FGAEffectHandle(); - //} - //UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); - - //FGAEffect effect; - //effect.World = Instigator->GetWorld(); - //if (Ability) - //{ - // InEffect->SetPredictionHandle(Ability->GetPredictionHandle()); - // effect.PredictionHandle = Ability->GetPredictionHandle(); - // - //} - // - //FAFPropertytHandle Property = FAFPropertytHandle::Generate(*InEffect); - //FAFEffectParams Params(Property); - //FAFEffectSpec* EffectSpec = new FAFEffectSpec(); - ////AddTagsToEffect(EffectSpec); - //Params.Context = Context; - // - //Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); - - //IAFAbilityInterface* InstigatorInterface = Cast(Instigator); - //FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); - FGAEffectHandle NewHandle; - return NewHandle; -} -FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , const FHitResult& Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier) -{ - return ApplyEffect(InEffect, Handle, Target.GetActor(), Instigator, Causer, Target, Modifier); -} - -FGAEffectHandle UGABlueprintLibrary::ApplyEffectToActor( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class AActor* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier) -{ - FHitResult Hit(ForceInit); - return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); -} - -FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier) -{ - FHitResult Hit(ForceInit); - return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); -} - -FAFContextHandle UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, - AActor* InAvatar, UObject* Causer, const FHitResult& HitIn) -{ - IAFAbilityInterface* targetAttr = Cast(Target); - IAFAbilityInterface* instiAttr = Cast(Instigator); - if (!targetAttr && !instiAttr) - { - UE_LOG(GameAttributesEffects, Error, TEXT("Target and Instigator does not implement IAFAbilityInterface interface")); - return FAFContextHandle(); - } - UAFAbilityComponent* targetComp = nullptr; - UAFAbilityComponent* instiComp = nullptr; - if (targetAttr) - { - targetComp = targetAttr->GetAbilityComp(); - } - if (instiAttr) - { - instiComp = instiAttr->GetAbilityComp(); - } - - FVector location = targetComp ? targetComp->GetOwner()->GetActorLocation() : FVector(HitIn.ImpactPoint.X, HitIn.ImpactPoint.Y, HitIn.ImpactPoint.Z); - FGAEffectContext* Context = new FGAEffectContext( - targetAttr ? targetAttr->GetAttributes() : nullptr - , instiAttr ? instiAttr->GetAttributes() : nullptr - , location - , Target - , Causer - , Instigator - , targetComp - , instiComp - , InAvatar); - - Context->HitResult = HitIn; - - FAFContextHandle Handle = FAFContextHandle::Generate(Context); - - return Handle; -} - -void UGABlueprintLibrary::AddTagsToEffect(FAFEffectSpec* EffectIn) -{ - if (EffectIn) - { - EffectIn->AddOwnedTags(EffectIn->GetSpec()->OwnedTags); - EffectIn->AddApplyTags(EffectIn->GetSpec()->ApplyTags); - } -} - -FGAEffectContext& UGABlueprintLibrary::GetContext(const FAFContextHandle& InHandle) -{ - return InHandle.GetRef(); -} - -UAFAbilityComponent* UGABlueprintLibrary::GetTargetComponent(const FGAEffectHandle& InHandle) -{ - return nullptr;// InHandle.GetContextRef().InstigatorComp.Get(); -} - -UAFAbilityComponent* UGABlueprintLibrary::GetInstigatorComponent(const FGAEffectHandle& InHandle) -{ - return nullptr;// InHandle.GetContextRef().TargetComp.Get(); -} - -void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag) -{ - IAFAbilityInterface* targetAttr = Cast(Target); - if (!targetAttr) - return; - - UAFAbilityComponent* TargetComp = targetAttr->GetAbilityComp(); - if (!TargetComp) - return; - - //FAFEventData EventData; - //TargetComp->NativeTriggerTagEvent(EventTag, EventData); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h deleted file mode 100644 index 62faec3..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GABlueprintLibrary.h +++ /dev/null @@ -1,111 +0,0 @@ -#pragma once -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "Attributes/GAAttributeBase.h" -#include "GAEffectGlobalTypes.h" -#include "GABlueprintLibrary.generated.h" - -UCLASS(BlueprintType, Blueprintable) -class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_UCLASS_BODY() -public: - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToObject( - UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier); - - /* - Makes outgoing effect spec and assign handle to it. - If valid handle is provided it will instead reuse existing effect spec from handle, - and just change context of effect. - */ - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToActor( - UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle - , class AActor* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier); - - /* - Makes outgoing effect spec and assign handle to it. - If valid handle is provided it will instead reuse existing effect spec from handle, - and just change context of effect. - */ - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToLocation( - UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle - , const FHitResult& Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier); - - static FGAEffectHandle ApplyEffect( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FHitResult& HitIn - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - static FGAEffectHandle ApplyEffect( - FGAEffectProperty* InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FHitResult& HitIn - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - static FGAEffectHandle ApplyEffectFromHit( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , const FHitResult& Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier); - - static FGAEffectHandle ApplyEffectToActor( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class AActor* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier); - - static FGAEffectHandle ApplyEffectToObject( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FAFFunctionModifier& Modifier); - /* - Create Effect but does not apply it. - */ - - static FAFContextHandle MakeContext(class UObject* Target, class APawn* Instigator, AActor* InAvatar, - UObject* Causer, const FHitResult& HitIn); - static void AddTagsToEffect(FAFEffectSpec* EffectIn); - - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") - static FGAEffectContext& GetContext(const FAFContextHandle& InHandle); - - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") - static UAFAbilityComponent* GetTargetComponent(const FGAEffectHandle& InHandle); - - UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") - static UAFAbilityComponent* GetInstigatorComponent(const FGAEffectHandle& InHandle); - - UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static void BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp deleted file mode 100644 index 2fa6e5d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.cpp +++ /dev/null @@ -1,11 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "../GAGlobalTypes.h" -#include "GACustomCalculation.h" - -UGACustomCalculation::UGACustomCalculation(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h deleted file mode 100644 index 265264d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GACustomCalculation.h +++ /dev/null @@ -1,30 +0,0 @@ -#pragma once -#include "../GAGlobalTypes.h" -#include "../GAHelperTemplates.h" -#include "../Attributes/GAAttributeBase.h" -#include "GAGameEffect.h" -#include "GACustomCalculation.generated.h" - -/* - Simple base class for custom magnitude calculation. - You can implement here any kind of formula, taking arbitrary information, for calculations. - - Object is instanced inside effect spec, so you can add custom properties set up, as per - effect spec base. - - Please refrain from making super complicated things, which calculate everything, it's - generally not purpose of this class, but if you really want.. (;. -*/ -UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGACustomCalculation : public UObject -{ - GENERATED_BODY() -public: - UGACustomCalculation(const FObjectInitializer& ObjectInitializer); - - //UFUNCTION(BlueprintNativeEvent, Category = "Attributes") - // float CalculateMagnitude(const FGAEffectContext& ContextIn); - - - virtual float NativeCalculateMagnitude(const FGAEffectContext& ContextIn) { return 0; } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp deleted file mode 100644 index 1edd0b9..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GAEffectBlueprint.h" - -////////////////////////////////////////////////////////////////////////// -// UGameplayAbilityBlueprint - -UGAEffectBlueprint::UGAEffectBlueprint(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#if WITH_EDITOR - -/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ -UGAEffectBlueprint* UGAEffectBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectBlueprint* DerivedBlueprint) -{ - UGAEffectBlueprint* ParentBP = NULL; - - // Determine if there is a gameplay ability blueprint in the ancestry of this class - for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) - { - if (UGAEffectBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) - { - ParentBP = TestBP; - } - } - - return ParentBP; -} - -#endif diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h deleted file mode 100644 index 953751b..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectBlueprint.h +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Engine/Blueprint.h" -#include "GAEffectBlueprint.generated.h" - -/** - * Game Effect Blueprint - */ - -UCLASS(BlueprintType) -class ABILITYFRAMEWORK_API UGAEffectBlueprint : public UBlueprint -{ - GENERATED_UCLASS_BODY() - -#if WITH_EDITOR - - // UBlueprint interface - virtual bool SupportedByDefaultBlueprintFactory() const override - { - return false; - } - // End of UBlueprint interface - - /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ - static UGAEffectBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectBlueprint* DerivedBlueprint); - -#endif -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp deleted file mode 100644 index 0564782..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.cpp +++ /dev/null @@ -1,162 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../AbilityFramework.h" -#include "MovieScene.h" -#include "GAEffectCueSequence.h" -#include "ActorSequencePlayer.h" -#include "GAEffectCue.h" - -AGAEffectCue::AGAEffectCue(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - PrimaryActorTick.bCanEverTick = true; - PrimaryActorTick.bStartWithTickEnabled = true; - StartTime = 0; - EndTime = 5; - if (HasAnyFlags(RF_ClassDefaultObject) || GetArchetype() == GetDefault()) - { - Sequence = ObjectInitializer.CreateDefaultSubobject(this, "Sequence"); - Sequence->SetFlags(RF_Public | RF_Transactional); - SequencePlayer = ObjectInitializer.CreateDefaultSubobject(this, "SequencePlayer"); - } -} -void AGAEffectCue::PostInitProperties() -{ - UpdateAssetRegistryInfo(); - Super::PostInitProperties(); -} - -void AGAEffectCue::Serialize(FArchive& Ar) -{ - if (Ar.IsSaving()) - { - UpdateAssetRegistryInfo(); - } - - Super::Serialize(Ar); - - if (Ar.IsLoading()) - { - UpdateAssetRegistryInfo(); - } -} -#if WITH_EDITORONLY_DATA -void AGAEffectCue::UpdateAssetBundleData() -{ - AssetBundleData.Reset(); - UpdateAssetRegistryInfo(); - - // By default parse the metadata - if (UAssetManager::IsValid()) - { - UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); - } -} - -void AGAEffectCue::PreSave(const class ITargetPlatform* TargetPlatform) -{ - Super::PreSave(TargetPlatform); - - UpdateAssetBundleData(); - - if (UAssetManager::IsValid()) - { - // Bundles may have changed, refresh - UAssetManager::Get().RefreshAssetData(this); - } -} -#endif -void AGAEffectCue::PostLoad() -{ - Super::PostLoad(); - -#if WITH_EDITORONLY_DATA - FAssetBundleData OldData = AssetBundleData; - - UpdateAssetBundleData(); - - if (UAssetManager::IsValid() && OldData != AssetBundleData) - { - // Bundles changed, refresh - UAssetManager::Get().RefreshAssetData(this); - } -#endif -} -FPrimaryAssetId AGAEffectCue::GetPrimaryAssetId() const -{ - FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); - - const AGAEffectCue* A = this; - return FPrimaryAssetId(FPrimaryAssetType("EffectCue"), dupa1); - //if (HasAnyFlags(RF_ClassDefaultObject)) - { - UClass* SearchNativeClass = GetClass(); - - while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) - { - SearchNativeClass = SearchNativeClass->GetSuperClass(); - } - - if (SearchNativeClass && SearchNativeClass != GetClass()) - { - // If blueprint, return native class and asset name - - } - - // Native CDO, return nothing - return FPrimaryAssetId(); - } - - // Data assets use Class and ShortName by default, there's no inheritance so class works fine - //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); -} - -void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) -{ - Sequence = InSequence; -} -// Called when the game starts or when spawned -void AGAEffectCue::BeginPlay() -{ - if (!SequencePlayer) - { - SequencePlayer = NewObject(this, UActorSequencePlayer::StaticClass(), "SequencerPlayer"); - } - SequencePlayer->Initialize(Sequence, PlaybackSettings); - - Super::BeginPlay(); - //NativeBeginCue(); -} - -// Called every frame -void AGAEffectCue::Tick( float DeltaTime ) -{ - Super::Tick( DeltaTime ); - if (SequencePlayer) - { - SequencePlayer->Update(DeltaTime); - } -} -void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, - const FHitResult& HitInfo, const FGAEffectCueParams& CueParams) -{ - BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); - if (!SequencePlayer) - { - SequencePlayer->Play(); - } -} - -void AGAEffectCue::NativeOnExecuted() -{ - OnExecuted(); -} -void AGAEffectCue::NativeOnRemoved() -{ - OnRemoved(); -} - -void AGAEffectCue::UpdateAssetRegistryInfo() -{ - EffectCueTagSearch = CueTag.GetTagName(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h deleted file mode 100644 index 0301b04..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCue.h +++ /dev/null @@ -1,85 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GameFramework/Actor.h" -#include "MovieSceneSequencePlayer.h" -#include "GAGlobalTypes.h" -#include "GameplayTags.h" -#include "AssetBundleData.h" -#include "Engine/AssetManager.h" -#include "GAEffectCue.generated.h" -class UActorSequencePlayer; -UCLASS() -class ABILITYFRAMEWORK_API AGAEffectCue : public AActor -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere, Category = "Cue") - FGameplayTag CueTag; - UPROPERTY(AssetRegistrySearchable) - FName EffectCueTagSearch; - UPROPERTY() - FAssetBundleData AssetBundleData; -public: - // Sets default values for this actor's properties - AGAEffectCue(const FObjectInitializer& ObjectInitializer); - void PostInitProperties() override; - - void Serialize(FArchive& Ar) override; - -#if WITH_EDITORONLY_DATA - void UpdateAssetBundleData(); - void PreSave(const class ITargetPlatform* TargetPlatform) override; -#endif //WITH_EDITORONLY_DATA - void PostLoad() override; - FPrimaryAssetId GetPrimaryAssetId() const override; - // Called when the game starts or when spawned - virtual void BeginPlay() override; - - // Called every frame - virtual void Tick( float DeltaSeconds ) override; - - - UFUNCTION(BlueprintImplementableEvent) - void BeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, - const FHitResult& HitInfo); - - UFUNCTION(BlueprintImplementableEvent) - void OnExecuted(); - - UFUNCTION(BlueprintImplementableEvent) - void OnExpired(); - - UFUNCTION(BlueprintImplementableEvent) - void OnRemoved(); - - void NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, - const FHitResult& HitInfo, const FGAEffectCueParams& CueParams); - - void NativeOnExecuted(); - void NativeOnRemoved(); - UPROPERTY() - float Duration; - UPROPERTY() - float Period; - - void SetAnimation(class UGAEffectCueSequence* InSequence); - UPROPERTY() - double StartTime; - UPROPERTY() - double EndTime; - /** Animation being played */ - UPROPERTY(EditAnywhere, Instanced, Export, Category = Animation) - UGAEffectCueSequence* Sequence; - UPROPERTY(transient, BlueprintReadOnly, Category = Animation) - UActorSequencePlayer* SequencePlayer; - - UPROPERTY(EditAnywhere, Category = "Playback", meta = (ShowOnlyInnerProperties)) - FMovieSceneSequencePlaybackSettings PlaybackSettings; - - FTimerHandle PeriodTimer; - -protected: - void UpdateAssetRegistryInfo(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp deleted file mode 100644 index 580daab..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.cpp +++ /dev/null @@ -1,13 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GAEffectCueBlueprintGeneratedClass.h" - -////////////////////////////////////////////////////////////////////////// -// UGameplayAbilityBlueprint - -UGAEffectCueBlueprintGeneratedClass::UGAEffectCueBlueprintGeneratedClass(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h deleted file mode 100644 index d6af270..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueBlueprintGeneratedClass.h +++ /dev/null @@ -1,17 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Engine/BlueprintGeneratedClass.h" -#include "GAEffectCueBlueprintGeneratedClass.generated.h" - -/** - * Game Effect Blueprint - */ - -UCLASS(BlueprintType) -class ABILITYFRAMEWORK_API UGAEffectCueBlueprintGeneratedClass : public UBlueprintGeneratedClass -{ - GENERATED_UCLASS_BODY() -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp deleted file mode 100644 index 3f57b12..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.cpp +++ /dev/null @@ -1,51 +0,0 @@ -#pragma once -#include "../AbilityFramework.h" -#include "../AFAbilityComponent.h" -#include "GAEffectCueGlobals.h" - -void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn) -{ - //if (!CueIn) - //{ - // return; - //} - //UGAEffectCue* Cue = NewObject(OwningComponent.Get(), CueIn); - //Cues.Add(HandleIn, Cue); - //Cue->SetParameters(OwningComponent->GetOwner(), CueParamsIn); - //Cue->BeginCue(); -} -void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn) -{ - //Cues.Add(HandleIn, CueIn); -} -class UGAEffectCue* FGACueContainer::GetCue(const FGAEffectHandle& HandleIn) -{ - //UGAEffectCue* Cue = nullptr; - //Cue = Cues.FindRef(HandleIn); - return nullptr; -} -void FGACueContainer::ExecuteCue(const FGAEffectHandle& HandleIn) -{ - //UGAEffectCue* Cue = GetCue(HandleIn); - //if (Cue) - //{ - // Cue->ExecuteCue(); - //} -} -void FGACueContainer::RemoveCue(const FGAEffectHandle& HandleIn) -{ - //UGAEffectCue* Cue; - //if (Cues.Num() > 0) - //{ - // Cues.RemoveAndCopyValue(HandleIn, Cue); - // if (Cue) - // { - // Cue->EndCue(); - // Cue->MarkPendingKill(); - // } - //} -} -void FGACueContainer::CueExpired(const FGAEffectHandle& HandleIn) -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h deleted file mode 100644 index bed97a4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueGlobals.h +++ /dev/null @@ -1,26 +0,0 @@ -#pragma once -#include "GameplayTagContainer.h" -#include "../GAGlobalTypes.h" -#include "GAGameEffect.h" -#include "GAEffectCueGlobals.generated.h" - -USTRUCT() -struct FGACueContainer -{ - GENERATED_USTRUCT_BODY() -public: - TWeakObjectPtr OwningComponent; - - void AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn); - - void AddCue(const FGAEffectHandle& HandleIn); - - /* Return cue. Might return null so always check it first! */ - class UGAEffectCue* GetCue(const FGAEffectHandle& HandleIn); - - void ExecuteCue(const FGAEffectHandle& HandleIn); - - void RemoveCue(const FGAEffectHandle& HandleIn); - - void CueExpired(const FGAEffectHandle& HandleIn); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp deleted file mode 100644 index b373f14..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.cpp +++ /dev/null @@ -1,130 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "../AbilityFramework.h" -#include "GAEffectCue.h" -#include "MovieScene.h" -#include "MovieSceneCommonHelpers.h" -#include "Modules/ModuleManager.h" -#include "Engine/BlueprintGeneratedClass.h" -#include "Engine/Blueprint.h" -#include "GameFramework/Actor.h" -#include "Classes/Engine/SCS_Node.h" -#include "Classes/Engine/SimpleConstructionScript.h" -#include "Engine/Blueprint.h" -#include "UObject/Package.h" -#include "ActorSequenceObjectReference.h" -#include "GAEffectCueSequence.h" - - -#if WITH_EDITOR -UGAEffectCueSequence::FOnInitialize UGAEffectCueSequence::OnInitializeSequenceEvent; -#endif - -UGAEffectCueSequence::UGAEffectCueSequence(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) - , MovieScene(nullptr) -#if WITH_EDITOR - , bHasBeenInitialized(false) -#endif -{ - bParentContextsAreSignificant = true; - - MovieScene = ObjectInitializer.CreateDefaultSubobject(this, "MovieScene"); - MovieScene->SetFlags(RF_Transactional); -} - -void UGAEffectCueSequence::PostInitProperties() -{ -#if WITH_EDITOR && WITH_EDITORONLY_DATA - AGAEffectCue* OwnerCue = Cast(GetOuter()); - if (!bHasBeenInitialized && !HasAnyFlags(RF_ClassDefaultObject) && OwnerCue && !OwnerCue->HasAnyFlags(RF_ClassDefaultObject)) - { - FGuid BindingID = MovieScene->AddPossessable(OwnerCue ? OwnerCue->GetActorLabel() : TEXT("Owner"), OwnerCue ? OwnerCue->GetClass() : AGAEffectCue::StaticClass()); - //ObjectReferences.CreateBinding(BindingID, FActorSequenceObjectReference::CreateForContextActor()); - - OnInitializeSequenceEvent.Broadcast(this); - bHasBeenInitialized = true; - } -#endif - - Super::PostInitProperties(); -} -#if WITH_EDITOR -UGAEffectCueSequence* UGAEffectCueSequence::GetNullAnimation() -{ - static UGAEffectCueSequence* NullAnimation = nullptr; - - if (!NullAnimation) - { - NullAnimation = NewObject(GetTransientPackage(), NAME_None); - NullAnimation->AddToRoot(); - NullAnimation->MovieScene = NewObject(NullAnimation, FName("No Animation")); - NullAnimation->MovieScene->AddToRoot(); - } - - return NullAnimation; -} -#endif //WITH_EDITOR -FFrameNumber UGAEffectCueSequence::GetStartTime() const -{ - return MovieScene->GetPlaybackRange().GetLowerBoundValue(); -} - - -FFrameNumber UGAEffectCueSequence::GetEndTime() const -{ - return MovieScene->GetPlaybackRange().GetUpperBoundValue(); -} - - -/* UMovieSceneAnimation overrides -*****************************************************************************/ - - -void UGAEffectCueSequence::BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) -{ - AActor* ActorContext = CastChecked(Context); - - if (AActor* Actor = Cast(&PossessedObject)) - { - //ObjectReferences.CreateBinding(ObjectId, FActorSequenceObjectReference::CreateForActor(Actor, ActorContext)); - } -} - - -bool UGAEffectCueSequence::CanPossessObject(UObject& Object, UObject* InPlaybackContext) const -{ - AActor* ActorContext = CastChecked(InPlaybackContext); - - if (AActor* Actor = Cast(&Object)) - { - return Actor == InPlaybackContext || Actor->GetLevel() == ActorContext->GetLevel(); - } - return true; -} - -void UGAEffectCueSequence::LocateBoundObjects(const FGuid& ObjectId, UObject* Context, TArray>& OutObjects) const -{ - if (Context) - { - //ObjectReferences.ResolveBinding(ObjectId, CastChecked(Context), OutObjects); - } -} - - -UMovieScene* UGAEffectCueSequence::GetMovieScene() const -{ - return MovieScene; -} - - -UObject* UGAEffectCueSequence::GetParentObject(UObject* Object) const -{ - - return GetOuter(); -} - -void UGAEffectCueSequence::UnbindPossessableObjects(const FGuid& ObjectId) -{ - //ObjectReferences.RemoveBinding(ObjectId); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h deleted file mode 100644 index c61235f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectCueSequence.h +++ /dev/null @@ -1,69 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "GameFramework/Actor.h" -#include "MovieSceneSequence.h" -#include "MovieScene.h" -#include "LazyObjectPtr.h" -#include "ActorSequence.h" -#include "FrameNumber.h" -#include "GAEffectCueSequence.generated.h" - -UCLASS(BlueprintType, DefaultToInstanced) -class ABILITYFRAMEWORK_API UGAEffectCueSequence : public UMovieSceneSequence -{ - GENERATED_BODY() - -public: - UPROPERTY(Instanced) - UMovieScene* MovieScene; -private: - /** Collection of object references. */ - //UPROPERTY() - // FActorSequenceObjectReferenceMap ObjectReferences; - -#if WITH_EDITORONLY_DATA -private: - bool bHasBeenInitialized; -#endif -public: - // Sets default values for this actor's properties - UGAEffectCueSequence(const FObjectInitializer& ObjectInitializer); - virtual void PostInitProperties() override; -#if WITH_EDITOR - /** - * Get a placeholder animation. - * - * @return Placeholder animation. - */ - static UGAEffectCueSequence* GetNullAnimation(); - - /** Event that is fired to initialize default state for a sequence */ - DECLARE_EVENT_OneParam(UGAEffectCueSequence, FOnInitialize, UGAEffectCueSequence*) - static FOnInitialize OnInitializeSequenceEvent; -public: - static FOnInitialize& OnInitializeSequence() { return OnInitializeSequenceEvent; } - - -#endif -public: - inline UMovieScene* GetMovieScene() { return MovieScene; } - UFUNCTION(BlueprintCallable, Category = "Animation") - FFrameNumber GetStartTime() const; - - /** - * Get the end time of this animation. - * - * @return End time in seconds. - * @see GetStartTime - */ - UFUNCTION(BlueprintCallable, Category = "Animation") - FFrameNumber GetEndTime() const; - virtual void BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) override; - virtual bool CanPossessObject(UObject& Object, UObject* InPlaybackContext) const override; - virtual UMovieScene* GetMovieScene() const override; - virtual UObject* GetParentObject(UObject* Object) const override; - virtual void UnbindPossessableObjects(const FGuid& ObjectId) override; - virtual void LocateBoundObjects(const FGuid& ObjectId, UObject* Context, TArray>& OutObjects) const override; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp deleted file mode 100644 index bcfbe5e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.cpp +++ /dev/null @@ -1,24 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "../GAGlobalTypes.h" -#include "../Attributes/GAAttributeBase.h" -#include "../AFAbilityComponent.h" -#include "GAEffectExecution.h" - -UGAEffectExecution::UGAEffectExecution(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} -void UGAEffectExecution::PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context) -{ - UE_LOG(GameAttributesEffects, Log, TEXT("Sample execution class implementation")); -} -void UGAEffectExecution::ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, - const FAFEffectParams& Params, - const FAFFunctionModifier& Modifier) -{ - PreModifyAttribute(HandleIn, ModIn, Params.GetContext()); - Params.GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty()); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h deleted file mode 100644 index 2236b08..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExecution.h +++ /dev/null @@ -1,22 +0,0 @@ -#pragma once -#include "../GAGlobalTypes.h" -#include "../Attributes/GAAttributeBase.h" -#include "GAGameEffect.h" -#include "GAEffectGlobalTypes.h" -#include "GAEffectExecution.generated.h" - -/* - -*/ -UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGAEffectExecution : public UObject -{ - GENERATED_BODY() -public: - UGAEffectExecution(const FObjectInitializer& ObjectInitializer); - - virtual void PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context); - virtual void ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, - const FAFEffectParams& Params, - const FAFFunctionModifier& Modifier = FAFFunctionModifier()); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp deleted file mode 100644 index 8bd4fac..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.cpp +++ /dev/null @@ -1,70 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "AFEffectsComponent.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "GAEffectExtension.h" - -UGAEffectExtension::UGAEffectExtension(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ -} -void UGAEffectExtension::SetParameters(const FGAEffectContext& ContextIn) -{ - Context = ContextIn; -} -void UGAEffectExtension::BeginEffect() -{ -} - -void UGAEffectExtension::NativeOnEffectApplied() -{ - OnEffectApplied(); -} -void UGAEffectExtension::NativeOnEffectExecuted() -{ - OnEffectExecuted(); -} -void UGAEffectExtension::NativeOnEffectExpired() -{ - OnEffectExpired(); -} -void UGAEffectExtension::NativeOnEffectRemoved() -{ - OnEffectRemoved(); -} - -UWorld* UGAEffectExtension::GetWorld() const -{ - if (Context.Target.IsValid()) - return Context.Target->GetWorld(); - - return nullptr; -} - -void UGAEffectExtension::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) -{ - if (!InstanceName.IsNone()) - { - Tasks.Add(InstanceName, TaskIn); - } -}; -void UGAEffectExtension::AddReplicatedTask(class UAFTaskBase* TaskIn) -{ - //AbilityComponent->ReplicatedTasks.Add(TaskIn); -} -void UGAEffectExtension::OnLatentTaskRemoved(class UAFTaskBase* TaskIn) -{ -}; - -void UGAEffectExtension::OnLatentTaskActivated(class UAFTaskBase* TaskIn) -{ -}; -void UGAEffectExtension::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) -{ -}; - -class UAFTaskBase* UGAEffectExtension::GetCachedLatentAction(FName TaskName) -{ - return Tasks.FindRef(TaskName); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h deleted file mode 100644 index 342e234..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectExtension.h +++ /dev/null @@ -1,79 +0,0 @@ -#pragma once -#include "GameplayTagContainer.h" -#include "../GAGlobalTypes.h" -#include "GAGameEffect.h" - -#include "GameplayTaskOwnerInterface.h" -#include "GAEffectExtension.generated.h" -/* - Instanced effect with active event graph, where you can bind events - on application. - - One instance per ability is applied per actor. (ie, one ability can apply only one instanced - effect to each actor). - So this is not suitable for effects which should have ability to be applied multiple times the same - actor to stack in intensity and still have different durations. - - When the same type of instanced effect from the same instigator will be applied to the same actor - old effect will be terminated and new one will be applied. - Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). -*/ -UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatentInterface //this interface is not needed, but NewTask is expting those functions. -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintReadOnly, Category = "Context") - FGAEffectContext Context; - UPROPERTY() - class UAFEffectsComponent* OwningComponent; - UPROPERTY() - class AActor* Avatar; - - UPROPERTY() - TSet ActiveTasks; - - UPROPERTY() - TMap Tasks; - -public: - UGAEffectExtension(const FObjectInitializer& ObjectInitializer); - void SetParameters(const FGAEffectContext& ContextIn); - void BeginEffect(); - - /* - This event is always executed once upon application. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") - void OnEffectApplied(); - UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") - void OnEffectExecuted(); - /* - Event executed when effet naturally expires. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") - void OnEffectExpired(); - /* - Event executed when this effect is removed by force. - */ - UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") - void OnEffectRemoved(); - - void NativeOnEffectApplied(); - void NativeOnEffectExecuted(); - void NativeOnEffectExpired(); - void NativeOnEffectRemoved(); - - virtual UWorld* GetWorld() const override; - - /* IAFLatentInterface */ - virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn); - virtual void AddReplicatedTask(class UAFTaskBase* TaskIn); - virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn); - - virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn); - virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn); - - virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); - /* IAFLatentInterface */ -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp deleted file mode 100644 index 30e0213..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.cpp +++ /dev/null @@ -1,48 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" - -#include "../Abilities/GAAbilityBase.h" - -#include "GAEffectField.h" - -AGAEffectField::AGAEffectField(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - bReplicates = true; - SetReplicates(true); -} - -void AGAEffectField::InitializeField() -{ - //if (bIsFieldPersistent && AbilityInstigator) - //{ - - //} - //else if (!bIsFieldPersistent && AbilityInstigator) - //{ - // AbilityInstigator->OnAbilityCastEnd.AddUObject(this, &AGAEffectField::DestroyField); - //} - - //1. Automaticallt gather all collision componenets from blueprinted version. - // don't want to hardcode any kind of collision inside base class - // let designer decide what exactly he wants to do with it. - // but on other hand encapsulate this functionality so - // designer won't have to deal with binding/assiging events inside blueprint. - //2. Bind Events from them. -} - -void AGAEffectField::DestroyField() -{ - -} - -void AGAEffectField::OnAbilityExecuted_Implementation() -{ - -} - -void AGAEffectField::OnOtherFieldOverlap_Implementation() -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h deleted file mode 100644 index 6c02bb4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectField.h +++ /dev/null @@ -1,60 +0,0 @@ -#pragma once -#include "GAEffectField.generated.h" - -/* - Base class for effect field. - These fields might exist in two states: - 1. As long as ability is channeled. - 2. They are persistent on their own, which means that ability only create them once - and from create tim they might exist set amount of time (including indefinetly), or - until they are manually removed or destroyed. - - Main use cases: - 1. Createing persistent level effects (fire wall, oil puddle, wall of ice etc). - 2. Spawning other actors (rain of meteors, other pawns). - - Possible functionaltity: - 1. Interacting with other fields (Wind field can extinguish fire field). - 2. Interacting with other direct damage/attribute changes (fire damage, can - ignite oil field, creating fire field). - Not sure about this. I would probabaly need to implement this functionality down the line in - GameSystem Module, or add GameAttributes dependency here. - - Fields are only created on server, and then replicated back to clients. - - Need custom K2 Node to properly spawn this actor!. Default SpawnActorFromClass is - not sufficient. -*/ - -UCLASS(BlueprintType, Blueprintable, DefaultToInstanced) -class ABILITYFRAMEWORK_API AGAEffectField : public AActor -{ - GENERATED_UCLASS_BODY() -public: - /** - * If false, field will exist only as long as ability is channeled. - * Otherwise specific life time. - */ - UPROPERTY(BlueprintReadOnly, meta=(ExposeOnSpawn), Category = "Config") - bool bIsFieldPersistent; - - /** - * How long this field will live in world ? - * Only applicable if bIsFieldPersistent = true; - */ - UPROPERTY(BlueprintReadOnly, meta = (ExposeOnSpawn), Category = "Config") - float Lifetime; - - //UPROPERTY(BlueprintReadOnly, Category = "Owner") - //class AGASAbility* AbilityInstigator; - - void InitializeField(); - - void DestroyField(); - - UFUNCTION(BlueprintNativeEvent, Category = "Ability Field") - void OnAbilityExecuted(); - - UFUNCTION(BlueprintNativeEvent, Category = "Ability Field") - void OnOtherFieldOverlap(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp deleted file mode 100644 index a099560..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.cpp +++ /dev/null @@ -1,143 +0,0 @@ -#pragma once -#include "../AbilityFramework.h" -#include "../AFAbilityComponent.h" -#include "../Attributes/GAAttributeBase.h" -#include "GAEffectExecution.h" -#include "AFAbilityInterface.h" -#include "GAGameEffect.h" -#include "GACustomCalculation.h" - - - -float FGADirectModifier::GetValue() { return Value; } -float FGADirectModifier::GetValue() const { return Value; } -float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) -{ - FAFAttributeBase* attr = nullptr; - float Result = 0; - switch (Source) - { - case EGAAttributeSource::Instigator: - { - IAFAbilityInterface* AttrInt = Cast(Context.Instigator.Get()); - UGAAttributesBase* Attributes = AttrInt->GetAttributes(); - attr = Attributes->GetAttribute(Attribute); - //attr = Context.InstigatorComp->GetAttribute(Attribute); - break; - } - case EGAAttributeSource::Target: - { - IAFAbilityInterface* AttrInt = Cast(Context.Target.Get()); - UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; - attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); - break; - } - case EGAAttributeSource::Causer: - { - IAFAbilityInterface* AttrInt = Cast(Context.Causer.Get()); - UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; - attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); - break; - } - default: - return 0; - } - Result = (Coefficient * (PreMultiply + attr->GetFinalValue()) + PostMultiply) * PostCoefficient; - if (!bUseSecondaryAttribute) - return Result; - - return 0; -} -float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) const -{ - FAFAttributeBase* attr = nullptr; - float Result = 0; - - switch (Source) - { - case EGAAttributeSource::Instigator: - { - IAFAbilityInterface* AttrInt = Cast(Context.Instigator.Get()); - UGAAttributesBase* Attributes = AttrInt->GetAttributes(); - attr = Attributes->GetAttribute(Attribute); - //attr = Context.InstigatorComp->GetAttribute(Attribute); - break; - } - case EGAAttributeSource::Target: - { - IAFAbilityInterface* AttrInt = Cast(Context.Target.Get()); - UGAAttributesBase* Attributes = AttrInt->GetAttributes(); - attr = Attributes->GetAttribute(Attribute); - break; - } - case EGAAttributeSource::Causer: - { - IAFAbilityInterface* AttrInt = Cast(Context.Causer.Get()); - UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; - attr = Attributes->GetAttribute(Attribute); - break; - } - default: - return 0; - } - Result = (Coefficient * (PreMultiply + attr->GetFinalValue()) + PostMultiply) * PostCoefficient; - if (!bUseSecondaryAttribute) - return Result; - - return 0; -} - -float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) -{ - FAFAttributeBase* attr = nullptr; - float Result = 0; - switch (Source) - { - case EGAAttributeSource::Instigator: - attr = ContextIn.InstigatorComp->GetAttribute(Attribute); - break; - case EGAAttributeSource::Target: - attr = ContextIn.TargetComp->GetAttribute(Attribute); - break; - default: - return 0; - } - FString ContextString(TEXT("Evaluating modifier value.")); - Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); - return Result; -} -float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) const -{ - FAFAttributeBase* attr = nullptr; - float Result = 0; - switch (Source) - { - case EGAAttributeSource::Instigator: - attr = ContextIn.InstigatorComp->GetAttribute(Attribute); - break; - case EGAAttributeSource::Target: - attr = ContextIn.TargetComp->GetAttribute(Attribute); - break; - default: - return 0; - } - FString ContextString(TEXT("Evaluating modifier value.")); - Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); - return Result; -} -float FGACustomCalculationModifier::GetValue(const FGAEffectContext& ContextIn) -{ - if (CustomCalculation) - { - return CustomCalculation->NativeCalculateMagnitude(ContextIn); - } - return 0; -} -float FGACustomCalculationModifier::GetValue(const FGAEffectContext& ContextIn) const -{ - if (CustomCalculation) - { - return CustomCalculation->NativeCalculateMagnitude(ContextIn); - } - return 0; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h deleted file mode 100644 index 0b2fc2c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAEffectGlobalTypes.h +++ /dev/null @@ -1,155 +0,0 @@ -#pragma once -#include "../AbilityFramework.h" -#include "../Attributes/GAAttributeGlobals.h" -#include "GameplayTagContainer.h" -#include "../GAGlobalTypes.h" -#include "GAEffectGlobalTypes.generated.h" - - -USTRUCT(BlueprintType) -struct FAFFunctionModifier -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - float Additive; - UPROPERTY() - float Subtract; - UPROPERTY() - float Multiply; - UPROPERTY() - float Divide; - - FAFFunctionModifier() - {}; -}; - -/* -Base concept behind those attributes calculations (not sure if these are any good solutions -/performance firendly but: -1. Prefer getting values directly of attributes (GetBaseValue(), GetFinalValue(), GetBonus() etc), -as attributes can track their own state, we don't need any sophisticated way to access them and calculate bonuses). -2. Prefer simple and direct formulas (either evaluate from CurveTable, just plain add, Multiply various numbers, -or get value directly). -3. This system is not inteded, to calculate absolute final value on effect, before that effect is applied. -It will calculate absolute maximum value from the informations it have access to. -Further modifications like increasing specific damage type value, or reducing damage by value, are done -on AttributeComponent, by implementing approperiate functions, or by existing effects, which happen to intercept -incoming effect. -This might change in future though. But even if, I still prefer the magnitude calculations to be simple, -and we will add needed buffs/debuffs as we progress trough execution chain. -4. All calculations are linear. -*/ -//EGAMagnitudeCalculation::Direct -USTRUCT(BlueprintType) -struct FGADirectModifier -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere) - float Value; - - float GetValue(); - float GetValue() const; -}; -//EGAMagnitudeCalculation::AttributeBased -USTRUCT(BlueprintType) -struct FGAAttributeBasedModifier -{ - /* - We also need to add concept of backing attributes, - though I'm not sure how I want to handle them at this point. - */ - GENERATED_USTRUCT_BODY() -public: - /* - Source of Attribute for this calculation. - */ - UPROPERTY(EditAnywhere) - EGAAttributeSource Source; - /* - Name of attribute Used for calculation. - */ - UPROPERTY(EditAnywhere) - FGAAttribute Attribute; - - UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) - float Coefficient; - UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) - float PreMultiply; - UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) - float PostMultiply; - UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) - float PostCoefficient; - /* - Should we use secondary attribute for this ecalculation ? - */ - UPROPERTY(EditAnywhere) - bool bUseSecondaryAttribute; - /* - Source for secondary attribute - */ - UPROPERTY(EditAnywhere) - EGAAttributeSource SecondarySource; - /* - Name of secondary attribute used in calculation. - */ - UPROPERTY(EditAnywhere) - FGAAttribute SecondaryAttribute; - - FGAAttributeBasedModifier() - : Source(EGAAttributeSource::Instigator), - Coefficient(1), - PreMultiply(0), - PostMultiply(0), - PostCoefficient(1), - bUseSecondaryAttribute(false) - {} - - float GetValue(const FGAEffectContext& Context); - float GetValue(const FGAEffectContext& Context) const; -}; -//EGAMagnitudeCalculation::CurveBased -USTRUCT(BlueprintType) -struct FGACurveBasedModifier -{ - GENERATED_USTRUCT_BODY() -public: - /* - Source of Attribute for this calculation. - */ - UPROPERTY(EditAnywhere) - EGAAttributeSource Source; - /* - Name of attribute from which we will take XValue for Curve - */ - UPROPERTY(EditAnywhere) - FGAAttribute Attribute; - /* - Curve and row from which we will take YValue. - */ - UPROPERTY(EditAnywhere) - FCurveTableRowHandle CurveTable; - - float GetValue(const FGAEffectContext& ContextIn); - float GetValue(const FGAEffectContext& ContextIn) const; -}; -//EGAMagnitudeCalculation::CustomCalculation -USTRUCT(BlueprintType) -struct FGACustomCalculationModifier -{ - GENERATED_USTRUCT_BODY() -public: - /* - Instanced, so we can setup custom properties this class might provide, per effect spec. - */ - UPROPERTY(EditAnywhere, Instanced) - class UGACustomCalculation* CustomCalculation; - - FGACustomCalculationModifier() - : CustomCalculation(nullptr) - {}; - - float GetValue(const FGAEffectContext& ContextIn); - float GetValue(const FGAEffectContext& ContextIn) const; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp deleted file mode 100644 index 64304ce..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.cpp +++ /dev/null @@ -1,847 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "GameplayTagContainer.h" -#include "AFEffectsComponent.h" -#include "Attributes/GAAttributesBase.h" -#include "AFAbilityInterface.h" - -#include "GAEffectExecution.h" -#include "GAEffectExtension.h" -#include "GAGlobalTypes.h" - -#include "AFEffectApplicationRequirement.h" -#include "AFEffectCustomApplication.h" -#include "GAGameEffect.h" -#include "GABlueprintLibrary.h" - -DEFINE_STAT(STAT_GatherModifiers); - - -void FAFEffectSpec::OnApplied() -{ - if (Extension) - { - Extension->NativeOnEffectApplied(); - } -} -void FAFEffectSpec::OnExpired() -{ - if (Extension) - { - Extension->NativeOnEffectExpired(); - } -} -void FAFEffectSpec::OnRemoved() -{ - if (Extension) - { - Extension->NativeOnEffectRemoved(); - } -} -void FAFEffectSpec::OnExecuted() -{ - if (Extension) - { - Extension->NativeOnEffectExecuted(); - } -} -FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass) - : SpecClass(InSpecClass) -{ - Context = InContext; - Extension = nullptr; - if (InSpecClass.GetDefaultObject()->Extension) - { - Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); - Extension->OwningComponent = Context.GetPtr()->TargetInterface->GetEffectsComponent(); - } - OwnedTags.AppendTags(InSpecClass.GetDefaultObject()->OwnedTags); -} - -float FAFEffectSpec::GetFloatFromAttributeMagnitude( - const FGAMagnitude& AttributeIn - , const FGAEffectContext& InContext) const -{ - switch (AttributeIn.CalculationType) - { - case EGAMagnitudeCalculation::Direct: - { - return AttributeIn.DirectModifier.GetValue(); - } - case EGAMagnitudeCalculation::AttributeBased: - { - return AttributeIn.AttributeBased.GetValue(InContext); - } - case EGAMagnitudeCalculation::CurveBased: - { - return AttributeIn.CurveBased.GetValue(InContext); - } - case EGAMagnitudeCalculation::CustomCalculation: - { - return AttributeIn.Custom.GetValue(InContext); - } - default: - break; - } - - return 0; -} -float FAFEffectSpec::GetDuration(const FGAEffectContext& InContext) -{ - return GetFloatFromAttributeMagnitude(GetSpec()->Duration, InContext); -} -float FAFEffectSpec::GetPeriod(const FGAEffectContext& InContext) -{ - return GetFloatFromAttributeMagnitude(GetSpec()->Period, InContext); -} -FGAEffectProperty::FGAEffectProperty() - : ApplicationRequirement(nullptr) - , Application(nullptr) - , Execution(nullptr) - , Spec(nullptr) - , Duration(0) - , Period(0) - , bInstant(true) -{ - ApplicationRequirement = nullptr; - Application = nullptr; - Execution = nullptr; - Spec = nullptr; - Duration= 0; - Period = 0; -}; -FGAEffectProperty::FGAEffectProperty(TSubclassOf InClass) - : ApplicationRequirement(nullptr) - , Application(nullptr) - , Execution(nullptr) - , Spec(nullptr) - , Duration(0) - , Period(0) - , bInstant(true) -{ -}; -void FGAEffectProperty::PostScriptConstruct() -{ - ApplicationRequirement = nullptr; - Application = nullptr; - Execution = nullptr; - Spec = nullptr; - Duration = 0; - Period = 0; -} -void FGAEffectProperty::Initialize(TSubclassOf EffectClass) -{ - if (EffectClass) - { - Spec = EffectClass->GetDefaultObject(); - ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); - Application = GetSpec()->Application.GetDefaultObject(); - Execution = GetSpec()->ExecutionType.GetDefaultObject(); - } -} -void FGAEffectProperty::InitializeIfNotInitialized(const FGAEffectContext& InContext - , TSubclassOf EffectClass) -{ - if (!IsInitialized()) - { - Initialize(EffectClass); - } - if (Spec.IsValid()) - { - Duration = GetSpec()->Duration.GetFloatValue(InContext); - Period = GetSpec()->Period.GetFloatValue(InContext); - - if ((Duration > 0) || (Period > 0)) - { - bInstant = false; - } - } -} -bool FGAEffectProperty::CanApply( - const struct FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& InParams - , const FGAEffectHandle& InHandle) -{ - return ApplicationRequirement->CanApply(EffectIn, InParams, InHandle, InContainer); -} -bool FGAEffectProperty::ApplyEffect( - const FGAEffectHandle& InHandle - , const struct FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& InParams - , const FAFFunctionModifier& Modifier) -{ - return Application->ApplyEffect(InHandle, EffectIn, InContainer, InParams, Modifier); -} -void FGAEffectProperty::ApplyExecute(const FGAEffectHandle& InHandle - , const FAFEffectParams& InParams - , const FAFFunctionModifier& Modifier) -{ - Application->ApplyExecute(InHandle, InParams, Modifier); -} - -void FGAEffectProperty::ExecuteEffect( - const FGAEffectHandle& HandleIn - , FGAEffectMod& ModIn - , const FAFEffectParams& InParams - , const FAFFunctionModifier& Modifier) -{ - Execution->ExecuteEffect(HandleIn, ModIn, InParams, Modifier); -} - -void FGAEffect::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) -{ - //const_cast(InArraySerializer).RemoveFromReplication(Handle, PredictionHandle); -} -void FGAEffect::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) -{ - World = InArraySerializer.OwningComponent->GetWorld(); - AppliedTime = World->TimeSeconds; - LastTickTime = World->TimeSeconds; - - - Handle = FGAEffectHandle::GenerateHandle(); - - //const_cast(InArraySerializer).ApplyFromReplication(Handle, PredictionHandle); -} -void FGAEffect::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) -{ - -} - -float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) -{ - switch (CalculationType) - { - case EGAMagnitudeCalculation::Direct: - { - return DirectModifier.GetValue(); - } - case EGAMagnitudeCalculation::AttributeBased: - { - return AttributeBased.GetValue(Context); - } - case EGAMagnitudeCalculation::CurveBased: - { - return CurveBased.GetValue(Context); - } - case EGAMagnitudeCalculation::CustomCalculation: - { - return Custom.GetValue(Context); - } - default: - return 0; - } - - return 0; -} - -float FAFStatics::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn - , const FGAEffectContext& InContext - , const FGAEffectHandle& InHandle) -{ - switch (AttributeIn.CalculationType) - { - case EGAMagnitudeCalculation::Direct: - { - return AttributeIn.DirectModifier.GetValue(); - } - case EGAMagnitudeCalculation::AttributeBased: - { - return AttributeIn.AttributeBased.GetValue(InContext); - } - case EGAMagnitudeCalculation::CurveBased: - { - return AttributeIn.CurveBased.GetValue(InContext); - } - case EGAMagnitudeCalculation::CustomCalculation: - { - return AttributeIn.Custom.GetValue(InContext); - } - default: - break; - } - - return 0; -} -FGAEffectMod FAFStatics::GetAttributeModifier(FGAAttributeModifier& ModInfoIn - , class UGAGameEffectSpec* InSpec - , const FGAEffectContext& InContext - , const FGAEffectHandle& InHandle) -{ - FGAEffectMod ModOut; - if (InSpec) - { - switch (ModInfoIn.Magnitude.CalculationType) - { - case EGAMagnitudeCalculation::Direct: - { - return FGAEffectMod(ModInfoIn.Attribute, - ModInfoIn.Magnitude.DirectModifier.GetValue(), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); - } - case EGAMagnitudeCalculation::AttributeBased: - { - return FGAEffectMod(ModInfoIn.Attribute, - ModInfoIn.Magnitude.AttributeBased.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); - - } - case EGAMagnitudeCalculation::CurveBased: - { - return FGAEffectMod(ModInfoIn.Attribute, - ModInfoIn.Magnitude.CurveBased.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); - - } - case EGAMagnitudeCalculation::CustomCalculation: - { - return FGAEffectMod(ModInfoIn.Attribute, - ModInfoIn.Magnitude.Custom.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); - - } - default: - break; - } - } - return ModOut; -} - -FGAEffect::~FGAEffect() -{ -} - - -float FGAEffect::GetDurationTime() const -{ - return Duration;// GetFloatFromAttributeMagnitude(GetEffect()->Duration); -} -float FGAEffect::GetPeriodTime() const -{ - return Period;// GetFloatFromAttributeMagnitude(GetEffect()->Period); -} - -float FGAEffect::GetCurrentDuration() const -{ - if (World) - { - float CurrentTime = World->TimeSeconds; - return CurrentTime - AppliedTime; - } - - return 0; -} -FTimerManager& FAFEffectParams::GetTargetTimerManager() -{ - return Context.GetPtr()->TargetComp->GetWorld()->GetTimerManager(); -} -UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() -{ - return Context.GetPtr()->GetTargetEffectsComponent(); -} -UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() const -{ - return Context.GetPtr()->GetTargetEffectsComponent(); -} -void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams) -{ - /*if (!EffectCue) - { - return; - } - AActor* Instigator = EffectHandle.GetContext().Instigator.Get(); - UGAEffectCue* NewCue = NewObject(Instigator, EffectCue); - if (NewCue && Instigator) - { - NewCue->SetParameters(Instigator, CueParams); - NewCue->Context = EffectHandle.GetContext(); - NewCue->BeginCue(); - }*/ -} - -FGAEffectHandle FGAEffectContainer::ApplyEffect( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier) -{ - FGAEffectHandle Handle; - FGAEffectProperty& InProperty = Params.GetProperty(); - - bool bHasDuration = InProperty.GetDuration() > 0; - bool bHasPeriod = InProperty.GetPeriod() > 0; - - //InProperty.DataTest->ID++; - - ENetRole role = OwningComponent->GetOwnerRole(); - ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); - if (!Params.bRecreated) - { - Handle = FGAEffectHandle::GenerateHandle(); - } - else - { - Handle = InHandle; - } - if (InProperty.CanApply(EffectIn, this, Params, Handle)) - { - if(!Params.bPeriodicEffect) //instatnt effect. - { - const_cast(EffectIn).SetHandle(Handle); - if (InProperty.ApplyEffect(Handle, - EffectIn, this, Params)) - { - Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() - , Handle - , Params.Context - , Params.EffectSpec); - - InProperty.ApplyExecute(Handle, Params, Modifier); - - // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); - } - } - else - { - const_cast(EffectIn).SetHandle(Handle); - if (InProperty.ApplyEffect(Handle, - EffectIn, this, Params)) - { - FAFEffectSpec& Spec = Params.GetSpec(); - FGAEffectContext& Context = Params.GetContext(); - - Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() - , Handle - , Params.Context - , Params.EffectSpec); - - const_cast(EffectIn).AppliedTime = OwningComponent->GetWorld()->TimeSeconds; - const_cast(EffectIn).LastTickTime = OwningComponent->GetWorld()->TimeSeconds; - const_cast(EffectIn).Duration = Spec.GetDuration(Context); - const_cast(EffectIn).Period = Spec.GetPeriod(Context); - MarkItemDirty(const_cast(EffectIn)); - int32 newItem = ActiveEffectInfos.Add(EffectIn); - MarkArrayDirty(); - AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &ActiveEffectInfos[newItem], InProperty); - - //InProperty.ApplyExecute(Handle, Params, Modifier); - //generate it only on client, and apply prediction key from client. - //if server replicates with valid key, then nothing happens. - //if not we try to rewind effect application. - //we probabaly don't need to unwind attribute changes, since next replication from - //server will overridem them anyway. - - bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; - } - } - - } - //right place ? - Params.GetSpec().OnApplied(); - - FAFEventData EventData; - const FGameplayTagContainer& AppliedEvents = InProperty.GetSpec()->AppliedEventTags; - for(const FGameplayTag& Event : AppliedEvents) - OwningComponent->TriggerAppliedEvent(Event, EventData); - - FGAEffectContext& InContext = Params.GetContext(); - TArray& Effects = InProperty.GetSpec()->IfHaveTagEffect.Effects; - for (FAFConditionalEffect& Effect : Effects) - { - if (Effect.RequiredTag.IsValid() - && InContext.GetTargetEffectsComponent()->HasTag(Effect.RequiredTag)) - { - //Hack. We need a way store handles for conditional effects. - FAFPropertytHandle PropertyNew(Effect.Effect); - FGAEffectHandle Handle; - Handle = UGABlueprintLibrary::ApplyEffect(PropertyNew - , Handle - , InContext.Target.Get() - , InContext.Instigator.Get() - , InContext.Causer.Get() - , InContext.HitResult); - } - } - - - return Handle; - -} - -TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectProperty& InProperty -, const FGAEffectContext& InContext) -{ - TSet Handles; - UGAGameEffectSpec* Spec = InProperty.GetSpec(); - EGAEffectAggregation Aggregation = Spec->EffectAggregation; - UClass* EffectClass = Spec->GetClass(); - - switch (Aggregation) - { - case EGAEffectAggregation::AggregateByInstigator: - { - UAFAbilityComponent* Instigator = InContext.InstigatorComp.Get(); - TMap>* EffectByClassMap = InstigatorEffectByClass.Find(Instigator); - //TSet* EffectByClass; - if (EffectByClassMap) - { - return EffectByClassMap->FindRef(EffectClass); - } - - break; - } - case EGAEffectAggregation::AggregateByTarget: - { - UAFAbilityComponent* Target = InContext.TargetComp.Get(); - TSet* TargetEffect = TargetEffectByClass.Find(EffectClass); - if (TargetEffect) - { - return *TargetEffect; - } - break; - } - default: - break; - } - return Handles; -} - -void FGAEffectContainer::AddEffect( - const FGAEffectHandle& InHandle - , const FAFPredictionHandle& InPredHandle - , FGAEffect* InEffect - , const FGAEffectProperty& InProperty - , bool bInfinite) -{ - HandleByPrediction.Add(InPredHandle, InHandle); - PredictionByHandle.Add(InHandle, InPredHandle); - PredictedEffectInfos.Add(InPredHandle, InEffect); - UGAGameEffectSpec* Spec = InProperty.GetSpec(); - UClass* SpecClass = Spec->GetClass(); - FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); - - TSet& Effects = EffectByAttribute.FindOrAdd(Spec->AtributeModifier.Attribute); - Effects.Add(InHandle); - - FObjectKey EffectKey(SpecClass); - TArray& EffectClass = EffectByClass.FindOrAdd(EffectKey); - EffectClass.Add(InHandle); - - switch (Spec->EffectAggregation) - { - case EGAEffectAggregation::AggregateByInstigator: - { - TMap>& InstEffectClass = InstigatorEffectByClass.FindOrAdd(Context.Instigator.Get()); - TSet& EffectClass2 = InstEffectClass.FindOrAdd(SpecClass); - EffectClass2.Add(InHandle); - break; - } - case EGAEffectAggregation::AggregateByTarget: - { - TSet& EffectClass = TargetEffectByClass.FindOrAdd(SpecClass); - EffectClass.Add(InHandle); - break; - } - } - - ActiveEffects.Add(InHandle, InEffect); - FGAEffectContainer* sss = this; - int dbg = 0; -} - -void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty) -{ - RemoveEffectInternal(InProperty, InHandle); -} - -TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num) -{ - UGAGameEffectSpec* Spec = HandleIn.GetSpec(); - EGAEffectAggregation Aggregation = Spec->EffectAggregation; - FObjectKey key(HandleIn.GetClass()); - TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); - FGAEffectContainer* sss = this; - if (!handles) - return TArray(); - TArray copy = *handles; - - for (int32 idx = 0; idx < Num; idx++) - { - if (handles->IsValidIndex(0)) - { - FGAEffectHandle OutHandle = (*handles)[idx]; - RemoveEffectInternal(HandleIn, OutHandle); - const_cast(HandleIn).CleanUp(OutHandle); - } - } - - - - return copy; -} - -bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) -{ - if (ActiveEffects.Contains(HandleIn)) - { - return true; - } - return false; -} -bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) const -{ - if (ActiveEffects.Contains(HandleIn)) - { - return true; - } - return false; -} -bool FGAEffectContainer::ContainsEffectOfClass(const FAFPropertytHandle& InProperty) -{ - FObjectKey key(InProperty.GetClass()); - if (EffectByClass.Contains(key)) - { - return true; - } - return false; -} - -void FGAEffectContainer::ApplyFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle, FGAEffect* InEffect) -{ - //AddEffect(InHandle, InPredHandle, InEffect); -} -void FGAEffectContainer::RemoveFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle) -{ - //FGAEffect* Effect = ActiveEffects[InHandle]; - //APawn* Instigator = Effect->GetContext().Instigator.Get(); - //UObject* Target = Effect->GetContext().Target.Get(); - - //HandleByPrediction.Remove(InPredHandle); - //PredictionByHandle.Remove(InHandle); - //PredictedEffectInfos.Remove(InPredHandle); - - //FGAAttribute Attribute = Effect->GetEffect()->AtributeModifier.Attribute; - - //TSet* Effects = EffectByAttribute.Find(Attribute); - //if (Effects) - //{ - // Effects->Remove(InHandle); - // if (Effects->Num() == 0) - // { - // EffectByAttribute.Remove(Attribute); - // } - //} - - //FObjectKey EffectKey(Effect->GameEffectClass); - //TArray* EffectClass = EffectByClass.Find(EffectKey); - //if (EffectClass) - //{ - // EffectClass->Remove(InHandle); - // if (EffectClass->Num() == 0) - // { - // EffectByClass.Remove(EffectKey); - // } - //} - - //switch (Effect->GetEffect()->EffectAggregation) - //{ - //case EGAEffectAggregation::AggregateByInstigator: - //{ - // TMap>* InstEffectClass = InstigatorEffectByClass.Find(Instigator); - // if (InstEffectClass) - // { - // TSet* EffectClass2 = InstEffectClass->Find(Effect->GameEffectClass); - // if (EffectClass2) - // { - // EffectClass2->Remove(InHandle); - // if (EffectClass2->Num() == 0) - // { - // InstEffectClass->Remove(Effect->GameEffectClass); - // } - // } - // if (InstEffectClass->Num() == 0) - // { - // InstigatorEffectByClass.Remove(Instigator); - // } - // } - // - // break; - //} - //case EGAEffectAggregation::AggregateByTarget: - //{ - // TSet* EffectClass2 = TargetEffectByClass.Find(Effect->GameEffectClass); - // if (EffectClass2) - // { - // EffectClass2->Remove(InHandle); - // if (EffectClass2->Num() == 0) - // { - // TargetEffectByClass.Remove(Effect->GameEffectClass); - // } - // } - // break; - //} - //} -} -UWorld* FGAEffectContainer::GetWorld() const -{ - if (OwningComponent) - { - return OwningComponent->GetWorld(); - } - return nullptr; -} - -UGAGameEffectSpec::UGAGameEffectSpec() -{ - ExecutionType = UGAEffectExecution::StaticClass(); - ApplicationRequirement = UAFEffectApplicationRequirement::StaticClass(); - Application = UAFEffectCustomApplication::StaticClass(); -} - -float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) const -{ - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); - if (Effect) - { - const FGAEffect* Ptr = *Effect; - float Duration = Ptr->GetDurationTime(); - return FMath::Clamp(Duration - Ptr->GetCurrentDuration(), 0, Duration); - } - return 0; -} -float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const -{ - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); - if (Effect) - { - const FGAEffect* Ptr = *Effect; - float CurrentDuration = Ptr->GetCurrentDuration(); - float MaxDuration = Ptr->GetDurationTime(); - - float CurrentTime = ((CurrentDuration / MaxDuration) - 1) * (-1); - - return CurrentTime;// FMath::Clamp(CurrentTime, 1, 0); - } - return 0; -} -float FGAEffectContainer::GetCurrentTime(const FGAEffectHandle& InHandle) const -{ - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); - if (Effect) - { - const FGAEffect* Ptr = *Effect; - return Ptr->GetCurrentDuration(); - } - return 0; -} -float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const -{ - const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); - if (Effect) - { - const FGAEffect* Ptr = *Effect; - float CurrentDuration = Ptr->GetCurrentDuration(); - float MaxDuration = Ptr->GetDurationTime(); - return CurrentDuration * 1 / MaxDuration; - } - return 0; -} -float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const -{ - return 0; -} - -void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle) -{ - FGAEffect* Effect = ActiveEffects[InHandle]; - UGAGameEffectSpec* Spec = InProperty.GetSpec(); - UClass* SpecClass = Spec->GetClass(); - FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); - - FTimerManager& DurationTimer = Context.TargetComp->GetWorld()->GetTimerManager(); - DurationTimer.ClearTimer(Effect->DurationTimerHandle); - DurationTimer.ClearTimer(Effect->PeriodTimerHandle); - - APawn* Instigator = Context.Instigator.Get(); - UObject* Target = Context.Target.Get(); - FAFPredictionHandle PredHandle = PredictionByHandle[InHandle]; - - HandleByPrediction.Remove(PredHandle); - PredictionByHandle.Remove(InHandle); - PredictedEffectInfos.Remove(PredHandle); - - FGAAttribute Attribute = Spec->AtributeModifier.Attribute; - EGAAttributeMod AttributeMod = Spec->AtributeModifier.AttributeMod;; - - TSet* Effects = EffectByAttribute.Find(Spec->AtributeModifier.Attribute); - if (Effects) - { - IAFAbilityInterface* Target = Context.TargetInterface; - Target->RemoveBonus(Attribute, InHandle, AttributeMod); - Effects->Remove(InHandle); - if (Effects->Num() == 0) - { - EffectByAttribute.Remove(Spec->AtributeModifier.Attribute); - } - } - - FObjectKey EffectKey(SpecClass); - TArray* EffectClass = EffectByClass.Find(EffectKey); - if (EffectClass) - { - EffectClass->Remove(InHandle); - if (EffectClass->Num() == 0) - { - EffectByClass.Remove(EffectKey); - } - } - - switch (Spec->EffectAggregation) - { - case EGAEffectAggregation::AggregateByInstigator: - { - TMap>* InstEffectClass = InstigatorEffectByClass.Find(Instigator); - if (InstEffectClass) - { - TSet* EffectClass2 = InstEffectClass->Find(SpecClass); - if (EffectClass2) - { - EffectClass2->Remove(InHandle); - if (EffectClass2->Num() == 0) - { - InstEffectClass->Remove(SpecClass); - } - } - if (InstEffectClass->Num() == 0) - { - InstigatorEffectByClass.Remove(Instigator); - } - } - - break; - } - case EGAEffectAggregation::AggregateByTarget: - { - TSet* EffectClass2 = TargetEffectByClass.Find(SpecClass); - if (EffectClass2) - { - EffectClass2->Remove(InHandle); - if (EffectClass2->Num() == 0) - { - TargetEffectByClass.Remove(SpecClass); - } - } - break; - } - } - ActiveEffects.Remove(InHandle); -} - -bool FGAEffectContainer::IsEffectActive(TSubclassOf EffectClass) -{ - FObjectKey EffectKey(EffectClass); - if (EffectByClass.Contains(EffectKey)) - { - return true; - } - return false; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h deleted file mode 100644 index 3f15281..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Effects/GAGameEffect.h +++ /dev/null @@ -1,1346 +0,0 @@ -#pragma once -//#include "GAGlobalTypes.h" -#include "GAEffectGlobalTypes.h" -#include "GameplayTagContainer.h" -#include "UObject/ObjectMacros.h" -#include "UObject/GCObject.h" -#include "GAGameEffect.generated.h" - -DECLARE_STATS_GROUP(TEXT("GameEffect"), STATGROUP_GameEffect, STATCAT_Advanced); -DECLARE_CYCLE_STAT_EXTERN(TEXT("GatherModifiers"), STAT_GatherModifiers, STATGROUP_GameEffect, ); - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAMagnitude -{ - GENERATED_USTRUCT_BODY() -public: - /* - Type of calculation we want to perform for this Magnitude. - */ - UPROPERTY(EditAnywhere) - EGAMagnitudeCalculation CalculationType; - - UPROPERTY(EditAnywhere) - FGADirectModifier DirectModifier; - /* - Simple calculation based on attribute: - (Coefficient * (PreMultiply + AttributeValue) + PostMultiply) * PostCoefficient - - There is no any magic manipulation, it straight off pull attribute from selected source, - and make this operation on it. - */ - UPROPERTY(EditAnywhere) - FGAAttributeBasedModifier AttributeBased; - /* - Get value from selected CurveTable, based on selected attribute value. - */ - UPROPERTY(EditAnywhere) - FGACurveBasedModifier CurveBased; - /* - Provide custom calculation class. - */ - UPROPERTY(EditAnywhere) - FGACustomCalculationModifier Custom; - - float GetFloatValue(const FGAEffectContext& Context); -}; -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAAttributeModifier -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Instant Spec") - FGAAttribute Attribute; - - UPROPERTY(EditAnywhere, Category = "Instant Spec") - EGAAttributeMod AttributeMod; - - /* - Who will be target of this attribute change. - Instigator - pawn which applied effect (regardless of to whom). - Target - targeted pawn (regardless of who applied). - */ - UPROPERTY(EditAnywhere) - EGAModifierTarget ModifierTarget; - /* - How modifier will be executed on target. - */ - //UPROPERTY(EditAnywhere, Category = "Execution Type") - // TSubclassOf ExecutionType; - - /* - Modifier value applied to attribute - */ - UPROPERTY(EditAnywhere) - FGAMagnitude Magnitude; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFAttributeModifierContainer -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Modifiers; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FAFCueContainer -{ - GENERATED_BODY() -public: - /* Cues to apply */ - UPROPERTY(EditAnywhere) - FGameplayTagContainer CueTags; -}; - -USTRUCT(BlueprintType) -struct FAFConditionalEffect -{ - GENERATED_BODY() - /* If target have this tag apply specified effects */ - UPROPERTY(EditAnywhere) - FGameplayTag RequiredTag; - UPROPERTY(EditAnywhere) - TSubclassOf Effect; -}; -USTRUCT(BlueprintType) -struct FAFConditionalEffectContainer -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Effects; -}; - - -/* - Base effect class. You can derive your own specialized classes from it - with preset customizations and values. You should never directly inherit blueprints from it. -*/ -UCLASS(Blueprintable, BlueprintType, Abstract, DefaultToInstanced, EditInlineNew) -class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject -{ - GENERATED_BODY() -public: - /* - Replicate effect back to clients ? - */ - UPROPERTY(EditAnywhere, Category = "Network") - bool bReplicate; - - /* - Individual Tag descrbing effect type. - ie. Condition.Burning - */ - UPROPERTY(EditAnywhere, Category = "Effect Info") - FGameplayTag EffectTag; - - UPROPERTY(EditAnywhere, meta=(UseDisplayName), Category = "Effect Info") - TSubclassOf ApplicationRequirement; - /* - How effect should stack. Only relevelant for periodic effects - and modifiers applied on period. - */ - UPROPERTY(EditAnywhere, meta = (UseDisplayName), Category = "Effect Info") - TSubclassOf Application; - - UPROPERTY(EditAnywhere, Category = "Stacking") - int32 MaxStacks; - - /* - Who should aggregate this effect. Relevelant for stacking type - and by this only relevelant for periodic effects. - */ - UPROPERTY(EditAnywhere, Category = "Stacking") - EGAEffectAggregation EffectAggregation; - - /* Total duration of effect (if applicable) */ - UPROPERTY(EditAnywhere, Category = "Duration") - FGAMagnitude Duration; - /* Duration of single period. */ - UPROPERTY(EditAnywhere, Category = "Period") - FGAMagnitude Period; - /* Total duration of effect (if applicable) */ - UPROPERTY(EditAnywhere, Category = "Duration") - float MaxStackedDuration; - - /* IF true, effect will tick instantly upon application. */ - UPROPERTY(EditAnywhere, Category = "Duration") - bool bTickOnApplication; - UPROPERTY(EditAnywhere, Category = "Duration") - bool bExecuteOnApplication; - - - /* - Modifier applied to attribute - */ - UPROPERTY(EditAnywhere, Category = "Attribute Modifiers") - FGAAttributeModifier AtributeModifier; - UPROPERTY(EditAnywhere, Category = "Attribute Modifiers") - FAFAttributeModifierContainer Modifiers; - - UPROPERTY(EditAnywhere, Category = "Execution Type") - TSubclassOf ExecutionType; - - UPROPERTY(EditAnywhere, Category = "Modifiers") - TSubclassOf Extension; - - /* Cues to apply by this effect. */ - UPROPERTY(EditAnywhere, Category = "Cues") - FAFCueContainer Cues; - /* - Effects applied when this effect is applied. - These effects will be applied with the same context and the same target as - effect, which stores them. - */ - UPROPERTY(EditAnywhere, Category = "Linked Effects") - TArray> OnAppliedEffects; - - /* Effects applied when this effect expire*/ - UPROPERTY(EditAnywhere, Category = "Linked Effects") - TArray> OnExpiredEffects; - - /* Effects applied when this effect is removed. */ - UPROPERTY(EditAnywhere, Category = "Linked Effects") - TArray> OnRemovedEffects; - - UPROPERTY(EditAnywhere, Category = "Event Tags") - FGameplayTag OnExpiredEvent; - UPROPERTY(EditAnywhere, Category = "Event Tags") - FGameplayTag OnPeriodEvent; - UPROPERTY(EditAnywhere, Category = "Event Tags") - FGameplayTag OnRemovedEvent; - - - UPROPERTY(EditAnywhere, Category = "Event Application Tags") - FGameplayTag OnEffectApplyToTargetEvent; - UPROPERTY(EditAnywhere, Category = "Event Application Tags") - FGameplayTag OnEffectApplyToSelfEvent; - - /* - Effects applied only when certain criteria are met. - Just dumbed here it needs it's own structure that will actually alow to setup those conditions. - */ - UPROPERTY(EditAnywhere, Category = "Linked Effects") - FAFConditionalEffectContainer IfHaveTagEffect; - - - /* Remove effects with these tags. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer RemoveEffectWithTags; - - /* - Tags descrbing what this effect does. - */ - /* Tags I own and I don't apply. New tags can be added here as the effect is applied. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer OwnedTags; - /* Tags owned by this effect and not applied. Describe the type of this effect. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer EffectTags; - - /* - When effect is appied trigger events with these tags. - */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer AppliedEventTags; - /* - When effect is executed trigger events with these tags. - */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer ExecuteEventTags; - - /* - Tags applied to attribute when effect is applying non-instant effect. - Owned tags of another effect are checked against these tags to calculate - modifier. - Also it's checked when tag is applied to determine effect stacking, - when stacking is set to Override or StrongerOverride. - - Use only single tag here, with proper hierarchy. - Using multiple tags should be reserved only for special cases. - */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer AttributeTags; - - /* If Target have these tags I will not be applied to it. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer DenyTags; - - /* Applied immunity tags. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer AppliedImmunityTags; - - /* Tags, which are applied to Target when effect is Duration/Periodic based. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer ApplyTags; - - /* Tags, required for this effect to be applied. If these tags are not present, effect will be ignored. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer RequiredTags; - - /* Tags, required for this effect to be executed. If these tags are not present, effect will be ignored. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer ExecutionRequiredTags; -public: - UGAGameEffectSpec(); -}; -/* - Base effect class to extend from when creating effect blueprints. -*/ -UCLASS(Blueprintable, BlueprintType, Abstract) -class ABILITYFRAMEWORK_API UAFEffectSpecBase : public UGAGameEffectSpec -{ - GENERATED_BODY() -public: -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectClass -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Effect") - TSubclassOf SpecClass; - - FGAEffectClass() - {} - FGAEffectClass(TSubclassOf InClass) - : SpecClass(InClass) - {} - const bool operator==(const FGAEffectClass& Other) const - { - return SpecClass == Other.SpecClass; - } - const bool operator==(const TSubclassOf& OtherClass) const - { - return SpecClass == OtherClass; - } - void operator=(const FGAEffectClass& Other) - { - SpecClass = Other.SpecClass; - } - void operator=(const TSubclassOf& Other) - { - SpecClass = Other; - } - void operator=(UGAGameEffectSpec* Other) - { - SpecClass = Other->GetClass(); - } -}; - -USTRUCT(BlueprintType) -struct FAFContextHandle -{ - GENERATED_BODY() -private: - TSharedPtr DataPtr; - uint32 ID; -public: - static FAFContextHandle Generate(FGAEffectContext* InContext) - { - static uint32 id = 0; - id++; - - TSharedPtr PropPtr = MakeShareable(InContext); - FAFContextHandle Handle(PropPtr, id); - - return Handle; - } - - FAFContextHandle() - : ID(0) - {}; -protected: - FAFContextHandle(TSharedPtr InProperty, uint32 InID) - : DataPtr(InProperty) - , ID(InID) - {}; - -public: - bool IsValid() - { - return DataPtr.IsValid(); - } - - FGAEffectContext& GetRef() - { - return DataPtr.ToSharedRef().Get(); - } - FGAEffectContext& GetRef() const - { - return DataPtr.ToSharedRef().Get(); - } - FGAEffectContext* GetPtr() - { - return DataPtr.Get(); - } - FGAEffectContext* GetPtr() const - { - return DataPtr.Get(); - } - - void SetTarget(UObject* NewTarget) - { - DataPtr->SetTarget(NewTarget); - } - - bool operator==(const FAFContextHandle& Other) const - { - return ID == Other.ID; - } - - bool operator==(const FObjectKey& Other) const - { - return *DataPtr.Get() == Other; - } - bool operator==(UObject* Other) const - { - return *DataPtr.Get() == Other; - } - - friend uint32 GetTypeHash(const FAFContextHandle& InHandle) - { - return InHandle.ID; - } -}; - -template<> -struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithCopy = true, - }; -}; - -/* - -*/ - -struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject -{ -private: - FAFContextHandle Context; - UGAEffectExtension* Extension; //week ptr ? - - TSubclassOf SpecClass; -public: - - FGameplayTagContainer OwnedTags; - FGameplayTagContainer ApplyTags; - FGameplayTagContainer RequiredTags; - -public: - FAFEffectSpec() - : Extension(nullptr) - {} - - FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass); - - void OnApplied(); - void OnExpired(); - void OnRemoved(); - void OnExecuted(); - - void AddOwnedTags(const FGameplayTagContainer& InTags) - { - OwnedTags.AppendTags(InTags); - } - void AddApplyTags(const FGameplayTagContainer& InTags) - { - ApplyTags.AppendTags(InTags); - } - - UGAGameEffectSpec* GetSpec() - { - return SpecClass.GetDefaultObject(); - } - - float GetFloatFromAttributeMagnitude( - const FGAMagnitude& AttributeIn - , const FGAEffectContext& InContext) const; - - float GetDuration(const FGAEffectContext& InContext); - float GetPeriod(const FGAEffectContext& InContext); - - const TSubclassOf& GetEffectClass() - { - return SpecClass; - } - - virtual void AddReferencedObjects(FReferenceCollector& Collector) override - { - Collector.AddReferencedObject(Extension, Context.GetPtr()->Target.Get()); - } - -}; -USTRUCT(BlueprintType) -struct FAFEffectSpecHandle -{ - GENERATED_BODY() -public: - TSharedPtr SpecPtr; - uint32 ID; - -public: - static FAFEffectSpecHandle Generate(FAFEffectSpec* Effect) - { - static uint32 id = 0; - id++; - - TSharedPtr PropPtr = MakeShareable(Effect); - FAFEffectSpecHandle Handle(PropPtr, id); - - return Handle; - } - - FAFEffectSpecHandle() - : ID(0) - {} - FAFEffectSpecHandle(TSharedPtr Ptr, uint32 InID) - : SpecPtr(Ptr) - , ID(InID) - {} - - bool IsValid() - { - return SpecPtr.IsValid(); - } - - TSharedPtr GetPtr() - { - return SpecPtr; - } - FAFEffectSpec& GetRef() - { - return SpecPtr.ToSharedRef().Get(); - } - FAFEffectSpec& GetRef() const - { - return SpecPtr.ToSharedRef().Get(); - } -}; -template<> -struct TStructOpsTypeTraits< FAFEffectSpecHandle > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithCopy = true, - }; -}; - - - -/* - Container for: - 1. Effect handles applied from this property, sorted per target. - 2. Their contexts (each effect have it's own context). - 3. Targets affected by effect from this container (and which effect). - - Also contains hard pointers to base classes/assets used by effect (Execution, Application, Specification). -*/ - -struct FAFEffectParams; - -struct ABILITYFRAMEWORK_API FGAEffectProperty -{ -protected: - - TWeakObjectPtr ApplicationRequirement; - TWeakObjectPtr Application; - TWeakObjectPtr Execution; - TWeakObjectPtr Spec; - FAFPredictionHandle PredictionHandle; - - float Duration; - float Period; - bool bInstant; - /* - Handle to effect created from SpecClass - This handle is only created and kept for instant effects, - so we don't create new object every time instant effect is created - as potentially there can be quite a lot of allocations. - */ - /* - Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. - - */ - - FAFContextHandle InstantContext; - FAFEffectSpecHandle InstantEffectSpec; - - TMap EffectSpecs; - //Cached context per created effect. - TMap Contexts; - //possibly multiple handles per target ? - TMap Handles; - TMap HandleToTarget; - TMap EffectCues; -public: - FGAEffectProperty(); - - FGAEffectProperty(TSubclassOf InClass); - void PostScriptConstruct(); - - UGAGameEffectSpec* GetSpec() { return Spec.Get(); } - UGAGameEffectSpec* GetSpec() const { return Spec.Get(); } - - bool CanApply( - const struct FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& InParams - , const FGAEffectHandle& InHandle); - - bool ApplyEffect(const FGAEffectHandle& InHandle - , const struct FGAEffect& EffectIn - , struct FGAEffectContainer* InContainer - , const FAFEffectParams& InParams - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - void ApplyExecute(const FGAEffectHandle& InHandle - , const FAFEffectParams& InParams - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - void ExecuteEffect(const FGAEffectHandle& HandleIn - , FGAEffectMod& ModIn - , const FAFEffectParams& InParams - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - //intentionally non const. - //FGAEffectHandle& GetHandleRef() { return Handle; } - //void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; - void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} - - void Initialize(TSubclassOf EffectClass); - void InitializeIfNotInitialized(const FGAEffectContext& InContext - , TSubclassOf EffectClass); - - bool GetIsInstant() const - { - return bInstant; - } - inline float GetPeriod() const - { - return Period; - } - inline float GetDuration() const - { - return Duration; - } - - void RegisterHandle( - UObject* Target - , const FGAEffectHandle& InHandle - , const FAFContextHandle& Context - , const FAFEffectSpecHandle& Spec) - { - if (bInstant) - { - InstantContext = Context; - InstantEffectSpec = Spec; - return; - } - if (HandleToTarget.Contains(InHandle)) - { - UE_LOG(GameAttributes, Log, TEXT("FGAEffectProperty::RegisterHandle Handle already registered \n")); - return; - } - - AddHandle(Target, InHandle); - AddContext(InHandle, Context); - AddEffectSpec(InHandle, Spec); - } - - void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) - { - FObjectKey key(Target); - Handles.Add(key, InHandle); - HandleToTarget.Add(InHandle, Target); - } - - FGAEffectHandle GetHandle(UObject* From) - { - FObjectKey key(From); - if (FGAEffectHandle* handle = Handles.Find(key)) - return *handle; - - return FGAEffectHandle(); - } - FGAEffectHandle GetHandle(UObject* From) const - { - FObjectKey key(From); - if (const FGAEffectHandle* handle = Handles.Find(key)) - return *handle; - - return FGAEffectHandle(); - } - - FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) - { - if (bInstant) - { - return InstantContext; - } - FAFContextHandle* Ctx = Contexts.Find(InHandle); - if (Ctx) - { - return *Ctx; - } - return InstantContext; - } - const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const - { - if (bInstant) - { - return InstantContext; - } - const FAFContextHandle* Ctx = Contexts.Find(InHandle); - if (Ctx) - { - return *Ctx; - } - return InstantContext; - } - - void AddContext(const FGAEffectHandle& InHandle, const FAFContextHandle& ContextHandle) - { - Contexts.Add(InHandle, ContextHandle); - } - - void RemoveContext(const FGAEffectHandle& InHandle) - { - Contexts.Remove(InHandle); - } - - FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) - { - if (bInstant) - { - return InstantEffectSpec; - } - FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); - if (Spec) - { - return *Spec; - } - return InstantEffectSpec; - } - const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const - { - if (bInstant) - { - return InstantEffectSpec; - } - const FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); - if (Spec) - { - return *Spec; - } - return InstantEffectSpec; - } - - void AddEffectSpec(const FGAEffectHandle& InHandle, const FAFEffectSpecHandle& ContextHandle) - { - EffectSpecs.Add(InHandle, ContextHandle); - } - - void RemoveEffectSpec(const FGAEffectHandle& InHandle) - { - EffectSpecs.Remove(InHandle); - } - - inline FAFPredictionHandle GetPredictionHandle() const - { - return PredictionHandle; - } - - bool IsHandleValid(UObject* For) - { - FObjectKey Key(For); - FGAEffectHandle* Handle = Handles.Find(Key); - if (Handle) - { - return Handle->IsValid(); - } - return false; - } - bool IsHandleValid(UObject* For) const - { - FObjectKey Key(For); - const FGAEffectHandle* Handle = Handles.Find(Key); - if (Handle) - { - return Handle->IsValid(); - } - return false; - } - void RemoveHandle(const FGAEffectHandle& InHandle) - { - UObject* Target = nullptr; - HandleToTarget.RemoveAndCopyValue(InHandle, Target); - if(Target) - { - FObjectKey key(Target); - Handles.Remove(key); - } - } - - void CleanUp(const FGAEffectHandle& InHandle) - { - RemoveContext(InHandle); - EffectCues.Remove(InHandle); - RemoveHandle(InHandle); - RemoveEffectSpec(InHandle); - } - - void SetPredictionHandle(const FAFPredictionHandle& InHandle) - { - PredictionHandle = InHandle; - } - - FGAAttributeModifier& GetAttributeModifier() - { - return Spec->AtributeModifier; - } - - - const bool IsInitialized() const - { - return ApplicationRequirement.IsValid() && Application.IsValid() && Execution.IsValid() && Spec.IsValid(); - } - /*const bool IsValidHandle() const - { - return Handle.IsValid(); - }*/ - -}; -template<> -struct TStructOpsTypeTraits< FGAEffectProperty > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithCopy = true, - WithPostScriptConstruct = true, - }; -}; - -USTRUCT(BlueprintType) -struct FAFPropertytHandle -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Effect") - FGAEffectClass SpecClass; - - TSharedPtr DataPtr; - //TSharedRef Test; - - uint32 ID; -public: - FAFPropertytHandle() - : ID(0) - { - if (!DataPtr.IsValid()) - { - DataPtr = MakeShareable(new FGAEffectProperty()); - } - }; - - FAFPropertytHandle(TSubclassOf InSpecClass) - : ID(0) - { - SpecClass = InSpecClass; - if (!DataPtr.IsValid()) - { - DataPtr = MakeShareable(new FGAEffectProperty()); - } - }; - - FAFPropertytHandle(const FAFPropertytHandle& Other) - { - SpecClass = Other.SpecClass; - DataPtr = Other.DataPtr; - }; - - - - void PostScriptConstruct() - { - } - /*FAFPropertytHandle(TSharedRef InPtr, uint32 InID) - : Test(InPtr) - , ID(InID) - {}*/ - - TSubclassOf GetClass() const { return SpecClass.SpecClass; } - const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } -public: - - void InitializeIfNotInitialized(const FGAEffectContext& InContext) - { - DataPtr->InitializeIfNotInitialized(InContext, SpecClass.SpecClass); - } - FGAEffectProperty & GetRef() - { - return DataPtr.ToSharedRef().Get(); - } - FGAEffectProperty& GetRef() const - { - return DataPtr.ToSharedRef().Get(); - } - FGAEffectProperty* GetPtr() const - { - return DataPtr.Get(); - } - - FObjectKey GetClassKey() const - { - return FObjectKey(GetClass()); - } - inline float GetPeriod() const - { - return DataPtr->GetPeriod(); - } - inline float GetDuration() const - { - return DataPtr->GetDuration(); - } - - UGAGameEffectSpec* GetSpec() - { - return DataPtr->GetSpec(); - } - UGAGameEffectSpec* GetSpec() const - { - return DataPtr->GetSpec(); - } - FGAEffectHandle GetHandle(UObject* From) - { - return DataPtr->GetHandle(From); - } - FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) - { - return DataPtr->GetContext(InHandle); - } - const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const - { - return DataPtr->GetContext(InHandle); - } - FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) - { - return DataPtr->GetEffectSpec(InHandle); - } - const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const - { - return DataPtr->GetEffectSpec(InHandle); - } - void CleanUp(const FGAEffectHandle& InHandle) - { - DataPtr->CleanUp(InHandle); - } - const bool IsInitialized() const - { - return DataPtr->IsInitialized(); - } - const bool IsValid() const - { - return SpecClass.SpecClass ? true : false; - } - const bool operator==(const FAFPropertytHandle& Other) const - { - return SpecClass == Other.SpecClass; - } - const bool operator==(const TSubclassOf& OtherClass) const - { - return SpecClass == OtherClass; - } - FAFPropertytHandle& operator=(const FAFPropertytHandle& Rhs) - { - if (this == &Rhs) - return *this; - DataPtr = Rhs.DataPtr; - SpecClass = Rhs.SpecClass; - return *this; - } - void operator=(const TSubclassOf& Other) - { - SpecClass = Other; - } - void operator=(UGAGameEffectSpec* Other) - { - SpecClass = Other->GetClass(); - } -}; - -template<> -struct TStructOpsTypeTraits< FAFPropertytHandle > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithCopy = true, - WithPostScriptConstruct = true, - }; -}; - -USTRUCT() -struct FAFEffectParams -{ - GENERATED_BODY() - //make this private and allow assign only trough constructr. - FAFContextHandle Context; - FAFPropertytHandle Property; - FAFEffectSpecHandle EffectSpec; - bool bRecreated; - bool bPeriodicEffect; -public: - FAFEffectParams() - {}; - FAFEffectParams(FAFPropertytHandle InProperty) - : bRecreated(false) - , Property(InProperty) - {}; - - FGAEffectContext & GetContext() - { - return Context.GetRef(); - } - FGAEffectContext& GetContext() const - { - return Context.GetRef(); - } - - FGAEffectProperty& GetProperty() const - { - return Property.GetRef(); - } - - FAFEffectSpec& GetSpec() - { - return EffectSpec.SpecPtr.ToSharedRef().Get(); - } - FAFEffectSpec& GetSpec() const - { - return EffectSpec.SpecPtr.ToSharedRef().Get(); - } - FTimerManager& GetTargetTimerManager(); - - UAFEffectsComponent* GetTargetEffectsComponent(); - UAFEffectsComponent* GetTargetEffectsComponent() const; - -}; - -USTRUCT(BlueprintType) -struct FAFEventData -{ - GENERATED_BODY() -public: - UPROPERTY(BlueprintReadOnly) - FAFContextHandle ContextHandle; - UPROPERTY(BlueprintReadOnly) - FAFEffectSpecHandle SpecHandle; - UPROPERTY(BlueprintReadOnly) - FAFPropertytHandle PropertyHandle; - - FAFEventData() - {}; - - FAFEventData(FAFContextHandle InContextHandle - , FAFEffectSpecHandle InSpecHandle - , FAFPropertytHandle InPropertyHandle - ) - : ContextHandle(InContextHandle) - , SpecHandle(InSpecHandle) - , PropertyHandle(InPropertyHandle) - {}; - - FAFEventData(const FAFEffectParams& EffectParams) - : ContextHandle(EffectParams.Context) - , SpecHandle(EffectParams.EffectSpec) - , PropertyHandle(EffectParams.Property) - {}; - -}; - -struct FAFStatics -{ - static float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn - , const FGAEffectContext& InContext - , const FGAEffectHandle& InHandle); - static FGAEffectMod GetAttributeModifier(FGAAttributeModifier& ModInfoIn - , class UGAGameEffectSpec* InSpec, - const FGAEffectContext& InContext, - const FGAEffectHandle& InHandle); -}; - -/* - Calculcated magnitudes, captured attributes and tags, set duration. - Final effect which then is used to apply custom calculations and attribute changes. -*/ -DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectMulicastDelegate, const FGAEffectHandle&); -UENUM() -enum class ERepInfoType : uint8 -{ - LocallyPredicted, - RemotePredicted, - Server -}; - -USTRUCT() -struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, TSharedFromThis -{ - GENERATED_BODY() - - FGAEffectHandle Handle; - UPROPERTY() - FAFPredictionHandle PredictionHandle; - - mutable FTimerHandle PeriodTimerHandle; - mutable FTimerHandle DurationTimerHandle; - - UWorld* World; - -public: - float AppliedTime; - float LastTickTime; - float Period; - float Duration; -public: - void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); - void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); - void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); - - inline void SetHandle(const FGAEffectHandle& InHandle) - { - Handle = InHandle; - } - - float GetDurationTime() const; - float GetPeriodTime() const; - float GetCurrentDuration() const; - //float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const; - - FGAEffect() - {} - - ~FGAEffect(); - - - bool operator==(const FGAEffect& Other) const - { - return Handle == Other.Handle; - } -}; - -/* - Minimum replicated info about applied info, so we don't replicate full effect if not needed. - Also provide callbacks for cues assigned to this Effect, so they can be predictevly, - executed on clients. - - Add replication optimization. -*/ - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectAttributeModifier -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere) - FGAAttribute Attribute; - UPROPERTY(EditAnywhere) - float Value; -}; -USTRUCT(BlueprintType) -struct FGAEffectDuration -{ - GENERATED_USTRUCT_BODY() -public: - /* - -1 infinite duration, 0-no duration >0 - set duration - */ - UPROPERTY(EditAnywhere, Category = "Duration") - float Duration; - /* - <=0 - no period >0 - set period - */ - UPROPERTY(EditAnywhere, Category = "Duration") - float Period; - /* - If PeriodNum > 0 and Period > 0, then duration of - effect is PeriodNum * Period - */ - UPROPERTY(EditAnywhere, Category = "Duration") - float PeriodNum; -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer -{ - GENERATED_USTRUCT_BODY() - - UPROPERTY() - TArray Effects; -}; - - -USTRUCT() -struct ABILITYFRAMEWORK_API FGAGameCue -{ - GENERATED_BODY() - - - //Handle to effect, which spawned this cue. - UPROPERTY() - FGAEffectHandle EffectHandle; -}; - -USTRUCT() -struct ABILITYFRAMEWORK_API FGameCueContainer -{ - GENERATED_USTRUCT_BODY() - - TWeakObjectPtr OwningComp; -public: - void AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams); -}; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer -{ - GENERATED_BODY() -public: - UPROPERTY() - TArray ActiveEffectInfos; - - UPROPERTY() - TMap HandleByPrediction; - - UPROPERTY() - TMap PredictionByHandle; - - - TMap PredictedEffectInfos; - - - TMap> EffectByAttribute; - - - TMap> EffectByClass; - - TMap ActiveEffects; - /* - Contains effects with infinite duration. - Infinite effects are considred to be special case, where they can only be self spplied - and must be manually removed. - */ - UPROPERTY() - TSet InfiniteEffects; - - //not really sure if we really need set.\ - // it could be usefull, for effects which stack in add. - /* - UObject* - Instigator - FName = Effect class name - FGAEffectHandle = handle to effect of class. - */ - - TMap>> InstigatorEffectByClass; - - /* - FName = Effect class name - FGAEffectHandle = handle to effect of class. - */ - - TMap> TargetEffectByClass; - - //Conditonally applied effects. Only duration/periodic. - //TMap ConditionalEffects; - - UPROPERTY(NotReplicated) - class UAFEffectsComponent* OwningComponent; -public: - - /* - * @call Order: - * Previous Function: UAFAbilityComponent::ApplyEffectToSelf - * Next Function: InProperty.Application->ApplyEffect(); - * FGAEffectContainer::ApplyReplicationInfo() - * - * Apply target to Me. Try to apply effect to container and launch Events in: - * TMap OnEffectEvent - event is called before application; - * TMap OnEffectApplyToSelf - event is called before application; - * - * @param EffectIn* - Effect to apply - * @param InProperty - cached effect information - * @param InContext - Context about effect application. Target, instigator, causer. - * @param Modifier - optional modifier which can be applied to effect. - * @return Handle to Effect @ UAFAbilityComponent::ApplyEffectToSelf - */ - FGAEffectHandle ApplyEffect( - const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle - , const FAFEffectParams& Params - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - TArray RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num = 1); - /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty); - - inline int32 GetEffectsNum() const { return ActiveEffectInfos.Num(); }; - - TSet GetHandlesByClass(const FGAEffectProperty& InProperty, - const FGAEffectContext& InContext); - - void AddEffect( - const FGAEffectHandle& InHandle - , const FAFPredictionHandle& InPredHandle - , FGAEffect* InEffect - , const FGAEffectProperty& InProperty - , bool bInfinite = false); - - //modifiers - void ApplyEffectsFromMods() {}; - void DoesQualify() {}; - bool IsEffectActive(const FGAEffectHandle& HandleIn); - bool IsEffectActive(const FGAEffectHandle& HandleIn) const; - bool ContainsEffectOfClass(const FAFPropertytHandle& InProperty); - - void ApplyFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle, FGAEffect* InEffect); - void RemoveFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle); - - bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) - { - //return FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); - return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); - } - - UWorld* GetWorld() const; - - ///Helpers - float GetRemainingTime(const FGAEffectHandle& InHandle) const; - float GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const; - /* Get Current effect ime clamped to max duration */ - float GetCurrentTime(const FGAEffectHandle& InHandle) const; - float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const; - float GetEndTime(const FGAEffectHandle& InHandle) const; - - FGAEffect* GetEffect(const FGAEffectHandle& InHandle) - { - return ActiveEffects[InHandle]; - } - bool IsEffectActive(TSubclassOf EffectClass); -private: - void RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle); -}; -template<> -struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithNetDeltaSerializer = true, - WithCopy = false - }; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp deleted file mode 100644 index ff8bdb1..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.cpp +++ /dev/null @@ -1,353 +0,0 @@ -#pragma once -#include "AbilityFramework.h" -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "GameplayTagContainer.h" -#include "AFAbilityComponent.h" -#include "Attributes/GAAttributeBase.h" -#include "Effects/GAEffectExecution.h" -#include "AFAbilityInterface.h" -#include "Effects/GACustomCalculation.h" - -void AddLogDebugInfo(FString Text, UWorld* World) -{ - bool bIsServer = GEngine->GetNetMode(World) == ENetMode::NM_DedicatedServer; - UE_LOG(AbilityFramework, Log, TEXT("%s :: %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Text); -} - -FGAEffectContext::FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, - const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, - TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, - TWeakObjectPtr TargetCompIn, - TWeakObjectPtr InstigatorCompIn, - TWeakObjectPtr InAvatar) - : TargetHitLocation(TargetHitLocationIn), - TargetAttributes(TargetAttributesIn), - InstigatorAttributes(InstigatorAttributesIn), - Target(TargetIn), - Causer(CauserIn), - Instigator(InstigatorIn), - Avatar(InAvatar), - TargetComp(TargetCompIn), - InstigatorComp(InstigatorCompIn) -{ - TargetInterface = Cast(TargetIn.Get()); - InstigatorInterface = Cast(Instigator.Get()); - IAFAbilityInterface* CauserInterface = Cast(Causer.Get()); -} -void FGAEffectContext::SetTarget(UObject* NewTarget) -{ - IAFAbilityInterface* ATI = Cast(NewTarget); - if (!ATI) - { - return; - } - - TargetComp = ATI->GetAbilityComp(); - Target = NewTarget; - TargetInterface = ATI; - TargetAttributes = ATI->GetAttributes(); -} -FGAEffectHandle::FGAEffectHandle() - : Handle(0) -{ - Handle = 0; -} -FGAEffectHandle::FGAEffectHandle(uint32 HandleIn) - : Handle(HandleIn) -{ -} -void FGAEffectHandle::PostScriptConstruct() -{ - Handle = 0; -} -FGAEffectHandle::~FGAEffectHandle() -{ -} - -/* Executes effect trough provided execution class. */ - -FGAEffectHandle FGAEffectHandle::GenerateHandle() -{ - static int32 Handle; - Handle++; - return FGAEffectHandle(Handle); -} - -bool FGAEffectHandle::IsValid() const -{ - return (Handle > 0);// && EffectPtr->Context.IsValid(); -} -void FGAEffectHandle::Reset() -{ - Handle = 0; -} - -FAFPredictionHandle FAFPredictionHandle::GenerateClientHandle(UAFAbilityComponent* InComponent) -{ - if (InComponent->GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - static uint32 Counter = 1; - Counter++; - FAFPredictionHandle Handle; - Handle.Handle = Counter; - return Handle; - } - return FAFPredictionHandle(); -} - -FGAHashedGameplayTagContainer::FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn) - : Tags(TagsIn) -{ - GenerateFNameKey(); -} -void FGAHashedGameplayTagContainer::GenerateFNameKey() -{ - FString RetString; - for (const FGameplayTag& tag : Tags) - { - RetString += TEXT("."); - RetString += tag.ToString(); - RetString += TEXT("."); - } - Key = *RetString; -} - -void FGAEffectContext::operator=(const FGAEffectContext& Other) -{ - HitResult = Other.HitResult; - TargetHitLocation = Other.TargetHitLocation; - TargetAttributes = Other.TargetAttributes; - InstigatorAttributes = Other.InstigatorAttributes; - Target = Other.Target; - Causer = Other.Causer; - Instigator = Other.Instigator; - Avatar = Other.Avatar; - TargetComp = Other.TargetComp; - InstigatorComp = Other.InstigatorComp; - TargetInterface = Other.TargetInterface; - InstigatorInterface = Other.InstigatorInterface; -} -FGAEffectContext::FGAEffectContext(const FGAEffectContext& Other) -{ - HitResult = Other.HitResult; - TargetHitLocation = Other.TargetHitLocation; - TargetAttributes = Other.TargetAttributes; - InstigatorAttributes = Other.InstigatorAttributes; - Target = Other.Target; - Causer = Other.Causer; - Instigator = Other.Instigator; - Avatar = Other.Avatar; - TargetComp = Other.TargetComp; - InstigatorComp = Other.InstigatorComp; - TargetInterface = Other.TargetInterface; - InstigatorInterface = Other.InstigatorInterface; -} -void FGAEffectContext::Reset() -{ - Target.Reset(); - Causer.Reset(); - Instigator.Reset(); - TargetComp.Reset(); - InstigatorComp.Reset(); - TargetInterface = nullptr; - InstigatorInterface = nullptr; -} -class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() -{ - if (TargetAttributes.IsValid()) - return TargetAttributes.Get(); - else - return nullptr; -} -class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() -{ - if(InstigatorComp.IsValid()) - return InstigatorComp->DefaultAttributes; - return nullptr; -} -class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() -{ - IAFAbilityInterface* AttrInt = Cast(Causer.Get()); - if (AttrInt) - { - return AttrInt->GetAttributes(); - } - return nullptr; -} - -class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() const -{ - if (TargetAttributes.IsValid()) - return TargetAttributes.Get(); - else - return nullptr; -} -class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() const -{ - if (InstigatorComp.IsValid()) - return InstigatorComp->DefaultAttributes; - return nullptr; -} -class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() const -{ - IAFAbilityInterface* AttrInt = Cast(Causer.Get()); - if (AttrInt) - { - return AttrInt->GetAttributes(); - } - return nullptr; -} - -class UAFEffectsComponent* FGAEffectContext::GetTargetEffectsComponent() -{ - IAFAbilityInterface* AttrInt = Cast(Target.Get()); - if (AttrInt) - { - return AttrInt->GetEffectsComponent(); - } - return nullptr; -} - -class UAFEffectsComponent* FGAEffectContext::GetTargetEffectsComponent() const -{ - IAFAbilityInterface* AttrInt = Cast(Target.Get()); - if (AttrInt) - { - return AttrInt->GetEffectsComponent(); - } - return nullptr; -} - -FGAEffectContext::~FGAEffectContext() -{ - Target.Reset(); - Causer.Reset(); - Instigator.Reset(); - TargetComp.Reset(); - InstigatorComp.Reset(); -} - -void FGACountedTagContainer::AddTag(const FGameplayTag& TagIn) -{ - int32& count = CountedTags.FindOrAdd(TagIn); - //if (count) - //{ - // *count += 1; - // return; - //} - count++; - //CountedTags.Add(TagIn, 1); - AllTags.AddTag(TagIn); -} -void FGACountedTagContainer::AddTagContainer(const FGameplayTagContainer& TagsIn) -{ - for (auto TagIt = TagsIn.CreateConstIterator(); TagIt; ++TagIt) - { - int32* count = CountedTags.Find(*TagIt); - if (count) - { - *count += 1; - } - else - { - CountedTags.Add(*TagIt, 1); - AllTags.AddTag(*TagIt); - } - } -} -void FGACountedTagContainer::RemoveTag(const FGameplayTag& TagIn) -{ - int32* count = CountedTags.Find(TagIn); - if (count) - { - *count -= 1; - if (*count <= 0) - { - CountedTags.Remove(TagIn); - AllTags.RemoveTag(TagIn); - } - } -} -void FGACountedTagContainer::RemoveTagContainer(const FGameplayTagContainer& TagsIn) -{ - for (auto TagIt = TagsIn.CreateConstIterator(); TagIt; ++TagIt) - { - int32* count = CountedTags.Find(*TagIt); - if (count) - { - *count -= 1; - } - if (*count <= 0) - { - CountedTags.Remove(*TagIt); - AllTags.RemoveTag(*TagIt); - } - } -} -bool FGACountedTagContainer::HasTag(const FGameplayTag& TagIn) -{ - return AllTags.HasTag(TagIn); -} -bool FGACountedTagContainer::HasTagExact(const FGameplayTag TagIn) -{ - return AllTags.HasTagExact(TagIn); -} -bool FGACountedTagContainer::HasAny(const FGameplayTagContainer& TagsIn) -{ - return AllTags.HasAny(TagsIn); -} -bool FGACountedTagContainer::HasAnyExact(const FGameplayTagContainer& TagsIn) -{ - return AllTags.HasAnyExact(TagsIn); -} -bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) -{ - return AllTags.HasAll(TagsIn); -} -bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) -{ - return AllTags.HasAllExact(TagsIn); -} - -bool FGACountedTagContainer::HasTag(const FGameplayTag& TagIn) const -{ - return AllTags.HasTag(TagIn); -} -bool FGACountedTagContainer::HasTagExact(const FGameplayTag TagIn) const -{ - return AllTags.HasTagExact(TagIn); -} -bool FGACountedTagContainer::HasAny(const FGameplayTagContainer& TagsIn) const -{ - return AllTags.HasAny(TagsIn); -} -bool FGACountedTagContainer::HasAnyExact(const FGameplayTagContainer& TagsIn) const -{ - return AllTags.HasAnyExact(TagsIn); -} -bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) const -{ - return AllTags.HasAll(TagsIn); -} -bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) const -{ - return AllTags.HasAllExact(TagsIn); -} - -FAFCueHandle FAFCueHandle::GenerateHandle() -{ - static uint32 HandleIndex = 0; - HandleIndex++; - - FAFCueHandle NewHandle(HandleIndex); - - return NewHandle; -} - -FGAEffectCueParams::FGAEffectCueParams(const FGAEffectContext& InContext, const struct FGAEffectProperty& InProperty) - : HitResult(InContext.HitResult) - , Instigator(InContext.Instigator) - , Causer(InContext.Causer) - , CueTags(InProperty.GetSpec()->Cues.CueTags) -{}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h deleted file mode 100644 index 015aabd..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAGlobalTypes.h +++ /dev/null @@ -1,790 +0,0 @@ -#pragma once -#include "AbilityFramework.h" -#include "GameplayTagsModule.h" -#include "GameplayTagContainer.h" -//#include "Messaging.h" -#include "GAGlobalTypes.generated.h" - -void AddLogDebugInfo(FString Text, UWorld* World); - -/* - Explanation of tags from Fred K, on forums: - https://forums.unrealengine.com/showthread.php?57988-GameplayAbilities-questions&p=220315#post220315 - Here are some examples to illustrate the possible results. Let's assume that our - tag container contains exactly one tag, "A.B.C". - - HasTag("A.B.C", Explicit, Explicit) returns true. - HasTag("A.B", Explicit, Explicit) returns false. - HasTag("A.B.C.D", Explicit, Explicit) returns false. - HasTag("E.B.C", Explicit, Explicit) returns false. - HasTag("A.B.C", IncludeParentTags, IncludeParentTags) returns true. - HasTag("A.B", IncludeParentTags, IncludeParentTags) returns true. - HasTag("A.B.C.D", IncludeParentTags, IncludeParentTags) returns true. - HasTag("E.B.C", IncludeParentTags, IncludeParentTags) returns false. - HasTag("A.B.C", IncludeParentTags, Explicit) returns true. - HasTag("A.B", IncludeParentTags, Explicit) returns true. - HasTag("A.B.C.D", IncludeParentTags, Explicit) returns false. - HasTag("E.B.C", IncludeParentTags, Explicit) returns false. - HasTag("A.B.C", Explicit, IncludeParentTags) returns true. - HasTag("A.B", Explicit, IncludeParentTags) returns false. - HasTag("A.B.C.D", Explicit, IncludeParentTags) returns true. - HasTag("E.B.C", Explicit, IncludeParentTags) returns false. -*/ - -/* - I seriosuly need to clean this shit up. -*/ -/* - TODO:: I probabaly need to change it to normal enum. - So I can use it as array indexes. -*/ -UENUM() -enum class EGAAttributeMod : int32 -{ - Add = 0, //Value = Value + X - Subtract = 1, //Value = Value - X - Multiply = 2, //Value = Value * X - Divide = 3,//Value = Value * X - ok its's not really divide. - Set = 4, //Value = X - PercentageAdd = 5, - PercentageSubtract = 6, - Invalid = 7 -}; - -UENUM() -enum class EGAAttributeSource : uint8 -{ - Instigator, - Target, - Causer, - Ability -}; - -UENUM() -enum class EGAModifierTarget : uint8 -{ - Instigator, - Target -}; - -UENUM() -enum class EGAAttributeValue : uint8 -{ - Base, - Current, - Final, - Bonus -}; - -UENUM() -enum class EGAEffectType : uint8 -{ - Instant = 0, - Duration = 1, - Infinite = 2, -}; - -/* - - StrongetOverride - Does not check for effect type/tags. It will just check if modified - attribute, is already modified, and if incoming effect is stronger it will override - all modifiers affecting this attribute, and remove all weaker ones. - - Override - does not check if it is stronger/weaker, it will simply override any existing modifiers - and effects with the same name. - - Duration - Will add duration to existing effect of EXACTLY the same type. - - Intensity - Undefined. It will either add new effects to stack, - or it will simply sum modifiers, from all effects of the same types, for the same attributes - and refresh duration to the latest applied effect. - - Add - no checks, simply add new effect to stack. -*/ -UENUM() -enum class EGAEffectStacking : uint8 -{ - Add = 0, - Duration = 1, - Override = 2, //override existing effect of the same type, and all other effects which have override the same attribute and have same AttributeTags - Intensity = 3, - //will add duration to existing effect - //will simply add new effect -}; - -UENUM() -enum class EGAMagnitudeCalculation : uint8 -{ - Direct, //straight float value, no calculations. - AttributeBased, //calculate based on attribute Attribute * RestOfEquationToBeDecided - CurveBased, //Takes value of attribute, and then gets value from curve based on this attribute. - CustomCalculation,//uses custom object to calculate magnitude. - Invalid -}; - - -/* -Rules for where we should aggregate effects. -Concept might look bit muddy at first look, but it is actually very simple. - -Let's say we have additive effect which modify Health by 50 points, and effect which modify health by 100. -We want, to only the highest one, affect target (positive bonus). Regardless of who applied this effect. - -To do it we need to tell this effect, that it should be aggregated by target and set effect stacking rule to -HighestOverride. - -Now say we have effect which reduce Health by 30 points, and second which reduce by 20 points. -We might want negative effects from diffrent source to stack. -To do this we need to aggregate those effects by Instigator. -And then we can decide how those effects will stack within single Instigator. -*/ -UENUM() -enum class EGAEffectAggregation : uint8 -{ - /* - Effect will be stacked/aggregated by Instigator who applied it. - Checking for stacking rules will be done only against other effects from the same Instigator. - */ - AggregateByInstigator, - /* - Effects will be stacked/aggregated by Target. - Checking for stacking rules, will be done only for effects, with the same target. - */ - AggregateByTarget -}; - -USTRUCT() -struct FAFAtributeRowData : public FTableRowBase -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, BlueprintReadOnly) - float BaseValue; - UPROPERTY(EditAnywhere, BlueprintReadOnly) - float MinValue; - UPROPERTY(EditAnywhere, BlueprintReadOnly) - float MaxValue; - UPROPERTY(EditAnywhere, BlueprintReadOnly) - float CurrentValue; - UPROPERTY(EditAnywhere, BlueprintReadOnly) - TSubclassOf Extension; -}; - - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectContext -{ - GENERATED_USTRUCT_BODY() -public: - /* - Just copy entire hit result struct. - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - FHitResult HitResult; - /** - * Where exactly we hit target. - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - FVector TargetHitLocation; - - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr TargetAttributes; - - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr InstigatorAttributes; - - /** - * Direct Reference to TargetActor (I will possibly remove FHitResult Target! - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr Target; - /** - * Object which caused this effect. Might be ability, weapon, projectile etc. - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr Causer; - /** - * Pawn, which originally instigated effect (an owned AttributeComponent). - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr Instigator; - - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr Avatar; - /** - * Attribute component of Target. - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr TargetComp; - /** - * Attribute component of Intigator - */ - UPROPERTY(BlueprintReadOnly, Category = "Spec") - TWeakObjectPtr InstigatorComp; - - class IAFAbilityInterface* TargetInterface; - class IAFAbilityInterface* InstigatorInterface; - - void SetTarget(UObject* NewTarget); - template - inline T* GetTarget() - { - return Cast(Target); - } - - inline bool IsValid() const - { - /*if (Target.IsValid() && Causer.IsValid() && Instigator.IsValid() && TargetComp.IsValid() && InstigatorComp.IsValid()) - return true;*/ - if (Causer.IsValid() && Instigator.IsValid() && InstigatorComp.IsValid() && TargetInterface) - return true; - //UE_LOG(GameAttributesEffects, Error, TEXT("Effect Context Is Not Valid")); - return false; - } - - inline FString ToString() - { - if (!IsValid()) - { - //UE_LOG(GameAttributesEffects, Error, TEXT("Effect Context Is Not Valid")); - return FString("Context Is not valid"); - } - FString ret; - ret = "TargetHitLocation: "; - ret += TargetHitLocation.ToString(); - ret += "\n"; - ret += "Target: "; - ret += Target->GetName(); - ret += "\n"; - ret += "Causer: "; - ret += Causer->GetName(); - ret += "\n"; - ret += "Instigator: "; - ret += Instigator->GetName(); - ret += "\n"; - ret += "TargetComp: "; - return ret; - } - - bool operator==(UObject* Other) const - { - return FObjectKey(Target.Get()) == FObjectKey(Other); - } - - bool operator==(const FObjectKey& Other) const - { - return FObjectKey(Target.Get()) == Other; - } - - void Reset(); - - class UGAAttributesBase* GetTargetAttributes(); - class UGAAttributesBase* GetInstigatorAttributes(); - class UGAAttributesBase* GetCauserAttributes(); - - class UGAAttributesBase* GetTargetAttributes() const; - class UGAAttributesBase* GetInstigatorAttributes() const; - class UGAAttributesBase* GetCauserAttributes() const; - - class UAFEffectsComponent* GetTargetEffectsComponent(); - class UAFEffectsComponent* GetTargetEffectsComponent() const; - void operator=(const FGAEffectContext& Other); - FGAEffectContext() - {} - - FGAEffectContext(const FGAEffectContext& Other); - - FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, - const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, - TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, - TWeakObjectPtr TargetCompIn, - TWeakObjectPtr InstigatorCompIn, - TWeakObjectPtr InAvatar); - - ~FGAEffectContext(); -}; - - -struct FGAEffect; -class UGAGameEffectSpec; -struct FGAEffectMod; -struct FGAAttribute; - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectHandle -{ - GENERATED_BODY() -protected: - //just to be safe we don't run out of numbers.. - UPROPERTY(VisibleAnywhere, Transient) - int32 Handle; //Fname Guid ? -public: - int32 GetHandle() const - { - return Handle; - } - static FGAEffectHandle GenerateHandle(); - bool operator==(const FGAEffectHandle& Other) const - { - return Handle == Other.Handle; - } - bool operator!=(const FGAEffectHandle& Other) const - { - return Handle != Other.Handle; - } - - //FGAEffectHandle& operator=(const FGAEffectHandle& Other) - //{ - // Handle = Other.Handle; - // EffectPtr = Other.EffectPtr; - // return *this; - //} - - void Reset(); - bool IsValid() const; - friend uint32 GetTypeHash(const FGAEffectHandle& InHandle) - { - return InHandle.Handle; - } - - FGAEffectHandle(); - - FGAEffectHandle(uint32 HandleIn); - void PostScriptConstruct(); -public: - ~FGAEffectHandle(); -}; -// -template<> -struct TStructOpsTypeTraits< FGAEffectHandle > : public TStructOpsTypeTraitsBase2 -{ - enum - { - WithPostScriptConstruct = true, - }; -}; - -USTRUCT() -struct FAFPredictionHandle -{ - GENERATED_BODY() -public: - //ID of current handle. - UPROPERTY() - uint32 Handle; - UPROPERTY() - FGAEffectHandle EffectHandle; - - uint64 Timestamp; - - static FAFPredictionHandle GenerateClientHandle(UAFAbilityComponent* InComponent); - /* - Was prediction successful ? - If true nothing happens on client (might interpolate to result from server). - If false, server will override client predicted results. - */ - UPROPERTY() - bool bPredictionValid; - - - bool IsValid() const - { - return true; - } - - const bool operator==(const FAFPredictionHandle& Other) const - { - return Handle == Other.Handle; - } - friend uint32 GetTypeHash(const FAFPredictionHandle& InHandle) - { - return InHandle.Handle; - } -}; - -DECLARE_MULTICAST_DELEGATE(FGAGenericDelegate); - -struct ABILITYFRAMEWORK_API EnumToString -{ - static FString GetStatckingAsString(EGAEffectStacking Stacking) - { - switch (Stacking) - { - case EGAEffectStacking::Override: - return FString("Override"); - case EGAEffectStacking::Intensity: - return FString("Intensity"); - case EGAEffectStacking::Duration: - return FString("Duration"); - case EGAEffectStacking::Add: - return FString("Add"); - } - return FString(""); - } -}; - -/* - Special struct, which allows to use FGameplayTagContainer as key, for TSet and TMap. - Bear in mind slower inserts/remove, but allow for complex keys. -*/ -struct ABILITYFRAMEWORK_API FGAHashedGameplayTagContainer -{ -public: - FGameplayTagContainer Tags; - -private: - FName Key; - void GenerateFNameKey(); - -public: - FGAHashedGameplayTagContainer() - {}; - FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn); - - friend uint32 GetTypeHash(const FGAHashedGameplayTagContainer& InHandle) - { - return ::GetTypeHash(InHandle.Key); - } -}; - -USTRUCT(BlueprintType) -struct FGAIndividualMods -{ - GENERATED_BODY() -public: - UPROPERTY() - float Additive; - UPROPERTY() - float Subtractive; - UPROPERTY() - float Multiplicative; - UPROPERTY() - float Divide; - UPROPERTY() - float PercentageAdd; - UPROPERTY() - float PercentageSubtract; - - FGAIndividualMods() - : Additive(0.0f), - Subtractive(0.0f), - Multiplicative(0.0f), - Divide(0.0f), - PercentageAdd(0.0f), - PercentageSubtract(0.0f) - {}; - FGAIndividualMods(float AdditiveIn, - float SubtractiveIn, - float MultiplicativeIn, - float DivideIn, - float PercentageAddIn, - float PercentageSubtractIn - ) - : Additive(AdditiveIn), - Subtractive(SubtractiveIn), - Multiplicative(MultiplicativeIn), - Divide(DivideIn), - PercentageAdd(PercentageAddIn), - PercentageSubtract(PercentageSubtractIn) - {} -}; -/** -* Struct representing single attribute. Needed for Pin customization. -* What we really need is to use this struct for making "complex" attributes. -* Which means attributes, which needs to track their own state. -* Bonuses applied to them, types of bonues, and who applied those bonuses -* so we can properly remove them, get them, track them, and controll order -* in which theyare added. -* we will two have attributes types. Staless (transient), auxiallry attttributes -* and staefull attributes, which are going to track their state. -*/ -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAAttribute -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere, BlueprintReadOnly) - FName AttributeName; - - inline bool operator== (const FGAAttribute& OtherAttribute) const - { - return (OtherAttribute.AttributeName == AttributeName); - } - - inline bool operator!= (const FGAAttribute& OtherAttribute) const - { - return (OtherAttribute.AttributeName != AttributeName); - } - - inline bool IsValid() const - { - return !AttributeName.IsNone(); - } - - inline FString ToString() - { - return AttributeName.ToString(); - } - - FGAAttribute() - { - AttributeName = NAME_None; - }; - FGAAttribute(const FName& AttributeNameIn) - { - AttributeName = AttributeNameIn; - }; - friend uint32 GetTypeHash(const FGAAttribute& InAttribute) - { - return GetTypeHash(InAttribute.AttributeName); - } - //FGAAttribute(const FString& AttributeNameIn) - //{ - // AttributeName = *AttributeNameIn; - //}; -}; - -/* Final calculcated mod from effect, which can be modified by Calculation object. */ -USTRUCT() -struct FGAEffectMod -{ - GENERATED_BODY() - FGAAttribute Attribute; - float Value; - EGAAttributeMod AttributeMod; - struct FGAEffectHandle Handle; - FGameplayTagContainer AttributeTags; - /* - Spec from which this mod has been derived. - Used to do not copy to much heavy data around. - */ - inline bool CompareMods(const FGAEffectMod& OtherMod) const - { - return AttributeMod == OtherMod.AttributeMod; - } - inline bool HasAllTags(const FGameplayTagContainer& TagsIn) const - { - return AttributeTags.HasAll(TagsIn); - } - inline bool HasAllTagsExact(const FGAEffectMod& OtherMod) const - { - return AttributeTags.HasAllExact(OtherMod.AttributeTags); - } - inline bool HasAllTagsExact(const FGameplayTagContainer& TagsIn) const - { - return AttributeTags.HasAllExact(TagsIn); - } - inline bool HasAllTagsIncludingChildren(const FGameplayTagContainer& TagsIn) const - { - return TagsIn.HasAll(AttributeTags); - } - const bool operator==(const FGAEffectMod& Other) const - { - return Value == Other.Value && AttributeMod == Other.AttributeMod; - } - const bool operator!=(const FGAEffectMod& Other) const - { - return Value != Other.Value && AttributeMod == Other.AttributeMod; - } - - const bool operator>(const FGAEffectMod& Other) const - { - return Value > Other.Value && AttributeMod == Other.AttributeMod; - } - - const bool operator<(const FGAEffectMod& Other) const - { - return Value < Other.Value && AttributeMod == Other.AttributeMod; - } - const bool operator>=(const FGAEffectMod& Other) const - { - return Value >= Other.Value && AttributeMod == Other.AttributeMod; - } - - const bool operator<=(const FGAEffectMod& Other) const - { - return Value <= Other.Value && AttributeMod == Other.AttributeMod; - } - - - FGAEffectMod() - : Attribute(NAME_None), - Value(0), - AttributeMod(EGAAttributeMod::Invalid) - {}; - - FGAEffectMod(const FGAAttribute& AttributeIn, float ValueIn, - EGAAttributeMod AttributeModIn, FGAEffectHandle HandleIn, FGameplayTagContainer AttributeTagsIn) - : Attribute(AttributeIn), - Value(ValueIn), - AttributeMod(AttributeModIn), - Handle(HandleIn), - AttributeTags(AttributeTagsIn) - { - }; -}; - -USTRUCT(BlueprintType) -struct FAFAttributeChangedData -{ - GENERATED_BODY() -public: - FGAEffectMod Mod; - UPROPERTY() - TWeakObjectPtr Target; - //HitLocation of applicable; - FVector Location; - float NewValue; -}; - -/* -Struct representing final modifier applied to attribute. -*/ -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAModifier -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY() - EGAAttributeMod AttributeMod; - UPROPERTY() - float Value; - - FGameplayTagContainer Tags; - /* - Weak pointer to effect, which added this modifier. - Useful because, while effect exist it have lots of useful informations. - */ - struct FGAEffectHandle Handle; - - FGAModifier() - {}; - FGAModifier(EGAAttributeMod ModIn, float ValueIn) - : AttributeMod(ModIn), - Value(ValueIn) - {}; - FGAModifier(EGAAttributeMod ModIn, float ValueIn, FGAEffectHandle HandleIn) - : AttributeMod(ModIn), - Value(ValueIn), - Handle(HandleIn) - {}; - - FGAModifier(const FGAEffectMod& ModIn) - : AttributeMod(ModIn.AttributeMod), - Value(ModIn.Value), - Handle(ModIn.Handle) - {}; -}; - -USTRUCT() -struct ABILITYFRAMEWORK_API FGACountedTagContainer -{ - GENERATED_USTRUCT_BODY() -protected: - /* - Here we will store counted GamaplayTags. - If tag is already in map, we just incremement count. - */ - TMap CountedTags; - - /* - Here we store all currently posesd tags. - It is equivalent of CountedTags, except this does not track count of tags, but we need it - to have something against which we can perform queries. - */ -public: - UPROPERTY() - FGameplayTagContainer AllTags; -public: - - inline FGameplayTagContainer GetTags() { return AllTags; }; - - void AddTag(const FGameplayTag& TagIn); - void AddTagContainer(const FGameplayTagContainer& TagsIn); - void RemoveTag(const FGameplayTag& TagIn); - void RemoveTagContainer(const FGameplayTagContainer& TagsIn); - - bool HasTag(const FGameplayTag& TagIn); - bool HasTagExact(const FGameplayTag TagIn); - bool HasAny(const FGameplayTagContainer& TagsIn); - bool HasAnyExact(const FGameplayTagContainer& TagsIn); - bool HasAll(const FGameplayTagContainer& TagsIn); - bool HasAllExact(const FGameplayTagContainer& TagsIn); - - bool HasTag(const FGameplayTag& TagIn) const; - bool HasTagExact(const FGameplayTag TagIn) const; - bool HasAny(const FGameplayTagContainer& TagsIn) const; - bool HasAnyExact(const FGameplayTagContainer& TagsIn) const; - bool HasAll(const FGameplayTagContainer& TagsIn) const; - bool HasAllExact(const FGameplayTagContainer& TagsIn) const; - - inline FGameplayTagContainer& GetAllTags() - { - return AllTags; - } - - inline int32 GetTagCount(const FGameplayTag& TagIn) const - { - return CountedTags.FindRef(TagIn); - } -}; - - -USTRUCT(BlueprintType) -struct ABILITYFRAMEWORK_API FGAEffectCueParams -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(BlueprintReadOnly, Category = "Gameplay Cue") - FHitResult HitResult; - - /** Instigator actor, the actor that owns the ability system component */ - UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") - TWeakObjectPtr Instigator; - - /** The physical actor that actually did the damage, can be a weapon or projectile */ - UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") - TWeakObjectPtr Causer; - - UPROPERTY(BlueprintReadOnly) - FGameplayTagContainer CueTags; - - FGAEffectCueParams() - {}; - FGAEffectCueParams(const FHitResult& InHitResult, AActor* InstigatorIn, UObject* CauserIn) - : HitResult(InHitResult), - Instigator(InstigatorIn), - Causer(CauserIn) - {}; - FGAEffectCueParams(const FGAEffectContext& InContext, const struct FGAEffectProperty& InProperty); - //bool NetSerialize(FArchive& Ar, class UPackageMap* Map, bool& bOutSuccess); -}; - -USTRUCT() -struct FAFCueHandle -{ - GENERATED_BODY(); -private: - UPROPERTY() - uint32 Handle; - - FAFCueHandle(uint32 InHandle) - : Handle(InHandle) - {} -public: - FAFCueHandle() - : Handle(0) - {} - - static FAFCueHandle GenerateHandle(); - - bool operator==(const FAFCueHandle Other) const - { - return Handle == Other.Handle; - } - - friend uint32 GetTypeHash(const FAFCueHandle& InHandle) - { - return InHandle.Handle; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp deleted file mode 100644 index 0451e0e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.cpp +++ /dev/null @@ -1,5 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAHelperTemplates.h" - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h deleted file mode 100644 index 34b2f98..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAHelperTemplates.h +++ /dev/null @@ -1,59 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once -#include "Engine/NetSerialization.h" -#include "GameplayTags.h" -#include "AFAbilityComponent.h" -#include "GAHelperTemplates.generated.h" - -USTRUCT(BlueprintType) -struct FGAAttributeSource -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - EGAAttributeSource Source; - /* Class which is source for attribute set. */ - UPROPERTY(EditAnywhere)//, meta = (MustImplement = "IGAAbilities")) - FGameplayTag AttributeSource; -}; - -USTRUCT(BlueprintType) -struct FGAAttributeCapture -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - FGAAttributeSource Source; - - UPROPERTY(EditAnywhere) - FGameplayTagContainer RequiredTags; - UPROPERTY(EditAnywhere) - FGameplayTagContainer DenyTags; - - template - T* GetAttributeSet(const FGAEffectContext& ContextIn) - { - UAFAbilityComponent* TargetComp = ContextIn.TargetComp.Get(); - UAFAbilityComponent* InstigatorComp = ContextIn.InstigatorComp.Get(); - T* AttributeSet = nullptr; - switch (Source.Source) - { - case EGAAttributeSource::Causer: - { - break; - } - case EGAAttributeSource::Target: - { - AttributeSet = TargetComp->GetAttributeSet(Source.AttributeSource); - break; - } - case EGAAttributeSource::Instigator: - { - AttributeSet = InstigatorComp->GetAttributeSet(Source.AttributeSource); - break; - } - } - return AttributeSet; - } -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp deleted file mode 100644 index 05718f4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAPhysicalMaterial.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h deleted file mode 100644 index 429f1bd..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAPhysicalMaterial.h +++ /dev/null @@ -1,19 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "PhysicalMaterials/PhysicalMaterial.h" -#include "GAPhysicalMaterial.generated.h" - -/** - * - */ -UCLASS(Blueprintable) -class ABILITYFRAMEWORK_API UGAPhysicalMaterial : public UPhysicalMaterial -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Fx") - UParticleEmitter* SurfaceHitFX; - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp deleted file mode 100644 index 6e90d29..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFramework.h" -#include "GAUIData.h" - - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h b/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h deleted file mode 100644 index bc6d205..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/GAUIData.h +++ /dev/null @@ -1,16 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "Object.h" -#include "GAUIData.generated.h" - -/** - * Base class for UI data for effect. - * Do not instance it. Just use CDO, to get data from it. - */ -UCLASS() -class ABILITYFRAMEWORK_API UGAUIData : public UObject -{ - GENERATED_BODY() -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h deleted file mode 100644 index 3b4bce0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/IAbilityFramework.h +++ /dev/null @@ -1,37 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "ModuleManager.h" - - -/** - * The public interface to this module. In most cases, this interface is only public to sibling modules - * within this plugin. - */ -class IAbilityFramework : public IModuleInterface -{ - -public: - /** - * Singleton-like access to this module's interface. This is just for convenience! - * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. - * - * @return Returns singleton instance, loading the module on demand if needed - */ - static inline IAbilityFramework& Get() - { - return FModuleManager::LoadModuleChecked< IAbilityFramework >( "AbilityFramework" ); - } - - /** - * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. - * - * @return True if the module is loaded and ready to use - */ - static inline bool IsAvailable() - { - return FModuleManager::Get().IsModuleLoaded( "AbilityFramework" ); - } -}; - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp deleted file mode 100644 index abdf620..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.cpp +++ /dev/null @@ -1,8 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "AFLatentInterface.h" -UAFLatentInterface::UAFLatentInterface(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h deleted file mode 100644 index 0ce54c8..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFLatentInterface.h +++ /dev/null @@ -1,25 +0,0 @@ -#pragma once -#include "AFLatentInterface.generated.h" - - -struct FAFAttributeBase; -struct FGAEffectHandle; -UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) -class ABILITYFRAMEWORK_API UAFLatentInterface : public UInterface -{ - GENERATED_UINTERFACE_BODY() -}; - -class IAFLatentInterface -{ - GENERATED_IINTERFACE_BODY() -public: - virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) = 0; - virtual void AddReplicatedTask(class UAFTaskBase* TaskIn) = 0; - virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn) = 0; - - virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn) = 0; - virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) = 0; - - virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName) = 0; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp deleted file mode 100644 index 7b0fce9..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.cpp +++ /dev/null @@ -1,100 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "AFLatentInterface.h" - -#include "AFTaskBase.h" - -void FGALatentFunctionTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) -{ - if (Target && !Target->IsPendingKillOrUnreachable()) - { - FScopeCycleCounterUObject ActorScope(Target); - Target->TickTask(DeltaTime, TickType, *this); - } -} - -FString FGALatentFunctionTick::DiagnosticMessage() -{ - return Target->GetFullName() + TEXT("[TickAction]"); -} - -UAFTaskBase::UAFTaskBase(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - TickFunction.TickGroup = TG_PrePhysics; - // Default to no tick function, but if we set 'never ticks' to false (so there is a tick function) it is enabled by default - TickFunction.bCanEverTick = false; - TickFunction.bStartWithTickEnabled = true; - TickFunction.bAllowTickOnDedicatedServer = true; - TickFunction.bRunOnAnyThread = true; - - TickFunction.SetTickFunctionEnable(true); - SetFlags(RF_StrongRefOnFrame); - TaskState = EState::Waiting; -} - -void UAFTaskBase::Initialize() -{ - if (GetWorld()) - { - TickFunction.Target = this; - ULevel* level = GetWorld()->GetCurrentLevel(); - if (level) - { - TickFunction.RegisterTickFunction(level); - } - } -} - -void UAFTaskBase::ReadyForActivation() -{ - if (TaskOwner) - { - if (TaskState != EState::Active) - { - TaskState = EState::Active; - Activate(); - Cast(TaskOwner)->OnLatentTaskActivated(this); - } - - } - else - { - EndTask(); - } -} - -void UAFTaskBase::EndTask() -{ - if (TickFunction.bCanEverTick && TickFunction.IsTickFunctionRegistered()) - { - TickFunction.UnRegisterTickFunction(); - TickFunction.SetTickFunctionEnable(false); - } - OnTaskEnded(); - Cast(TaskOwner)->OnLatentTaskDeactivated(this); - TaskState = EState::Finished; - //MarkPendingKill(); -} -void UAFTaskBase::BeginDestroy() -{ - Super::BeginDestroy(); -} - -bool UAFTaskBase::IsNameStableForNetworking() const -{ - return false; -} -void UAFTaskBase::SetNetAddressable() -{ - -} -UWorld* UAFTaskBase::GetWorld() const -{ - if (TaskOwner) - { - return TaskOwner->GetWorld(); - } - return nullptr; -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h deleted file mode 100644 index 2db8241..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskBase.h +++ /dev/null @@ -1,102 +0,0 @@ -#pragma once -#include "CoreMinimal.h" -#include "Engine/EngineBaseTypes.h" -#include "AFLatentInterface.h" - -#include "AFTaskBase.generated.h" - -struct FGALatentFunctionTick: public FTickFunction -{ - /** AActor that is the target of this tick **/ - class UAFTaskBase* Target; - - /** - * Abstract function actually execute the tick. - * @param DeltaTime - frame time to advance, in seconds - * @param TickType - kind of tick for this frame - * @param CurrentThread - thread we are executing on, useful to pass along as new tasks are created - * @param MyCompletionGraphEvent - completion event for this task. Useful for holding the completetion of this task until certain child tasks are complete. - **/ - virtual void ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) override; - /** Abstract function to describe this tick. Used to print messages about illegal cycles in the dependency graph **/ - virtual FString DiagnosticMessage() override; -}; - -UCLASS(meta = (ExposedAsyncProxy = "true")) -class ABILITYFRAMEWORK_API UAFTaskBase : public UObject -{ - GENERATED_BODY() - //never access internals of these classes directly. Use messages instead. -protected: - enum class EState : uint8 - { - Waiting, - Active, - Finished - }; - - EState TaskState; - bool bReplicated; - - UPROPERTY() - UObject* TaskOwner; - friend struct FGALatentFunctionTick; - FGALatentFunctionTick TickFunction; - - UAFTaskBase(const FObjectInitializer& ObjectInitializer); - virtual UWorld* GetWorld() const override; - - //virtual void Tick(float DeltaSecondsIn); - virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) {}; - virtual void Initialize(); -public: - UFUNCTION(BlueprintCallable, meta = (BlueprintInternalUseOnly = "true"), Category = "Latent Action") - virtual void ReadyForActivation(); -protected: - virtual void Activate() {}; - virtual void EndTask(); - virtual void BeginDestroy() override; - virtual void OnTaskEnded() {}; -public: - /* Replication */ - bool IsNameStableForNetworking() const override; - - bool IsSupportedForNetworking() const override - { - return bReplicated; - } - void SetNetAddressable(); - -protected: - - //use template to avoid using interface - template - static TaskType* NewTask(UObject* WorldContextObject, OwnerType* InTaskOwner, FName InstanceName = FName()) - { - TaskType* MyObj = nullptr; - - if (!InstanceName.IsNone()) - { - MyObj = Cast(InTaskOwner->GetCachedLatentAction(InstanceName)); - if (!MyObj) - { - MyObj = NewObject(WorldContextObject); - - InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); - } - } - else - { - MyObj = NewObject(WorldContextObject); - - InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); - } - if (MyObj->bReplicated) - { - InTaskOwner->AddReplicatedTask(MyObj); - } - MyObj->TaskOwner = InTaskOwner; - - return MyObj; - } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp deleted file mode 100644 index 10382b4..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.cpp +++ /dev/null @@ -1,25 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "AFTaskManager.h" - -UAFTaskManager* UAFTaskManager::Instance = nullptr; - -UAFTaskManager::UAFTaskManager(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ -} - -UAFTaskManager* UAFTaskManager::Get() -{ - if (Instance) - { - return Instance; - } - else - { - Instance = NewObject(); - Instance->AddToRoot(); - return Instance; - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h deleted file mode 100644 index 8a39299..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/AFTaskManager.h +++ /dev/null @@ -1,17 +0,0 @@ -#pragma once -#include "CoreMinimal.h" -#include "Engine/EngineBaseTypes.h" - -#include "AFTaskManager.generated.h" - -UCLASS() -class ABILITYFRAMEWORK_API UAFTaskManager : public UObject -{ - GENERATED_BODY() - - static UAFTaskManager* Instance; - -public: - UAFTaskManager(const FObjectInitializer& ObjectInitializer); - static UAFTaskManager* Get(); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp deleted file mode 100644 index be34c49..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.cpp +++ /dev/null @@ -1,51 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFramework.h" -#include "GAWaitAction.h" - -UGAWaitAction::UGAWaitAction(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - TickFunction.bCanEverTick = true; - TickFunction.bStartWithTickEnabled = true; - TickFunction.bAllowTickOnDedicatedServer = true; - TickFunction.bRunOnAnyThread = true; - SetFlags(RF_StrongRefOnFrame); -} - -UGAWaitAction* UGAWaitAction::NewGAWaitAction(UObject* InTaskOwner, float Time) -{ - UGAWaitAction* MyTask = nullptr;/*NewTask(InTaskOwner, InTaskOwner); - if (MyTask) - { - MyTask->Time = Time; - }*/ - return MyTask; -} - -void UGAWaitAction::Activate() -{ - OnInitialized.Broadcast(); - if (GEngine) - { - GEngine->AddOnScreenDebugMessage(0, 1, FColor::Red, FString("ObjectName: ") + GetName()); - } - if (TaskOwner && TaskOwner->GetWorld()) - { - UWorld* World = TaskOwner->GetWorld(); - TimeStarted = World->GetTimeSeconds(); - - // Use a dummy timer handle as we don't need to store it for later but we don't need to look for something to clear - FTimerHandle TimerHandle; - World->GetTimerManager().SetTimer(TimerHandle, this, &UGAWaitAction::OnTimeFinish, Time, false); - } -} -void UGAWaitAction::TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) -{ - OnTick.Broadcast(); -}; -void UGAWaitAction::OnTimeFinish() -{ - OnFinish.Broadcast(); - EndTask(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h b/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h deleted file mode 100644 index af68fc7..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/LatentActions/GAWaitAction.h +++ /dev/null @@ -1,42 +0,0 @@ -#pragma once -#include "AFTaskBase.h" -#include "GAWaitAction.generated.h" -/* - AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and - the should be activated from ability. - Then can perform tasks, like spawn tagetting helpers (splines, circles), spawn actors, - gather targeting data etc. - - Should they be activated automatically after ability is initialized, (it'e ability enterted in - active state, which means it's ready to be fired and display helpers, but did not yet received input, - or should designer in blueprint decide when to launch actions ?). -*/ -UCLASS(meta = (ExposedAsyncProxy = "true") ) -class ABILITYFRAMEWORK_API UGAWaitAction : public UAFTaskBase -{ - GENERATED_BODY() - -public: - UGAWaitAction(const FObjectInitializer& ObjectInitializer); - float Time; - float TimeStarted; - - DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAWaitActionDelegate); - UPROPERTY(BlueprintAssignable) - FGAWaitActionDelegate OnInitialized; - UPROPERTY(BlueprintAssignable) - FGAWaitActionDelegate OnFinish; - - UPROPERTY(BlueprintAssignable) - FGAWaitActionDelegate OnTick; - - //virtual void Tick(float DeltaSecondsIn); - - virtual void Activate() override; - virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; - UFUNCTION(BlueprintCallable, Category = "Latent Actions", meta = (AdvancedDisplay = "InTaskOwner, Priority", DefaultToSelf = "InTaskOwner", BlueprintInternalUseOnly = "TRUE")) - static UGAWaitAction* NewGAWaitAction(UObject* InTaskOwner, float Time); - - void OnTimeFinish(); - -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp deleted file mode 100644 index 8069c17..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.cpp +++ /dev/null @@ -1,11 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFramework.h" -#include "GAGlobalTypes.h" -#include "GAAttributeMod.h" - -UGAAttributeMod::UGAAttributeMod(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h b/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h deleted file mode 100644 index 1363965..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Mods/GAAttributeMod.h +++ /dev/null @@ -1,32 +0,0 @@ -#pragma once -#include "GAGlobalTypes.h" -#include "GameplayTagContainer.h" -#include "GAAttributeMod.generated.h" -/* - Using this class you can perform actions, when change to attribute is instigated. - Outcoming are modifiers appiled by instigator. - Incoming are modifiers appiled by target. - - Common applications are generic mods like damage reduction by armor or other attribute. - Increasing damage. - - Fireing other actions, when certain critera has been meet. - - This system is actually similiar to Effects from GameEffectSystem module. - - The main difference is that, attribute mods, cannot be appiled by other objects. You can add or remove - them on runtime, by providing set of classes, that can be added to component and the constructed. - - But you can't apply those mods by means like weapons or abilities. - They are always passive (as they are listening for events), they are always infinite - (their duration is for the entire lifetime of pawn/controller/game) - and they can't affect other attribute mods. They can only affect attributes, and trigger actions - based on them. This might include launching effects. - - As per usual using GameplayTags is recommened for defining behaviour. -*/ -UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInlineNew) -class ABILITYFRAMEWORK_API UGAAttributeMod : public UObject -{ - GENERATED_UCLASS_BODY() -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp deleted file mode 100644 index 02f483d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.cpp +++ /dev/null @@ -1,75 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Abilities/AFAbilityActivationSpec.h" -#include "AFAbilityActionSpecDetails.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFEffectCustomizationCommon.h" -TSharedRef FAFAbilityActivationSpecDetails::MakeInstance() -{ - return MakeShareable(new FAFAbilityActivationSpecDetails); -} - -void FAFAbilityActivationSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - MyDetailLayout = &DetailLayout; - - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - - ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); - UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityActivationSpecDetails::OnDurationPolicyChange); - ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - for (TWeakObjectPtr obj : Objects) - { - if (UAFAbilityActivationSpec* Spec = Cast(obj.Get())) - { - bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); - bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); - - DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); - PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(DurationProperty); - DetailLayout.HideProperty(PeriodProperty); - DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); - DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - } - } -} -void FAFAbilityActivationSpecDetails::OnDurationPolicyChange() -{ - MyDetailLayout->ForceRefreshDetails(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h deleted file mode 100644 index 75a6c49..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityActionSpecDetails.h +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FAFAbilityActivationSpecDetails : public IDetailCustomization -{ - -protected: - bool bIsDuration; - bool bIsPeriodic; - TSharedPtr ApplicationTypeHandle; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - -private: - TSharedPtr MyProperty; - TSharedPtr DurationProperty; - TSharedPtr PeriodProperty; - TSharedPtr DurationCalcTypeProp; - IDetailLayoutBuilder* MyDetailLayout; - FSimpleDelegate UpdateEffectTypeyDelegate; - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; - - void OnDurationPolicyChange(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp deleted file mode 100644 index 217ee21..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.cpp +++ /dev/null @@ -1,75 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Abilities/AFAbilityCooldownSpec.h" -#include "AFAbilityCooldownSpecDetails.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFEffectCustomizationCommon.h" -TSharedRef FAFAbilityCooldownSpecDetails::MakeInstance() -{ - return MakeShareable(new FAFAbilityCooldownSpecDetails); -} - -void FAFAbilityCooldownSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - MyDetailLayout = &DetailLayout; - - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - - ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); - FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityCooldownSpecDetails::OnDurationPolicyChange); - ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - for (TWeakObjectPtr obj : Objects) - { - if (UAFAbilityCooldownSpec* Spec = Cast(obj.Get())) - { - bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); - bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); - - DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); - PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(DurationProperty); - DetailLayout.HideProperty(PeriodProperty); - DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); - DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - } - } -} -void FAFAbilityCooldownSpecDetails::OnDurationPolicyChange() -{ - MyDetailLayout->ForceRefreshDetails(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h deleted file mode 100644 index be653a3..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityCooldownSpecDetails.h +++ /dev/null @@ -1,30 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FAFAbilityCooldownSpecDetails : public IDetailCustomization -{ - -protected: - bool bIsDuration; - bool bIsPeriodic; - TSharedPtr ApplicationTypeHandle; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - -private: - TSharedPtr MyProperty; - TSharedPtr DurationProperty; - TSharedPtr PeriodProperty; - TSharedPtr DurationCalcTypeProp; - IDetailLayoutBuilder* MyDetailLayout; - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; - - void OnDurationPolicyChange(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp deleted file mode 100644 index d99ea2b..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.cpp +++ /dev/null @@ -1,83 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Abilities/AFAbilityInfiniteDurationSpec.h" -#include "AFAbilityInfiniteDurationSpecDetails.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFEffectCustomizationCommon.h" -TSharedRef FAFAbilityInfiniteDurationSpecDetails::MakeInstance() -{ - return MakeShareable(new FAFAbilityInfiniteDurationSpecDetails); -} - -void FAFAbilityInfiniteDurationSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - MyDetailLayout = &DetailLayout; - - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - - ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); - FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityInfiniteDurationSpecDetails::OnDurationPolicyChange); - ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - for (TWeakObjectPtr obj : Objects) - { - if (UAFAbilityInfiniteDurationSpec* Spec = Cast(obj.Get())) - { - bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); - bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); - - DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); - PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); - DetailLayout.HideCategory("Duration"); - DetailLayout.HideCategory("Period"); - - DetailLayout.HideProperty(DurationProperty); - DetailLayout.HideProperty(PeriodProperty); - DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); - PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); - - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); - - DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - } - } -} -void FAFAbilityInfiniteDurationSpecDetails::OnDurationPolicyChange() -{ - MyDetailLayout->ForceRefreshDetails(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h deleted file mode 100644 index c1b4218..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfiniteDurationSpecDetails.h +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FAFAbilityInfiniteDurationSpecDetails : public IDetailCustomization -{ - -protected: - bool bIsDuration; - bool bIsPeriodic; - TSharedPtr ApplicationTypeHandle; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - -private: - TSharedPtr MyProperty; - TSharedPtr DurationProperty; - TSharedPtr PeriodProperty; - TSharedPtr DurationCalcTypeProp; - TSharedPtr PeriodCalcTypeProp; - IDetailLayoutBuilder* MyDetailLayout; - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; - - void OnDurationPolicyChange(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp deleted file mode 100644 index 38f91d2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.cpp +++ /dev/null @@ -1,83 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Abilities/AFAbilityPeriodicInfiniteSpec.h" -#include "AFAbilityInfinitePeriodSpecDetails.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFEffectCustomizationCommon.h" -TSharedRef FAFAbilityInfinitePeriodSpecDetails::MakeInstance() -{ - return MakeShareable(new FAFAbilityInfinitePeriodSpecDetails); -} - -void FAFAbilityInfinitePeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - MyDetailLayout = &DetailLayout; - - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - - ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); - FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityInfinitePeriodSpecDetails::OnDurationPolicyChange); - ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - for (TWeakObjectPtr obj : Objects) - { - if (UAFAbilityPeriodicInfiniteSpec* Spec = Cast(obj.Get())) - { - bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); - bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); - - DetailLayout.HideCategory("Duration"); - - DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); - PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(DurationProperty); - DetailLayout.HideProperty(PeriodProperty); - DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); - PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); - - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); - - DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - } - } -} -void FAFAbilityInfinitePeriodSpecDetails::OnDurationPolicyChange() -{ - MyDetailLayout->ForceRefreshDetails(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h deleted file mode 100644 index bdffbdd..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityInfinitePeriodSpecDetails.h +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FAFAbilityInfinitePeriodSpecDetails : public IDetailCustomization -{ - -protected: - bool bIsDuration; - bool bIsPeriodic; - TSharedPtr ApplicationTypeHandle; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - -private: - TSharedPtr MyProperty; - TSharedPtr DurationProperty; - TSharedPtr PeriodProperty; - TSharedPtr DurationCalcTypeProp; - TSharedPtr PeriodCalcTypeProp; - IDetailLayoutBuilder* MyDetailLayout; - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; - - void OnDurationPolicyChange(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp deleted file mode 100644 index 8fe5b22..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.cpp +++ /dev/null @@ -1,81 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Abilities/AFAbilityPeriodSpec.h" -#include "AFAbilityPeriodSpecDetails.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFEffectCustomizationCommon.h" -TSharedRef FAFAbilityPeriodSpecDetails::MakeInstance() -{ - return MakeShareable(new FAFAbilityPeriodSpecDetails); -} - -void FAFAbilityPeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - MyDetailLayout = &DetailLayout; - - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - - ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); - FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityPeriodSpecDetails::OnDurationPolicyChange); - ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - for (TWeakObjectPtr obj : Objects) - { - if (UAFAbilityPeriodSpec* Spec = Cast(obj.Get())) - { - bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); - bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); - - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); - - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); - - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); - //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); - - DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); - PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(DurationProperty); - DetailLayout.HideProperty(PeriodProperty); - DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); - PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); - - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); - - DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - } - } -} -void FAFAbilityPeriodSpecDetails::OnDurationPolicyChange() -{ - MyDetailLayout->ForceRefreshDetails(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h deleted file mode 100644 index b5e4527..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFAbilityPeriodSpecDetails.h +++ /dev/null @@ -1,31 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FAFAbilityPeriodSpecDetails : public IDetailCustomization -{ - -protected: - bool bIsDuration; - bool bIsPeriodic; - TSharedPtr ApplicationTypeHandle; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - -private: - TSharedPtr MyProperty; - TSharedPtr DurationProperty; - TSharedPtr PeriodProperty; - TSharedPtr DurationCalcTypeProp; - TSharedPtr PeriodCalcTypeProp; - IDetailLayoutBuilder* MyDetailLayout; - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; - - void OnDurationPolicyChange(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp deleted file mode 100644 index f0898d5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.cpp +++ /dev/null @@ -1,79 +0,0 @@ - -#include "AbilityFrameworkEditor.h" -#include "Kismet/KismetMathLibrary.h" -#include "Kismet/KismetArrayLibrary.h" -#include "LatentActions/AFTaskBase.h" -#include "Effects/EffectTasks/AFEffectTask.h" -#include "Effects/GAEffectExtension.h" -#include "KismetCompiler.h" -#include "BlueprintEditorUtils.h" -#include "AFEK2Node_AsyncEffectTaskCall.h" -#include "K2Node_EnumLiteral.h" -#include "BlueprintFunctionNodeSpawner.h" -#include "BlueprintActionDatabaseRegistrar.h" - -#define LOCTEXT_NAMESPACE "K2Node" - -UAFEK2Node_AsyncEffectTaskCall::UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); -} - -bool UAFEK2Node_AsyncEffectTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const -{ - bool bIsCompatible = false; - - EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); - bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); - - if (bAllowLatentFuncs) - { - UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); - if (MyBlueprint && MyBlueprint->GeneratedClass) - { - if (MyBlueprint->GeneratedClass->IsChildOf(UGAEffectExtension::StaticClass())) - { - bIsCompatible = true; - } - } - } - return bIsCompatible; -} - - -void UAFEK2Node_AsyncEffectTaskCall::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const -{ - //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); - struct GetMenuActions_Utils - { - static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) - { - UAFEK2Node_AsyncEffectTaskCall* AsyncTaskNode = CastChecked(NewNode); - if (FunctionPtr.IsValid()) - { - UFunction* Func = FunctionPtr.Get(); - UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); - - AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); - AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); - AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; - } - } - }; - - UClass* NodeClass = GetClass(); - //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); - ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* - { - UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); - check(NodeSpawner != nullptr); - NodeSpawner->NodeClass = NodeClass; - - TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); - NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); - return NodeSpawner; - })); -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h deleted file mode 100644 index d9c7d0f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEK2Node_AsyncEffectTaskCall.h +++ /dev/null @@ -1,20 +0,0 @@ - -#pragma once -#include "EdGraph/EdGraphPin.h" -#include "EdGraphSchema_K2.h" -#include "K2Node_BaseAsyncTask.h" -#include "AFEK2Node_AsyncEffectTaskCall.generated.h" - -UCLASS() -class UAFEK2Node_AsyncEffectTaskCall : public UK2Node_BaseAsyncTask -{ - GENERATED_BODY() - -public: - UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer); - - // UEdGraphNode interface - virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; - virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; - // End of UEdGraphNode interface -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp deleted file mode 100644 index ea1ff60..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.cpp +++ /dev/null @@ -1,111 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AbilityFrameworkEditor.h" -#include "Effects/GAGameEffect.h" -#include "DetailLayoutBuilder.h" -#include "DetailCategoryBuilder.h" -#include "IDetailGroup.h" -#include "AFEffectCustomizationCommon.h" - -FAFEffectCustomizationCommon::FAFEffectCustomizationCommon() -{ -} - -FAFEffectCustomizationCommon::~FAFEffectCustomizationCommon() -{ -} -void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, - TSharedPtr& InProperty, FName InCategory) -{ - IDetailCategoryBuilder& DurationCategory = DetailLayout.EditCategory(InCategory); - - TSharedPtr DurationCalcTypeProp = InProperty->GetChildHandle("CalculationType"); - - uint8 CalcType = 0; - DurationCalcTypeProp->GetValue(CalcType); - - TSharedPtr DirectModifier = InProperty->GetChildHandle("DirectModifier"); - TSharedPtr AttributeBased = InProperty->GetChildHandle("AttributeBased"); - TSharedPtr CurveBased = InProperty->GetChildHandle("CurveBased"); - TSharedPtr Custom = InProperty->GetChildHandle("Custom"); - - DurationCategory.AddProperty(DurationCalcTypeProp.ToSharedRef()); - switch (CalcType) - { - case 0: //Direct - { - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(Custom); - - TSharedPtr Value = DirectModifier->GetChildHandle("Value"); - DurationCategory.AddProperty(Value.ToSharedRef()); - //DetailGroup. - break; - } - case 1: //AttributeBased - { - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(Custom); - - TSharedPtr Source = AttributeBased->GetChildHandle("Source"); - TSharedPtr Attribute = AttributeBased->GetChildHandle("Attribute"); - TSharedPtr Coefficient = AttributeBased->GetChildHandle("Coefficient"); - TSharedPtr PreMultiply = AttributeBased->GetChildHandle("PreMultiply"); - TSharedPtr PostMultiply = AttributeBased->GetChildHandle("PostMultiply"); - TSharedPtr PostCoefficient = AttributeBased->GetChildHandle("PostCoefficient"); - TSharedPtr bUseSecondaryAttribute = AttributeBased->GetChildHandle("bUseSecondaryAttribute"); - TSharedPtr SecondarySource = AttributeBased->GetChildHandle("SecondarySource"); - TSharedPtr SecondaryAttribute = AttributeBased->GetChildHandle("SecondaryAttribute"); - - DurationCategory.AddProperty(Source.ToSharedRef()); - DurationCategory.AddProperty(Attribute.ToSharedRef()); - DurationCategory.AddProperty(Coefficient.ToSharedRef()); - DurationCategory.AddProperty(PreMultiply.ToSharedRef()); - DurationCategory.AddProperty(PostMultiply.ToSharedRef()); - DurationCategory.AddProperty(PostCoefficient.ToSharedRef()); - DurationCategory.AddProperty(bUseSecondaryAttribute.ToSharedRef()); - DurationCategory.AddProperty(SecondarySource.ToSharedRef()); - DurationCategory.AddProperty(SecondaryAttribute.ToSharedRef()); - - break; - } - case 2: //CurveBased - { - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(Custom); - - TSharedPtr Source = CurveBased->GetChildHandle("Source"); - TSharedPtr Attribute = CurveBased->GetChildHandle("Attribute"); - TSharedPtr CurveTable = CurveBased->GetChildHandle("CurveTable"); - - DurationCategory.AddProperty(Source.ToSharedRef()); - DurationCategory.AddProperty(Attribute.ToSharedRef()); - DurationCategory.AddProperty(CurveTable.ToSharedRef()); - break; - } - case 3: //CustomCalculation - { - DetailLayout.HideProperty(AttributeBased); - DetailLayout.HideProperty(CurveBased); - DetailLayout.HideProperty(DirectModifier); - DetailLayout.HideProperty(Custom); - - TSharedPtr CustomCalculation = Custom->GetChildHandle("CustomCalculation"); - DurationCategory.AddProperty(CustomCalculation.ToSharedRef()); - break; - } - } -} -void FAFEffectCustomizationCommon::HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName) -{ - UProperty* prop = UGAGameEffectSpec::StaticClass()->FindPropertyByName(InName); - - TSharedPtr Property = DetailLayout.GetProperty(InName, UGAGameEffectSpec::StaticClass()); - DetailLayout.HideProperty(Property); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h deleted file mode 100644 index 2c495a7..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AFEffectCustomizationCommon.h +++ /dev/null @@ -1,19 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "IDetailCustomization.h" -#include "PropertyHandle.h" -/** - * - */ -class ABILITYFRAMEWORKEDITOR_API FAFEffectCustomizationCommon -{ -public: - FAFEffectCustomizationCommon(); - ~FAFEffectCustomizationCommon(); - static void CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, - TSharedPtr& InProperty, FName InCategory); - static void HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName); -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp deleted file mode 100644 index 0e2b42a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp +++ /dev/null @@ -1,57 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "AssetTypeActions_GAAbilityBlueprint.h" -#include "Misc/MessageDialog.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "GAAbilityEditor.h" -#include "Abilities/GAAbilityBlueprint.h" -#include "Abilities/GAAbilityBase.h" -#include "GAAbilityBlueprintFactory.h" - -#define LOCTEXT_NAMESPACE "AssetTypeActions" - -FText FAssetTypeActions_GAAbilityBlueprint::GetName() const -{ - return FText::FromString("Ability"); -} -UClass* FAssetTypeActions_GAAbilityBlueprint::GetSupportedClass() const -{ - return UGAAbilityBlueprint::StaticClass(); -} - -void FAssetTypeActions_GAAbilityBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) -{ - EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; - - for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) - { - auto Blueprint = Cast(*ObjIt); - if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) - { - TSharedRef< FGAAbilityEditor > NewEditor(new FGAAbilityEditor()); - - TArray Blueprints; - Blueprints.Add(Blueprint); - - NewEditor->InitAbilitiesEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); - } - else - { - FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); - } - } -} - -bool FAssetTypeActions_GAAbilityBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const -{ - return false; -} - -UFactory* FAssetTypeActions_GAAbilityBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const -{ - UGAAbilityBlueprintFactory* AbilityBlueprintFactory = NewObject(); - AbilityBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); - return AbilityBlueprintFactory; -} - -#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h deleted file mode 100644 index 78b71c1..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once -#include "CoreMinimal.h" -#include "Toolkits/IToolkitHost.h" -#include "AssetTypeCategories.h" -//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" -#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" - -class UFactory; - -class FAssetTypeActions_GAAbilityBlueprint : public FAssetTypeActions_Blueprint -{ -public: - // IAssetTypeActions Implementation - virtual FText GetName() const override; - virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } - virtual UClass* GetSupportedClass() const override; - virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; - virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } - // End IAssetTypeActions Implementation - - // FAssetTypeActions_Blueprint interface - virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; - -private: - /** Returns true if the blueprint is data only */ - bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp deleted file mode 100644 index 3493cac..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.cpp +++ /dev/null @@ -1,334 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "GAAbilityBlueprintFactory.h" -#include "InputCoreTypes.h" -#include "UObject/Interface.h" -#include "Layout/Visibility.h" -#include "Input/Reply.h" -#include "Widgets/SWidget.h" -#include "Widgets/DeclarativeSyntaxSupport.h" -#include "Misc/MessageDialog.h" -#include "Modules/ModuleManager.h" -#include "Effects/GAGameEffect.h" -#include "Widgets/SCompoundWidget.h" -#include "Widgets/SBoxPanel.h" -#include "Widgets/SWindow.h" -#include "Widgets/Layout/SBorder.h" -#include "Widgets/Text/STextBlock.h" -#include "Widgets/Layout/SBox.h" -#include "Widgets/Layout/SUniformGridPanel.h" -#include "Widgets/Input/SButton.h" -#include "EditorStyleSet.h" -#include "Editor.h" -#include "EdGraphSchema_K2.h" - -#include "ClassViewerModule.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "Engine/BlueprintGeneratedClass.h" -#include "Kismet2/KismetEditorUtilities.h" -#include "BlueprintEditorSettings.h" - -#include "Abilities/GAAbilityBlueprint.h" -#include "Abilities/GAAbilityBase.h" -#include "GAAbilityGraph.h" -#include "GAAbilityGraphSchema.h" - -#include "ClassViewerFilter.h" - -#include "SlateOptMacros.h" - -// ------------------------------------------------------------------------------ -// Dialog to configure creation properties -// ------------------------------------------------------------------------------ -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION - -class SAbilityBlueprintCreateDialog : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAbilityBlueprintCreateDialog){} - - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs) - { - bOkClicked = false; - ParentClass = UGAAbilityBase::StaticClass(); - - ChildSlot - [ - SNew(SBorder) - .Visibility(EVisibility::Visible) - .BorderImage(FEditorStyle::GetBrush("Menu.Background")) - [ - SNew(SBox) - .Visibility(EVisibility::Visible) - .WidthOverride(500.0f) - [ - SNew(SVerticalBox) - + SVerticalBox::Slot() - .FillHeight(1) - [ - SNew(SBorder) - .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) - .Content() - [ - SAssignNew(ParentClassContainer, SVerticalBox) - ] - ] - - // Ok/Cancel buttons - + SVerticalBox::Slot() - .AutoHeight() - .HAlign(HAlign_Right) - .VAlign(VAlign_Bottom) - .Padding(8) - [ - SNew(SUniformGridPanel) - .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) - .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) - .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) - + SUniformGridPanel::Slot(0, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SAbilityBlueprintCreateDialog::OkClicked) - .Text(FText::FromString("OK")) - ] - + SUniformGridPanel::Slot(1, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SAbilityBlueprintCreateDialog::CancelClicked) - .Text(FText::FromString("Cancel")) - ] - ] - ] - ] - ]; - - MakeParentClassPicker(); - } - - /** Sets properties for the supplied AbilitiesBlueprintFactory */ - bool ConfigureProperties(TWeakObjectPtr InAbilitiesBlueprintFactory) - { - AbilitiesBlueprintFactory = InAbilitiesBlueprintFactory; - - TSharedRef Window = SNew(SWindow) - .Title(FText::FromString("Create Ability Blueprint")) - .ClientSize(FVector2D(400, 700)) - .SupportsMinimize(false).SupportsMaximize(false) - [ - AsShared() - ]; - - PickerWindow = Window; - - GEditor->EditorAddModalWindow(Window); - AbilitiesBlueprintFactory.Reset(); - - return bOkClicked; - } - -private: - class FAbilityBlueprintParentFilter : public IClassViewerFilter - { - public: - /** All children of these classes will be included unless filtered out by another setting. */ - TSet< const UClass* > AllowedChildrenOfClasses; - - FAbilityBlueprintParentFilter() {} - - virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; - } - - virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; - } - }; - - /** Creates the combo menu for the parent class */ - void MakeParentClassPicker() - { - // Load the classviewer module to display a class picker - FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); - - // Fill in options - FClassViewerInitializationOptions Options; - Options.Mode = EClassViewerMode::ClassPicker; - - // Only allow parenting to base blueprints. - Options.bIsBlueprintBaseOnly = true; - - TSharedPtr Filter = MakeShareable(new FAbilityBlueprintParentFilter); - - // All child child classes of UGameplayAbility are valid. - Filter->AllowedChildrenOfClasses.Add(UGAAbilityBase::StaticClass()); - Options.ClassFilter = Filter; - - ParentClassContainer->ClearChildren(); - ParentClassContainer->AddSlot() - .AutoHeight() - [ - SNew(STextBlock) - .Text(FText::FromString("Parent Class:")) - .ShadowOffset(FVector2D(1.0f, 1.0f)) - ]; - - ParentClassContainer->AddSlot() - [ - ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SAbilityBlueprintCreateDialog::OnClassPicked)) - ]; - } - - /** Handler for when a parent class is selected */ - void OnClassPicked(UClass* ChosenClass) - { - ParentClass = ChosenClass; - } - - /** Handler for when ok is clicked */ - FReply OkClicked() - { - if (AbilitiesBlueprintFactory.IsValid()) - { - AbilitiesBlueprintFactory->BlueprintType = BPTYPE_Normal; - AbilitiesBlueprintFactory->ParentClass = ParentClass.Get(); - } - - CloseDialog(true); - - return FReply::Handled(); - } - - void CloseDialog(bool bWasPicked = false) - { - bOkClicked = bWasPicked; - if (PickerWindow.IsValid()) - { - PickerWindow.Pin()->RequestDestroyWindow(); - } - } - - /** Handler for when cancel is clicked */ - FReply CancelClicked() - { - CloseDialog(); - return FReply::Handled(); - } - - FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) - { - if (InKeyEvent.GetKey() == EKeys::Escape) - { - CloseDialog(); - return FReply::Handled(); - } - return SWidget::OnKeyDown(MyGeometry, InKeyEvent); - } - -private: - /** The factory for which we are setting up properties */ - TWeakObjectPtr AbilitiesBlueprintFactory; - - /** A pointer to the window that is asking the user to select a parent class */ - TWeakPtr PickerWindow; - - /** The container for the Parent Class picker */ - TSharedPtr ParentClassContainer; - - /** The selected class */ - TWeakObjectPtr ParentClass; - - /** True if Ok was clicked */ - bool bOkClicked; -}; - -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -/*------------------------------------------------------------------------------ - UAbilitiesBlueprintFactory implementation. -------------------------------------------------------------------------------*/ - -UGAAbilityBlueprintFactory::UGAAbilityBlueprintFactory(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bCreateNew = true; - bEditAfterNew = true; - SupportedClass = UGAAbilityBlueprint::StaticClass(); - ParentClass = UGAAbilityBase::StaticClass(); -} - -bool UGAAbilityBlueprintFactory::ConfigureProperties() -{ - TSharedRef Dialog = SNew(SAbilityBlueprintCreateDialog); - return Dialog->ConfigureProperties(this); -}; - -UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) -{ - // Make sure we are trying to factory a gameplay ability blueprint, then create and init one - check(Class->IsChildOf(UGAAbilityBlueprint::StaticClass())); - - // If they selected an interface, force the parent class to be UInterface - if (BlueprintType == BPTYPE_Interface) - { - ParentClass = UInterface::StaticClass(); - } - - if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(UGAAbilityBase::StaticClass()) ) - { - FFormatNamedArguments Args; - Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); - FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); - return NULL; - } - else - { - UGAAbilityBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAAbilityBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); - - if (NewBP) - { - UGAAbilityBlueprint* AbilityBP = UGAAbilityBlueprint::FindRootGameplayAbilityBlueprint(NewBP); - if (AbilityBP == NULL) - { - const UEdGraphSchema_K2* K2Schema = GetDefault(); -#if WITH_EDITORONLY_DATA - // Only allow a gameplay ability graph if there isn't one in a parent blueprint - UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAAbilityGraph::StaticClass(), UGAAbilityGraphSchema::StaticClass()); - - if (NewBP->UbergraphPages.Num()) - { - FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); - } - - FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); - NewBP->LastEditedDocuments.Add(NewGraph); - NewGraph->bAllowDeletion = false; -#endif - UBlueprintEditorSettings* Settings = GetMutableDefault(); - if(Settings && Settings->bSpawnDefaultBlueprintNodes) - { - int32 NodePositionY = 0; - //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); - //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); - } - } - } - - return NewBP; - } -} - -UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) -{ - return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h deleted file mode 100644 index ec61b23..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityBlueprintFactory.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Templates/SubclassOf.h" -#include "Engine/Blueprint.h" -#include "Factories/Factory.h" -#include "AssetTypeCategories.h" -#include "GAAbilityBlueprintFactory.generated.h" - -UCLASS(HideCategories=Object, MinimalAPI) -class UGAAbilityBlueprintFactory : public UFactory -{ - GENERATED_UCLASS_BODY() - - // The type of blueprint that will be created - UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TEnumAsByte BlueprintType; - - // The parent class of the created blueprint - UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TSubclassOf ParentClass; - - //~ Begin UFactory Interface - virtual bool ConfigureProperties() override; - virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; - virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; - - //~ Begin UFactory Interface -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp deleted file mode 100644 index ef34e13..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.cpp +++ /dev/null @@ -1,142 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "GAAbilityEditor.h" -#include "EditorReimportHandler.h" - -#if WITH_EDITOR -#include "Editor.h" -#endif -#include "ISequencerModule.h" -#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" -#include "Toolkits/ToolkitManager.h" -#include "Toolkits/GlobalEditorCommonCommands.h" - -#include "Abilities/GAAbilityBlueprint.h" -#include "GAAbilityBlueprintFactory.h" -#include "GAAbilityGraphSchema.h" -#include "Kismet2/BlueprintEditorUtils.h" - -#define LOCTEXT_NAMESPACE "FGAAbilityEditor" - - -///////////////////////////////////////////////////// -// FGameplayAbilitiesEditor - -FGAAbilityEditor::FGAAbilityEditor() -{ - -} - -FGAAbilityEditor::~FGAAbilityEditor() -{ - FEditorDelegates::OnAssetPostImport.RemoveAll(this); - FReimportManager::Instance()->OnPostReimport().RemoveAll(this); - - // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor -} -void FGAAbilityEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) -{ - FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, ObjectsToEdit, bInIsToolbarFocusable); -} -void FGAAbilityEditor::InitAbilitiesEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) -{ - InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); - - for (auto Blueprint : InBlueprints) - { - EnsureAbilityBlueprintIsUpToDate(Blueprint); - } -} - -void FGAAbilityEditor::EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint) -{ -#if WITH_EDITORONLY_DATA - int32 Count = Blueprint->UbergraphPages.Num(); - for (auto Graph : Blueprint->UbergraphPages) - { - // remove the default event graph, if it exists, from existing Gameplay Ability Blueprints - if (Graph->GetName() == "EventGraph" && Graph->Nodes.Num() == 0) - { - check(!Graph->Schema->GetClass()->IsChildOf(UGAAbilityGraphSchema::StaticClass())); - FBlueprintEditorUtils::RemoveGraph(Blueprint, Graph); - break; - } - } -#endif -} -bool FGAAbilityEditor::IsBlueprintEditor() const -{ - return true; -} -// FRED_TODO: don't merge this back -// FName FGameplayAbilitiesEditor::GetToolkitContextFName() const -// { -// return GetToolkitFName(); -// } - -FName FGAAbilityEditor::GetToolkitFName() const -{ - return FName("GameAbilityEditor"); -} - -FText FGAAbilityEditor::GetBaseToolkitName() const -{ - return FText::FromString("Game Ability Editor"); -} - -FText FGAAbilityEditor::GetToolkitName() const -{ - const TArray& EditingObjs = GetEditingObjects(); - - check(EditingObjs.Num() > 0); - - FFormatNamedArguments Args; - - const UObject* EditingObject = EditingObjs[0]; - - const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); - - Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); - Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); - return FText::Format(FText::FromString("{ObjectName}{DirtyState}"), Args); -} - -FText FGAAbilityEditor::GetToolkitToolTipText() const -{ - const UObject* EditingObject = GetEditingObject(); - - check (EditingObject != NULL); - - return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); -} - -FString FGAAbilityEditor::GetWorldCentricTabPrefix() const -{ - return TEXT("AbilityEditor"); -} - -FLinearColor FGAAbilityEditor::GetWorldCentricTabColorScale() const -{ - return FLinearColor::White; -} - -UBlueprint* FGAAbilityEditor::GetBlueprintObj() const -{ - const TArray& EditingObjs = GetEditingObjects(); - for (int32 i = 0; i < EditingObjs.Num(); ++i) - { - if (EditingObjs[i]->IsA()) - { - return (UBlueprint*)EditingObjs[i]; - } - } - return nullptr; -} - -FString FGAAbilityEditor::GetDocumentationLink() const -{ - return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation -} - -#undef LOCTEXT_NAMESPACE - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h deleted file mode 100644 index cfd9ffa..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityEditor.h +++ /dev/null @@ -1,64 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "Framework/Commands/UICommandList.h" -#include "Framework/MultiBox/MultiBoxExtender.h" -#include "GraphEditor.h" -#include "ISequencer.h" -#include "Editor/Kismet/Public/BlueprintEditor.h" - -////////////////////////////////////////////////////////////////////////// -// FGameplayAbilitiesEditor - -/** - * Gameplay abilities asset editor (extends Blueprint editor) - */ -class FGAAbilityEditor : public FBlueprintEditor -{ -public: - virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; - /** - * Edits the specified gameplay ability asset(s) - * - * @param Mode Asset editing mode for this editor (standalone or world-centric) - * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within - * @param InBlueprints The blueprints to edit - * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode - */ - - void InitAbilitiesEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); - -private: - /** - * Updates existing gameplay ability blueprints to make sure that they are up to date - * - * @param Blueprint The blueprint to be updated - */ - void EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint); - -public: - FGAAbilityEditor(); - - virtual ~FGAAbilityEditor(); - -public: - // IToolkit interface - // FRED_TODO: don't merge this back -// virtual FName GetToolkitContextFName() const override; - virtual FName GetToolkitFName() const override; - virtual FText GetBaseToolkitName() const override; - virtual FText GetToolkitName() const override; - virtual FText GetToolkitToolTipText() const override; - virtual FString GetWorldCentricTabPrefix() const override; - virtual FLinearColor GetWorldCentricTabColorScale() const override; - virtual bool IsBlueprintEditor() const override; - // End of IToolkit interface - - /** @return the documentation location for this editor */ - virtual FString GetDocumentationLink() const override; - - /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ - virtual UBlueprint* GetBlueprintObj() const override; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp deleted file mode 100644 index da482a3..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAAbilityGraph.h" - -#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" - -///////////////////////////////////////////////////// -// UGameplayAbilityGraph - -UGAAbilityGraph::UGAAbilityGraph(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h deleted file mode 100644 index dcc6890..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraph.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "EdGraph/EdGraph.h" -#include "GAAbilityGraph.generated.h" - -UCLASS(MinimalAPI) -class UGAAbilityGraph : public UEdGraph -{ - GENERATED_UCLASS_BODY() -}; - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp deleted file mode 100644 index f51d3ff..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAAbilityGraphSchema.h" -#include "EdGraphSchema_K2_Actions.h" -#include "Effects/GAGameEffect.h" -#include "Kismet2/BlueprintEditorUtils.h" - -UGAAbilityGraphSchema::UGAAbilityGraphSchema(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ -} - -UK2Node_VariableGet* UGAAbilityGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const -{ - return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); -} - -UK2Node_VariableSet* UGAAbilityGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const -{ - return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h deleted file mode 100644 index 1c099f8..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityEditor/GAAbilityGraphSchema.h +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "EdGraphSchema_K2.h" -#include "GAAbilityGraphSchema.generated.h" - -UCLASS(MinimalAPI) -class UGAAbilityGraphSchema : public UEdGraphSchema_K2 -{ - GENERATED_UCLASS_BODY() - - /** - * Creates a new variable getter node and adds it to ParentGraph - * - * @param GraphPosition The location of the new node inside the graph - * @param ParentGraph The graph to spawn the new node in - * @param VariableName The name of the variable - * @param Source The source of the variable - * @return A pointer to the newly spawned node - */ - virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; - - /** - * Creates a new variable setter node and adds it to ParentGraph - * - * @param GraphPosition The location of the new node inside the graph - * @param ParentGraph The graph to spawn the new node in - * @param VariableName The name of the variable - * @param Source The source of the variable - * @return A pointer to the newly spawned node - */ - virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; - - virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs index 5df26d0..341096a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.Build.cs @@ -8,16 +8,6 @@ public class AbilityFrameworkEditor : ModuleRules public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) { var EngineDir = Path.GetFullPath(Target.RelativeEnginePath); - PublicIncludePaths.AddRange( - new string[] { - "AbilityFramework", - "AbilityFramework/Abilities", - "AbilityFramework/Attributes", - "AbilityFramework/Effects", - "AbilityFramework/Public" - // ... add public include paths required here ... - } - ); PrivateIncludePaths.AddRange( new string[] { @@ -26,11 +16,6 @@ public AbilityFrameworkEditor(ReadOnlyTargetRules Target) : base(Target) Path.Combine(EngineDir, @"Source/Editor/Kismet/Private"), Path.Combine(EngineDir, @"Source/Editor/PropertyEditor/Private"), Path.Combine(EngineDir, @"Source/Developer/AssetTools/Private"), - "AbilityFramework", - "AbilityFramework/Abilities", - "AbilityFramework/Attributes", - "AbilityFramework/Effects", - "AbilityFramework/Public" // ... add other private include paths required here ... } ); diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp deleted file mode 100644 index 342153e..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.cpp +++ /dev/null @@ -1,161 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "AbilityFrameworkEditor.h" -#include "GAAttributePin.h" -#include "Attributes/GAAttributeGlobals.h" -#include "Effects/GAEffectCue.h" -#include "GAAttributePanelGraphPinFactory.h" -#include "GAAttributeDetailCustomization.h" - -#include "GAEffectDetails.h" -//#include "GAEffectSpecStructCustomization.h" -#include "GAEffectPropertyStructCustomization.h" -#include "AFAbilityActionSpecDetails.h" -#include "AFAbilityPeriodSpecDetails.h" -#include "AFAbilityCooldownSpecDetails.h" -#include "AFAbilityInfiniteDurationSpecDetails.h" -#include "AFAbilityInfinitePeriodSpecDetails.h" - -#include "EffectEditor/AssetTypeActions_GAEffectBlueprint.h" -#include "AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h" -#include "EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h" -#include "EffectCueEditor/AFEffectCueDetails.h" - - - -#include "AFCueManager.h" - -TSet FAbilityFrameworkEditor::EffectClasses = TSet(); -/** Shared class type that ensures safe binding to RegisterBlueprintEditorTab through an SP binding without interfering with module ownership semantics */ -FEffectCueequenceEditorTabBinding::FEffectCueequenceEditorTabBinding() -{ - FBlueprintEditorModule& BlueprintEditorModule = FModuleManager::LoadModuleChecked("Kismet"); - BlueprintEditorTabSpawnerHandle = BlueprintEditorModule.OnRegisterTabsForEditor().AddRaw(this, &FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorTab); - BlueprintEditorLayoutExtensionHandle = BlueprintEditorModule.OnRegisterLayoutExtensions().AddRaw(this, &FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorLayout); -} - -void FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) -{ - Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); -} - -void FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) -{ - TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); -} - -FEffectCueequenceEditorTabBinding::~FEffectCueequenceEditorTabBinding() -{ - FBlueprintEditorModule* BlueprintEditorModule = FModuleManager::GetModulePtr("Kismet"); - if (BlueprintEditorModule) - { - BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); - BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); - } -} - - -void FAbilityFrameworkEditor::RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action) -{ - AssetTools.RegisterAssetTypeActions(Action); - CreatedAssetTypeActions.Add(Action); -} -void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequence) -{ - auto* ProjectSettings = GetDefault(); - AGAEffectCue* Cue = Cast(Sequence->GetOuter()); - - - if (Cue) - { - TRange Frames(static_cast(Cue->StartTime), static_cast(Cue->EndTime)); - Sequence->GetMovieScene()->SetPlaybackRange(Frames, true); - } - else - { - TRange Frames; - Sequence->GetMovieScene()->SetPlaybackRange(Frames, true); - } -} - /** IModuleInterface implementation */ -void FAbilityFrameworkEditor::StartupModule() -{ - if(GEditor) - BlueprintEditorTabBinding = MakeShared(); - - - - FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); - PropertyModule.RegisterCustomPropertyTypeLayout("GAAttribute", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAAttributeDetailCustomization::MakeInstance)); - //PropertyModule.RegisterCustomPropertyTypeLayout("GAEffectProperty", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); - PropertyModule.RegisterCustomPropertyTypeLayout("AFPropertytHandle", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); - - TSharedPtr GAAttributePanelGraphPinFactory = MakeShareable(new FGAAttributePanelGraphPinFactory()); - FEdGraphUtilities::RegisterVisualPinFactory(GAAttributePanelGraphPinFactory); - - PropertyModule.RegisterCustomClassLayout("AFEffectSpecBase", FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); - PropertyModule.RegisterCustomClassLayout("AFAbilityActivationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); - PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); - PropertyModule.RegisterCustomClassLayout("AFAbilityCooldownSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); - PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodicInfiniteSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityInfinitePeriodSpecDetails::MakeInstance)); - PropertyModule.RegisterCustomClassLayout("AFAbilityInfiniteDurationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityInfiniteDurationSpecDetails::MakeInstance)); - - PropertyModule.RegisterCustomClassLayout("GAEffectCue", FOnGetDetailCustomizationInstance::CreateStatic(&FAFEffectCueDetails::MakeInstance)); - - IAssetTools& AssetTools = FModuleManager::LoadModuleChecked("AssetTools").Get(); - TSharedRef GABAction = MakeShareable(new FAssetTypeActions_GAEffectBlueprint()); - RegisterAssetTypeAction(AssetTools, GABAction); - TSharedRef GAAbilityAction = MakeShareable(new FAssetTypeActions_GAAbilityBlueprint()); - RegisterAssetTypeAction(AssetTools, GAAbilityAction); - TSharedRef GAEffectCueAction = MakeShareable(new FAssetTypeActions_GAEffectCueBlueprint()); - RegisterAssetTypeAction(AssetTools, GAEffectCueAction); - - //BlueprintEditorTabBinding = MakeShared(); - OnInitializeSequenceHandle = UGAEffectCueSequence::OnInitializeSequence().AddStatic(FAbilityFrameworkEditor::OnInitializeSequence); -} -void FAbilityFrameworkEditor::ShutdownModule() -{ - BlueprintEditorTabBinding = nullptr; - FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); - PropertyModule.UnregisterCustomClassLayout("AFEffectSpecBase"); - PropertyModule.UnregisterCustomClassLayout("AFAbilityActivationSpec"); - PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodSpec"); - PropertyModule.UnregisterCustomClassLayout("AFAbilityCooldownSpec"); - PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodicInfiniteSpec"); - PropertyModule.UnregisterCustomClassLayout("AFAbilityInfiniteDurationSpec"); - - PropertyModule.UnregisterCustomPropertyTypeLayout("GAAttribute"); - //PropertyModule.UnregisterCustomPropertyTypeLayout("GAEffectProperty"); - PropertyModule.UnregisterCustomPropertyTypeLayout("AFPropertytHandle"); - - UGAEffectCueSequence::OnInitializeSequence().Remove(OnInitializeSequenceHandle); - BlueprintEditorTabBinding = nullptr; - if (FModuleManager::Get().IsModuleLoaded("AssetTools")) - { - IAssetTools& AssetToolsModule = FModuleManager::GetModuleChecked("AssetTools").Get(); - for (auto& AssetTypeAction : CreatedAssetTypeActions) - { - if (AssetTypeAction.IsValid()) - { - AssetToolsModule.UnregisterAssetTypeActions(AssetTypeAction.ToSharedRef()); - } - } - } -} - -IMPLEMENT_GAME_MODULE(FAbilityFrameworkEditor, AbilityFrameworkEditor); - - -//void FGameAttributesEditor::StartupModule() -//{ -// -//} -// -// -//void FGameAttributesEditor::ShutdownModule() -//{ -// -//} - - - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h deleted file mode 100644 index 5a235e7..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/AbilityFrameworkEditor.h +++ /dev/null @@ -1,60 +0,0 @@ -#pragma once -#include "Engine.h" -#include "AbilityFramework.h" -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "EditorStyle.h" -#include "Effects/GAEffectCueSequence.h" -#include "EffectCueEditor/GAEffectCueEditor.h" - -#include "UnrealEd.h" -#include "AssetToolsModule.h" -#include "IAssetTypeActions.h" - -#include "BlueprintEditorModule.h" -#include "BlueprintEditorTabs.h" -#include "LayoutExtender.h" -#include "LevelEditor.h" -#include "MovieSceneToolsProjectSettings.h" -#include "PropertyEditorModule.h" -#include "Styling/SlateStyle.h" -#include "WorkflowTabManager.h" -#include "Modules/ModuleManager.h" -#include "Widgets/Docking/SDockTab.h" - -#include "ISettingsModule.h" - -#include "IAbilityFrameworkEditor.h" -class FEffectCueequenceEditorTabBinding - : public TSharedFromThis -{ -public: - - FEffectCueequenceEditorTabBinding(); - - void RegisterBlueprintEditorLayout(FLayoutExtender& Extender); - - void RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor); - ~FEffectCueequenceEditorTabBinding(); - -private: - - /** Delegate binding handle for FBlueprintEditorModule::OnRegisterTabsForEditor */ - FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; -}; -//add static list of registered custom derived effcts. Will be used to specify, from which classes -//new effect blueprints can be created, and which classes are allowed to pick (if not specified -//in metaData. -class FAbilityFrameworkEditor : public IAbilityFrameworkEditor -{ - TArray< TSharedPtr > CreatedAssetTypeActions; - TSharedPtr BlueprintEditorTabBinding; - FDelegateHandle OnInitializeSequenceHandle; - static TSet EffectClasses; - - void RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action); - static void OnInitializeSequence(UGAEffectCueSequence* Sequence); - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp deleted file mode 100644 index 5840655..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.cpp +++ /dev/null @@ -1,28 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "GACurveTableDetailCustomization.h" - -TSharedRef FGACurveTableDetailCustomization::MakeInstance() -{ - return MakeShareable(new FGACurveTableDetailCustomization); -} - -FGACurveTableDetailCustomization::~FGACurveTableDetailCustomization() -{ - -} - -void FGACurveTableDetailCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} -void FGACurveTableDetailCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h deleted file mode 100644 index 2b09d86..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/CurveTable/GACurveTableDetailCustomization.h +++ /dev/null @@ -1,23 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "../GAGlobalTypesEditor.h" - -#include "IPropertyTypeCustomization.h" -#include "PropertyHandle.h" - -class FGACurveTableDetailCustomization : public IPropertyTypeCustomization -{ -public: - static TSharedRef MakeInstance(); - /** - * Destructor - */ - virtual ~FGACurveTableDetailCustomization(); - - /** IPropertyTypeCustomization interface */ - virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - - - -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp deleted file mode 100644 index f301611..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.cpp +++ /dev/null @@ -1,353 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Effects/GAEffectCue.h" -#include "Effects/GAEffectCueSequence.h" -#include "EditorReimportHandler.h" -#include "MovieScene.h" -#include "Tracks/MovieScenePropertyTrack.h" -#if WITH_EDITOR -#include "Editor.h" -#endif -#include "ISequencerModule.h" -#include "LevelEditorSequencerIntegration.h" -#include "SSCSEditor.h" -#include "SlateIconFinder.h" -#include "BlueprintEditorUtils.h" -#include "Framework/MultiBox/MultiBoxBuilder.h" -#include "Framework/Application/SlateApplication.h" - -#include "AFEffectCueDetails.h" - -class SEffectCueSequenceEditorWidget - : public SCompoundWidget -{ -private: - TWeakObjectPtr WeakSequence; - AGAEffectCue* EffectCue; - TWeakPtr WeakBlueprintEditor; - - TSharedPtr Content; - TSharedPtr Sequencer; - FDelegateHandle OnBlueprintPreCompileHandle; - FDelegateHandle OnObjectSavedHandle; - FDelegateHandle OnSequenceChangedHandle; - FDelegateHandle OnBlueprintCompileHandle; - FDelegateHandle OnBlueprintReinstancedHandle; -public: - - SLATE_BEGIN_ARGS(SEffectCueSequenceEditorWidget) {} - SLATE_END_ARGS(); - - void Construct(const FArguments&, TWeakPtr InBlueprintEditor) - { - OnBlueprintPreCompileHandle = GEditor->OnBlueprintPreCompile().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintPreCompile); - OnObjectSavedHandle = FCoreUObjectDelegates::OnObjectSaved.AddSP(this, &SEffectCueSequenceEditorWidget::OnObjectPreSave); - OnBlueprintCompileHandle = GEditor->OnBlueprintCompiled().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintCompiled); - OnBlueprintReinstancedHandle = GEditor->OnBlueprintReinstanced().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintReinstanced); - - WeakBlueprintEditor = InBlueprintEditor; - - ChildSlot - [ - SAssignNew(Content, SBox) - .MinDesiredHeight(200) - ]; - } - void OnBlueprintCompiled() - { - TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); - UBlueprint* bp = BlueprintEditor->GetBlueprintObj(); - float dupa = 0; - } - void OnBlueprintReinstanced() - { - float dupa = 0; - } - ~SEffectCueSequenceEditorWidget() - { - if (Sequencer.IsValid()) - { - Sequencer->Close(); - Sequencer = nullptr; - } - - GEditor->OnBlueprintPreCompile().Remove(OnBlueprintPreCompileHandle); - GEditor->OnBlueprintCompiled().Remove(OnBlueprintCompileHandle); - GEditor->OnBlueprintReinstanced().Remove(OnBlueprintReinstancedHandle); - FCoreUObjectDelegates::OnObjectSaved.Remove(OnObjectSavedHandle); - } - void OnObjectPreSave(UObject* InObject) - { - TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); - if (Sequencer.IsValid() && BlueprintEditor.IsValid() && InObject && InObject == BlueprintEditor->GetBlueprintObj()) - { - Sequencer->RestorePreAnimatedState(); - } - } - - void OnBlueprintPreCompile(UBlueprint* InBlueprint) - { - TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); - if (Sequencer.IsValid() && BlueprintEditor.IsValid() && InBlueprint && InBlueprint == BlueprintEditor->GetBlueprintObj()) - { - Sequencer->RestorePreAnimatedState(); - } - } - void OnSequenceChanged() - { - UGAEffectCueSequence* ActorSequence = WeakSequence.Get(); - /*UBlueprint* Blueprint = ActorSequence ? ActorSequence->GetParentBlueprint() : nullptr; - - if (Blueprint) - { - FBlueprintEditorUtils::MarkBlueprintAsModified(Blueprint); - }*/ - } - void OnSequencerReceivedFocus() - { - if (Sequencer.IsValid()) - { - FLevelEditorSequencerIntegration::Get().OnSequencerReceivedFocus(Sequencer.ToSharedRef()); - } - } - UObject* GetPlaybackContext() const - { - UGAEffectCueSequence* LocalActorSequence = WeakSequence.Get(); - if (LocalActorSequence) - { - if (AActor* Actor = LocalActorSequence->GetTypedOuter()) - { - return Actor; - } - else if (UBlueprintGeneratedClass* GeneratedClass = LocalActorSequence->GetTypedOuter()) - { - return GeneratedClass->SimpleConstructionScript->GetComponentEditorActorInstance(); - } - } - - return nullptr; - } - - TArray GetEventContexts() const - { - TArray Contexts; - if (auto* Context = GetPlaybackContext()) - { - Contexts.Add(Context); - } - return Contexts; - } - AActor* GetPreviewActor() const - { - TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); - if (BlueprintEditor.IsValid()) - { - return BlueprintEditor->GetPreviewActor(); - } - if (UGAEffectCueSequence* Sequence = WeakSequence.Get()) - { - return Sequence->GetTypedOuter(); - } - return nullptr; - } - void OnSelectionUpdated(TSharedPtr SelectedNode) - { - if (SelectedNode->GetNodeType() != FSCSEditorTreeNode::ComponentNode) - { - return; - } - - UActorComponent* EditingComponent = nullptr; - - TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); - if (BlueprintEditor.IsValid()) - { - UBlueprint* Blueprint = BlueprintEditor->GetBlueprintObj(); - if (Blueprint) - { - EditingComponent = SelectedNode->GetEditableComponentTemplate(Blueprint); - } - } - else if (AActor* Actor = GetPreviewActor()) - { - EditingComponent = SelectedNode->FindComponentInstanceInActor(Actor); - } - - if (EditingComponent) - { - const FScopedTransaction Transaction(FText::FromString("Add component to Sequencer")); - Sequencer->GetHandleToObject(EditingComponent, true); - } - - FSlateApplication::Get().DismissAllMenus(); - } - void AddPossessComponentMenuExtensions(FMenuBuilder& MenuBuilder) - { - AActor* Actor = GetPreviewActor(); - if (!Actor) - { - return; - } - - Sequencer->State.ClearObjectCaches(*Sequencer); - TSet AllBoundObjects; - if (UGAEffectCueSequence* Sequence = WeakSequence.Get()) - { - AllBoundObjects.Add(Sequence->GetTypedOuter()); - //return Sequence->GetTypedOuter(); - } - UMovieScene* MovieScene = Sequencer->GetFocusedMovieSceneSequence()->GetMovieScene(); - for (int32 Index = 0; Index < MovieScene->GetPossessableCount(); ++Index) - { - FMovieScenePossessable& Possessable = MovieScene->GetPossessable(Index); - for (TWeakObjectPtr<> WeakObject : Sequencer->FindBoundObjects(Possessable.GetGuid(), Sequencer->GetFocusedTemplateID())) - { - if (UObject* Object = WeakObject.Get()) - { - AllBoundObjects.Add(Object); - } - } - } - - bool bIdent = false; - /*MenuBuilder.AddWidget( - SNew(SComponentSelectionTree, Actor) - .IsInEditMode(WeakBlueprintEditor.Pin().IsValid()) - .OnComponentSelected(this, &SEffectCueSequenceEditorWidget::OnSelectionUpdated) - .IsComponentValid_Lambda( - [AllBoundObjects](UActorComponent* Component) - { - return !AllBoundObjects.Contains(Component); - } - ) - , FText(), !bIdent - );*/ - } - void SetActorSequence(UGAEffectCueSequence* NewSequence, AGAEffectCue* InEffectCue) - { - if (UGAEffectCueSequence* OldSequence = WeakSequence.Get()) - { - if (OnSequenceChangedHandle.IsValid()) - { - OldSequence->OnSignatureChanged().Remove(OnSequenceChangedHandle); - } - } - EffectCue = InEffectCue; - WeakSequence = NewSequence; - - if (NewSequence) - { - OnSequenceChangedHandle = NewSequence->OnSignatureChanged().AddSP(this, &SEffectCueSequenceEditorWidget::OnSequenceChanged); - } - - // If we already have a sequencer open, just assign the sequence - if (Sequencer.IsValid() && NewSequence) - { - if (Sequencer->GetRootMovieSceneSequence() != NewSequence) - { - Sequencer->ResetToNewRootSequence(*NewSequence); - } - return; - } - - // If we're setting the sequence to none, destroy sequencer - if (!NewSequence) - { - //Content->SetContent(SNew(STextBlock).Text(LOCTEXT("NothingSelected", "Select a sequence"))); - return; - } - - // We need to initialize a new sequencer instance - FSequencerInitParams SequencerInitParams; - { - TWeakObjectPtr LocalWeakSequence = NewSequence; - - SequencerInitParams.RootSequence = NewSequence; - SequencerInitParams.EventContexts = TAttribute>(this, &SEffectCueSequenceEditorWidget::GetEventContexts); - SequencerInitParams.PlaybackContext = TAttribute(this, &SEffectCueSequenceEditorWidget::GetPlaybackContext); - - TSharedRef AddMenuExtender = MakeShareable(new FExtender); - - AddMenuExtender->AddMenuExtension("AddTracks", EExtensionHook::Before, nullptr, - FMenuExtensionDelegate::CreateLambda([=](FMenuBuilder& MenuBuilder) { - - MenuBuilder.AddSubMenu( - FText::FromString("Component"), - FText::FromString("Add a binding to one of this actor's components and allow it to be animated by Sequencer"), - FNewMenuDelegate::CreateRaw(this, &SEffectCueSequenceEditorWidget::AddPossessComponentMenuExtensions), - false /*bInOpenSubMenuOnClick*/, - FSlateIcon()//"LevelSequenceEditorStyle", "LevelSequenceEditor.PossessNewActor") - ); - - }) - ); - - SequencerInitParams.ViewParams.bReadOnly = false;// !WeakBlueprintEditor.IsValid() && !NewSequence->IsEditable(); - SequencerInitParams.bEditWithinLevelEditor = false; - SequencerInitParams.ViewParams.AddMenuExtender = AddMenuExtender; - SequencerInitParams.ViewParams.UniqueName = "EffectCueActorSequenceEditor"; - SequencerInitParams.ViewParams.OnReceivedFocus.BindRaw(this, &SEffectCueSequenceEditorWidget::OnSequencerReceivedFocus); - } - - Sequencer = FModuleManager::LoadModuleChecked("Sequencer").CreateSequencer(SequencerInitParams); - Content->SetContent(Sequencer->GetSequencerWidget()); - } -}; - - - -FEffectCueSequenceEditorSummoner::FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor) - : FWorkflowTabFactory("EmbeddedEffectCueSequenceID", BlueprintEditor) - , WeakBlueprintEditor(BlueprintEditor) -{ - bIsSingleton = true; - - TabLabel = FText::FromString("Cue Sequencer"); -} - -TSharedRef FEffectCueSequenceEditorSummoner::CreateTabBody(const FWorkflowTabSpawnInfo& Info) const -{ - return SNew(SEffectCueSequenceEditorWidget, WeakBlueprintEditor); -} - -TSharedRef FAFEffectCueDetails::MakeInstance() -{ - return MakeShareable(new FAFEffectCueDetails); -} - -void FAFEffectCueDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - const IDetailsView* DetailsView = DetailLayout.GetDetailsView(); - if (DetailsView) - { - TSharedPtr HostTabManager = DetailsView->GetHostTabManager(); - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - AGAEffectCue* EffectCue = Cast(Objects[0].Get()); - - if (HostTabManager.IsValid() && HostTabManager->CanSpawnTab("EmbeddedEffectCueSequenceID")) - { - TSharedPtr ExistingTab = HostTabManager->FindExistingLiveTab(FName("EmbeddedEffectCueSequenceID")); - if (ExistingTab.IsValid()) - { - //EffectCue->StaticClass()->GetDefaultObject()->Sequence - - //auto SequencerWidget = StaticCastSharedRef(ExistingTab->GetContent()); - StaticCastSharedRef(ExistingTab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); - //bIsExternalTabAlreadyOpened = ThisSequence && SequencerWidget->GetSequence() == ThisSequence; - return; - } - //EffectCue->Sequence - if (!Tab.IsValid()) - Tab = HostTabManager->InvokeTab(FName("EmbeddedEffectCueSequenceID")); - //Tab->SetContent(Sequencer->GetSequencerWidget()); - StaticCastSharedRef(Tab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); - } - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h deleted file mode 100644 index 611e2aa..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AFEffectCueDetails.h +++ /dev/null @@ -1,36 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -#include "GraphEditor.h" -#include "ISequencer.h" -#include "Effects/GAEffectCueSequence.h" -#include "Editor/Kismet/Public/BlueprintEditor.h" -#include "WorkflowTabFactory.h" - -struct FEffectCueSequenceEditorSummoner - : public FWorkflowTabFactory -{ - FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor); - - virtual TSharedRef CreateTabBody(const FWorkflowTabSpawnInfo& Info) const override; - /*virtual TSharedRef SpawnTab(const FWorkflowTabSpawnInfo& Info) const override;*/ -protected: - TWeakPtr WeakBlueprintEditor; -}; -class FAFEffectCueDetails : public IDetailCustomization -{ -protected: - TSharedPtr Sequencer; - FDelegateHandle OnBlueprintPreCompileHandle; - TSharedPtr Tab; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp deleted file mode 100644 index 326f96c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp +++ /dev/null @@ -1,57 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "AssetTypeActions_GAEffectCueBlueprint.h" -#include "Misc/MessageDialog.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "GAEffectCueEditor.h" -#include "GAEffectCueBlueprint.h" -#include "Effects/GAEffectCue.h" -#include "GAEffectCueBlueprintFactory.h" - -#define LOCTEXT_NAMESPACE "AssetTypeActions" - -FText FAssetTypeActions_GAEffectCueBlueprint::GetName() const -{ - return FText::FromString("Effect Cue"); -} -UClass* FAssetTypeActions_GAEffectCueBlueprint::GetSupportedClass() const -{ - return UGAEffectCueBlueprint::StaticClass(); -} - -void FAssetTypeActions_GAEffectCueBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) -{ - EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; - - for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) - { - auto Blueprint = Cast(*ObjIt); - if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) - { - TSharedRef< FGAEffectCueEditor > NewEditor(new FGAEffectCueEditor()); - - TArray Blueprints; - Blueprints.Add(Blueprint); - - NewEditor->InitEffectCueEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); - } - else - { - FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); - } - } -} - -bool FAssetTypeActions_GAEffectCueBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const -{ - return false; -} - -UFactory* FAssetTypeActions_GAEffectCueBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const -{ - UGAEffectCueBlueprintFactory* EffectCueBlueprintFactory = NewObject(); - EffectCueBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); - return EffectCueBlueprintFactory; -} - -#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h deleted file mode 100644 index 55a06ad..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once -#include "CoreMinimal.h" -#include "Toolkits/IToolkitHost.h" -#include "AssetTypeCategories.h" -//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" -#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" - -class UFactory; - -class FAssetTypeActions_GAEffectCueBlueprint : public FAssetTypeActions_Blueprint -{ -public: - // IAssetTypeActions Implementation - virtual FText GetName() const override; - virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } - virtual UClass* GetSupportedClass() const override; - virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; - virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } - // End IAssetTypeActions Implementation - - // FAssetTypeActions_Blueprint interface - virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; - -private: - /** Returns true if the blueprint is data only */ - bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp deleted file mode 100644 index dcbb00a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAEffectCueBlueprint.h" - -////////////////////////////////////////////////////////////////////////// -// UGameplayAbilityBlueprint - -UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#if WITH_EDITOR - -/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ -UGAEffectCueBlueprint* UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint) -{ - UGAEffectCueBlueprint* ParentBP = NULL; - - // Determine if there is a gameplay ability blueprint in the ancestry of this class - for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) - { - if (UGAEffectCueBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) - { - ParentBP = TestBP; - } - } - - return ParentBP; -} - -#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h deleted file mode 100644 index e3a7eaf..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprint.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Engine/Blueprint.h" -#include "GAEffectCueBlueprint.generated.h" - -/** - * Game Effect Blueprint - */ - -UCLASS(BlueprintType) -class ABILITYFRAMEWORKEDITOR_API UGAEffectCueBlueprint : public UBlueprint -{ - GENERATED_UCLASS_BODY() -UPROPERTY() - class UGAEffectCueSequence* Animation; -#if WITH_EDITOR - - // UBlueprint interface - virtual bool SupportedByDefaultBlueprintFactory() const override - { - return false; - } - // End of UBlueprint interface - - /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ - static UGAEffectCueBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint); - -#endif -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp deleted file mode 100644 index f37eefc..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.cpp +++ /dev/null @@ -1,334 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "GAEffectCueBlueprintFactory.h" -#include "InputCoreTypes.h" -#include "UObject/Interface.h" -#include "Layout/Visibility.h" -#include "Input/Reply.h" -#include "Widgets/SWidget.h" -#include "Widgets/DeclarativeSyntaxSupport.h" -#include "Misc/MessageDialog.h" -#include "Modules/ModuleManager.h" -#include "Effects/GAGameEffect.h" -#include "Widgets/SCompoundWidget.h" -#include "Widgets/SBoxPanel.h" -#include "Widgets/SWindow.h" -#include "Widgets/Layout/SBorder.h" -#include "Widgets/Text/STextBlock.h" -#include "Widgets/Layout/SBox.h" -#include "Widgets/Layout/SUniformGridPanel.h" -#include "Widgets/Input/SButton.h" -#include "EditorStyleSet.h" -#include "Editor.h" -#include "EdGraphSchema_K2.h" - -#include "ClassViewerModule.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "Engine/BlueprintGeneratedClass.h" -#include "Kismet2/KismetEditorUtilities.h" -#include "BlueprintEditorSettings.h" - -#include "GAEffectCueBlueprint.h" -#include "Effects/GAEffectCue.h" -#include "GAEffectCueGraph.h" -#include "GAEffectCueGraphSchema.h" - -#include "ClassViewerFilter.h" - -#include "SlateOptMacros.h" - -// ------------------------------------------------------------------------------ -// Dialog to configure creation properties -// ------------------------------------------------------------------------------ -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION - -class SEffectCueBlueprintCreateDialog : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SEffectCueBlueprintCreateDialog){} - - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs) - { - bOkClicked = false; - ParentClass = AGAEffectCue::StaticClass(); - - ChildSlot - [ - SNew(SBorder) - .Visibility(EVisibility::Visible) - .BorderImage(FEditorStyle::GetBrush("Menu.Background")) - [ - SNew(SBox) - .Visibility(EVisibility::Visible) - .WidthOverride(500.0f) - [ - SNew(SVerticalBox) - + SVerticalBox::Slot() - .FillHeight(1) - [ - SNew(SBorder) - .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) - .Content() - [ - SAssignNew(ParentClassContainer, SVerticalBox) - ] - ] - - // Ok/Cancel buttons - + SVerticalBox::Slot() - .AutoHeight() - .HAlign(HAlign_Right) - .VAlign(VAlign_Bottom) - .Padding(8) - [ - SNew(SUniformGridPanel) - .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) - .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) - .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) - + SUniformGridPanel::Slot(0, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectCueBlueprintCreateDialog::OkClicked) - .Text(FText::FromString("OK")) - ] - + SUniformGridPanel::Slot(1, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectCueBlueprintCreateDialog::CancelClicked) - .Text(FText::FromString("Cancel")) - ] - ] - ] - ] - ]; - - MakeParentClassPicker(); - } - - /** Sets properties for the supplied AbilitiesBlueprintFactory */ - bool ConfigureProperties(TWeakObjectPtr InEffectCueBlueprintFactory) - { - EffectCueBlueprintFactory = InEffectCueBlueprintFactory; - - TSharedRef Window = SNew(SWindow) - .Title(FText::FromString("Create Ability Blueprint")) - .ClientSize(FVector2D(400, 700)) - .SupportsMinimize(false).SupportsMaximize(false) - [ - AsShared() - ]; - - PickerWindow = Window; - - GEditor->EditorAddModalWindow(Window); - EffectCueBlueprintFactory.Reset(); - - return bOkClicked; - } - -private: - class FEffectCueBlueprintParentFilter : public IClassViewerFilter - { - public: - /** All children of these classes will be included unless filtered out by another setting. */ - TSet< const UClass* > AllowedChildrenOfClasses; - - FEffectCueBlueprintParentFilter() {} - - virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; - } - - virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; - } - }; - - /** Creates the combo menu for the parent class */ - void MakeParentClassPicker() - { - // Load the classviewer module to display a class picker - FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); - - // Fill in options - FClassViewerInitializationOptions Options; - Options.Mode = EClassViewerMode::ClassPicker; - - // Only allow parenting to base blueprints. - Options.bIsBlueprintBaseOnly = true; - - TSharedPtr Filter = MakeShareable(new FEffectCueBlueprintParentFilter); - - // All child child classes of UGameplayAbility are valid. - Filter->AllowedChildrenOfClasses.Add(AGAEffectCue::StaticClass()); - Options.ClassFilter = Filter; - - ParentClassContainer->ClearChildren(); - ParentClassContainer->AddSlot() - .AutoHeight() - [ - SNew(STextBlock) - .Text(FText::FromString("Parent Class:")) - .ShadowOffset(FVector2D(1.0f, 1.0f)) - ]; - - ParentClassContainer->AddSlot() - [ - ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCueBlueprintCreateDialog::OnClassPicked)) - ]; - } - - /** Handler for when a parent class is selected */ - void OnClassPicked(UClass* ChosenClass) - { - ParentClass = ChosenClass; - } - - /** Handler for when ok is clicked */ - FReply OkClicked() - { - if (EffectCueBlueprintFactory.IsValid()) - { - EffectCueBlueprintFactory->BlueprintType = BPTYPE_Normal; - EffectCueBlueprintFactory->ParentClass = ParentClass.Get(); - } - - CloseDialog(true); - - return FReply::Handled(); - } - - void CloseDialog(bool bWasPicked = false) - { - bOkClicked = bWasPicked; - if (PickerWindow.IsValid()) - { - PickerWindow.Pin()->RequestDestroyWindow(); - } - } - - /** Handler for when cancel is clicked */ - FReply CancelClicked() - { - CloseDialog(); - return FReply::Handled(); - } - - FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) - { - if (InKeyEvent.GetKey() == EKeys::Escape) - { - CloseDialog(); - return FReply::Handled(); - } - return SWidget::OnKeyDown(MyGeometry, InKeyEvent); - } - -private: - /** The factory for which we are setting up properties */ - TWeakObjectPtr EffectCueBlueprintFactory; - - /** A pointer to the window that is asking the user to select a parent class */ - TWeakPtr PickerWindow; - - /** The container for the Parent Class picker */ - TSharedPtr ParentClassContainer; - - /** The selected class */ - TWeakObjectPtr ParentClass; - - /** True if Ok was clicked */ - bool bOkClicked; -}; - -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -/*------------------------------------------------------------------------------ - UAbilitiesBlueprintFactory implementation. -------------------------------------------------------------------------------*/ - -UGAEffectCueBlueprintFactory::UGAEffectCueBlueprintFactory(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bCreateNew = true; - bEditAfterNew = true; - SupportedClass = UGAEffectCueBlueprint::StaticClass(); - ParentClass = AGAEffectCue::StaticClass(); -} - -bool UGAEffectCueBlueprintFactory::ConfigureProperties() -{ - TSharedRef Dialog = SNew(SEffectCueBlueprintCreateDialog); - return Dialog->ConfigureProperties(this); -}; - -UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) -{ - // Make sure we are trying to factory a gameplay ability blueprint, then create and init one - check(Class->IsChildOf(UGAEffectCueBlueprint::StaticClass())); - - // If they selected an interface, force the parent class to be UInterface - if (BlueprintType == BPTYPE_Interface) - { - ParentClass = UInterface::StaticClass(); - } - - if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(AGAEffectCue::StaticClass()) ) - { - FFormatNamedArguments Args; - Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); - FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); - return NULL; - } - else - { - UGAEffectCueBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectCueBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); - - if (NewBP) - { - UGAEffectCueBlueprint* AbilityBP = UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(NewBP); - if (AbilityBP == NULL) - { - const UEdGraphSchema_K2* K2Schema = GetDefault(); - - // Only allow a gameplay ability graph if there isn't one in a parent blueprint - UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAEffectCueGraph::StaticClass(), UGAEffectCueGraphSchema::StaticClass()); -#if WITH_EDITORONLY_DATA - if (NewBP->UbergraphPages.Num()) - { - FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); - } -#endif - FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); - NewBP->LastEditedDocuments.Add(NewGraph); - NewGraph->bAllowDeletion = false; - - UBlueprintEditorSettings* Settings = GetMutableDefault(); - if(Settings && Settings->bSpawnDefaultBlueprintNodes) - { - int32 NodePositionY = 0; - //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); - //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); - } - } - } - - return NewBP; - } -} - -UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) -{ - return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h deleted file mode 100644 index 1c78872..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueBlueprintFactory.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Templates/SubclassOf.h" -#include "Engine/Blueprint.h" -#include "Factories/Factory.h" -#include "AssetTypeCategories.h" -#include "GAEffectCueBlueprintFactory.generated.h" - -UCLASS(HideCategories=Object, MinimalAPI) -class UGAEffectCueBlueprintFactory : public UFactory -{ - GENERATED_UCLASS_BODY() - - // The type of blueprint that will be created - UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TEnumAsByte BlueprintType; - - // The parent class of the created blueprint - UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TSubclassOf ParentClass; - - //~ Begin UFactory Interface - virtual bool ConfigureProperties() override; - virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; - virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; - - //~ Begin UFactory Interface -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp deleted file mode 100644 index 4c50866..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.cpp +++ /dev/null @@ -1,210 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "Effects/GAEffectCue.h" -#include "GAEffectCueEditor.h" -#include "Effects/GAEffectCueSequence.h" -#include "EditorReimportHandler.h" -#include "MovieScene.h" -#include "Tracks/MovieScenePropertyTrack.h" -#if WITH_EDITOR -#include "Editor.h" -#endif -#include "ISequencerModule.h" -#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" -#include "Toolkits/ToolkitManager.h" -#include "Toolkits/GlobalEditorCommonCommands.h" - -#include "GAEffectCueBlueprint.h" -#include "GAEffectCueBlueprintFactory.h" -#include "GAEffectCueGraphSchema.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "SDockTab.h" -#include "BlueprintEditorTabs.h" -#include "LayoutExtender.h" -#include "BlueprintEditorModes.h" -#include "BlueprintEditorTabs.h" - -#define LOCTEXT_NAMESPACE "FGAEffectCueEditor" - - -//TSharedRef FEffectCueSequenceEditorSummoner::SpawnTab(const FWorkflowTabSpawnInfo& Info) const -//{ -// TSharedRef Tab = FWorkflowTabFactory::SpawnTab(Info); -// -// TSharedPtr BlueprintEditorPtr = StaticCastSharedPtr(HostingApp.Pin()); -// BlueprintEditorPtr->GetInspector()->SetOwnerTab(Tab); -// -// BlueprintEditorPtr->GetInspector()->GetPropertyView()->SetHostTabManager(Info.TabManager); -// -// return Tab; -//} - -///////////////////////////////////////////////////// -// FGameplayAbilitiesEditor - -FGAEffectCueEditor::FGAEffectCueEditor() -{ - EditedCue = nullptr; - FBlueprintEditorModule& BlueprintEditorModule = FModuleManager::LoadModuleChecked("Kismet"); - BlueprintEditorTabSpawnerHandle = BlueprintEditorModule.OnRegisterTabsForEditor().AddRaw(this, &FGAEffectCueEditor::RegisterBlueprintEditorTab); - BlueprintEditorLayoutExtensionHandle = BlueprintEditorModule.OnRegisterLayoutExtensions().AddRaw(this, &FGAEffectCueEditor::RegisterBlueprintEditorLayout); -} - -void FGAEffectCueEditor::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) -{ - //Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); -} - -void FGAEffectCueEditor::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) -{ - //TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); -} -TArray FGAEffectCueEditor::GetAnimationEventContexts() const -{ - TArray EventContexts; - return EventContexts; -} - -void FGAEffectCueEditor::OnSequenceChanged() -{ - UBlueprint* Blueprint = GetBlueprintObj(); - - if (Blueprint) - { - FBlueprintEditorUtils::MarkBlueprintAsModified(Blueprint); - } -} -void FGAEffectCueEditor::OnMovieSceneDataChanged() -{ -} -void FGAEffectCueEditor::ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView) -{ -} -FGAEffectCueEditor::~FGAEffectCueEditor() -{ - FEditorDelegates::OnAssetPostImport.RemoveAll(this); - FReimportManager::Instance()->OnPostReimport().RemoveAll(this); - FBlueprintEditorModule* BlueprintEditorModule = &FModuleManager::LoadModuleChecked("Kismet"); - BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); - BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); - BlueprintEditorTabSpawnerHandle.Reset(); - BlueprintEditorLayoutExtensionHandle.Reset(); - TabManager.Pin()->UnregisterTabSpawner(FName("EmbeddedEffectCueSequenceID")); - // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor -} - -void FGAEffectCueEditor::RegisterTabSpawners(const TSharedRef& InTabManager) -{ - TabManager = InTabManager; - FBlueprintEditor::RegisterTabSpawners(InTabManager); -} -void FGAEffectCueEditor::UnregisterTabSpawners(const TSharedRef& InTabManager) -{ - FAssetEditorToolkit::RegisterTabSpawners(InTabManager); -} - -void FGAEffectCueEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) -{ - - FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, ObjectsToEdit, bInIsToolbarFocusable); -} -void FGAEffectCueEditor::InitEffectCueEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) -{ - InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); - UBlueprint* BP = InBlueprints[0]; - EditedCue = BP->GeneratedClass->GetDefaultObject(); - CueClass = BP->GeneratedClass; - - for (auto Blueprint : InBlueprints) - { - EnsureAbilityBlueprintIsUpToDate(Blueprint); - } -} - -void FGAEffectCueEditor::EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint) -{ -#if WITH_EDITORONLY_DATA - int32 Count = Blueprint->UbergraphPages.Num(); - for (auto Graph : Blueprint->UbergraphPages) - { - // remove the default event graph, if it exists, from existing Gameplay Ability Blueprints - if (Graph->GetName() == "EventGraph" && Graph->Nodes.Num() == 0) - { - check(!Graph->Schema->GetClass()->IsChildOf(UGAEffectCueGraphSchema::StaticClass())); - FBlueprintEditorUtils::RemoveGraph(Blueprint, Graph); - break; - } - } -#endif -} -bool FGAEffectCueEditor::IsBlueprintEditor() const -{ - return true; -} - -FName FGAEffectCueEditor::GetToolkitFName() const -{ - return FName("EffectCueEditor"); -} - -FText FGAEffectCueEditor::GetBaseToolkitName() const -{ - return FText::FromString("Game Effect Cue"); -} - -FText FGAEffectCueEditor::GetToolkitName() const -{ - const TArray& EditingObjs = GetEditingObjects(); - - check(EditingObjs.Num() > 0); - - FFormatNamedArguments Args; - - const UObject* EditingObject = EditingObjs[0]; - - const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); - - Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); - Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); - return FText::Format(FText::FromString("{ObjectName}{DirtyState}"), Args); -} - -FText FGAEffectCueEditor::GetToolkitToolTipText() const -{ - const UObject* EditingObject = GetEditingObject(); - - check (EditingObject != NULL); - - return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); -} - -FString FGAEffectCueEditor::GetWorldCentricTabPrefix() const -{ - return TEXT("EffectCueEditor"); -} - -FLinearColor FGAEffectCueEditor::GetWorldCentricTabColorScale() const -{ - return FLinearColor::White; -} - -UBlueprint* FGAEffectCueEditor::GetBlueprintObj() const -{ - const TArray& EditingObjs = GetEditingObjects(); - for (int32 i = 0; i < EditingObjs.Num(); ++i) - { - if (EditingObjs[i]->IsA()) - { - return (UBlueprint*)EditingObjs[i]; - } - } - return nullptr; -} - -FString FGAEffectCueEditor::GetDocumentationLink() const -{ - return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation -} - -#undef LOCTEXT_NAMESPACE - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h deleted file mode 100644 index 9094f6b..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueEditor.h +++ /dev/null @@ -1,79 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "Framework/Commands/UICommandList.h" -#include "Framework/MultiBox/MultiBoxExtender.h" -#include "GraphEditor.h" -#include "ISequencer.h" -#include "Effects/GAEffectCueSequence.h" -#include "Editor/Kismet/Public/BlueprintEditor.h" -#include "WorkflowTabFactory.h" -////////////////////////////////////////////////////////////////////////// -// FGameplayAbilitiesEditor -class UGAEffectCueSequence; -/** - * Gameplay abilities asset editor (extends Blueprint editor) - */ - -class FGAEffectCueEditor : public FBlueprintEditor -{ - TWeakPtr TabManager; - FDelegateHandle OnSequenceChangedHandle; - - TArray GetAnimationEventContexts() const; - FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; - class AGAEffectCue* EditedCue; - TSubclassOf CueClass; - TWeakObjectPtr EditedSequence; - void ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView); - void OnMovieSceneDataChanged(); - void OnSequenceChanged(); - void RegisterBlueprintEditorLayout(FLayoutExtender& Extender); - void RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor); -public: - virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; - /** - * Edits the specified gameplay ability asset(s) - * - * @param Mode Asset editing mode for this editor (standalone or world-centric) - * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within - * @param InBlueprints The blueprints to edit - * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode - */ - - void InitEffectCueEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); -private: - /** - * Updates existing gameplay ability blueprints to make sure that they are up to date - * - * @param Blueprint The blueprint to be updated - */ - void EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint); - -public: - FGAEffectCueEditor(); - - virtual ~FGAEffectCueEditor(); - -public: - // IToolkit interface - // FRED_TODO: don't merge this back - virtual void RegisterTabSpawners(const TSharedRef& InTabManager) override; - virtual void UnregisterTabSpawners(const TSharedRef& InTabManager) override; - virtual FName GetToolkitFName() const override; - virtual FText GetBaseToolkitName() const override; - virtual FText GetToolkitName() const override; - virtual FText GetToolkitToolTipText() const override; - virtual FString GetWorldCentricTabPrefix() const override; - virtual FLinearColor GetWorldCentricTabColorScale() const override; - virtual bool IsBlueprintEditor() const override; - // End of IToolkit interface - - /** @return the documentation location for this editor */ - virtual FString GetDocumentationLink() const override; - - /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ - virtual UBlueprint* GetBlueprintObj() const override; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp deleted file mode 100644 index 1487984..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAEffectCueGraph.h" - -#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" - -///////////////////////////////////////////////////// -// UGameplayAbilityGraph - -UGAEffectCueGraph::UGAEffectCueGraph(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h deleted file mode 100644 index 5a3bfe0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraph.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "EdGraph/EdGraph.h" -#include "GAEffectCueGraph.generated.h" - -UCLASS(MinimalAPI) -class UGAEffectCueGraph : public UEdGraph -{ - GENERATED_UCLASS_BODY() -}; - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp deleted file mode 100644 index bae2670..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAEffectCueGraphSchema.h" -#include "EdGraphSchema_K2_Actions.h" -#include "Effects/GAGameEffect.h" -#include "Kismet2/BlueprintEditorUtils.h" - -UGAEffectCueGraphSchema::UGAEffectCueGraphSchema(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ -} - -UK2Node_VariableGet* UGAEffectCueGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const -{ - return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); -} - -UK2Node_VariableSet* UGAEffectCueGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const -{ - return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h deleted file mode 100644 index 1f9b8cc..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectCueEditor/GAEffectCueGraphSchema.h +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "EdGraphSchema_K2.h" -#include "GAEffectCueGraphSchema.generated.h" - -UCLASS(MinimalAPI) -class UGAEffectCueGraphSchema : public UEdGraphSchema_K2 -{ - GENERATED_UCLASS_BODY() - - /** - * Creates a new variable getter node and adds it to ParentGraph - * - * @param GraphPosition The location of the new node inside the graph - * @param ParentGraph The graph to spawn the new node in - * @param VariableName The name of the variable - * @param Source The source of the variable - * @return A pointer to the newly spawned node - */ - virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; - - /** - * Creates a new variable setter node and adds it to ParentGraph - * - * @param GraphPosition The location of the new node inside the graph - * @param ParentGraph The graph to spawn the new node in - * @param VariableName The name of the variable - * @param Source The source of the variable - * @return A pointer to the newly spawned node - */ - virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; - - virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp deleted file mode 100644 index 44ef642..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp +++ /dev/null @@ -1,57 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "AssetTypeActions_GAEffectBlueprint.h" -#include "Misc/MessageDialog.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "GAEffectEditor.h" -#include "Effects/GAEffectBlueprint.h" -#include "Effects/GAGameEffect.h" -#include "GAEffectBlueprintFactory.h" - -#define LOCTEXT_NAMESPACE "AssetTypeActions" - -FText FAssetTypeActions_GAEffectBlueprint::GetName() const -{ - return FText::FromString("Effect Data"); -} -UClass* FAssetTypeActions_GAEffectBlueprint::GetSupportedClass() const -{ - return UGAEffectBlueprint::StaticClass(); -} - -void FAssetTypeActions_GAEffectBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) -{ - EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; - - for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) - { - auto Blueprint = Cast(*ObjIt); - if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) - { - TSharedRef< FGAEffectEditor > NewEditor(new FGAEffectEditor()); - - TArray Blueprints; - Blueprints.Add(Blueprint); - - NewEditor->InitEffectEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); - } - else - { - FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Gameplay Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); - } - } -} - -bool FAssetTypeActions_GAEffectBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const -{ - return true; -} - -UFactory* FAssetTypeActions_GAEffectBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const -{ - UGAEffectBlueprintFactory* EffectBlueprintFactory = NewObject(); - EffectBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); - return EffectBlueprintFactory; -} - -#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h deleted file mode 100644 index ad3cabd..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/AssetTypeActions_GAEffectBlueprint.h +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once -#include "CoreMinimal.h" -#include "Toolkits/IToolkitHost.h" -#include "AssetTypeCategories.h" -//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" -#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" - -class UFactory; - -class FAssetTypeActions_GAEffectBlueprint : public FAssetTypeActions_Blueprint -{ -public: - // IAssetTypeActions Implementation - virtual FText GetName() const override; - virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } - virtual UClass* GetSupportedClass() const override; - virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; - virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } - // End IAssetTypeActions Implementation - - // FAssetTypeActions_Blueprint interface - virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; - -private: - /** Returns true if the blueprint is data only */ - bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp deleted file mode 100644 index c84d883..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.cpp +++ /dev/null @@ -1,347 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "GAEffectBlueprintFactory.h" -#include "InputCoreTypes.h" -#include "UObject/Interface.h" -#include "Layout/Visibility.h" -#include "Input/Reply.h" -#include "Widgets/SWidget.h" -#include "Widgets/DeclarativeSyntaxSupport.h" -#include "Misc/MessageDialog.h" -#include "Modules/ModuleManager.h" -#include "Effects/GAGameEffect.h" -#include "Widgets/SCompoundWidget.h" -#include "Widgets/SBoxPanel.h" -#include "Widgets/SWindow.h" -#include "Widgets/Layout/SBorder.h" -#include "Widgets/Text/STextBlock.h" -#include "Widgets/Layout/SBox.h" -#include "Widgets/Layout/SUniformGridPanel.h" -#include "Widgets/Input/SButton.h" -#include "EditorStyleSet.h" -#include "Editor.h" -#include "EdGraphSchema_K2.h" - -#include "ClassViewerModule.h" -#include "Kismet2/BlueprintEditorUtils.h" -#include "Engine/BlueprintGeneratedClass.h" -#include "Kismet2/KismetEditorUtilities.h" -#include "BlueprintEditorSettings.h" - -#include "Effects/GAEffectBlueprint.h" -#include "GAEffectGraph.h" -#include "GAEffectGraphSchema.h" -#include "Abilities/AFAbilityActivationSpec.h" -#include "Abilities/AFAbilityCooldownSpec.h" -#include "Abilities/AFAbilityPeriodSpec.h" -#include "Abilities/AFAbilityInfiniteDurationSpec.h" - -#include "ClassViewerFilter.h" - -#include "SlateOptMacros.h" - -#define LOCTEXT_NAMESPACE "UEffectBlueprintFactory" - - -// ------------------------------------------------------------------------------ -// Dialog to configure creation properties -// ------------------------------------------------------------------------------ -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION - -class SEffectBlueprintCreateDialog : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SEffectBlueprintCreateDialog){} - - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs) - { - bOkClicked = false; - ParentClass = UGAGameEffectSpec::StaticClass(); - - ChildSlot - [ - SNew(SBorder) - .Visibility(EVisibility::Visible) - .BorderImage(FEditorStyle::GetBrush("Menu.Background")) - [ - SNew(SBox) - .Visibility(EVisibility::Visible) - .WidthOverride(500.0f) - [ - SNew(SVerticalBox) - + SVerticalBox::Slot() - .FillHeight(1) - [ - SNew(SBorder) - .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) - .Content() - [ - SAssignNew(ParentClassContainer, SVerticalBox) - ] - ] - - // Ok/Cancel buttons - + SVerticalBox::Slot() - .AutoHeight() - .HAlign(HAlign_Right) - .VAlign(VAlign_Bottom) - .Padding(8) - [ - SNew(SUniformGridPanel) - .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) - .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) - .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) - + SUniformGridPanel::Slot(0, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectBlueprintCreateDialog::OkClicked) - .Text(FText::FromString("OK")) - ] - + SUniformGridPanel::Slot(1, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectBlueprintCreateDialog::CancelClicked) - .Text(FText::FromString("Cancel")) - ] - ] - ] - ] - ]; - - MakeParentClassPicker(); - } - - /** Sets properties for the supplied EffectBlueprintFactory */ - bool ConfigureProperties(TWeakObjectPtr InEffectlueprintFactory) - { - EffectBlueprintFactory = InEffectlueprintFactory; - - TSharedRef Window = SNew(SWindow) - .Title(FText::FromString("Create Game Effect Blueprint")) - .ClientSize(FVector2D(400, 700)) - .SupportsMinimize(false).SupportsMaximize(false) - [ - AsShared() - ]; - - PickerWindow = Window; - - GEditor->EditorAddModalWindow(Window); - EffectBlueprintFactory.Reset(); - - return bOkClicked; - } - -private: - class FEffectBlueprintParentFilter : public IClassViewerFilter - { - public: - /** All children of these classes will be included unless filtered out by another setting. */ - TSet< const UClass* > AllowedChildrenOfClasses; - - FEffectBlueprintParentFilter() {} - - virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; - } - - virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; - } - }; - - /** Creates the combo menu for the parent class */ - void MakeParentClassPicker() - { - // Load the classviewer module to display a class picker - FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); - - // Fill in options - FClassViewerInitializationOptions Options; - Options.Mode = EClassViewerMode::ClassPicker; - - // Only allow parenting to base blueprints. - Options.bIsBlueprintBaseOnly = true; - - TSharedPtr Filter = MakeShareable(new FEffectBlueprintParentFilter); - - // All child child classes of UGameplayAbility are valid. - Filter->AllowedChildrenOfClasses.Add(UAFEffectSpecBase::StaticClass()); - Filter->AllowedChildrenOfClasses.Add(UAFAbilityActivationSpec::StaticClass()); - Filter->AllowedChildrenOfClasses.Add(UAFAbilityCooldownSpec::StaticClass()); - Filter->AllowedChildrenOfClasses.Add(UAFAbilityPeriodSpec::StaticClass()); - Filter->AllowedChildrenOfClasses.Add(UAFAbilityInfiniteDurationSpec::StaticClass()); - - Options.ClassFilter = Filter; - - ParentClassContainer->ClearChildren(); - ParentClassContainer->AddSlot() - .AutoHeight() - [ - SNew(STextBlock) - .Text(FText::FromString("Parent Class:")) - .ShadowOffset(FVector2D(1.0f, 1.0f)) - ]; - - ParentClassContainer->AddSlot() - [ - ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectBlueprintCreateDialog::OnClassPicked)) - ]; - } - - /** Handler for when a parent class is selected */ - void OnClassPicked(UClass* ChosenClass) - { - ParentClass = ChosenClass; - } - - /** Handler for when ok is clicked */ - FReply OkClicked() - { - if (EffectBlueprintFactory.IsValid()) - { - EffectBlueprintFactory->BlueprintType = BPTYPE_Normal; - EffectBlueprintFactory->ParentClass = ParentClass.Get(); - } - - CloseDialog(true); - - return FReply::Handled(); - } - - void CloseDialog(bool bWasPicked = false) - { - bOkClicked = bWasPicked; - if (PickerWindow.IsValid()) - { - PickerWindow.Pin()->RequestDestroyWindow(); - } - } - - /** Handler for when cancel is clicked */ - FReply CancelClicked() - { - CloseDialog(); - return FReply::Handled(); - } - - FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) - { - if (InKeyEvent.GetKey() == EKeys::Escape) - { - CloseDialog(); - return FReply::Handled(); - } - return SWidget::OnKeyDown(MyGeometry, InKeyEvent); - } - -private: - /** The factory for which we are setting up properties */ - TWeakObjectPtr EffectBlueprintFactory; - - /** A pointer to the window that is asking the user to select a parent class */ - TWeakPtr PickerWindow; - - /** The container for the Parent Class picker */ - TSharedPtr ParentClassContainer; - - /** The selected class */ - TWeakObjectPtr ParentClass; - - /** True if Ok was clicked */ - bool bOkClicked; -}; - -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -/*------------------------------------------------------------------------------ - UEffectBlueprintFactory implementation. -------------------------------------------------------------------------------*/ - -UGAEffectBlueprintFactory::UGAEffectBlueprintFactory(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - bCreateNew = true; - bEditAfterNew = true; - SupportedClass = UGAEffectBlueprint::StaticClass(); - ParentClass = UGAGameEffectSpec::StaticClass(); -} - -bool UGAEffectBlueprintFactory::ConfigureProperties() -{ - TSharedRef Dialog = SNew(SEffectBlueprintCreateDialog); - return Dialog->ConfigureProperties(this); -}; - -UObject* UGAEffectBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) -{ - // Make sure we are trying to factory a gameplay ability blueprint, then create and init one - check(Class->IsChildOf(UGAEffectBlueprint::StaticClass())); - - // If they selected an interface, force the parent class to be UInterface - if (BlueprintType == BPTYPE_Interface) - { - ParentClass = UInterface::StaticClass(); - } - - if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass()) ) - { - FFormatNamedArguments Args; - Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : LOCTEXT("Null", "(null)") ); - FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Effect Blueprint based on the class '{ClassName}'."), Args ) ); - return NULL; - } - else - { - UGAEffectBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); - - if (NewBP) - { - UGAEffectBlueprint* AbilityBP = UGAEffectBlueprint::FindRootGameplayAbilityBlueprint(NewBP); - if (AbilityBP == NULL) - { - const UEdGraphSchema_K2* K2Schema = GetDefault(); - - // Only allow a gameplay ability graph if there isn't one in a parent blueprint - //UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Not Used Effect Graph"), UGAEffectGraph::StaticClass(), UGAEffectGraphSchema::StaticClass()); -#if WITH_EDITORONLY_DATA - if (NewBP->UbergraphPages.Num()) - { - FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); - } -#endif - //FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); - //NewBP->LastEditedDocuments.Add(NewGraph); - //NewGraph->bAllowDeletion = false; - - UBlueprintEditorSettings* Settings = GetMutableDefault(); - if(Settings && Settings->bSpawnDefaultBlueprintNodes) - { - int32 NodePositionY = 0; - //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAGameEffectSpec::StaticClass(), NodePositionY); - //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAGameEffectSpec::StaticClass(), NodePositionY); - } - } - } - - return NewBP; - } -} - -UObject* UGAEffectBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) -{ - return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h deleted file mode 100644 index 8a9b850..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectBlueprintFactory.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Templates/SubclassOf.h" -#include "Engine/Blueprint.h" -#include "Factories/Factory.h" -#include "AssetTypeCategories.h" -#include "GAEffectBlueprintFactory.generated.h" - -UCLASS(HideCategories=Object, MinimalAPI) -class UGAEffectBlueprintFactory : public UFactory -{ - GENERATED_UCLASS_BODY() - - // The type of blueprint that will be created - UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TEnumAsByte BlueprintType; - - // The parent class of the created blueprint - UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TSubclassOf ParentClass; - - //~ Begin UFactory Interface - virtual bool ConfigureProperties() override; - virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; - virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; - - //~ Begin UFactory Interface -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp deleted file mode 100644 index 5559a8d..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.cpp +++ /dev/null @@ -1,124 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "GAEffectEditor.h" -#include "EditorReimportHandler.h" - -#if WITH_EDITOR -#include "Editor.h" -#endif -//Editor\UnrealEd\Public\Toolkits\ToolkitManager.h -//\Editor\UnrealEd\Private\Toolkits\SStandaloneAssetEditorToolkitHost.h -#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" -#include "Toolkits/ToolkitManager.h" -//#include "Toolkits/AssetEditorCommonCommands.h" -#include "Toolkits/GlobalEditorCommonCommands.h" - -#include "Effects/GAEffectBlueprint.h" -#include "GAEffectBlueprintFactory.h" -#include "GAEffectGraphSchema.h" -#include "Kismet2/BlueprintEditorUtils.h" - -#define LOCTEXT_NAMESPACE "FGAEffectEditor" - - -///////////////////////////////////////////////////// -// FGameplayAbilitiesEditor - -FGAEffectEditor::FGAEffectEditor() -{ - // todo: Do we need to register a callback for when properties are changed? - //bCreateMenuExtenders = true; - //bCreateDefaultStandaloneMenu = false; - //bCreateDefaultToolbar = false; -} - -FGAEffectEditor::~FGAEffectEditor() -{ - FEditorDelegates::OnAssetPostImport.RemoveAll(this); - FReimportManager::Instance()->OnPostReimport().RemoveAll(this); - - // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor -} -void FGAEffectEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) -{ - FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, true, true, ObjectsToEdit, true); -} -void FGAEffectEditor::InitEffectEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) -{ - InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); - RemoveAllToolbarWidgets(); -} - - -// FRED_TODO: don't merge this back -// FName FGameplayAbilitiesEditor::GetToolkitContextFName() const -// { -// return GetToolkitFName(); -// } - -FName FGAEffectEditor::GetToolkitFName() const -{ - return FName("GameEffectEditor"); -} - -FText FGAEffectEditor::GetBaseToolkitName() const -{ - return FText::FromString("Game Effect Editor"); -} - -FText FGAEffectEditor::GetToolkitName() const -{ - const TArray& EditingObjs = GetEditingObjects(); - - check(EditingObjs.Num() > 0); - - FFormatNamedArguments Args; - - const UObject* EditingObject = EditingObjs[0]; - - const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); - - Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); - Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); - return FText::Format(LOCTEXT("GameplayAbilitiesToolkitName", "{ObjectName}{DirtyState}"), Args); -} - -FText FGAEffectEditor::GetToolkitToolTipText() const -{ - const UObject* EditingObject = GetEditingObject(); - - check(EditingObject != NULL); - - return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); -} - -FString FGAEffectEditor::GetWorldCentricTabPrefix() const -{ - return TEXT("EffectEditor"); -} - -FLinearColor FGAEffectEditor::GetWorldCentricTabColorScale() const -{ - return FLinearColor::White; -} - -UBlueprint* FGAEffectEditor::GetBlueprintObj() const -{ - const TArray& EditingObjs = GetEditingObjects(); - for (int32 i = 0; i < EditingObjs.Num(); ++i) - { - if (EditingObjs[i]->IsA()) - { - return (UBlueprint*)EditingObjs[i]; - } - } - return nullptr; -} - -FString FGAEffectEditor::GetDocumentationLink() const -{ - return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation -} - -#undef LOCTEXT_NAMESPACE - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h deleted file mode 100644 index e0dd625..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectEditor.h +++ /dev/null @@ -1,53 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "Editor/Kismet/Public/BlueprintEditor.h" - -////////////////////////////////////////////////////////////////////////// -// FGameplayAbilitiesEditor - -/** - * Gameplay abilities asset editor (extends Blueprint editor) - */ -class FGAEffectEditor : public FBlueprintEditor -{ -public: - virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; - /** - * Edits the specified gameplay ability asset(s) - * - * @param Mode Asset editing mode for this editor (standalone or world-centric) - * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within - * @param InBlueprints The blueprints to edit - * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode - */ - - void InitEffectEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); -public: - FGAEffectEditor(); - - virtual ~FGAEffectEditor(); - -public: - // IToolkit interface - // FRED_TODO: don't merge this back -// virtual FName GetToolkitContextFName() const override; - virtual FName GetToolkitFName() const override; - virtual FText GetBaseToolkitName() const override; - virtual FText GetToolkitName() const override; - virtual FText GetToolkitToolTipText() const override; - virtual FString GetWorldCentricTabPrefix() const override; - virtual FLinearColor GetWorldCentricTabColorScale() const override; - virtual bool IsAssetEditor() const override { return true; } - virtual bool IsBlueprintEditor() const override { return false; }; - virtual void PostRegenerateMenusAndToolbars() override { RemoveAllToolbarWidgets(); }; - // End of IToolkit interface - - /** @return the documentation location for this editor */ - virtual FString GetDocumentationLink() const override; - - /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ - virtual UBlueprint* GetBlueprintObj() const override; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp deleted file mode 100644 index a802167..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAEffectGraph.h" - -#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" - -///////////////////////////////////////////////////// -// UGameplayAbilityGraph - -UGAEffectGraph::UGAEffectGraph(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h deleted file mode 100644 index 3492fc2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraph.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "EdGraph/EdGraph.h" -#include "GAEffectGraph.generated.h" - -UCLASS(MinimalAPI) -class UGAEffectGraph : public UEdGraph -{ - GENERATED_UCLASS_BODY() -}; - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp deleted file mode 100644 index 1404740..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAEffectGraphSchema.h" -#include "EdGraphSchema_K2_Actions.h" -#include "Effects/GAGameEffect.h" -#include "Kismet2/BlueprintEditorUtils.h" - -UGAEffectGraphSchema::UGAEffectGraphSchema(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) -{ -} - -UK2Node_VariableGet* UGAEffectGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const -{ - return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); -} - -UK2Node_VariableSet* UGAEffectGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const -{ - return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); -} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h deleted file mode 100644 index d435fae..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/EffectEditor/GAEffectGraphSchema.h +++ /dev/null @@ -1,38 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "EdGraphSchema_K2.h" -#include "GAEffectGraphSchema.generated.h" - -UCLASS(MinimalAPI) -class UGAEffectGraphSchema : public UEdGraphSchema_K2 -{ - GENERATED_UCLASS_BODY() - - /** - * Creates a new variable getter node and adds it to ParentGraph - * - * @param GraphPosition The location of the new node inside the graph - * @param ParentGraph The graph to spawn the new node in - * @param VariableName The name of the variable - * @param Source The source of the variable - * @return A pointer to the newly spawned node - */ - virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; - - /** - * Creates a new variable setter node and adds it to ParentGraph - * - * @param GraphPosition The location of the new node inside the graph - * @param ParentGraph The graph to spawn the new node in - * @param VariableName The name of the variable - * @param Source The source of the variable - * @return A pointer to the newly spawned node - */ - virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; - - virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp deleted file mode 100644 index 81cbfa0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.cpp +++ /dev/null @@ -1,90 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "SGAAttributeWidget.h" - -#include "GAAttributeDetailCustomization.h" - -TSharedRef FGAAttributeDetailCustomization::MakeInstance() -{ - return MakeShareable(new FGAAttributeDetailCustomization); -} - -FGAAttributeDetailCustomization::~FGAAttributeDetailCustomization() -{ - -} - -void FGAAttributeDetailCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - SocketNameHandle = InStructPropertyHandle->GetChildHandle(GET_MEMBER_NAME_CHECKED(FGAAttribute, AttributeName)); - check(SocketNameHandle.IsValid()); - - HeaderRow - .NameContent() - [ - InStructPropertyHandle->CreatePropertyNameWidget() - ] - .ValueContent() - .MaxDesiredWidth(512) - [ - SNew(SHorizontalBox) - + SHorizontalBox::Slot() - .AutoWidth() - .VAlign(VAlign_Center) - [ - SNew(SComboButton) - .OnGetMenuContent(this, &FGAAttributeDetailCustomization::GetSocketTree) - .ContentPadding(FMargin(0.4)) - .ButtonContent() - [ - SNew(STextBlock) - .Margin(FMargin(0.6)) - .Text(this, &FGAAttributeDetailCustomization::GetAttributeName) - ] - ] - ]; -} -void FGAAttributeDetailCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} - -FText FGAAttributeDetailCustomization::GetAttributeName() const -{ - FName attributeName; - if (SocketNameHandle.IsValid()) - { - SocketNameHandle->GetValue(attributeName); - return FText::FromName(attributeName); - } - return FText::FromName(attributeName); -} - -TSharedRef FGAAttributeDetailCustomization::GetSocketTree() -{ - return SNew(SVerticalBox) - + SVerticalBox::Slot() - .AutoHeight() - .MaxHeight(400) - [ - SNew(SGAAttributeWidget) - .OnAttributeSelectedIn(this, &FGAAttributeDetailCustomization::SetSocketName) - ]; -} - -void FGAAttributeDetailCustomization::SetSocketName(FString AttributeNameIn) -{ - FName name; - FName nameToSet = *AttributeNameIn; - SocketNameHandle->GetValue(name); - if (name != nameToSet) - { - SocketNameHandle->SetValue(nameToSet); - } -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h deleted file mode 100644 index 7b28395..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributeDetailCustomization.h +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IPropertyTypeCustomization.h" -#include "PropertyHandle.h" - -class FGAAttributeDetailCustomization : public IPropertyTypeCustomization -{ -public: - static TSharedRef MakeInstance(); - /** - * Destructor - */ - virtual ~FGAAttributeDetailCustomization(); - - /** IPropertyTypeCustomization interface */ - virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - - -protected: - /** Cached Property Handle */ - TSharedPtr SocketNameHandle; - - /** Used with Combobox, show up socket tree widget. */ - TSharedRef GetSocketTree(); - - FText GetAttributeName() const; - - void SetSocketName(FString AttributeNameIn); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp deleted file mode 100644 index 347b0d0..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" - - - -//TSharedPtr FGAAttributePanelGraphPinFactory::CreatePin(class UEdGraphPin* InPin) const -//{ -// const UEdGraphSchema_K2* K2Schema = GetDefault(); -// if (InPin->PinType.PinCategory == K2Schema->PC_Struct) -// //&& InPin->PinType.PinSubCategoryObject == FGAAttribute::StaticStruct()) -// { -// -// } -// return nullptr; -//} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h deleted file mode 100644 index 047dc24..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePanelGraphPinFactory.h +++ /dev/null @@ -1,23 +0,0 @@ -#pragma once -#include "SlateBasics.h" -#include "Attributes/GAAttributeGlobals.h" -#include "EdGraph/EdGraphPin.h" -#include "EdGraph/EdGraphSchema.h" -#include "EdGraphSchema_K2.h" -#include "GAAttributePanelGraphPinFactory.h" -#include "GAAttributePin.h" -#include "EdGraphUtilities.h" - -class FGAAttributePanelGraphPinFactory : public FGraphPanelPinFactory -{ - virtual TSharedPtr CreatePin(class UEdGraphPin* InPin) const override - { - const UEdGraphSchema_K2* K2Schema = GetDefault(); - if (InPin->PinType.PinCategory == K2Schema->PC_Struct - && InPin->PinType.PinSubCategoryObject == FGAAttribute::StaticStruct()) - { - return SNew(SGAAttributePin, InPin); - } - return nullptr; - } -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp deleted file mode 100644 index 51b9723..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.cpp +++ /dev/null @@ -1,105 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" - -#include "KismetEditorUtilities.h" - -#include "STextComboBox.h" -#include "EdGraph/EdGraphPin.h" -#include "EdGraph/EdGraphSchema.h" - -#include "Effects/GAGameEffect.h" -#include "GAGlobalTypes.h" -#include "Attributes/GAAttributesBase.h" -#include "SGAAttributeWidget.h" -#include "GAAttributePin.h" - -void SGAAttributePin::Construct(const FArguments& InArgs, UEdGraphPin* InGraphPinObj) -{ - AttributesList.Empty(); - - SelectedAttribute = InGraphPinObj->GetDefaultAsString(); - SelectedAttribute.RemoveFromStart("(AttributeName=\""); - SelectedAttribute.RemoveFromEnd("\")"); - - for (TObjectIterator ClassIt; ClassIt; ++ClassIt) - { - UClass* Class = *ClassIt; - if (Class->IsChildOf(UGAAttributesBase::StaticClass()) - && !FKismetEditorUtilities::IsClassABlueprintSkeleton(Class)) - { - for (TFieldIterator PropertyIt(Class, EFieldIteratorFlags::ExcludeSuper); PropertyIt; ++PropertyIt) - { - UProperty* Prop = *PropertyIt; - //I need array within array, one for list of attributes, and one for class names. - TSharedPtr attribute = MakeShareable(new FString(Prop->GetName())); - AttributesList.Add(attribute); - } - } - } - SGraphPin::Construct(SGraphPin::FArguments(), InGraphPinObj); -} -TSharedRef SGAAttributePin::GetDefaultValueWidget() -{ - //AttributesList.Empty(); - return SNew(SVerticalBox) - + SVerticalBox::Slot() - .AutoHeight() - [ - SAssignNew(AttributeComboButton, SComboButton) - .OnGetMenuContent(this, &SGAAttributePin::GetAttributesMenu) - .ButtonContent() - [ - SNew(STextBlock) - .Text(this, &SGAAttributePin::GetSelectedAttributeText) - ] - ]; - //return SNew(STextComboBox) - // .OptionsSource(&AttributesList) - // .OnSelectionChanged(this, &SGAAttributePin::OnAttributeSelected); - //return AttributeComboButton.ToSharedRef(); - -} - -TSharedRef SGAAttributePin::GetAttributesMenu() -{ - return SNew(SVerticalBox) - + SVerticalBox::Slot() - .AutoHeight() - .MaxHeight(400) - [ - SNew(SGAAttributeWidget) - .OnAttributeSelectedIn(this, &SGAAttributePin::OnAttributeSelected) - ]; -} - -FText SGAAttributePin::GetSelectedAttributeText() const -{ - return FText::FromString(SelectedAttribute); -} -void SGAAttributePin::OnAttributeSelected(FString ItemSelected) -{ - SelectedAttribute = ItemSelected; - //FString CurrentValue = GraphPinObj->GetDefaultAsString(); - FString CurrentDefaultValue = GraphPinObj->GetDefaultAsString(); - FString attribute = ItemSelected; - if (CurrentDefaultValue.IsEmpty()) - { - CurrentDefaultValue = FString(TEXT("()")); - } - FString AttributeString = TEXT("("); - if (!attribute.IsEmpty()) - { - AttributeString += TEXT("AttributeName=\""); - AttributeString += attribute; - AttributeString += TEXT("\""); - } - AttributeString += TEXT(")"); - - if (!CurrentDefaultValue.Equals(AttributeString)) - { - GraphPinObj->GetSchema()->TrySetDefaultValue(*GraphPinObj, AttributeString); - } - - //if () -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h deleted file mode 100644 index 74aeb68..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAAttributePin.h +++ /dev/null @@ -1,27 +0,0 @@ -#pragma once -#include "SlateBasics.h" -#include "SGraphPin.h" - -class SGAAttributePin : public SGraphPin -{ -public: - SLATE_BEGIN_ARGS(SGAAttributePin) {} - SLATE_END_ARGS() - -public: - void Construct(const FArguments& InArgs, UEdGraphPin* InGraphPinObj); - - virtual TSharedRef GetDefaultValueWidget() override; - void OnAttributeSelected(FString ItemSelected); -private: - TArray> AttributesList; - - TSharedPtr AttributeComboButton; - - TSharedRef GetAttributesMenu(); - - FText GetSelectedAttributeText() const; - - FString SelectedAttribute; - -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp deleted file mode 100644 index 1784ae6..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.cpp +++ /dev/null @@ -1,79 +0,0 @@ - -#include "AbilityFrameworkEditor.h" -#include "Kismet/KismetMathLibrary.h" -#include "Kismet/KismetArrayLibrary.h" -#include "GameplayTask.h" -#include "Abilities/Tasks/GAAbilityTask.h" -#include "Abilities/GAAbilityBase.h" -#include "KismetCompiler.h" -#include "BlueprintEditorUtils.h" -#include "GAEK2Node_LatentAbilityTaskCall.h" -#include "K2Node_EnumLiteral.h" -#include "BlueprintFunctionNodeSpawner.h" -#include "BlueprintActionDatabaseRegistrar.h" - -#define LOCTEXT_NAMESPACE "K2Node" - -UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); -} - -bool UGAEK2Node_LatentAbilityTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const -{ - bool bIsCompatible = false; - - EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); - bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); - - if (bAllowLatentFuncs) - { - UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); - if (MyBlueprint && MyBlueprint->GeneratedClass) - { - if (MyBlueprint->GeneratedClass->IsChildOf(UGAAbilityBase::StaticClass())) - { - bIsCompatible = true; - } - } - } - return bIsCompatible; -} - - -void UGAEK2Node_LatentAbilityTaskCall::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const -{ - //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); - struct GetMenuActions_Utils - { - static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) - { - UGAEK2Node_LatentAbilityTaskCall* AsyncTaskNode = CastChecked(NewNode); - if (FunctionPtr.IsValid()) - { - UFunction* Func = FunctionPtr.Get(); - UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); - - AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); - AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); - AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; - } - } - }; - - UClass* NodeClass = GetClass(); - //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); - ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* - { - UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); - check(NodeSpawner != nullptr); - NodeSpawner->NodeClass = NodeClass; - - TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); - NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); - return NodeSpawner; - })); -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h deleted file mode 100644 index e81d718..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAbilityTaskCall.h +++ /dev/null @@ -1,20 +0,0 @@ - -#pragma once -#include "EdGraph/EdGraphPin.h" -#include "EdGraphSchema_K2.h" -#include "K2Node_BaseAsyncTask.h" -#include "GAEK2Node_LatentAbilityTaskCall.generated.h" - -UCLASS() -class UGAEK2Node_LatentAbilityTaskCall : public UK2Node_BaseAsyncTask//UK2Node_LatentGameplayTaskCall -{ - GENERATED_BODY() - -public: - UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer); - - // UEdGraphNode interface - virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; - virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; - // End of UEdGraphNode interface -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp deleted file mode 100644 index a5c474a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.cpp +++ /dev/null @@ -1,76 +0,0 @@ - -#include "AbilityFrameworkEditor.h" -#include "Kismet/KismetMathLibrary.h" -#include "Kismet/KismetArrayLibrary.h" -#include "KismetCompiler.h" -#include "BlueprintEditorUtils.h" -#include "GAEK2Node_LatentAction.h" -#include "K2Node_EnumLiteral.h" -#include "BlueprintFunctionNodeSpawner.h" -#include "BlueprintActionDatabaseRegistrar.h" -#include "LatentActions/AFTaskBase.h" -#define LOCTEXT_NAMESPACE "K2Node" - -UGAEK2Node_LatentAction::UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); -} - -bool UGAEK2Node_LatentAction::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const -{ - bool bIsCompatible = true; - - //EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); - //bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); - - //if (bAllowLatentFuncs) - //{ - // UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); - // if (MyBlueprint && MyBlueprint->GeneratedClass) - // { - // if (MyBlueprint->GeneratedClass->IsChildOf(UGAAbilityBase::StaticClass())) - // { - // bIsCompatible = true; - // } - // } - //} - return bIsCompatible; -} - - -void UGAEK2Node_LatentAction::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const -{ - //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); - struct GetMenuActions_Utils - { - static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) - { - UGAEK2Node_LatentAction* AsyncTaskNode = CastChecked(NewNode); - if (FunctionPtr.IsValid()) - { - UFunction* Func = FunctionPtr.Get(); - UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); - - AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); - AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); - AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; - } - } - }; - - UClass* NodeClass = GetClass(); - //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); - ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* - { - UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); - check(NodeSpawner != nullptr); - NodeSpawner->NodeClass = NodeClass; - - TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); - NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); - return NodeSpawner; - })); -} - -#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h deleted file mode 100644 index 5e88133..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEK2Node_LatentAction.h +++ /dev/null @@ -1,19 +0,0 @@ - -#pragma once -#include "EdGraph/EdGraphPin.h" -#include "EdGraphSchema_K2.h" -#include "K2Node_BaseAsyncTask.h" -#include "GAEK2Node_LatentAction.generated.h" - -UCLASS() -class UGAEK2Node_LatentAction : public UK2Node_BaseAsyncTask -{ - GENERATED_BODY() - -public: - UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer); - - // UEdGraphNode interface - virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; - virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp deleted file mode 100644 index 2eedb36..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.cpp +++ /dev/null @@ -1,856 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "IDetailsView.h" -#include "PropertyEditorModule.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" -#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" -#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" -#include "Editor/PropertyEditor/Private/SDetailsView.h" - -#include "STextCombobox.h" -#include "STreeView.h" -#include "SButton.h" -#include "STextBlock.h" - -#include "ClassViewerModule.h" -#include "ClassViewerFilter.h" - -#include "EditorClassUtils.h" -#include "IAssetTools.h" -#include "AssetRegistryModule.h" -#include "Dialogs/DlgPickAssetPath.h" -#include "AssetToolsModule.h" -#include "KismetCompilerModule.h" -#include "Kismet2/KismetEditorUtilities.h" -#include "Kismet2/CompilerResultsLog.h" -#include "EffectEditor/GAEffectEditor.h" -#include "SMyBlueprint.h" -#include "SKismetInspector.h" - -#include "SGAAttributeWidget.h" -#include "Effects/GAGameEffect.h" -#include "Effects/GAEffectBlueprint.h" -#include "EffectEditor/GAEffectBlueprintFactory.h" -#include "GAEffectClassStructWidget.h" -#include "GAEffectDetails.h" -#include "AFAbilityActionSpecDetails.h" -#include "AFAbilityPeriodSpecDetails.h" -#include "AFAbilityCooldownSpecDetails.h" -#include "Abilities/AFAbilityActivationSpec.h" -#include "Abilities/AFAbilityPeriodSpec.h" -#include "Abilities/AFAbilityCooldownSpec.h" - -class SEffectCreateDialog : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SEffectCreateDialog) {} - SLATE_ARGUMENT(TSet, MetaClass); - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs) - { - bOkClicked = false; - ParentClass = UGAGameEffectSpec::StaticClass(); - MetaClass = InArgs._MetaClass; - ChildSlot - [ - SNew(SBorder) - .Visibility(EVisibility::Visible) - .BorderImage(FEditorStyle::GetBrush("Menu.Background")) - [ - SNew(SBox) - .Visibility(EVisibility::Visible) - .WidthOverride(500.0f) - [ - SNew(SVerticalBox) - + SVerticalBox::Slot() - .FillHeight(1) - [ - SNew(SBorder) - .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) - .Content() - [ - SAssignNew(ParentClassContainer, SVerticalBox) - ] - ] - - // Ok/Cancel buttons - + SVerticalBox::Slot() - .AutoHeight() - .HAlign(HAlign_Right) - .VAlign(VAlign_Bottom) - .Padding(8) - [ - SNew(SUniformGridPanel) - .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) - .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) - .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) - + SUniformGridPanel::Slot(0, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectCreateDialog::OkClicked) - .Text(FText::FromString("OK")) - ] - + SUniformGridPanel::Slot(1, 0) - [ - SNew(SButton) - .HAlign(HAlign_Center) - .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectCreateDialog::CancelClicked) - .Text(FText::FromString("Cancel")) - ] - ] - ] - ] - ]; - - MakeParentClassPicker(); - } - - /** Sets properties for the supplied GameplayAbilitiesBlueprintFactory */ - bool ConfigureProperties(FGAEffectClassStructWidget* InGameplayAbilitiesBlueprintFactory) - { - GameplayAbilitiesBlueprintFactory = InGameplayAbilitiesBlueprintFactory; - - TSharedRef Window = SNew(SWindow) - .Title(FText::FromString("Create Game Effect Blueprint")) - .ClientSize(FVector2D(400, 700)) - .SupportsMinimize(false).SupportsMaximize(false) - [ - AsShared() - ]; - - PickerWindow = Window; - - GEditor->EditorAddModalWindow(Window); - GameplayAbilitiesBlueprintFactory = nullptr; - - return bOkClicked; - } - -private: - class FGameplayAbilityBlueprintParentFilter : public IClassViewerFilter - { - public: - /** All children of these classes will be included unless filtered out by another setting. */ - TSet< const UClass* > AllowedChildrenOfClasses; - - FGameplayAbilityBlueprintParentFilter() {} - - virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; - } - - virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; - } - }; - - /** Creates the combo menu for the parent class */ - void MakeParentClassPicker() - { - // Load the classviewer module to display a class picker - FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); - - // Fill in options - FClassViewerInitializationOptions Options; - Options.Mode = EClassViewerMode::ClassPicker; - Options.bShowDisplayNames = true; - // Only allow parenting to base blueprints. - Options.bIsBlueprintBaseOnly = true; - - TSharedPtr Filter = MakeShareable(new FGameplayAbilityBlueprintParentFilter); - - // All child child classes of UGameplayAbility are valid. - Filter->AllowedChildrenOfClasses = MetaClass; - Options.ClassFilter = Filter; - - ParentClassContainer->ClearChildren(); - ParentClassContainer->AddSlot() - .AutoHeight() - [ - SNew(STextBlock) - .Text(FText::FromString("Parent Class:")) - .ShadowOffset(FVector2D(1.0f, 1.0f)) - ]; - - ParentClassContainer->AddSlot() - [ - ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCreateDialog::OnClassPicked)) - ]; - } - - /** Handler for when a parent class is selected */ - void OnClassPicked(UClass* ChosenClass) - { - ParentClass = ChosenClass; - } - - /** Handler for when ok is clicked */ - FReply OkClicked() - { - if (GameplayAbilitiesBlueprintFactory) - { - GameplayAbilitiesBlueprintFactory->ParentClass = ParentClass.Get(); - } - - CloseDialog(true); - - return FReply::Handled(); - } - - void CloseDialog(bool bWasPicked = false) - { - bOkClicked = bWasPicked; - if (PickerWindow.IsValid()) - { - PickerWindow.Pin()->RequestDestroyWindow(); - } - } - - /** Handler for when cancel is clicked */ - FReply CancelClicked() - { - CloseDialog(); - return FReply::Handled(); - } - - FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) - { - if (InKeyEvent.GetKey() == EKeys::Escape) - { - CloseDialog(); - return FReply::Handled(); - } - return SWidget::OnKeyDown(MyGeometry, InKeyEvent); - } - -private: - /** The factory for which we are setting up properties */ - FGAEffectClassStructWidget* GameplayAbilitiesBlueprintFactory; - - /** A pointer to the window that is asking the user to select a parent class */ - TWeakPtr PickerWindow; - - /** The container for the Parent Class picker */ - TSharedPtr ParentClassContainer; - - /** The selected class */ - TWeakObjectPtr ParentClass; - - TSet MetaClass; - - /** True if Ok was clicked */ - bool bOkClicked; -}; -class FPropertyEditorClassFilter : public IClassViewerFilter -{ -public: - /** The meta class for the property that classes must be a child-of. */ - const UClass* ClassPropertyMetaClass; - - /** The interface that must be implemented. */ - const UClass* InterfaceThatMustBeImplemented; - - /** Whether or not abstract classes are allowed. */ - bool bAllowAbstract; - - bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - bool bMatchesFlags = !InClass->HasAnyClassFlags(CLASS_Hidden | CLASS_HideDropDown | CLASS_Deprecated) && - (bAllowAbstract || !InClass->HasAnyClassFlags(CLASS_Abstract)); - - if (bMatchesFlags && InClass->IsChildOf(ClassPropertyMetaClass) - && (!InterfaceThatMustBeImplemented || InClass->ImplementsInterface(InterfaceThatMustBeImplemented))) - { - return true; - } - - return false; - } - - virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - bool bMatchesFlags = !InClass->HasAnyClassFlags(CLASS_Hidden | CLASS_HideDropDown | CLASS_Deprecated) && - (bAllowAbstract || !InClass->HasAnyClassFlags(CLASS_Abstract)); - - if (bMatchesFlags && InClass->IsChildOf(ClassPropertyMetaClass) - && (!InterfaceThatMustBeImplemented || InClass->ImplementsInterface(InterfaceThatMustBeImplemented))) - { - return true; - } - - return false; - } -}; - -FGAEffectClassStructWidget::~FGAEffectClassStructWidget() -{ - -} - -TSharedRef FGAEffectClassStructWidget::CreateEffectClassWidget(UObject* OwnerObject) -{ - OuterObject = OwnerObject; - //TAttribute EffectName;// (); - //EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectClassStructWidget::GetClassName)); - return SNew(SHorizontalBox) - + SHorizontalBox::Slot() - .AutoWidth() - [ - SAssignNew(ComboButton, SComboButton) - .OnGetMenuContent(this, &FGAEffectClassStructWidget::GenerateClassPicker) - .ContentPadding(FMargin(2.0f, 2.0f)) - .ToolTipText(this, &FGAEffectClassStructWidget::GetDisplayValueAsString) - .ButtonContent() - [ - SNew(STextBlock) - .Text(this, &FGAEffectClassStructWidget::GetDisplayValueAsString) - //.Font(InArgs._Font) - ] - ] - +SHorizontalBox::Slot() - .AutoWidth() - [ - MakeNewBlueprintButton() - ] - +SHorizontalBox::Slot() - .AutoWidth() - [ - SNew(SButton) - .OnClicked(this, &FGAEffectClassStructWidget::OnEditButtonClicked) - [ - SNew(STextBlock) - .Text(FText::FromString("Edit")) - ] - ]; -} - -FText FGAEffectClassStructWidget::GetClassName() const -{ - if (StructPropertyHandle.IsValid()) - { - return StructPropertyHandle->GetPropertyDisplayName(); - } - return FText::FromString("No Effect Selected"); -} -static FString GetClassDisplayName(const UObject* Object) -{ - const UClass* Class = Cast(Object); - if (Class != NULL) - { - UBlueprint* BP = UBlueprint::GetBlueprintFromClass(Class); - if (BP != NULL) - { - return BP->GetName(); - } - } - return (Object) ? Object->GetName() : "None"; -} -FText FGAEffectClassStructWidget::GetDisplayValueAsString() const -{ - static bool bIsReentrant = false; - - // Guard against re-entrancy which can happen if the delegate executed below (SelectedClass.Get()) forces a slow task dialog to open, thus causing this to lose context and regain focus later starting the loop over again - if (!bIsReentrant) - { - TGuardValue(bIsReentrant, true); - if (EffectPropertyHandle.IsValid()) - { - UObject* ObjectValue = NULL; - FPropertyAccess::Result Result = EffectPropertyHandle->GetValue(ObjectValue); - - if (Result == FPropertyAccess::Success && ObjectValue != NULL) - { - return FText::FromString(GetClassDisplayName(ObjectValue)); - } - - return FText::FromString("None"); - } - - return FText::FromString("None"); - } - else - { - return FText::FromString("None"); - } - -} -UClass* FGAEffectClassStructWidget::GetClassFromString(const FString& ClassName) -{ - if (ClassName.IsEmpty() || ClassName == "None") - { - return nullptr; - } - - UClass* Class = FindObject(ANY_PACKAGE, *ClassName); - if (!Class) - { - Class = LoadObject(nullptr, *ClassName); - } - return Class; -} -TSharedRef FGAEffectClassStructWidget::GenerateClassPicker() -{ - FClassViewerInitializationOptions Options; - Options.bShowUnloadedBlueprints = true; - Options.bShowNoneOption = true; - - if (EffectPropertyHandle.IsValid()) - { - Options.PropertyHandle = EffectPropertyHandle; - } - - - class FGameplayAbilityBlueprintParentFilter : public IClassViewerFilter - { - public: - /** All children of these classes will be included unless filtered out by another setting. */ - TSet< const UClass* > AllowedChildrenOfClasses; - bool bAllowAbstract; - FGameplayAbilityBlueprintParentFilter() {} - - virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - if (!bAllowAbstract) - { - return !InClass->HasAnyClassFlags(CLASS_Abstract) && InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; - } - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; - } - - virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override - { - // If it appears on the allowed child-of classes list (or there is nothing on that list) - return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; - } - }; - TSharedPtr ClassFilter = MakeShareable(new FGameplayAbilityBlueprintParentFilter); - - TSet MetaClass; - TSharedPtr EffectPropertyHandleLocal = StructPropertyHandle->GetParentHandle(); - if (EffectPropertyHandleLocal.IsValid()) - { - FString ClassName = EffectPropertyHandleLocal->GetMetaData("AllowedClass"); - TArray ClassNames; - //ClassName.Pars - ClassName.ParseIntoArray(ClassNames, TEXT(",")); - if (ClassNames.Num() > 0) - { - for (const FString& name : ClassNames) - { - UClass* temp = GetClassFromString(name); - if (temp) - { - MetaClass.Add(temp); - } - } - } - else - { - MetaClass.Add(UGAGameEffectSpec::StaticClass()); - } - } - ClassFilter->AllowedChildrenOfClasses = MetaClass; - Options.ClassFilter = ClassFilter; - //ClassFilter->ClassPropertyMetaClass = MetaClass; - //ClassFilter->InterfaceThatMustBeImplemented = nullptr;// UInterface::StaticClass(); - ClassFilter->bAllowAbstract = false; - Options.bIsBlueprintBaseOnly = true; - Options.bIsPlaceableOnly = false; - Options.DisplayMode = EClassViewerDisplayMode::TreeView;// : EClassViewerDisplayMode::ListView; - Options.bAllowViewOptions = true; - Options.bShowDisplayNames = true; - - FOnClassPicked OnPicked(FOnClassPicked::CreateRaw(this, &FGAEffectClassStructWidget::OnClassPicked)); - - return SNew(SBox) - .WidthOverride(280) - [ - SNew(SVerticalBox) - + SVerticalBox::Slot() - .AutoHeight() - .MaxHeight(500) - [ - FModuleManager::LoadModuleChecked("ClassViewer").CreateClassViewer(Options, OnPicked) - ] - ]; -} - -void FGAEffectClassStructWidget::OnClassPicked(UClass* InClass) -{ - if (!InClass) - { - SendToObjects(TEXT("None")); - } - else - { - SendToObjects(InClass->GetPathName()); - } - - ComboButton->SetIsOpen(false); -} - -void FGAEffectClassStructWidget::SendToObjects(const FString& NewValue) -{ - if (EffectPropertyHandle.IsValid()) - { - EffectPropertyHandle->SetValueFromFormattedString(NewValue); - } - else - { - UClass* NewClass = FindObject(ANY_PACKAGE, *NewValue); - if (!NewClass) - { - NewClass = LoadObject(nullptr, *NewValue); - } - //OnSetClass.Execute(NewClass); - } -} - -TSharedRef FGAEffectClassStructWidget::MakeNewBlueprintButton() -{ - return - SNew(SButton) - .Text(FText::FromString("New Blueprint")) - //.ToolTipText(OptionalToolTipText.Get().IsEmpty() ? LOCTEXT("NewBlueprintButtonToolTipText", "Create New Blueprint") : OptionalToolTipText) - .OnClicked(this, &FGAEffectClassStructWidget::MakeNewBlueprint) - .IsEnabled(true) - .IsFocusable(false) - .ButtonColorAndOpacity(FSlateColor::UseForeground()) - [ - SNew(SImage) - .Image(FEditorStyle::GetBrush("PropertyWindow.Button_CreateNewBlueprint")) - ]; -} - -FReply FGAEffectClassStructWidget::MakeNewBlueprint() -{ - TSet MetaClass; - TSharedPtr EffectPropertyHandleLocal = StructPropertyHandle->GetParentHandle(); - FString ClassName = EffectPropertyHandleLocal->GetMetaData("AllowedClass"); - TArray ClassNames; - //ClassName.Pars - ClassName.ParseIntoArray(ClassNames, TEXT(",")); - if (ClassNames.Num() > 0) - { - for (const FString& name : ClassNames) - { - UClass* temp = GetClassFromString(name); - if (temp) - { - MetaClass.Add(temp); - } - } - } - else - { - MetaClass.Add(UAFEffectSpecBase::StaticClass()); - } - TSharedRef Dialog = SNew(SEffectCreateDialog).MetaClass(MetaClass); - Dialog->ConfigureProperties(this); - if (ParentClass) - { - check(FKismetEditorUtilities::CanCreateBlueprintOfClass(UGAGameEffectSpec::StaticClass())); - - // Pre-generate a unique asset name to fill out the path picker dialog with. - FString OuterName; - FString OuterName2; - - if (StructPropertyHandle.IsValid()) - { - UProperty* prop = StructPropertyHandle->GetProperty(); - OuterName = prop->GetOuter()->GetName(); - OuterName = prop->GetPathName(); - OuterName = StructPropertyHandle->GeneratePathToProperty(); - } - - - UPackage* OuterMost = OuterObject->GetOutermost(); - FString AssetName = OuterObject->GetName(); - FString Path = OuterMost->GetFullName(); - FJsonSerializableArray OutArray; - Path = Path.RightChop(7); - Path.ParseIntoArrayWS(OutArray, TEXT("/")); - FString OutAsset = OutArray[OutArray.Num() - 1]; - OutArray.RemoveAt(OutArray.Num() - 1); - // OutArray.RemoveAt(0); - FString OutPath = "/"; - for (const FString& str : OutArray) - { - OutPath += str; - OutPath += "/"; - } - OutPath += FString::Printf(TEXT("E_%s_"), *OutAsset); - - FString NewNameSuggestion = "";// FString::Printf(TEXT("E_%s_"), *OutAsset); - UClass* BlueprintClass = UGAGameEffectSpec::StaticClass(); - UClass* BlueprintGeneratedClass = UGAEffectBlueprint::StaticClass(); - - IKismetCompilerInterface& KismetCompilerModule = FModuleManager::LoadModuleChecked("KismetCompiler"); - KismetCompilerModule.GetBlueprintTypesForClass(UGAGameEffectSpec::StaticClass(), BlueprintClass, BlueprintGeneratedClass); - - FString PackageName = OutPath + NewNameSuggestion; - FString OutPackageName; - FString Name; - FAssetToolsModule& AssetToolsModule = FModuleManager::LoadModuleChecked("AssetTools"); - AssetToolsModule.Get().CreateUniqueAssetName(PackageName, NewNameSuggestion, OutPackageName, Name); - - - - TSharedPtr PickAssetPathWidget = - SNew(SDlgPickAssetPath) - .Title(FText::FromString("Create New Effect")) - .DefaultAssetPath(FText::FromString(OutPath)); - UBlueprint* Blueprint = nullptr; - if (EAppReturnType::Ok == PickAssetPathWidget->ShowModal()) - { - // Get the full name of where we want to create the physics asset. - FString UserPackageName = PickAssetPathWidget->GetFullAssetPath().ToString(); - FName BPName(*FPackageName::GetLongPackageAssetName(UserPackageName)); - - // Check if the user inputed a valid asset name, if they did not, give it the generated default name - if (BPName == NAME_None) - { - // Use the defaults that were already generated. - UserPackageName = PackageName; - BPName = *Name; - } - - // Then find/create it. - UPackage* Package = CreatePackage(NULL, *UserPackageName); - check(Package); - - // Create and init a new Blueprint - Blueprint = FKismetEditorUtilities::CreateBlueprint(ParentClass, Package, BPName, BPTYPE_Normal, UGAEffectBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), FName("LevelEditorActions")); - if (Blueprint) - { - // Notify the asset registry - FAssetRegistryModule::AssetCreated(Blueprint); - - // Mark the package dirty... - Package->MarkPackageDirty(); - } - } - if (Blueprint != NULL && Blueprint->GeneratedClass ) - { - UGAEffectBlueprint* eff = Cast(Blueprint); - if (eff) - { - EffectPropertyHandle->SetValueFromFormattedString(eff->GeneratedClass->GetPathName()); - - FAssetEditorManager::Get().OpenEditorForAsset(eff); - return FReply::Handled(); - } - } - } - return FReply::Unhandled(); -} - -FReply FGAEffectClassStructWidget::OnEditButtonClicked() -{ - if (EffectEditorWindow.IsValid()) - { - //EffectEditorWindow->RequestDestroyWindow(); - EffectEditorWindow->DestroyWindowImmediately(); - EffectEditorWindow.Reset(); - // already open, just show it - //EffectEditorWindow->BringToFront(true); - } - - { - UObject* OutVal = nullptr; - UGAEffectBlueprint* Blueprint = nullptr; - UProperty* Prop; - UBlueprintGeneratedClass* Class = nullptr; - if (EffectPropertyHandle.IsValid()) - { - EffectPropertyHandle->GetValue(OutVal); - EffectPropertyHandle->CreatePropertyValueWidget(); - Prop = EffectPropertyHandle->GetProperty(); - - if (OutVal) - { - Class = Cast(OutVal); - if (Class && Class->ClassGeneratedBy && Class->ClassGeneratedBy->IsA(UGAEffectBlueprint::StaticClass())) - { - Blueprint = Cast(Class->ClassGeneratedBy); - } - } - } - - FDetailsViewArgs Args; - Args.bHideSelectionTip = true; - Args.bLockable = false; - FPropertyEditorModule& PropertyEditorModule = FModuleManager::GetModuleChecked("PropertyEditor"); - TSharedRef DetailView = PropertyEditorModule.CreateDetailView(Args); - TArray InObjects; - if (Blueprint) - { - EditedBlueprint = Blueprint; - if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityActivationSpec::StaticClass())) - { - DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityActivationSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); - } - else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityPeriodSpec::StaticClass())) - { - DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityPeriodSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); - } - else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityCooldownSpec::StaticClass())) - { - DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityCooldownSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); - } - else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass())) - { - // DetailView->UnregisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass()); - // DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); - } - } - if(!Class) - { - return FReply::Unhandled(); - } - if (!Class->ClassDefaultObject) - { - return FReply::Unhandled(); - } - //DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); - InObjects.Add(Class->ClassDefaultObject); - DetailView->SetObjects(InObjects); - FString WindowTitle = "Effect Editor: "; - WindowTitle += Blueprint->GetName(); - EffectEditorWindow = SNew(SWindow) - .Title(FText::FromString(WindowTitle)) - .HasCloseButton(true) - .ClientSize(FVector2D(600, 400)); - EffectEditorWindow->SetContent( - SNew(SBorder) - .BorderImage(FEditorStyle::GetBrush(TEXT("PropertyWindow.WindowBorder"))) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - .AutoHeight() - .MaxHeight(24.0f) - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(this, &FGAEffectClassStructWidget::OnSaveButtonClicked) - [ - SNew(STextBlock) - .Text(FText::FromString("Save")) - ] - ] - + SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(this, &FGAEffectClassStructWidget::OnSaveCloseButtonClicked) - [ - SNew(STextBlock) - .Text(FText::FromString("Save/Close")) - ] - ] - + SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(this, &FGAEffectClassStructWidget::OnCloseButtonClicked) - .IsEnabled(true) - .IsFocusable(false) - [ - SNew(STextBlock) - .Text(FText::FromString("Close")) - ] - ] - ] - +SVerticalBox::Slot() - .FillHeight(1) - [ - DetailView - ] - ] - ); - - if (FGlobalTabmanager::Get()->GetRootWindow().IsValid()) - { - FSlateApplication::Get().AddWindowAsNativeChild(EffectEditorWindow.ToSharedRef(), FGlobalTabmanager::Get()->GetRootWindow().ToSharedRef()); - } - else - { - FSlateApplication::Get().AddWindow(EffectEditorWindow.ToSharedRef()); - } - } - - return FReply::Handled(); -} -FReply FGAEffectClassStructWidget::OnSaveButtonClicked() -{ - if (EditedBlueprint) - { - FCompilerResultsLog LogResults; - LogResults.BeginEvent(TEXT("Compile")); - LogResults.bLogDetailedResults = false; - LogResults.EventDisplayThresholdMs = 0.1; - EBlueprintCompileOptions CompileOptions = EBlueprintCompileOptions::None; - CompileOptions |= EBlueprintCompileOptions::SaveIntermediateProducts; - - FKismetEditorUtilities::CompileBlueprint(EditedBlueprint, CompileOptions, &LogResults); - TArray PackagesToSave; - check((EditedBlueprint != nullptr) && EditedBlueprint->IsAsset()); - PackagesToSave.Add(EditedBlueprint->GetOutermost()); - - FEditorFileUtils::PromptForCheckoutAndSave(PackagesToSave, true, /*bPromptToSave=*/ false); - //EditedBlueprint = nullptr; - } - return FReply::Unhandled(); -} -FReply FGAEffectClassStructWidget::OnSaveCloseButtonClicked() -{ - if (EditedBlueprint) - { - FCompilerResultsLog LogResults; - LogResults.BeginEvent(TEXT("Compile")); - LogResults.bLogDetailedResults = false; - LogResults.EventDisplayThresholdMs = 0.1; - EBlueprintCompileOptions CompileOptions = EBlueprintCompileOptions::None; - CompileOptions |= EBlueprintCompileOptions::SaveIntermediateProducts; - - FKismetEditorUtilities::CompileBlueprint(EditedBlueprint, CompileOptions, &LogResults); - TArray PackagesToSave; - check((EditedBlueprint != nullptr) && EditedBlueprint->IsAsset()); - PackagesToSave.Add(EditedBlueprint->GetOutermost()); - - FEditorFileUtils::PromptForCheckoutAndSave(PackagesToSave, true, /*bPromptToSave=*/ false); - - EditedBlueprint = nullptr; - - if (EffectEditorWindow.IsValid()) - { - EffectEditorWindow->RequestDestroyWindow(); - EffectEditorWindow = nullptr; - - return FReply::Handled(); - } - } - - return FReply::Unhandled(); -} -FReply FGAEffectClassStructWidget::OnCloseButtonClicked() -{ - if (EffectEditorWindow.IsValid()) - { - EffectEditorWindow->RequestDestroyWindow(); - EffectEditorWindow = nullptr; - return FReply::Handled(); - } - return FReply::Unhandled(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h deleted file mode 100644 index f7e557f..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectClassStructWidget.h +++ /dev/null @@ -1,58 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IPropertyTypeCustomization.h" -#include "PropertyHandle.h" - -class FGAEffectClassStructWidget : public TSharedFromThis -{ -protected: - /* Handle to FGAEffectClass*/ - TSharedPtr StructPropertyHandle; - - /* Handle to TSubclassOf SpecClass */ - TSharedPtr EffectPropertyHandle; - - TSharedPtr ComboButton; - - TSharedPtr EffectEditorWindow; - UBlueprint* EditedBlueprint; - UObject* OuterObject; -public: - FGAEffectClassStructWidget() {}; - FGAEffectClassStructWidget(TSharedPtr InStructPropertyHandle, - TSharedPtr InEffectPropertyHandle) - : StructPropertyHandle(InStructPropertyHandle), - EffectPropertyHandle(InEffectPropertyHandle) - {}; - - TSubclassOf ParentClass; - TSharedRef CreateEffectClassWidget(UObject* OwnerObject); - void SetHandles(TSharedPtr InStructPropertyHandle, - TSharedPtr InEffectPropertyHandle) - { - StructPropertyHandle = InStructPropertyHandle; - EffectPropertyHandle = InEffectPropertyHandle; - } - - /** - * Destructor - */ - virtual ~FGAEffectClassStructWidget(); - - FText GetClassName() const; - FText GetDisplayValueAsString() const; - UClass* GetClassFromString(const FString& ClassName); - TSharedRef GenerateClassPicker(); - void OnClassPicked(UClass* InClass); - void SendToObjects(const FString& NewValue); - //FReply OnDrop(const FGeometry& MyGeometry, const FDragDropEvent& DragDropEvent); - TSharedRef MakeNewBlueprintButton(); - FReply MakeNewBlueprint(); - FReply OnEditButtonClicked(); - FReply OnSaveButtonClicked(); - FReply OnSaveCloseButtonClicked(); - FReply OnCloseButtonClicked(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp deleted file mode 100644 index b96e65c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.cpp +++ /dev/null @@ -1,112 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" - -#include "STextCombobox.h" -#include "STreeView.h" - -#include "Effects/GAGameEffect.h" -#include "GAEffectDetails.h" -#include "Effects/AFEffectCustomApplication.h" -#include "AFEffectCustomizationCommon.h" -#include "Abilities/AFAbilityActivationSpec.h" -#include "Abilities/AFAbilityPeriodSpec.h" -#include "Abilities/AFAbilityCooldownSpec.h" -TSharedRef FGAEffectDetails::MakeInstance() -{ - return MakeShareable(new FGAEffectDetails); -} - -void FGAEffectDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - MyDetailLayout = &DetailLayout; - - TArray> Objects; - DetailLayout.GetObjectsBeingCustomized(Objects); - - ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); - UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FGAEffectDetails::OnDurationPolicyChange); - ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - DurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); - PeriodHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); - DurationHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - PeriodHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - DurationCalcTypeHandle = DurationHandle->GetChildHandle("CalculationType"); - PeriodCalcTypeHandle = PeriodHandle->GetChildHandle("CalculationType"); - - DurationCalcTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - PeriodCalcTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); - - for (TWeakObjectPtr obj : Objects) - { - if (UAFEffectSpecBase* Spec = Cast(obj.Get())) - { - /*if (!Spec->IsA(UAFAbilityActivationSpec::StaticClass()) - && !Spec->IsA(UAFAbilityPeriodSpec::StaticClass()) - && !Spec->IsA(UAFAbilityCooldownSpec::StaticClass()) - )*/ - { - bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); - bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); - - if (bIsPeriodic && bIsDuration) - { - DetailLayout.HideProperty(PeriodHandle); - DetailLayout.HideProperty(DurationHandle); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationHandle, "Duration"); - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodHandle, "Period"); - } - else if (!bIsPeriodic && bIsDuration) - { - TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); - TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(MaxStacksProp); - DetailLayout.HideProperty(PeriodHandle); - DetailLayout.HideProperty(DurationHandle); - DetailLayout.HideProperty(MaxStackedDurationHandle); - - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationHandle, "Duration"); - } - else if (bIsPeriodic && !bIsDuration) - { - TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); - TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(MaxStacksProp); - DetailLayout.HideProperty(DurationHandle); - DetailLayout.HideProperty(PeriodHandle); - DetailLayout.HideProperty(MaxStackedDurationHandle); - - FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodHandle, "Period"); - } - else if (!bIsPeriodic && !bIsDuration) - { - TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); - TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); - - DetailLayout.HideProperty(MaxStacksProp); - DetailLayout.HideProperty(DurationHandle); - DetailLayout.HideProperty(PeriodHandle); - DetailLayout.HideProperty(MaxStackedDurationHandle); - DetailLayout.HideCategory("Duration"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); - FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplyTags"); - - } - } - } - } -} -void FGAEffectDetails::OnDurationPolicyChange() -{ - if(MyDetailLayout) - MyDetailLayout->ForceRefreshDetails(); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h deleted file mode 100644 index 8280469..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectDetails.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FGAEffectDetails : public IDetailCustomization -{ - -protected: - bool bIsDuration; - bool bIsPeriodic; - TSharedPtr ApplicationTypeHandle; -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - -private: - TSharedPtr MyProperty; - TSharedPtr DurationHandle; - TSharedPtr PeriodHandle; - TSharedPtr DurationCalcTypeHandle; - TSharedPtr PeriodCalcTypeHandle; - IDetailLayoutBuilder* MyDetailLayout; - FSimpleDelegate UpdateEffectTypeyDelegate; - /** IDetailCustomization interface */ - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; - - void OnDurationPolicyChange(); -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp deleted file mode 100644 index a10c616..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.cpp +++ /dev/null @@ -1,96 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkEditor.h" -#include "IDetailsView.h" -#include "PropertyEditorModule.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" -#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" -#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" -#include "Editor/PropertyEditor/Private/SDetailsView.h" -//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h -#include "STextCombobox.h" -#include "STreeView.h" -#include "SButton.h" -#include "STextBlock.h" - -#include "ClassViewerModule.h" -#include "ClassViewerFilter.h" - -#include "EditorClassUtils.h" -#include "IAssetTools.h" -#include "AssetRegistryModule.h" -#include "Dialogs/DlgPickAssetPath.h" -#include "AssetToolsModule.h" -#include "KismetCompilerModule.h" -#include "Kismet2/KismetEditorUtilities.h" -#include "EffectEditor/GAEffectEditor.h" -#include "SMyBlueprint.h" -#include "SKismetInspector.h" - -#include "SGAAttributeWidget.h" -#include "Effects/GAGameEffect.h" -#include "Effects/GAEffectBlueprint.h" -#include "EffectEditor/GAEffectBlueprintFactory.h" -#include "GAEffectPropertyStructCustomization.h" -#include "GAEffectDetails.h" - -TSharedRef FGAEffectPropertyStructCustomization::MakeInstance() -{ - return MakeShareable(new FGAEffectPropertyStructCustomization); -} - -FGAEffectPropertyStructCustomization::~FGAEffectPropertyStructCustomization() -{ - -} - -void FGAEffectPropertyStructCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - const TArray>& objs = StructCustomizationUtils.GetPropertyUtilities()->GetSelectedObjects(); - UObject* Owner = nullptr; - if (objs.Num() > 0) - { - Owner = objs[0].Get(); - } - StructPropertyHandle = InStructPropertyHandle; - TAttribute EffectName;// (); - EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectPropertyStructCustomization::GetClassName)); - /*SNew(SVerticalBox) - + SVerticalBox::Slot() - [ - SNew(STextBlock) - .Text(EffectName) - ]*/ - EffectPropertyHandle = InStructPropertyHandle->GetChildHandle(TEXT("SpecClass")); //struct - TSharedPtr ClassInStruct = EffectPropertyHandle->GetChildHandle(TEXT("SpecClass")); - EffectClassWidget = MakeShareable(new FGAEffectClassStructWidget()); - EffectClassWidget->SetHandles(EffectPropertyHandle, ClassInStruct); - - HeaderRow - .NameContent() - [ - InStructPropertyHandle->CreatePropertyNameWidget() - ] - .ValueContent() - .HAlign(HAlign_Fill) - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - .AutoWidth() - [ - EffectClassWidget->CreateEffectClassWidget(Owner) - ] - ]; -} -void FGAEffectPropertyStructCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} -FText FGAEffectPropertyStructCustomization::GetClassName() const -{ - if (StructPropertyHandle.IsValid()) - { - return StructPropertyHandle->GetPropertyDisplayName(); - } - return FText::FromString("No Effect Selected"); -} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h deleted file mode 100644 index 4ed717c..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAEffectPropertyStructCustomization.h +++ /dev/null @@ -1,28 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "Attributes/GAAttributeGlobals.h" -#include "GAGlobalTypesEditor.h" - -#include "IPropertyTypeCustomization.h" -#include "PropertyHandle.h" - -#include "GAEffectClassStructWidget.h" -class FGAEffectPropertyStructCustomization : public IPropertyTypeCustomization -{ -protected: - TSharedPtr StructPropertyHandle; - TSharedPtr EffectPropertyHandle; - TSharedPtr EffectClassWidget; -public: - static TSharedRef MakeInstance(); - /** - * Destructor - */ - virtual ~FGAEffectPropertyStructCustomization(); - - /** IPropertyTypeCustomization interface */ - virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - - FText GetClassName() const; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h deleted file mode 100644 index 3f87d07..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/GAGlobalTypesEditor.h +++ /dev/null @@ -1,35 +0,0 @@ - -#pragma once - -#include "GAGlobalTypesEditor.generated.h" - -USTRUCT() -struct FGAAttributeNode -{ - GENERATED_USTRUCT_BODY() -public: - //Name of current node, like class, category, attribute etc. - FString NodeName; - - FString ParentClassName; - - //current attribute for this node); - FString Attribute; - - TWeakPtr ParentNode; - - TArray > ChildNodes; - - /* - List of attributes containe within selected class (ParentClassName) - */ - TArray AttributeNames; - TArray CategoryNames; - FGAAttributeNode() {}; - ~FGAAttributeNode() - { - ParentClassName.Empty(); - Attribute.Empty(); - AttributeNames.Empty(); - }; -}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h deleted file mode 100644 index 6b825c2..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/IAbilityFrameworkEditor.h +++ /dev/null @@ -1,36 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "ModuleManager.h" - - -/** - * The public interface to this module. In most cases, this interface is only public to sibling modules - * within this plugin. - */ -class IAbilityFrameworkEditor : public IModuleInterface -{ -public: - - /** - * Singleton-like access to this module's interface. This is just for convenience! - * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. - * - * @return Returns singleton instance, loading the module on demand if needed - */ - static inline IAbilityFrameworkEditor& Get() - { - return FModuleManager::LoadModuleChecked< IAbilityFrameworkEditor >("AbilityFrameworkEditor"); - } - - /** - * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. - * - * @return True if the module is loaded and ready to use - */ - static inline bool IsAvailable() - { - return FModuleManager::Get().IsModuleLoaded( "AbilityFrameworkEditor" ); - } -}; - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp deleted file mode 100644 index 95453df..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.cpp +++ /dev/null @@ -1,151 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "AbilityFrameworkEditor.h" - -#include "KismetEditorUtilities.h" - -#include "STextComboBox.h" -#include "STreeView.h" -#include "GAGlobalTypesEditor.h" - -#include "Attributes/GAAttributesBase.h" -#include "SGAAttributeWidget.h" - -void SGAAttributeWidget::Construct(const FArguments& InArgs) -{ - AttributesList.Empty(); - AttributesNodes.Empty(); - OnAttributeSelected = InArgs._OnAttributeSelectedIn; - - /* - Intended look: - ClassName - --CategoryName - ----AttributeName - - Or: - ClassName - --CategoryName - ----AttributeType - ------AttributeName - - + search. We really need search! - */ - for (TObjectIterator ClassIt; ClassIt; ++ClassIt) - { - UClass* Class = *ClassIt; - if (Class->IsChildOf(UGAAttributesBase::StaticClass()) - && !FKismetEditorUtilities::IsClassABlueprintSkeleton(Class)) - { - FString className = Class->GetName(); - if (!className.Contains(TEXT("REINST_"))) - { - TSharedPtr classRootNode = MakeShareable(new FGAAttributeNode()); - classRootNode->Attribute = className; - //first let's find root of tree, which is class name - classRootNode->NodeName = className; - FString Category; - //now let's categories as childs - for (TFieldIterator PropertyIt(Class, EFieldIteratorFlags::ExcludeSuper); PropertyIt; ++PropertyIt) - { - UProperty* Prop = *PropertyIt; - Category = Prop->GetMetaData("Category"); - - //check if we already have this category added.. - bool bFoundExistingCategory = false; - if (!Category.IsEmpty()) - { - for (TSharedPtr childNode : classRootNode->ChildNodes) - { - if (childNode->NodeName == Category) - { - bFoundExistingCategory = true; - TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); - attrNode->NodeName = Prop->GetName(); - attrNode->ParentNode = childNode; - childNode->ChildNodes.Add(attrNode); - } - } - if (!bFoundExistingCategory) - { - TSharedPtr categoryNode = MakeShareable(new FGAAttributeNode()); - categoryNode->NodeName = Category; - categoryNode->ParentNode = classRootNode; - classRootNode->ChildNodes.Add(categoryNode); - - TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); - attrNode->NodeName = Prop->GetName(); - attrNode->ParentNode = categoryNode; - categoryNode->ChildNodes.Add(attrNode); - } - } - } - AttributesNodes.Add(classRootNode); - } - } - } - - ChildSlot - [ - SAssignNew(AttributeTreeWidget, STreeView>) - .OnSelectionChanged(this, &SGAAttributeWidget::OnItemSelected) - .TreeItemsSource(&AttributesNodes) - .OnGenerateRow(this, &SGAAttributeWidget::OnGenerateRow) - .OnGetChildren(this, &SGAAttributeWidget::OnGetChildren) - .OnExpansionChanged(this, &SGAAttributeWidget::OnExpansionChanged) - .SelectionMode(ESelectionMode::Single) - ]; -} -SGAAttributeWidget::~SGAAttributeWidget() -{ - AttributesNodes.Empty(); -} - -void SGAAttributeWidget::OnItemSelected(TSharedPtr SelectedItem, ESelectInfo::Type SelectInfo) -{ - if (SelectedItem.IsValid()) - { - if (OnAttributeSelected.IsBound()) - { - OnAttributeSelected.Execute(SelectedItem->NodeName); - } - } -} - -TSharedRef SGAAttributeWidget::OnGenerateRow(TSharedPtr InItem, const TSharedRef& OwnerTable) -{ - return SNew(STableRow< TSharedPtr >, OwnerTable) - [ - SNew(STextBlock) - .Text(FText::FromString(InItem->NodeName)) - ]; -} - -void SGAAttributeWidget::OnGetChildren(TSharedPtr InItem, TArray< TSharedPtr >& OutChildren) -{ - TArray> Children; - - TArray> Children2; - - for (const FString& attribute : InItem->AttributeNames) - { - TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); - attrNode->Attribute = attribute; - Children.Add(attrNode); - } - - for (TSharedPtr childs : InItem->ChildNodes) - { - Children2.Add(childs); - } - - OutChildren += Children2; -} - - -void SGAAttributeWidget::OnExpansionChanged(TSharedPtr InItem, bool bIsExpanded) -{ - -} - - diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h deleted file mode 100644 index 9ff94f5..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/SGAAttributeWidget.h +++ /dev/null @@ -1,64 +0,0 @@ - -#pragma once - -#include "SlateBasics.h" -#include "GAGlobalTypesEditor.h" - -DECLARE_DELEGATE_OneParam(FGAOnAttributeSelected, FString); - -class FAFAttributeNode -{ - FString NodeName; - - FString Attribute; - - TWeakPtr ParentNode; - - TArray > ChildNodes; -}; - -class FAFAttributeTree -{ - -}; - -class SGAAttributeWidget : public SCompoundWidget -{ - SLATE_BEGIN_ARGS(SGAAttributeWidget) - {} - SLATE_EVENT(FGAOnAttributeSelected, OnAttributeSelectedIn) - SLATE_END_ARGS(); - - void Construct(const FArguments& InArgs); - ~SGAAttributeWidget(); -private: - TArray> AttributesList; - - TArray > AttributesNodes; - - TSharedPtr > > AttributeTreeWidget; - - FGAOnAttributeSelected OnAttributeSelected; - - void OnItemSelected(TSharedPtr SelectedItem, ESelectInfo::Type SelectInfo); - /** - * Generate a row widget for the specified item node and table - * - * @param InItem Tag node to generate a row widget for - * @param OwnerTable Table that owns the row - * - * @return Generated row widget for the item node - */ - TSharedRef OnGenerateRow(TSharedPtr InItem, const TSharedRef& OwnerTable); - - /** - * Get children nodes of the specified node - * - * @param InItem Node to get children of - * @param OutChildren [OUT] Array of children nodes, if any - */ - void OnGetChildren(TSharedPtr InItem, TArray< TSharedPtr >& OutChildren); - - - void OnExpansionChanged(TSharedPtr InItem, bool bIsExpanded); -}; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp deleted file mode 100644 index 705f984..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.cpp +++ /dev/null @@ -1,107 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDAbilityGiveTrigger.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "Abilities/GAAbilityBase.h" - -// Sets default values -AAFDAbilityGiveTrigger::AAFDAbilityGiveTrigger() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - RootComp = CreateDefaultSubobject(RootCompName); - RootComponent = RootComp; - - Icon = CreateDefaultSubobject(IconName); - Icon->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); - Trigger = CreateDefaultSubobject(TriggerName); - Trigger->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); - - //Trigger2 = CreateDefaultSubobject(TriggerName); - //Trigger2->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); -} - -// Called when the game starts or when spawned -void AAFDAbilityGiveTrigger::BeginPlay() -{ - Super::BeginPlay(); - Trigger->OnComponentBeginOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::BeginOverlap); - Trigger->OnComponentEndOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::EndOverlap); -} - -// Called every frame -void AAFDAbilityGiveTrigger::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - -void AAFDAbilityGiveTrigger::BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, - int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) -{ - if (!AbilityConfig.AbilityTag.IsValid()) - return; - - IAFAbilityInterface* AbilityInterface = Cast(OtherActor); - if (!AbilityInterface) - return; - - if(!CurrentComponent) - CurrentComponent = AbilityInterface->GetAbilityComp(); - - //FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityReady, AbilityConfig.AbilityTag, - // AbilityConfig.InputTag); - - APawn* pawn = Cast(OtherActor); - if(pawn) - { - AController* AC = pawn->GetController(); - if(AC) - { - TArray Comps = AC->GetComponentsByTag(UAMAbilityManagerComponent::StaticClass(), TEXT("AbilityManager")); - if(Comps.Num() == 1 && !AbilityManager) - { - AbilityManager = Cast(Comps[0]); - } - - if(AbilityManager) - AbilityManager->NativeEquipAbility(AbilityConfig.AbilityTag, AbilityConfig.Group, AbilityConfig.Slot); - } - } - - //if(AbilityManager) - //{ - // - //} - //CurrentComponent->AddOnAbilityReadyDelegate(AbilityConfig.AbilityTag, del); - //CurrentComponent->NativeAddAbilityFromTag(AbilityConfig.AbilityTag, nullptr);// , /*Input*/ ShootInput); -} - -void AAFDAbilityGiveTrigger::EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex) -{ - if (!AbilityConfig.AbilityTag.IsValid()) - return; -} - -void AAFDAbilityGiveTrigger::OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) -{ - UGAAbilityBase* Ability = Cast(CurrentComponent->BP_GetAbilityByTag(InAbilityTag)); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityInputReady, - InAbilityTag, InAbilityInput); - - CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - } - else - { - CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); - } -} - - -void AAFDAbilityGiveTrigger::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h deleted file mode 100644 index 2df3625..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDAbilityGiveTrigger.h +++ /dev/null @@ -1,83 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "Components/BoxComponent.h" -#include "Components/ShapeComponent.h" -#include "GameplayTags.h" -#include "AMTypes.h" -#include "AMAbilityManagerComponent.h" -#include "AFDAbilityGiveTrigger.generated.h" - -USTRUCT(BlueprintType) -struct FAFDAbilityConfig -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - EAMGroup Group; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - EAMSlot Slot; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - TSoftClassPtr AbilityTag; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - TArray InputTag; -}; - -static const FName RootCompName = TEXT("RootComp"); -static const FName TriggerName = TEXT("Trigger"); -static const FName IconName = TEXT("Icon"); -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor -{ - GENERATED_BODY() -protected: - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - USceneComponent* RootComp; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - UBillboardComponent* Icon; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - UBoxComponent* Trigger; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - UShapeComponent* Trigger2; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - FAFDAbilityConfig AbilityConfig; - - UPROPERTY() - class UAFAbilityComponent* CurrentComponent; - UPROPERTY() - class UAMAbilityManagerComponent* AbilityManager; - -public: - // Sets default values for this actor's properties - AAFDAbilityGiveTrigger(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; -protected: - UFUNCTION() - void BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, - int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult); - /** Delegate for notification of end of overlap with a specific component */ - UFUNCTION() - void EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex); - - UFUNCTION() - void OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); - - UFUNCTION() - void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); - - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp deleted file mode 100644 index d33bda5..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.cpp +++ /dev/null @@ -1,11 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDBlueprintFunctionLibrary.h" -#include "AFDManager.h" - - - -//void UAFDBlueprintFunctionLibrary::OpenAbilityDebugger() -//{ -// FAFDManager::Get(); -//} diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h deleted file mode 100644 index 49d85b9..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDBlueprintFunctionLibrary.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Kismet/BlueprintFunctionLibrary.h" -#include "AFDBlueprintFunctionLibrary.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API UAFDBlueprintFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_BODY() -public: - //UFUNCTION(Exec) - // static void OpenAbilityDebugger(); - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp deleted file mode 100644 index dc9608a..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.cpp +++ /dev/null @@ -1,41 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDManager.h" -#include "EngineGlobals.h" -#include "Engine/Engine.h" -#include "Engine/GameViewportClient.h" -#include "Slate.h" -#include "SlateCore.h" -#include "DWManager.h" - -FAFDManager* FAFDManager::Instance = nullptr; - -FAFDManager::FAFDManager() -{ -} - -FAFDManager::~FAFDManager() -{ -} - -void FAFDManager::Init() -{ - Dekstop = SNew(SAFDDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); - GEngine->GameViewport->AddViewportWidgetContent(Dekstop.ToSharedRef()); -} - -FDWWWindowHandle FAFDManager::AddDebugWindow(TSharedPtr InWindowContent) -{ - return FDWManager::Get().CreateWindow(InWindowContent, "Debug"); -} - -#if WITH_EDITORONLY_DATA -void FAFDManager::PIEDestroy() -{ - if (Instance) - { - delete Instance; - Instance = nullptr; - } -} -#endif \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h deleted file mode 100644 index c309907..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AFDManager.h +++ /dev/null @@ -1,38 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SAFDDesktopWidget.h" -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API FAFDManager -{ -private: - static FAFDManager* Instance; - TSharedPtr Dekstop; -protected: - void Init(); -public: - - static FAFDManager& Get() - { - if(!Instance) - { - Instance = new FAFDManager(); - Instance->Init(); - } - return*Instance; - } - -#if WITH_EDITORONLY_DATA - static void PIEDestroy(); -#endif - - - FDWWWindowHandle AddDebugWindow(TSharedPtr InWindowContent); - - FAFDManager(); - ~FAFDManager(); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs index 5d1bd03..f0aa592 100644 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs @@ -8,14 +8,6 @@ public AbilityFrameworkDebugger(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "AbilityFrameworkDebugger/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "AbilityFrameworkDebugger/Private", diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp deleted file mode 100644 index e0ac611..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.cpp +++ /dev/null @@ -1,45 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkDebugger.h" -#include "HAL/IConsoleManager.h" -#include "AFDManager.h" -#if WITH_EDITORONLY_DATA -#include "Editor.H" -#endif -#define LOCTEXT_NAMESPACE "FAbilityFrameworkDebuggerModule" - -void FAbilityFrameworkDebuggerModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module - CommandOpenAbilityDebugger = IConsoleManager::Get().RegisterConsoleCommand( - TEXT("OpenAbilityDebugger"), - TEXT("Opens ability debugger"), - FConsoleCommandDelegate::CreateStatic(OpenAbilityDebugger), - ECVF_Default - ); - -#if WITH_EDITORONLY_DATA - FEditorDelegates::EndPIE.AddRaw(this, &FAbilityFrameworkDebuggerModule::HandlePIEEnd); -#endif //WITH_EDITORONLY_DATA -} - -void FAbilityFrameworkDebuggerModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. - IConsoleManager::Get().UnregisterConsoleObject(CommandOpenAbilityDebugger); -} - -void FAbilityFrameworkDebuggerModule::OpenAbilityDebugger() -{ - FAFDManager::Get(); -} -#if WITH_EDITORONLY_DATA -void FAbilityFrameworkDebuggerModule::HandlePIEEnd(bool InVal) -{ - FAFDManager::PIEDestroy(); -} -#endif -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FAbilityFrameworkDebuggerModule, AbilityFrameworkDebugger) \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h deleted file mode 100644 index d50fefe..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.h +++ /dev/null @@ -1,22 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FAbilityFrameworkDebuggerModule : public IModuleInterface -{ -private: - IConsoleObject* CommandOpenAbilityDebugger; - static void OpenAbilityDebugger(); -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; - -#if WITH_EDITORONLY_DATA - void HandlePIEEnd(bool InVal); -#endif -}; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp deleted file mode 100644 index 48c1171..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.cpp +++ /dev/null @@ -1,74 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDAttributes.h" -#include "SlateOptMacros.h" -#include "SListView.h" -#include "SGridPanel.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDAttributes::Construct(const FArguments& InArgs) -{ - AFInterface = InArgs._AbilityInterface; - ChildSlot - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SOverlay) - +SOverlay::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SListView>) - .ListItemsSource(&Attributes) - .OnGenerateRow(this, &SAFDAttributes::GenerateListRow) - ] - ]; - GatherAttributes(); -} -void SAFDAttributes::GatherAttributes() -{ - if (!AFInterface) - return; - - UGAAttributesBase* AttributesObject = AFInterface->GetAttributes(); - if (!AttributesObject) - return; - - Attributes.Empty(); - for(TFieldIterator It(AttributesObject->GetClass(), EFieldIteratorFlags::IncludeSuper); It; ++It) - { - TSharedPtr AttributeRow = MakeShareable(new FAttributeRow); - UStructProperty* Prop = *It; - FAFAttributeBase* Attr = Prop->ContainerPtrToValuePtr(AttributesObject); - if (Attr) - { - AttributeRow->Attribute = Attr; - AttributeRow->Name = It->GetName(); - AttributeRow->Value = TAttribute::Create(TAttribute::FGetter::CreateSP(AttributeRow.Get(), &FAttributeRow::GetValue)); - } - Attributes.Add(AttributeRow); - } - -} -TSharedRef SAFDAttributes::GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable) -{ - return - SNew(STableRow< TSharedRef >, OwnerTable) - [ - SNew(SGridPanel) - .FillColumn(0, 1) - +SGridPanel::Slot(0,0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(FText::FromString(NotifyName->Name)) - ] - + SGridPanel::Slot(1, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(NotifyName->Value) - ] - ]; -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h deleted file mode 100644 index 57f937b..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDAttributes.h +++ /dev/null @@ -1,39 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" -#include "AFAbilityInterface.h" -#include "Attributes/GAAttributesBase.h" - -struct FAttributeRow : public TSharedFromThis -{ - FString Name; - FAFAttributeBase* Attribute; - TAttribute Value; - - FText GetValue() const - { - return FText::AsNumber(Attribute->GetCurrentValue()); - } -}; - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDAttributes : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDAttributes) - {} - SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) - SLATE_END_ARGS() - - IAFAbilityInterface* AFInterface; - TArray> Attributes; - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - void GatherAttributes(); - TSharedRef GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp deleted file mode 100644 index d2091b4..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.cpp +++ /dev/null @@ -1,203 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDDesktopWidget.h" -#include "SlateCore.h" -#include "Slate.h" -#include "SlateOptMacros.h" -#include "SBoxPanel.h" -#include "SButton.h" -#include "STextBlock.h" -#include "AFDManager.h" -#include "Engine/Engine.h" -#include "Engine/GameViewportClient.h" -#include "GameFramework/PlayerController.h" -#include "SAFDViewportMouseCapture.h" -#include "SAFDEffects.h" -#include "SAFDAttributes.h" - -void SAFDMainWidget::Construct(const FArguments& InArgs) -{ - FWorldContext* WorldContext = GEngine->GetWorldContextFromGameViewport(GEngine->GameViewport); - UWorld* world = WorldContext->World(); - World = world; - FOnClicked OnPickActorClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnPickActorClicked); - - FOnClicked OnAttributesClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnAttributesClicked); - FOnClicked OnEffectsClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnEffectsClicked); - - ChildSlot - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - .FillHeight(1.0f) - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SOverlay) - +SOverlay::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Top) - .AutoHeight() - [ - SNew(STextBlock) - .Text(this, &SAFDMainWidget::GetActorName) - ] - + SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Top) - .MaxHeight(24) - .AutoHeight() - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(OnAttributesClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("Attributes")) - ] - ] - + SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(OnEffectsClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("Effects")) - ] - ] - ] - + SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - .FillWidth(1.0f) - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SAssignNew(Content, SWidgetSwitcher) - ] - ] - ] - ] - +SVerticalBox::Slot() - .MaxHeight(32.0f) - .AutoHeight() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Bottom) - [ - SNew(SButton) - .OnClicked(OnPickActorClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("Pick Actor")) - ] - ] - ]; -} - -FText SAFDMainWidget::GetActorName() const -{ - if(SelectedActor.IsValid()) - { - return FText::FromString(SelectedActor->GetName()); - } - return FText::FromString("Select Actor from viewport."); -} -FReply SAFDMainWidget::OnPickActorClicked() -{ - CaptureWidget = SNew(SAFDViewportMouseCapture); - FSimpleDelegate del = FSimpleDelegate::CreateSP(this, &SAFDMainWidget::OnActorPicked); - CaptureWidget->OnMouseButtonDownDelegate = del; - GEngine->GameViewport->AddViewportWidgetContent(CaptureWidget.ToSharedRef(), 1001); - - return FReply::Handled(); -} - -FReply SAFDMainWidget::OnAttributesClicked() -{ - Content->SetActiveWidgetIndex(0); - return FReply::Handled(); -} -FReply SAFDMainWidget::OnEffectsClicked() -{ - Content->SetActiveWidgetIndex(1); - return FReply::Handled(); -} - -void SAFDMainWidget::OnActorPicked() -{ - APlayerController* PC = World->GetFirstPlayerController(); - FHitResult OutHit; - PC->GetHitResultUnderCursor(ECollisionChannel::ECC_Visibility, false, OutHit); - - if(OutHit.bBlockingHit) - { - AActor* actor = OutHit.GetActor(); - SelectedActor = OutHit.Actor; - if(IAFAbilityInterface* Interface = Cast(OutHit.GetActor())) - { - Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SAFDAttributes) - .AbilityInterface(Interface) - ]; - Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SAFDEffects) - .AbilityInterface(Interface) - ]; - } - } - - GEngine->GameViewport->RemoveViewportWidgetContent(CaptureWidget.ToSharedRef()); -} -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDDesktopWidget::Construct(const FArguments& InArgs) -{ - FOnClicked OnNewDebugWindowClickedDel = FOnClicked::CreateSP(this, &SAFDDesktopWidget::OnNewDebugWindowClicked); - ChildSlot - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Right) - .VAlign(EVerticalAlignment::VAlign_Top) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - [ - SNew(SButton) - .OnClicked(OnNewDebugWindowClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("New Debug Window")) - ] - ] - ] - // Populate the widget - ]; - -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -FReply SAFDDesktopWidget::OnNewDebugWindowClicked() -{ - TSharedPtr wid = SNew(SAFDMainWidget); - FDWWWindowHandle Handle = FAFDManager::Get().AddDebugWindow(wid); - wid->SetWindowHandle(Handle); - return FReply::Handled(); -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h deleted file mode 100644 index 73f612c..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDDesktopWidget.h +++ /dev/null @@ -1,54 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" -#include "SDraggableWindowWidget.h" -#include "SWidgetSwitcher.h" - -class ABILITYFRAMEWORKDEBUGGER_API SAFDMainWidget : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDMainWidget) - {} - SLATE_END_ARGS() -protected: - TWeakObjectPtr World; - TWeakObjectPtr SelectedActor; - TSharedPtr Content; - FDWWWindowHandle WindowHandle; - TSharedPtr CaptureWidget; - /** Constructs this widget with InArgs */ -public: - void Construct(const FArguments& InArgs); -protected: - FReply OnPickActorClicked(); - FReply OnAttributesClicked(); - FReply OnEffectsClicked(); - - void OnActorPicked(); - - FText GetActorName() const; -public: - void SetWindowHandle(const FDWWWindowHandle& InHandle) - { - WindowHandle = InHandle; - } -}; - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDDesktopWidget : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDDesktopWidget) - {} - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - - FReply OnNewDebugWindowClicked(); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp deleted file mode 100644 index babb94a..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDEffectInspector.h" -#include "SlateOptMacros.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDEffectInspector::Construct(const FArguments& InArgs) -{ - /* - ChildSlot - [ - // Populate the widget - ]; - */ -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h deleted file mode 100644 index e9de984..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffectInspector.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDEffectInspector : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDEffectInspector) - {} - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp deleted file mode 100644 index 53bd36c..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.cpp +++ /dev/null @@ -1,105 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDEffects.h" -#include "SlateOptMacros.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDEffects::Construct(const FArguments& InArgs) -{ - AFInterface = InArgs._AbilityInterface; - AbilityComponent = AFInterface->GetAbilityComp(); - - InitializeEffects(); - ChildSlot - [ - SNew(SOverlay) - + SOverlay::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SAssignNew(ListView, SListView>) - .ListItemsSource(&Effects) - .OnGenerateRow(this, &SAFDEffects::GenerateListRow) - ] - ]; - -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION -SAFDEffects::~SAFDEffects() -{ - -} - -void SAFDEffects::InitializeEffects() -{ - if (!AbilityComponent.IsValid()) - return; - - //ListView->RebuildList(); -} - - -TSharedRef SAFDEffects::GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable) -{ - return - SNew(STableRow< TSharedRef >, OwnerTable) - [ - SNew(SGridPanel) - .FillColumn(0, 1) - /*.FillColumn(1,1) - .FillColumn(2,1)*/ - + SGridPanel::Slot(0, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(FText::FromString(EffectRow->EffectClassName)) - ] - + SGridPanel::Slot(1, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(EffectRow->TimeRemaining) - ] - + SGridPanel::Slot(2, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(EffectRow->PeriodTime) - ] - ]; -} - -void SAFDEffects::OnEffectApplied(FGAEffectHandle InHandle) -{ - TSharedPtr Row = MakeShareable(new FAFDEffectRow); - UE_LOG(LogTemp, Warning, TEXT("SAFDEffects::OnEffectAppliede")); - Effects.Add(Row); - - ListView->RebuildList(); -} -void SAFDEffects::OnEffectRemoved(FGAEffectHandle InHandle) -{ - class Predicate - { - FGAEffectHandle HandleC; - public: - Predicate(const FGAEffectHandle& InH) - :HandleC(InH) - {} - bool operator()(const FAFDEffectRow& Other) const - { - return HandleC == Other.Handle; - } - bool operator()(TSharedPtr Other) const - { - return HandleC == Other->Handle; - } - }; - int32 Idx = Effects.IndexOfByPredicate(Predicate(InHandle)); //Effects.IndexOfByKey(InHandle); - if(Idx > -1) - { - Effects.RemoveAt(Idx); - } - - ListView->RebuildList(); -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h deleted file mode 100644 index 6d17270..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDEffects.h +++ /dev/null @@ -1,82 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" - -#include "GAGlobalTypes.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" - -struct FAFDEffectRow : public TSharedFromThis -{ - FString EffectClassName; - FGAEffectHandle Handle; - TAttribute TimeRemaining; - TAttribute PeriodTime; - TWeakObjectPtr AbilityComponent; - - FText GetTimeRemaining() const - { - return FText::AsNumber(0); - //return FText::AsNumber(AbilityComponent->GameEffectContainer.GetRemainingTime(Handle)); - } - - FText GetPeriodTime() const - { - return FText::AsNumber(0); - //return FText::AsNumber(RepInfo->GetPeriodTime(static_cast(FPlatformTime::Seconds()))); - } - - const bool operator==(const FAFDEffectRow& Other) const - { - return Handle == Other.Handle; - } - - const bool operator==(const FGAEffectHandle& InHandle) const - { - return Handle == InHandle; - } - const bool operator==(FGAEffectHandle InHandle) const - { - return Handle == InHandle; - } - const bool operator==(TSharedPtr InHandle) const - { - return Handle == InHandle->Handle; - } -}; - - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDEffects : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDEffects) - {} - SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) - SLATE_END_ARGS() -protected: - IAFAbilityInterface* AFInterface; - TWeakObjectPtr AbilityComponent; - TSharedPtr>> ListView; - FDelegateHandle OnEffectAppliedHandle; - FDelegateHandle OnEffectRemovedHandle; - FDelegateHandle OnEffectExpiredHandle; - - TArray> Effects; - -public: - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - ~SAFDEffects(); -protected: - TSharedRef GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable); - void InitializeEffects(); - void OnEffectApplied(FGAEffectHandle InHandle); - void OnEffectRemoved(FGAEffectHandle InHandle); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp deleted file mode 100644 index 5560253..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDViewportMouseCapture.h" -#include "SlateOptMacros.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDViewportMouseCapture::Construct(const FArguments& InArgs) -{ - /* - ChildSlot - [ - // Populate the widget - ]; - */ -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -FReply SAFDViewportMouseCapture::OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) -{ - OnMouseButtonDownDelegate.ExecuteIfBound(); - return FReply::Handled(); -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h deleted file mode 100644 index 30e79b2..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/SAFDViewportMouseCapture.h +++ /dev/null @@ -1,24 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDViewportMouseCapture : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDViewportMouseCapture) - {} - SLATE_END_ARGS() - - FSimpleDelegate OnMouseButtonDownDelegate; - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - - virtual FReply OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) override; -}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp deleted file mode 100644 index 38779ca..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.cpp +++ /dev/null @@ -1,451 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AMAbilityManagerComponent.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.h" - -// Sets default values for this component's properties -UAMAbilityManagerComponent::UAMAbilityManagerComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - bWantsInitializeComponent = true; - SetIsReplicated(true); - // ... -} - - -// Called when the game starts -void UAMAbilityManagerComponent::BeginPlay() -{ - Super::BeginPlay(); - //OnNextGroupDelegate = FGroupConfirmDelegate::(this, UAMAbilityManagerComponent::OnNextGroupConfirmed); - // ... - -} -void UAMAbilityManagerComponent::InitializeComponent() -{ - uint8 GroupNum = Groups.Num(); - - AbilitySet.SetNum(GroupNum); - AbilityTagsSet.SetNum(GroupNum); - for(int32 Idx = 0; Idx < GroupNum; Idx++) - { - AbilitySet[Idx].SetNum(Groups[Idx].SlotNum); - AbilityTagsSet[Idx].SetNum(Groups[Idx].SlotNum); - } -} - -// Called every frame -void UAMAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} -void UAMAbilityManagerComponent::BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent) -{ - if (!AbilityComponent) - return; - - for (const FGameplayTag& Input : InputsToBind) - { - AbilityComponent->BindAbilityToAction(InputComponent, Input); - } -} - -UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) -{ - return AbilitySet.Num() >= Groups.Num() ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; -} -void UAMAbilityManagerComponent::SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility) -{ - if (AbilitySet.Num() < Groups.Num()) - return; - - AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbility; -} -void UAMAbilityManagerComponent::RemoveAbility(EAMGroup InGroup, EAMSlot InSlot) -{ - if (AbilitySet.Num() < Groups.Num()) - return; - - AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset();; -} - -TArray UAMAbilityManagerComponent::GetInputTag(EAMGroup InGroup, EAMSlot InSlot) -{ - return InputSetup.GetInputs(InGroup, InSlot); -} -void UAMAbilityManagerComponent::SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag) -{ - -} - -TSoftClassPtr UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) -{ - if (AbilityTagsSet.IsValidIndex(AMEnumToInt(InGroup)) - && AbilityTagsSet[AMEnumToInt(InGroup)].IsValidIndex(AMEnumToInt(InSlot))) - { - return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; - } - return TSoftClassPtr(); -} -void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag) -{ - AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; -} -void UAMAbilityManagerComponent::RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot) -{ - AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset(); -} - -void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - TArray IAbilityInput; - - if(ActiveGroup == InGroup) - IAbilityInput = GetInputTag(InGroup, InSlot); - - FAFOnAbilityReady del; - //if (IsClient()) - { - del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, - IAbilityInput, InGroup, InSlot, bBindInput); - AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - } - - AbilityComp->NativeAddAbility(InAbilityTag, IAbilityInput);// , /*Input*/ ShootInput); -} -void UAMAbilityManagerComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - FAFOnAbilityReady del; - //if (IsClient()) - { - //del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, - // IAbilityInput, InGroup, InSlot); - //AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - } - if (InAbilityTag.IsNull()) - InAbilityTag = GetAbilityTag(InGroup, InSlot); - - RemoveAbility(InGroup, InSlot); - RemoveAbilityTag(InGroup, InSlot); - - AbilityComp->NativeRemoveAbility(InAbilityTag); -} -void UAMAbilityManagerComponent::OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - if (bBindInput) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityInputReady, - InAbilityTag, InAbilityInput, InGroup, InSlot); - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - - ExecuteAbilityReadyEvent(InAbilityTag); - } - - } - else - { - SetAbility(InGroup, InSlot, Ability); - SetAbilityTag(InGroup, InSlot, InAbilityTag); - SetInputTag(InGroup, InSlot, InAbilityInput); - if (bBindInput) - { - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(InAbilityTag); - } - } - OnAbilityReady(InAbilityTag, InAbilityInput, InGroup, InSlot); -} - -void UAMAbilityManagerComponent::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - SetAbility(InGroup, InSlot, Ability); - SetAbilityTag(InGroup, InSlot, InAbilityTag); - SetInputTag(InGroup, InSlot, InAbilityInput); - //ExecuteAbilityReadyEvent(InAbilityTag); -} - -void UAMAbilityManagerComponent::NextGroup() -{ - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex++; - if(CurrentIndex > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - - if (ActiveGroup < AMIntToEnum(Groups.Num())) - { - } - else - { - ActiveGroup = EAMGroup::Group001; - } - } - - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNextGroup(AMEnumToInt(ActiveGroup)); - } -} - -void UAMAbilityManagerComponent::PreviousGroup() -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex--; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex < 0) - { - ActiveGroup = AMIntToEnum(Groups.Num() - 1); - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerPreviousGroup(static_cast(ActiveGroup)); - } -} - -void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponIndex) -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex++; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - if (ActiveGroup < AMIntToEnum(Groups.Num())) - { - } - else - { - ActiveGroup = EAMGroup::Group001; - } - //so Server index is different. Client might tried to cheat - //or sometrhing. We will override it. - //situation where client can chage multiple weapons within second - //should not have place, as there is animation and/or internal cooldown on weapon change. - //since it will be done trough ability. - if (ActiveGroup != AMIntToEnum(WeaponIndex)) - { - ClientNextGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientNextGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UAMAbilityManagerComponent::ServerNextGroup_Validate(int32 WeaponIndex) -{ - return true; -} -void UAMAbilityManagerComponent::ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) -{ - ActiveGroup = AMIntToEnum(WeaponIndex); - OnNextGroupConfirmed(ActiveGroup, bPredictionSuccess); -} - -void UAMAbilityManagerComponent::ServerPreviousGroup_Implementation(int32 WeaponIndex) -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex--; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex < 0) - { - ActiveGroup = AMIntToEnum(Groups.Num() -1); - } - if (ActiveGroup != AMIntToEnum(WeaponIndex)) - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UAMAbilityManagerComponent::ServerPreviousGroup_Validate(int32 WeaponIndex) -{ - return true; -} -void UAMAbilityManagerComponent::ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) -{ - ActiveGroup = AMIntToEnum(WeaponIndex); - OnPreviousGroupConfirmed(ActiveGroup, bPredictionSuccess); -} - -void UAMAbilityManagerComponent::SelectGroup(EAMGroup InGroup) -{ - if (AMEnumToInt(InGroup) > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = InGroup; - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerSelectGroup(InGroup); - } - else - { - OnGroupSelectionConfirmed(InGroup, true); - } -} -void UAMAbilityManagerComponent::ServerSelectGroup_Implementation(EAMGroup InGroup) -{ - if (AMEnumToInt(InGroup) > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = InGroup; - } - if (ActiveGroup != InGroup) - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UAMAbilityManagerComponent::ServerSelectGroup_Validate(EAMGroup InGroup) -{ - return true; -} - - -void UAMAbilityManagerComponent::ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess) -{ - if (bPredictionSuccess) - { - OnGroupSelectionConfirmed(InGroup, true); - } - else - { - ActiveGroup = InGroup; - OnGroupSelectionConfirmed(InGroup, false); - } -} - - -class UAFAbilityComponent* UAMAbilityManagerComponent::GetAbilityComponent() -{ - UAFAbilityComponent* AbilityComponent = nullptr; - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return AbilityComponent; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return AbilityComponent; - - AbilityComponent = ABInt->GetAbilityComp(); - - return AbilityComponent; -} - -bool UAMAbilityManagerComponent::IsServerOrStandalone() const -{ - AActor* Owner = GetOwner(); - if (Owner->GetNetMode() == ENetMode::NM_DedicatedServer - || Owner->GetNetMode() == ENetMode::NM_Standalone) - { - return true; - } - return false; -} -bool UAMAbilityManagerComponent::IsClientOrStandalone() const -{ - AActor* Owner = GetOwner(); - if (Owner->GetNetMode() == ENetMode::NM_Client - || Owner->GetNetMode() == ENetMode::NM_Standalone) - { - return true; - } - return false; -} -bool UAMAbilityManagerComponent::IsClient() const -{ - AActor* Owner = GetOwner(); - if (Owner->GetNetMode() == ENetMode::NM_Client - || Owner->Role < ENetRole::ROLE_Authority) - { - return true; - } - return false; -} - -void UAMAbilityManagerComponent::BindOnAbilityReadDelegate(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) -{ - -} diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h deleted file mode 100644 index 08d1adf..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AMAbilityManagerComponent.h +++ /dev/null @@ -1,201 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "Net/UnrealNetwork.h" -#include "Engine/ActorChannel.h" - -#include "AMTypes.h" -#include "GameplayTags.h" -#include "Abilities/GAAbilityBase.h" -#include "AMAbilityManagerComponent.generated.h" - - - -/* -- Group -- Set -- Ability --Inputs (multiple); - -*/ - -//all the inputs assigned to SINGLE ability; - -USTRUCT() -struct FAMAbilityInputSlot -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Inputs; - - TArray operator()() - { - return Inputs; - } -}; - - -USTRUCT() -struct FAMAbilityInputGroup -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Slots; -}; - - -USTRUCT() -struct FAMAbilityInputContainer -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Groups; - - - TArray GetInputs(EAMGroup InGroup, EAMSlot InSlot) - { - return Groups[AMEnumToInt(InGroup)].Slots[AMEnumToInt(InSlot)](); - } -}; - -USTRUCT() -struct FAMAbilitySlotConfig -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - uint8 SlotNum; -}; - -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere) - TArray Groups; - - //Map input bindings to particular slot and group. - UPROPERTY(EditAnywhere) - FAMAbilityInputContainer InputSetup; - - UPROPERTY(EditAnywhere, Category = "Input Config") - TArray InputsToBind; - - EAMGroup ActiveGroup; - - TArray>> AbilityTagsSet; - TArray>> AbilitySet; - TArray> ValidGroups; - TMap, FSimpleDelegate> AbilityReadyEvents; - - DECLARE_DELEGATE_TwoParams(FGroupConfirmDelegate, int32, bool) - - FGroupConfirmDelegate OnNextGroupDelegate; - FGroupConfirmDelegate OnPreviousGroupDelegate; - -public: - // Sets default values for this component's properties - UAMAbilityManagerComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - virtual void InitializeComponent() override; -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - void BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent); - UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); - void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); - void RemoveAbility(EAMGroup InGroup, EAMSlot InSlot); - - TSoftClassPtr GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); - void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag); - void RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot); - - TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); - void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); - - void NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); - void NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); -protected: - virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) {}; -private: - UFUNCTION() - void OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot, bool bBindInput); - -public: - UFUNCTION() - void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot); - - UFUNCTION(BlueprintCallable) - virtual void NextGroup(); - UFUNCTION(BlueprintCallable) - virtual void PreviousGroup(); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerNextGroup(int32 WeaponIndex); - void ServerNextGroup_Implementation(int32 WeaponIndex); - bool ServerNextGroup_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientNextGroup(int32 WeaponIndex, bool bPredictionSuccess); - void ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerPreviousGroup(int32 WeaponIndex); - void ServerPreviousGroup_Implementation(int32 WeaponIndex); - bool ServerPreviousGroup_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientPreviousGroup(int32 WeaponIndex, bool bPredictionSuccess); - void ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); - - - virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; - virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; - virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; - - UFUNCTION(BlueprintCallable) - void SelectGroup(EAMGroup InGroup); - UFUNCTION(Server, Reliable, WithValidation) - void ServerSelectGroup(EAMGroup InGroup); - void ServerSelectGroup_Implementation(EAMGroup InGroup); - bool ServerSelectGroup_Validate(EAMGroup InGroup); - UFUNCTION(Client, Reliable) - void ClientSelectGroup(EAMGroup InGroup, bool bPredictionSuccess); - void ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess); - - - void AddOnAbilityReadyEvent(const TSoftClassPtr& Ability, const FSimpleDelegate& Delegate) - { - if (!AbilityReadyEvents.Contains(Ability)) - { - AbilityReadyEvents.Add(Ability, Delegate); - } - } - - void ExecuteAbilityReadyEvent(const TSoftClassPtr& Ability) - { - if (FSimpleDelegate* Event = AbilityReadyEvents.Find(Ability)) - { - Event->ExecuteIfBound(); - AbilityReadyEvents.Remove(Ability); - } - } -protected: - class UAFAbilityComponent* GetAbilityComponent(); - void BindOnAbilityReadDelegate(TSoftClassPtr, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot); - bool IsServerOrStandalone() const; - bool IsClientOrStandalone() const; - bool IsClient() const; -}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp b/Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp deleted file mode 100644 index d34aeaf..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AMTypes.cpp +++ /dev/null @@ -1,3 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AMTypes.h" \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AMTypes.h b/Plugins/AbilityManager/Source/AbilityManager/AMTypes.h deleted file mode 100644 index 90b017d..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AMTypes.h +++ /dev/null @@ -1,95 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "AMTypes.generated.h" - -UENUM(BlueprintType) -enum class EAMSlot : uint8 -{ - Slot001 = 0, - Slot002 = 1, - Slot003 = 2, - Slot004 = 3, - Slot005 = 4, - Slot006 = 5, - Slot007 = 6, - Slot008 = 7, - Slot009 = 8, - Slot010 = 9, - Slot011 = 10, - Slot012 = 11, - Slot013 = 12, - Slot014 = 13, - Slot015 = 14, - Slot016 = 15, - Slot017 = 16, - Slot018 = 17, - Slot019 = 18, - Slot020 = 19, - Slot021 = 20, - Slot022 = 21, - Slot023 = 22, - Slot024 = 23, - Slot025 = 24, - Slot026 = 25, - Slot027 = 26, - Slot028 = 27, - Slot029 = 28, - Slot030 = 29, - Slot031 = 30, - Slot032 = 31, - MAX -}; - -UENUM(BlueprintType) -enum class EAMGroup : uint8 -{ - Group001 = 0, - Group002 = 1, - Group003 = 2, - Group004 = 3, - Group005 = 4, - Group006 = 5, - Group007 = 6, - Group008 = 7, - Group009 = 8, - Group010 = 9, - Group011 = 10, - Group012 = 11, - Group013 = 12, - Group014 = 13, - Group015 = 14, - Group016 = 15, - Group017 = 16, - Group018 = 17, - Group019 = 18, - Group020 = 19, - Group021 = 20, - Group022 = 21, - Group023 = 22, - Group024 = 23, - Group025 = 24, - Group026 = 25, - Group027 = 26, - Group028 = 27, - Group029 = 28, - Group030 = 29, - Group031 = 30, - Group032 = 31, - - MAX -}; - -template -int32 AMEnumToInt(T InVal) -{ - return static_cast(InVal); -} - -template -T AMIntToEnum(int32 InVal) -{ - return static_cast(InVal); -} \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs index 9729348..ef559fa 100644 --- a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs +++ b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs @@ -8,20 +8,8 @@ public AbilityManager(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "AbilityManager/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { - "AbilityManager/Private", - "AbilityManager/Abilities", - "AbilityManager/Attributes", - "AbilityManager/Effects", // ... add other private include paths required here ... } ); diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp deleted file mode 100644 index 3f142ff..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "AbilityManager.h" - -#define LOCTEXT_NAMESPACE "FAbilityManagerModule" - -void FAbilityManagerModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FAbilityManagerModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FAbilityManagerModule, AbilityManager) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h deleted file mode 100644 index 677d67e..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FAbilityManagerModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp deleted file mode 100644 index f87f7b0..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.cpp +++ /dev/null @@ -1,36 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "AMAbilityInputProperty.h" -#include "AbilityManagerEditor.h" -#include "IDetailsView.h" -#include "PropertyEditorModule.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" -#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" -#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" -#include "Editor/PropertyEditor/Private/SDetailsView.h" -//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h -#include "STextCombobox.h" -#include "STreeView.h" -#include "SButton.h" -#include "STextBlock.h" - -#include "EditorClassUtils.h" - - -TSharedRef FAMAbilityInputProperty::MakeInstance() -{ - return MakeShareable(new FAMAbilityInputProperty); -} - -FAMAbilityInputProperty::~FAMAbilityInputProperty() -{ - -} - -void FAMAbilityInputProperty::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} -void FAMAbilityInputProperty::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h deleted file mode 100644 index c31729d..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/AMAbilityInputProperty.h +++ /dev/null @@ -1,18 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "IPropertyTypeCustomization.h" -#include "PropertyHandle.h" - -class FAMAbilityInputProperty : public IPropertyTypeCustomization -{ -public: - static TSharedRef MakeInstance(); - /** - * Destructor - */ - virtual ~FAMAbilityInputProperty(); - - /** IPropertyTypeCustomization interface */ - virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; -}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs index c61e045..abec3a8 100644 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs @@ -8,14 +8,6 @@ public AbilityManagerEditor(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "AbilityManagerEditor/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "AbilityManagerEditor/Private", diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp deleted file mode 100644 index 06b8d0e..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "AbilityManagerEditor.h" - -#define LOCTEXT_NAMESPACE "FAbilityManagerEditor" - -void FAbilityManagerEditorModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FAbilityManagerEditorModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FAbilityManagerEditorModule, AbilityManagerEditor) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h deleted file mode 100644 index 0879ce8..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FAbilityManagerEditorModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp deleted file mode 100644 index 48e6f7b..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.cpp +++ /dev/null @@ -1,14 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "DWBPFunctionLibrary.h" -#include "DWManager.h" - - -FDWWWindowHandle UDWBPFunctionLibrary::CreateWindow(const FString& WindowName) -{ - return FDWManager::Get().CreateWindow(WindowName); -} -FDWWWindowHandle UDWBPFunctionLibrary::CreateWindowWithContent(UUserWidget* InWindowContent, const FString& WindowName) -{ - return FDWManager::Get().CreateWindow(InWindowContent->TakeWidget(), WindowName); -} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h deleted file mode 100644 index 1914c37..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWBPFunctionLibrary.h +++ /dev/null @@ -1,26 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Kismet/BlueprintFunctionLibrary.h" -#include "UserWidget.h" -#include "DWTypes.h" - -#include "DWBPFunctionLibrary.generated.h" - -/** - * - */ -UCLASS() -class DRAGGABLEWINDOW_API UDWBPFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_BODY() - -public: - UFUNCTION(BlueprintCallable, Category = "Draggable Window") - static FDWWWindowHandle CreateWindow(const FString& WindowName); - - UFUNCTION(BlueprintCallable, Category = "Draggable Window") - static FDWWWindowHandle CreateWindowWithContent(UUserWidget* InWindowContent, const FString& WindowName); -}; diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp deleted file mode 100644 index bf1b797..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.cpp +++ /dev/null @@ -1,72 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "DWManager.h" -#include "EngineGlobals.h" -#include "Engine/Engine.h" -#include "Engine/GameViewportClient.h" - -FDWManager* FDWManager::Instance = nullptr; -void FDWManager::Init() -{ - Desktop = SNew(SDraggableDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); - GEngine->GameViewport->AddViewportWidgetContent(Desktop.ToSharedRef(), 2000); -} -void FDWManager::CleanUp() -{ - Desktop->Clean(); - Desktop.Reset(); - WindowHandles.Empty(); - WindowHandles.Shrink(); -} -void FDWManager::RemoveWindow(const FDWWWindowHandle& InHandle) -{ - Desktop->RemoveWindow(InHandle.Window.Pin()); - WindowHandles.Remove(InHandle); -} -FDWManager& FDWManager::Get() -{ - if (!Instance) - { - Instance = new FDWManager(); - Instance->Init(); - } - return *Instance; -} -#if WITH_EDITORONLY_DATA -void FDWManager::PIEDestroy() -{ - if (Instance) - { - Instance->CleanUp(); - delete Instance; - Instance = nullptr; - } -} -#endif //WITH_EDITORONLY_DATA -FDWManager::FDWManager() -{ -} - -FDWManager::~FDWManager() -{ -} - -FDWWWindowHandle FDWManager::CreateWindow(const FString& WindowName) -{ - TSharedPtr NewWindow = SNew(SDraggableWindowWidget); - return AddWindow(NewWindow, WindowName); -} -FDWWWindowHandle FDWManager::CreateWindow(TSharedPtr InWindowContent, const FString& WindowName) -{ - - TSharedPtr NewWindow = SNew(SDraggableWindowWidget); - NewWindow->AddContent(InWindowContent); - return AddWindow(NewWindow, WindowName); -} -FDWWWindowHandle FDWManager::AddWindow(TSharedPtr InWindowWidget, const FString& WindowName) -{ - FDWWWindowHandle Handle = Desktop->AddWindow(InWindowWidget); - WindowHandles.Add(Handle); - WindowsByName.Add(FName(*WindowName), Handle); - return Handle; -} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h deleted file mode 100644 index 046d245..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWManager.h +++ /dev/null @@ -1,38 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SDraggableWindowWidget.h" - -/** - * - */ -class DRAGGABLEWINDOW_API FDWManager -{ -public: - friend class SDraggableWindowWidget; - friend class SDraggableDesktopWidget; -private: - static FDWManager* Instance; - TSharedPtr Desktop; - TSet WindowHandles; - //name of window, window handle - TMap WindowsByName; - void Init(); - void CleanUp(); - void RemoveWindow(const FDWWWindowHandle& InHandle); - FDWManager(); - -public: - static FDWManager& Get(); -#if WITH_EDITORONLY_DATA - static void PIEDestroy(); -#endif //WITH_EDITORONLY_DATA - ~FDWManager(); - - FDWWWindowHandle CreateWindow(const FString& WindowName); - FDWWWindowHandle CreateWindow(TSharedPtr InWindowContent, const FString& WindowName); - FDWWWindowHandle AddWindow(TSharedPtr InWindowWidget, const FString& WindowName); -}; -typedef FDWManager FDraggableWindowManager; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp deleted file mode 100644 index 3fe94f4..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.cpp +++ /dev/null @@ -1,3 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "DWTypes.h" \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h b/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h deleted file mode 100644 index d5e8c26..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DWTypes.h +++ /dev/null @@ -1,41 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "DWTypes.generated.h" - -USTRUCT(BlueprintType) -struct FDWWWindowHandle -{ - GENERATED_BODY() - TWeakPtr Window; -protected: - uint32 Handle; -public: - FDWWWindowHandle() - {}; - FDWWWindowHandle(uint32 InHandle) - : Handle(InHandle) - { - - } - - ~FDWWWindowHandle() - { - Handle = 0; - Window.Reset(); - } - - static FDWWWindowHandle Make(TSharedPtr InWindow); - - friend uint32 GetTypeHash(const FDWWWindowHandle& InHandle) - { - return InHandle.Handle; - } - - const bool operator==(const FDWWWindowHandle& InHandle) const - { - return Handle == InHandle.Handle; - } -}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs index 60f34c5..4396c51 100644 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs +++ b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.Build.cs @@ -8,14 +8,6 @@ public DraggableWindow(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "DraggableWindow/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "DraggableWindow/Private", diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp deleted file mode 100644 index e401549..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "DraggableWindow.h" -#include "DWManager.h" -#if WITH_EDITORONLY_DATA -#include "Editor.H" -#endif -#define LOCTEXT_NAMESPACE "FDraggableWindowModule" - -void FDraggableWindowModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module - -#if WITH_EDITORONLY_DATA - FEditorDelegates::EndPIE.AddRaw(this, &FDraggableWindowModule::HandlePIEEnd); -#endif //WITH_EDITORONLY_DATA - -} - -void FDraggableWindowModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} -#if WITH_EDITORONLY_DATA -void FDraggableWindowModule::HandlePIEEnd(bool InVal) -{ - FDWManager::PIEDestroy(); -} -#endif -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FDraggableWindowModule, DraggableWindow) \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h b/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h deleted file mode 100644 index 106e834..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/DraggableWindow.h +++ /dev/null @@ -1,21 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "Engine.h" -#include "CoreMinimal.h" -#include "ModuleManager.h" - - - -class FDraggableWindowModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -#if WITH_EDITORONLY_DATA - void HandlePIEEnd(bool InVal); -#endif -}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp deleted file mode 100644 index a930314..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.cpp +++ /dev/null @@ -1,706 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SDraggableWindowWidget.h" -#include "SlateOptMacros.h" - -#include "Slate.h" -#include "SlateCore.h" -#include "SBorder.h" -#include "Widgets/Layout/SGridPanel.h" -#include "Widgets/Layout/SBackgroundBlur.h" -#include "DWManager.h" -#include "EngineGlobals.h" -#include "Engine/Engine.h" -#include "Engine/GameViewportClient.h" -#include "SceneViewport.h" - -DECLARE_CYCLE_STAT(TEXT("DraggebleWindow.Tick"), STAT_DraggebleWindowTick, STATGROUP_DraggebleWindow); - -FDWWWindowHandle FDWWWindowHandle::Make(TSharedPtr InWindow) -{ - static uint32 NewHandle = 0; - NewHandle++; - FDWWWindowHandle Handle(NewHandle); - Handle.Window = InWindow; - InWindow->SetHandle(Handle); - return Handle; -} -void SDraggableDesktopWidget::Clean() -{ - for (TSharedPtr& Window : Windows) - { - Window.Reset(); - } - Windows.Empty(); - Windows.Shrink(); -} -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SDraggableDesktopWidget::Construct(const FArguments& InArgs) -{ - SetVisibility(EVisibility::SelfHitTestInvisible); - Container = SNew(SOverlay).Visibility(EVisibility::SelfHitTestInvisible); - ChildSlot - [ - Container.ToSharedRef() - ]; -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -FDWWWindowHandle SDraggableDesktopWidget::AddWindow(TSharedPtr InWindow) -{ - if (!Container.IsValid()) - return FDWWWindowHandle(); - - Container->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Left) - .VAlign(EVerticalAlignment::VAlign_Top) - [ - InWindow.ToSharedRef() - ]; - - FDWWWindowHandle Handle = FDWWWindowHandle::Make(InWindow); - Windows.Add(InWindow); - return Handle; -} - -void SDraggableDesktopWidget::RemoveWindow(TSharedPtr InWindow) -{ - Container->RemoveSlot(InWindow.ToSharedRef()); - Windows.Remove(InWindow); - InWindow.Reset(); -} - -void SWindowBox::Construct(const FArguments& InArgs) -{ - WidthOverride = InArgs._WidthOverride.Get(); - HeightOverride = InArgs._HeightOverride.Get(); - - ChildSlot - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - InArgs._Content.Widget - ]; -} -void SWindowBox::SetWidthOverride(float InWidthOverride) -{ - if (WidthOverride != InWidthOverride) - { - WidthOverride = InWidthOverride; - - Invalidate(EInvalidateWidget::Layout); - } -} - -void SWindowBox::SetHeightOverride(float InHeightOverride) -{ - if (HeightOverride != InHeightOverride) - { - HeightOverride = InHeightOverride; - - Invalidate(EInvalidateWidget::Layout); - } -} -void SWindowBox::OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedChildren& ArrangedChildren) const -{ - const EVisibility& MyCurrentVisibility = this->GetVisibility(); - if (ArrangedChildren.Accepts(MyCurrentVisibility)) - { - const FMargin SlotPadding(ChildSlot.SlotPadding.Get()); - bool bAlignChildren = true; - - AlignmentArrangeResult XAlignmentResult(0, 0); - AlignmentArrangeResult YAlignmentResult(0, 0); - - if (bAlignChildren) - { - XAlignmentResult = AlignChild(AllottedGeometry.GetLocalSize().X, ChildSlot, SlotPadding); - YAlignmentResult = AlignChild(AllottedGeometry.GetLocalSize().Y, ChildSlot, SlotPadding); - } - - const float AlignedSizeX = XAlignmentResult.Size; - const float AlignedSizeY = YAlignmentResult.Size; - - ArrangedChildren.AddWidget( - AllottedGeometry.MakeChild( - ChildSlot.GetWidget(), - FVector2D(XAlignmentResult.Offset, YAlignmentResult.Offset), - FVector2D(AlignedSizeX, AlignedSizeY) - ) - ); - } -} -FChildren* SWindowBox::GetChildren() -{ - return &ChildSlot; -} -FVector2D SWindowBox::ComputeDesiredSize(float) const -{ - EVisibility ChildVisibility = ChildSlot.GetWidget()->GetVisibility(); - - if (ChildVisibility != EVisibility::Collapsed) - { - // If the user specified a fixed width or height, those values override the Box's content. - - const float CurrentWidthOverride = WidthOverride; - const float CurrentHeightOverride = HeightOverride; - - - return FVector2D(CurrentWidthOverride, CurrentHeightOverride); - } - - return FVector2D::ZeroVector; -} -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SDraggableWindowWidget::Construct(const FArguments& InArgs) -{ - CurrentSize = FVector2D(1, 1); - ResizingState = EDDWState::NoResize; - bDestroyOnClose = true; - SetVisibility(EVisibility::SelfHitTestInvisible); - FSimpleDelegate OnPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnPressed); - FSimpleDelegate OnReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnReleased); - TAttribute posAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetPosition)); - - - FSimpleDelegate OnHorizontalPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizePressed); - FSimpleDelegate OnHorizontalReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeReleased); - FSimpleDelegate OnHorizontalLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeLeftPressed); - FSimpleDelegate OnHorizontalLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeLeftReleased); - - FSimpleDelegate OnVerticalTopPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalTopResizePressed); - FSimpleDelegate OnVerticalTopReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalTopResizeReleased); - FSimpleDelegate OnVerticalBottomPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalBottomResizePressed); - FSimpleDelegate OnVerticalBottomReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalBottomResizeReleased); - - FSimpleDelegate OnBottomRightPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomRightResizePressed); - FSimpleDelegate OnBottomRightReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomRightResizeReleased); - - FSimpleDelegate OnBottomLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizePressed); - FSimpleDelegate OnBottomLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizeReleased); - - FSimpleDelegate OnTopRightPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopRightResizePressed); - FSimpleDelegate OnTopRightReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopRightResizeReleased); - - FSimpleDelegate OnTopLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopLeftResizePressed); - FSimpleDelegate OnTopLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopLeftResizeReleased); - - - FSimpleDelegate OnCloseButtonPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnCloseButtonPressed); - - CurrentHeight = 200; - CurrentWidth = 200; - - FSlateBrush brush; - brush.DrawAs = ESlateBrushDrawType::Type::NoDrawType; - ButtonStyle.Normal = brush; - ButtonStyle.Hovered = brush; - ButtonStyle.Pressed = brush; - ButtonStyle.Disabled = brush; - BackgroundColor = FSlateColor(FLinearColor(0, 0, 0, 1)); - ChildSlot - [ - SNew(SCanvas) - + SCanvas::Slot() - .HAlign(EHorizontalAlignment::HAlign_Left) - .VAlign(EVerticalAlignment::VAlign_Top) - .Position(posAttr) - //.Size(sizeAttr) - [ - SNew(SGridPanel) - - +SGridPanel::Slot(0, 0) - [ - SNew(SBox) - .HeightOverride(3) - .WidthOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnTopLeftPressedDel) - .OnReleased(OnTopLeftReleasedDel) - .Cursor(EMouseCursor::ResizeSouthEast) - ] - ] - + SGridPanel::Slot(1 ,0) - [ - SNew(SBox) - .HeightOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnVerticalTopPressedDel) - .OnReleased(OnVerticalTopReleasedDel) - .Cursor(EMouseCursor::ResizeUpDown) - - ] - ] - + SGridPanel::Slot(2, 0) - [ - SNew(SBox) - .HeightOverride(3) - .WidthOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnTopRightPressedDel) - .OnReleased(OnTopRightReleasedDel) - .Cursor(EMouseCursor::ResizeSouthWest) - ] - ] - + SGridPanel::Slot(0, 1) - [ - SNew(SBox) - .WidthOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnHorizontalLeftPressedDel) - .OnReleased(OnHorizontalLeftReleasedDel) - .Cursor(EMouseCursor::ResizeLeftRight) - ] - ] - + SGridPanel::Slot(1, 1) - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SAssignNew(WindowBox, SWindowBox) - .Visibility(EVisibility::SelfHitTestInvisible) - //.HeightOverride(heightAttr) - //.WidthOverride(widthAttr) - [ - SNew(SVerticalBox) - .Visibility(EVisibility::SelfHitTestInvisible) - + SVerticalBox::Slot() - .AutoHeight() - .MaxHeight(24) - [ - SNew(SOverlay) - + SOverlay::Slot() - [ - SNew(SBackgroundBlur) - .BlurRadius(4) - .BlurStrength(16) - .Visibility(EVisibility::SelfHitTestInvisible) - ] - + SOverlay::Slot() - [ - SAssignNew(WindowBar, SButton) - .OnPressed(OnPressedDel) - .OnReleased(OnReleasedDel) - .VAlign(EVerticalAlignment::VAlign_Center) - .HAlign(EHorizontalAlignment::HAlign_Right) - .ContentPadding(FMargin(0)) - .ButtonStyle(&ButtonStyle) - [ - SNew(SHorizontalBox) - + SHorizontalBox::Slot() - .FillWidth(0.8f) - .AutoWidth() - [ - SNew(STextBlock) - .Visibility(EVisibility::SelfHitTestInvisible) - .Text(FText::FromString("Window Title")) - ] - + SHorizontalBox::Slot() - [ - SNew(SButton) - .OnPressed(OnCloseButtonPressedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("X")) - ] - ] - ] - ] - - ] - + SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - .FillHeight(1.0f) - [ - SNew(SBox) - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SOverlay) - + SOverlay::Slot() - [ - SNew(SBackgroundBlur) - .BlurRadius(4) - .BlurStrength(8) - .Visibility(EVisibility::SelfHitTestInvisible) - ] - +SOverlay::Slot() - [ - SAssignNew(Content, SOverlay) - .Visibility(EVisibility::SelfHitTestInvisible) - ] - - ] - ] - ] - - ] - + SGridPanel::Slot(2, 1) - [ - SNew(SBox) - .WidthOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnHorizontalPressedDel) - .OnReleased(OnHorizontalReleasedDel) - .Cursor(EMouseCursor::ResizeLeftRight) - ] - ] - + SGridPanel::Slot(0, 2) - [ - SNew(SBox) - .HeightOverride(3) - .WidthOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnBottomLeftPressedDel) - .OnReleased(OnBottomLeftReleasedDel) - .Cursor(EMouseCursor::ResizeSouthWest) - ] - ] - + SGridPanel::Slot(1, 2) - [ - SNew(SBox) - .HeightOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnVerticalBottomPressedDel) - .OnReleased(OnVerticalBottomReleasedDel) - .Cursor(EMouseCursor::ResizeUpDown) - ] - ] - + SGridPanel::Slot(2, 2) - [ - SNew(SBox) - .HeightOverride(3) - .WidthOverride(3) - [ - SNew(SButton) - .ButtonStyle(&ButtonStyle) - .OnPressed(OnBottomRightPressedDel) - .OnReleased(OnBottomRightReleasedDel) - .Cursor(EMouseCursor::ResizeSouthEast) - ] - ] - ] - ]; - WindowBox->SetHeightOverride(CurrentHeight); - WindowBox->SetWidthOverride(CurrentWidth); -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION -SDraggableWindowWidget::~SDraggableWindowWidget() -{ -} -FVector2D SDraggableWindowWidget::ComputeDesiredSize(float) const -{ - return SCompoundWidget::ComputeDesiredSize(1); -} -void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) -{ - SCOPE_CYCLE_COUNTER(STAT_DraggebleWindowTick); - SCompoundWidget::Tick(AllottedGeometry, InCurrentTime, InDeltaTime); - - FVector2D LastPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); - - FVector2D CurrentPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); - - float dist = FVector2D::Distance(CurrentPosition, LastPosition); - - switch (ResizingState) - { - case EDDWState::Dragging: - { - FVector2D AbsPos = FSlateApplicationBase::Get().GetCursorPos(); - - CurrentPosition = CurrentPosition - DragPosition; - AbsPosition = AbsPos - AbsDragPosition; - - FVector2D WindowPosition = GEngine->GameViewport->GetWindow()->GetPositionInScreen(); - FVector2D WindowSize = GEngine->GameViewport->GetWindow()->GetSizeInScreen() - 8; - - const float ApplicationScale = FSlateApplication::Get().GetApplicationScale(); - FVector2D AbsSize = AllottedGeometry.LocalToAbsolute(FVector2D(CurrentWidth, CurrentHeight)); - FVector2D GeomAbs = AllottedGeometry.GetAbsolutePosition(); - FVector2D localSize = WindowSize + WindowPosition; - CurrentCursorPosition = CurrentPosition; - if (CurrentPosition.X <= 0) - { - CurrentCursorPosition.X = 0; - } - if (CurrentPosition.Y <= 0) - { - CurrentCursorPosition.Y = 0; - } - if ((AbsPos.X + ((AbsSize.X - AbsDragPosition.X) * ApplicationScale)) >= localSize.X) - { - FVector2D localSize2 = AllottedGeometry.AbsoluteToLocal(WindowSize + WindowPosition); - CurrentCursorPosition.X = localSize2.X - CurrentWidth; - } - if ((AbsPos.Y + ((AbsSize.Y - AbsDragPosition.Y) * ApplicationScale)) >= localSize.Y) - { - FVector2D localSize2 = AllottedGeometry.AbsoluteToLocal(WindowSize + WindowPosition); - CurrentCursorPosition.Y = localSize2.Y - CurrentHeight; - } - break; - } - case EDDWState::HorizontalRight: - { - float CurrentXX = 0; - if (dist != 0) - { - CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); - } - CurrentWidth = CurrentWidth + CurrentXX; - WindowBox->SetWidthOverride(CurrentWidth); - break; - } - case EDDWState::HorizontalLeft: - { - float CurrentXX = 0; - if (dist != 0) - { - CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; - } - - CurrentCursorPosition.X -= CurrentXX; - CurrentWidth = CurrentWidth + CurrentXX; - WindowBox->SetWidthOverride(CurrentWidth); - break; - } - case EDDWState::VerticalTop: - { - float CurrentXX = 0; - float CurrentY = 0; - if (dist != 0) - { - CurrentXX = CurrentCursorPosition.Y - CurrentPosition.Y; - - } - CurrentCursorPosition.Y -= CurrentXX; - CurrentHeight = CurrentHeight + CurrentXX; - WindowBox->SetHeightOverride(CurrentHeight); - break; - } - case EDDWState::VerticalBottom: - { - float CurrentY = 0; - if (dist != 0) - { - CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); - } - - CurrentHeight = CurrentHeight + CurrentY; - WindowBox->SetHeightOverride(CurrentHeight); - break; - } - case EDDWState::DiagonalBottomRight: - { - float CurrentXX = 0; - float CurrentY = 0; - if (dist != 0) - { - CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); - CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); - } - CurrentWidth = CurrentWidth + CurrentXX; - CurrentHeight = CurrentHeight + CurrentY; - WindowBox->SetHeightOverride(CurrentHeight); - WindowBox->SetWidthOverride(CurrentWidth); - break; - } - case EDDWState::DiagonalBottomLeft: - { - float CurrentXX = 0; - float CurrentY = 0; - if (dist != 0) - { - CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; - CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); - } - CurrentCursorPosition.X -= CurrentXX; - CurrentWidth = CurrentWidth + CurrentXX; - CurrentHeight = CurrentHeight + CurrentY; - WindowBox->SetHeightOverride(CurrentHeight); - WindowBox->SetWidthOverride(CurrentWidth); - break; - } - case EDDWState::DiagonalTopRight: - { - float CurrentXX = 0; - float CurrentY = 0; - if (dist != 0) - { - CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; - CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); - } - CurrentCursorPosition.Y -= CurrentY; - - CurrentHeight = CurrentHeight + CurrentY; - CurrentWidth = CurrentWidth + CurrentXX; - WindowBox->SetHeightOverride(CurrentHeight); - WindowBox->SetWidthOverride(CurrentWidth); - break; - } - case EDDWState::DiagonalTopLeft: - { - float CurrentXX = 0; - float CurrentY = 0; - if (dist != 0) - { - CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; - CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; - } - CurrentCursorPosition.Y -= CurrentY; - CurrentCursorPosition.X -= CurrentXX; - CurrentHeight = CurrentHeight + CurrentY; - CurrentWidth = CurrentWidth + CurrentXX; - WindowBox->SetHeightOverride(CurrentHeight); - WindowBox->SetWidthOverride(CurrentWidth); - break; - } - case EDDWState::NoResize: - { break; - } - default: - break; - } -} -void SDraggableWindowWidget::AddContent(TSharedPtr InWidget) -{ - Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - InWidget.ToSharedRef() - ]; -} -void SDraggableWindowWidget::SetHandle(const FDWWWindowHandle& InHandle) -{ - Handle = InHandle; -} -void SDraggableWindowWidget::OnCloseButtonPressed() -{ - if(bDestroyOnClose) - FDWManager::Get().RemoveWindow(Handle); - else - { - SetVisibility(EVisibility::Collapsed); - } -} -void SDraggableWindowWidget::OnPressed() -{ - FGeometry geom = GetCachedGeometry(); - FVector2D CurrentPosAbs = FSlateApplicationBase::Get().GetLastCursorPos(); - FVector2D CurrentPosition = geom.AbsoluteToLocal(CurrentPosAbs); - //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed Pre DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); - DragPosition = CurrentPosition - CurrentCursorPosition; - AbsDragPosition = CurrentPosAbs - AbsPosition; - - //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentPosition X: %f Y: %f"), CurrentPosition.X, CurrentPosition.Y); - //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentCursorPosition X: %f Y: %f"), CurrentCursorPosition.X, CurrentCursorPosition.Y); - //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); - ResizingState = EDDWState::Dragging; -} -void SDraggableWindowWidget::OnReleased() -{ - ResizingState = EDDWState::NoResize; -} - -void SDraggableWindowWidget::OnHorizontalResizePressed() -{ - ResizingState = EDDWState::HorizontalRight; -} -void SDraggableWindowWidget::OnHorizontalResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} -void SDraggableWindowWidget::OnHorizontalResizeLeftPressed() -{ - ResizingState = EDDWState::HorizontalLeft; -} -void SDraggableWindowWidget::OnHorizontalResizeLeftReleased() -{ - ResizingState = EDDWState::NoResize; -} - -void SDraggableWindowWidget::OnVerticalTopResizePressed() -{ - ResizingState = EDDWState::VerticalTop; -} -void SDraggableWindowWidget::OnVerticalTopResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} -void SDraggableWindowWidget::OnVerticalBottomResizePressed() -{ - ResizingState = EDDWState::VerticalBottom; -} -void SDraggableWindowWidget::OnVerticalBottomResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} - -void SDraggableWindowWidget::OnDirectionalResizePressed() -{ -} - -void SDraggableWindowWidget::OnDirectionalResizeReleased() -{ -} - -void SDraggableWindowWidget::OnBottomRightResizePressed() -{ - ResizingState = EDDWState::DiagonalBottomRight; -} -void SDraggableWindowWidget::OnBottomRightResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} - -void SDraggableWindowWidget::OnBottomLeftResizePressed() -{ - ResizingState = EDDWState::DiagonalBottomLeft; -} -void SDraggableWindowWidget::OnBottomLeftResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} - -void SDraggableWindowWidget::OnTopRightResizePressed() -{ - ResizingState = EDDWState::DiagonalTopRight; -} -void SDraggableWindowWidget::OnTopRightResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} - -void SDraggableWindowWidget::OnTopLeftResizePressed() -{ - ResizingState = EDDWState::DiagonalTopLeft; -} -void SDraggableWindowWidget::OnTopLeftResizeReleased() -{ - ResizingState = EDDWState::NoResize; -} - -FVector2D SDraggableWindowWidget::GetPosition() const -{ - return CurrentCursorPosition; -} - -FText SDraggableWindowWidget::GetTitle() const -{ - return WindowTitle; -} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h deleted file mode 100644 index 13e96bc..0000000 --- a/Plugins/DraggableWindow/Source/DraggableWindow/SDraggableWindowWidget.h +++ /dev/null @@ -1,195 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Input/Events.h" -#include "Widgets/SCompoundWidget.h" -#include "SlateCore.h" -#include "Styling/SlateTypes.h" -#include "SOverlay.h" -#include "SGridPanel.h" -#include "SBox.h" -#include "SBorder.h" -#include "SButton.h" -#include "SConstraintCanvas.h" -#include "DWTypes.h" - -DECLARE_STATS_GROUP(TEXT("DraggebleWindow"), STATGROUP_DraggebleWindow, STATCAT_Advanced); - -enum class EDDWState : uint8 -{ - Dragging = 0, - HorizontalRight = 1, - HorizontalLeft = 2, - VerticalTop = 3, - VerticalBottom = 4, - DiagonalBottomRight = 5, - DiagonalBottomLeft = 6, - DiagonalTopRight = 7, - DiagonalTopLeft = 8, - - NoResize -}; -class DRAGGABLEWINDOW_API SDraggableDesktopWidget : public SCompoundWidget -{ - - SLATE_BEGIN_ARGS(SDraggableDesktopWidget) {} - SLATE_END_ARGS() -public: - friend class FDWManager; - friend class SDraggableWindowWidget; - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); -protected: - TArray> Windows; - TSharedPtr Container; - void Clean(); - FDWWWindowHandle AddWindow(TSharedPtr InWindow); - void RemoveWindow(TSharedPtr InWindow); -}; - -class SWindowBox : public SPanel -{ -public: - class FBoxSlot : public TSupportsOneChildMixin, public TSupportsContentAlignmentMixin, public TSupportsContentPaddingMixin - { - public: - FBoxSlot(SWidget* InOwner) - : TSupportsOneChildMixin(nullptr) - , TSupportsContentAlignmentMixin(HAlign_Fill, VAlign_Fill) - { - } - }; - SLATE_BEGIN_ARGS(SWindowBox) - : _Content() - , _WidthOverride() - , _HeightOverride() - { - _Visibility = EVisibility::SelfHitTestInvisible; - } - SLATE_DEFAULT_SLOT(FArguments, Content) - /** When specified, ignore the content's desired size and report the WidthOverride as the Box's desired width. */ - SLATE_ATTRIBUTE(float, WidthOverride) - - /** When specified, ignore the content's desired size and report the HeightOverride as the Box's desired height. */ - SLATE_ATTRIBUTE(float, HeightOverride) - SLATE_END_ARGS() -private: - /** When specified, ignore the content's desired size and report the.WidthOverride as the Box's desired width. */ - float WidthOverride; - - /** When specified, ignore the content's desired size and report the.HeightOverride as the Box's desired height. */ - float HeightOverride; -protected: - - FBoxSlot ChildSlot; -public: - SWindowBox() - : ChildSlot(this) - {} - void Construct(const FArguments& InArgs); - /** See WidthOverride attribute */ - void SetWidthOverride(float InWidthOverride); - - /** See HeightOverride attribute */ - void SetHeightOverride(float InHeightOverride); -protected: - /** - * Panels arrange their children in a space described by the AllottedGeometry parameter. The results of the arrangement - * should be returned by appending a FArrangedWidget pair for every child widget. See StackPanel for an example - * - * @param AllottedGeometry The geometry allotted for this widget by its parent. - * @param ArrangedChildren The array to which to add the WidgetGeometries that represent the arranged children. - */ - virtual void OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedChildren& ArrangedChildren) const override; - // Begin SWidget overrides. - virtual FVector2D ComputeDesiredSize(float) const override; - - /** - * All widgets must provide a way to access their children in a layout-agnostic way. - * Panels store their children in Slots, which creates a dilemma. Most panels - * can store their children in a TPanelChildren, where the Slot class - * provides layout information about the child it stores. In that case - * GetChildren should simply return the TPanelChildren. See StackPanel for an example. - */ - virtual FChildren* GetChildren() override; -}; - -/** - * Check IF cursor is moving during resizing. - */ -class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget -{ - SLATE_BEGIN_ARGS(SDraggableWindowWidget){} - SLATE_ATTRIBUTE(bool, HideOnClose) - SLATE_END_ARGS() -public: - friend struct FDWWWindowHandle; - friend class SDraggableDesktopWidget; - friend class FDWManager; - bool bDestroyOnClose; -protected: - EDDWState ResizingState; - - FVector2D CurrentSize; - FVector2D CurrentCursorPosition; - FVector2D DragPosition; - FVector2D AbsPosition; - FVector2D AbsDragPosition; - - TSharedPtr Content; - TSharedPtr WindowBox; - float CurrentHeight; - float CurrentWidth; - FButtonStyle ButtonStyle; - TAttribute BackgroundColor; - TSharedPtr WindowBar; - FDWWWindowHandle Handle; - - FText WindowTitle; -public: - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - ~SDraggableWindowWidget(); -protected: - virtual FVector2D ComputeDesiredSize(float) const override; - virtual void Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) override; - - void AddContent(TSharedPtr InWidget); - - void SetHandle(const FDWWWindowHandle& InHandle); - void OnCloseButtonPressed(); - - void OnPressed(); - void OnReleased(); - - void OnHorizontalResizePressed(); - void OnHorizontalResizeReleased(); - void OnHorizontalResizeLeftPressed(); - void OnHorizontalResizeLeftReleased(); - - void OnVerticalTopResizePressed(); - void OnVerticalTopResizeReleased(); - void OnVerticalBottomResizePressed(); - void OnVerticalBottomResizeReleased(); - - void OnDirectionalResizePressed(); - void OnDirectionalResizeReleased(); - - void OnBottomRightResizePressed(); - void OnBottomRightResizeReleased(); - - void OnBottomLeftResizePressed(); - void OnBottomLeftResizeReleased(); - - void OnTopRightResizePressed(); - void OnTopRightResizeReleased(); - - void OnTopLeftResizePressed(); - void OnTopLeftResizeReleased(); - - FVector2D GetPosition() const; - - FText GetTitle() const; -}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs index d8dc3b9..a1fee49 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs +++ b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs @@ -6,15 +6,7 @@ public class InventoryFramework : ModuleRules { public InventoryFramework(ReadOnlyTargetRules Target) : base(Target) { - PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - - PublicIncludePaths.AddRange( - new string[] { - "InventoryFramework/Public" - // ... add public include paths required here ... - } - ); - + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; PrivateIncludePaths.AddRange( new string[] { diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs index 6f78497..c0690be 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/InventoryFrameworkUI.Build.cs @@ -7,15 +7,7 @@ public class InventoryFrameworkUI : ModuleRules public InventoryFrameworkUI(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - - PublicIncludePaths.AddRange( - new string[] { - "InventoryFrameworkUI/Public" - // ... add public include paths required here ... - } - ); - - + PrivateIncludePaths.AddRange( new string[] { "InventoryFrameworkUI/Private", diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp deleted file mode 100644 index 33f85b1..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.cpp +++ /dev/null @@ -1,548 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#include "AnimNode_BlendLocomotionFour.h" -#include "AnimationRuntime.h" -#include "GameFramework/CharacterMovementComponent.h" -#include "GameFramework/Character.h" -#include "Animation/AnimClassInterface.h" -#include "Animation/AnimInstanceProxy.h" -#include "Animation/BlendProfile.h" -#include "DrawDebugHelpers.h" - -#include "Engine.h" -///////////////////////////////////////////////////// -// FAnimNode_BlendLocomotionFour -FString FDirToString(EFCardinalDirection Dir) -{ - switch (Dir) - { - case EFCardinalDirection::N: - return "N"; - case EFCardinalDirection::E: - return "E"; - case EFCardinalDirection::S: - return "S"; - case EFCardinalDirection::W: - return "W"; - default: - break; - } - return "Invalid"; -} -void FAnimNode_BlendLocomotionFour::Initialize_AnyThread(const FAnimationInitializeContext& Context) -{ - FAnimNode_Base::Initialize_AnyThread(Context); - - UAnimInstance* AnimInst = Cast(Context.AnimInstanceProxy->GetAnimInstanceObject()); - Character = Cast(AnimInst->TryGetPawnOwner()); - if (!Character) - return; - - CMC = Character->GetCharacterMovement(); - - if (!CMC) - return; - - const int NumPoses = BlendPose.Num(); - checkSlow(BlendTime.Num() == NumPoses); - - BlendWeights.Reset(NumPoses); - PosesToEvaluate.Reset(NumPoses); - if (NumPoses > 0) - { - // If we have at least 1 pose we initialize to full weight on - // the first pose - BlendWeights.AddZeroed(NumPoses); - BlendWeights[0] = 1.0f; - - PosesToEvaluate.Add(0); - - for (int32 ChildIndex = 0; ChildIndex < NumPoses; ++ChildIndex) - { - BlendPose[ChildIndex].Initialize(Context); - } - } - - RemainingBlendTimes.Empty(NumPoses); - RemainingBlendTimes.AddZeroed(NumPoses); - Blends.Empty(NumPoses); - Blends.AddZeroed(NumPoses); - - LastActiveChildIndex = INDEX_NONE; - - for (int32 i = 0; i < Blends.Num(); ++i) - { - FAlphaBlend& Blend = Blends[i]; - - Blend.SetBlendTime(0.0f); - Blend.SetBlendOption(BlendType); - Blend.SetCustomCurve(CustomBlendCurve); - } - Blends[0].SetAlpha(1.0f); - - if (BlendProfile) - { - // Initialise per-bone data - PerBoneSampleData.Empty(NumPoses); - PerBoneSampleData.AddZeroed(NumPoses); - - for (int32 Idx = 0; Idx < NumPoses; ++Idx) - { - FBlendSampleData& SampleData = PerBoneSampleData[Idx]; - SampleData.SampleDataIndex = Idx; - SampleData.PerBoneBlendData.AddZeroed(BlendProfile->GetNumBlendEntries()); - } - } -} - -void FAnimNode_BlendLocomotionFour::CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) -{ - for (int32 ChildIndex = 0; ChildIndexGetActorRightVector(); - FVector Forward = Character->GetActorForwardVector(); - - FTransform Transform = Character->GetTransform(); - FVector CurrentAcceleration = CMC->GetCurrentAcceleration(); - FVector CurrentVelocity = CMC->Velocity; - - FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal2D(); - FVector VelocityDirection = CurrentVelocity.GetSafeNormal2D(); - - FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); - FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); - - float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); - int32 Dir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; - DotBlendTime = FMath::Abs(FVector::DotProduct(LocalVelocity, LocalAcceleration)); - BlendTime[0] = DotBlendTime; - BlendTime[1] = DotBlendTime; - BlendTime[2] = DotBlendTime; - BlendTime[3] = DotBlendTime; - - NDot = FMath::RoundToInt(FVector::DotProduct(Forward, VelocityDirection)); - EDot = FMath::RoundToInt(FVector::DotProduct(Right, VelocityDirection)); - - const int NumPoses = BlendPose.Num(); - checkSlow((BlendTime.Num() == NumPoses) && (BlendWeights.Num() == NumPoses)); - - PosesToEvaluate.Empty(NumPoses); - - if (NumPoses > 0) - { - // Handle a change in the active child index; adjusting the target weights - const int32 ChildIndex = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4;; - - if (ChildIndex != LastActiveChildIndex) - { - bool LastChildIndexIsInvalid = (LastActiveChildIndex == INDEX_NONE); - - const float CurrentWeight = BlendWeights[ChildIndex]; - const float DesiredWeight = 1.0f; - const float WeightDifference = FMath::Clamp(FMath::Abs(DesiredWeight - CurrentWeight), 0.0f, 1.0f); - - // scale by the weight difference since we want always consistency: - // - if you're moving from 0 to full weight 1, it will use the normal blend time - // - if you're moving from 0.5 to full weight 1, it will get there in half the time - const float RemainingBlendTime = LastChildIndexIsInvalid ? 0.0f : (BlendTime[ChildIndex] * WeightDifference); - - for (int32 i = 0; i < RemainingBlendTimes.Num(); ++i) - { - RemainingBlendTimes[i] = RemainingBlendTime; - } - - // If we have a valid previous child and we're instantly blending - update that pose with zero weight - if (RemainingBlendTime == 0.0f && !LastChildIndexIsInvalid) - { - BlendPose[LastActiveChildIndex].Update(Context.FractionalWeight(0.0f)); - } - - for (int32 i = 0; i < Blends.Num(); ++i) - { - FAlphaBlend& Blend = Blends[i]; - - Blend.SetBlendTime(RemainingBlendTime); - - if (i == ChildIndex) - { - Blend.SetValueRange(BlendWeights[i], 1.0f); - } - else - { - Blend.SetValueRange(BlendWeights[i], 0.0f); - } - } - - // when this flag is true, we'll reinitialize the children - if (bResetChildOnActivation) - { - FAnimationInitializeContext ReinitializeContext(Context.AnimInstanceProxy); - - // reinitialize - BlendPose[ChildIndex].Initialize(ReinitializeContext); - } - - LastActiveChildIndex = ChildIndex; - } - - // Advance the weights - //@TODO: This means we advance even in a frame where the target weights/times just got modified; is that desirable? - float SumWeight = 0.0f; - for (int32 i = 0; i < Blends.Num(); ++i) - { - float& BlendWeight = BlendWeights[i]; - - FAlphaBlend& Blend = Blends[i]; - Blend.Update(Context.GetDeltaTime()); - BlendWeight = Blend.GetBlendedValue(); - - SumWeight += BlendWeight; - } - - // Renormalize the weights - if ((SumWeight > ZERO_ANIMWEIGHT_THRESH) && (FMath::Abs(SumWeight - 1.0f) > ZERO_ANIMWEIGHT_THRESH)) - { - float ReciprocalSum = 1.0f / SumWeight; - for (int32 i = 0; i < BlendWeights.Num(); ++i) - { - BlendWeights[i] *= ReciprocalSum; - } - } - - // Update our active children - for (int32 i = 0; i < BlendPose.Num(); ++i) - { - const float BlendWeight = BlendWeights[i]; - if (BlendWeight > ZERO_ANIMWEIGHT_THRESH) - { - BlendPose[i].Update(Context.FractionalWeight(BlendWeight)); - PosesToEvaluate.Add(i); - } - } - - // If we're using a blend profile, extract the scales and build blend sample data - if (BlendProfile) - { - for (int32 i = 0; i < BlendPose.Num(); ++i) - { - // Update Per-Bone Info - const float BlendWeight = BlendWeights[i]; - FBlendSampleData& PoseSampleData = PerBoneSampleData[i]; - PoseSampleData.TotalWeight = BlendWeight; - - for (int32 j = 0; j < PoseSampleData.PerBoneBlendData.Num(); ++j) - { - float& BoneBlend = PoseSampleData.PerBoneBlendData[j]; - float WeightScale = BlendProfile->GetEntryBlendScale(j); - - if (ChildIndex != i) - { - WeightScale = 1.0f / WeightScale; - } - - BoneBlend = BlendWeight * WeightScale; - } - } - - FBlendSampleData::NormalizeDataWeight(PerBoneSampleData); - } - } - - - switch (Dir) - { - case EFCardinalDirection::N: - { - FQuat ForwardQuat = FQuat::FindBetween(Forward, CurrentVelocity); - OrientN = FRotator(ForwardQuat).Yaw; - CurrentOrient = OrientN;// - //if (NDot == EDot) - /*{ - NorthPose.Update(Context.FractionalWeight(DotBlendTime)); - EastPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); - }*/ - /*else - { - NorthPose.Update(Context); - }*/ - - break; - } - case EFCardinalDirection::E: - { - FQuat LeftQuat = FQuat::FindBetween(Right, CurrentVelocity); - OrientE = FRotator(LeftQuat).Yaw; - CurrentOrient = OrientE; - //if (NDot == EDot) - /*{ - NorthPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); - EastPose.Update(Context.FractionalWeight(DotBlendTime)); - }*/ - /*else - { - EastPose.Update(Context); - }*/ - - // FMath::FInterpConstantTo(OldOrient, OrientE, DeltaTime, 300.0f); - break; - } - case EFCardinalDirection::S: - { - FQuat BackQuat = FQuat::FindBetween(Forward*(-1), CurrentVelocity); - OrientS = FRotator(BackQuat).Yaw; - CurrentOrient = OrientS; - break; - } - case EFCardinalDirection::W: - { - FQuat RightQuat = FQuat::FindBetween(Right*(-1), CurrentVelocity); - OrientW = FRotator(RightQuat).Yaw; - CurrentOrient = OrientW;// FMath::FInterpConstantTo(OldOrient, OrientW, DeltaTime, 300.0f); - break; - } - default: - break; - } - -} - -void FAnimNode_BlendLocomotionFour::Evaluate_AnyThread(FPoseContext& Output) -{ - ANIM_MT_SCOPE_CYCLE_COUNTER(BlendPosesInGraph, !IsInGameThread()); - { - //BlendPose[CurrentPose].Evaluate(Output); - } - const int32 NumPoses = PosesToEvaluate.Num(); - if ((NDot == EDot) && (NumPoses > 0) && (BlendPose.Num() == BlendWeights.Num())) - { - // Scratch arrays for evaluation, stack allocated - TArray> FilteredPoses; - TArray> FilteredCurve; - FilteredPoses.SetNum(NumPoses, false); - FilteredCurve.SetNum(NumPoses, false); - - int32 NumActivePoses = 0; - for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) - { - int32 PoseIndex = PosesToEvaluate[i]; - - FPoseContext EvaluateContext(Output); - - FPoseLink& CurrentPose = BlendPose[PoseIndex]; - CurrentPose.Evaluate(EvaluateContext); - - FilteredPoses[i].CopyBonesFrom(EvaluateContext.Pose); - FilteredCurve[i] = EvaluateContext.Curve; - } - - // Use the calculated blend sample data if we're blending per-bone - if (BlendProfile) - { - FAnimationRuntime::BlendPosesTogetherPerBone(FilteredPoses, FilteredCurve, BlendProfile, PerBoneSampleData, PosesToEvaluate, Output.Pose, Output.Curve); - } - else - { - FAnimationRuntime::BlendPosesTogether(FilteredPoses, FilteredCurve, BlendWeights, PosesToEvaluate, Output.Pose, Output.Curve); - } - - } - else - { - for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) - { - int32 PoseIndex = PosesToEvaluate[i]; - - FPoseLink& CurrentPose = BlendPose[PoseIndex]; - CurrentPose.Evaluate(Output); - - } - //Output.ResetToRefPose(); - } - - //FPoseContext EvaluateContext(Output); - //const FBoneContainer& BoneContainer = Output.AnimInstanceProxy->GetRequiredBones(); - //FComponentSpacePoseContext CSOutput(Output.AnimInstanceProxy); - //EFCardinalDirection ghf = Cast(Character)->GetCardianlDirection(); - //switch (Dir) - //{ - //case EFCardinalDirection::N: - //{ - // //if (OldDirection != Dir) - // { - // //if (NDot == EDot) - // { - // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); - - // FPoseContext Pose1(Output); - // FPoseContext Pose2(Output); - - // NorthPose.Evaluate(Pose1); - // EastPose.Evaluate(Pose2); - // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); - // - // } - // /*else - // { - // NorthPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); - // }*/ - // } - // /*else - // { - // NorthPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); - // }*/ - // break; - //} - //case EFCardinalDirection::E: - //{ - // - // //if (OldDirection != Dir) - // { - // //if (NDot == EDot) - // { - // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); - - // FPoseContext Pose1(Output); - // FPoseContext Pose2(Output); - - // NorthPose.Evaluate(Pose2); - // EastPose.Evaluate(Pose1); - // - // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); - // - // - // } - // /*else - // { - // EastPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); - // }*/ - - // } - // /*else - // { - // EastPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); - // }*/ - // break; - //} - //case EFCardinalDirection::S: - //{ - // break; - //} - //case EFCardinalDirection::W: - //{ - // break; - //} - //{ - //default: - // break; - //} - //} - -} - -void FAnimNode_BlendLocomotionFour::GatherDebugData(FNodeDebugData& DebugData) -{ - //const int32 ChildIndex = GetActiveChildIndex(); - - //FString DebugLine = GetNodeName(DebugData); - //DebugLine += FString::Printf(TEXT("(BlendTime: %f "), DotBlendTime); - - //DebugData.AddDebugItem(DebugLine); - - //NorthPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); - //EastPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); -} - - -void FAnimNode_BlendLocomotionFour::Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient) -{ - if (!FMath::IsNearlyZero(Orient, KINDA_SMALL_NUMBER)) - { - const FRotator DeltaRotation(0.0f, Orient, 0.f); - const FQuat DeltaQuat(DeltaRotation); - const FQuat MeshToComponentQuat(FRotator::ZeroRotator); - - // Convert our rotation from Component Space to Mesh Space. - const FQuat MeshSpaceDeltaQuat = MeshToComponentQuat.Inverse() * DeltaQuat * MeshToComponentQuat; - - // Apply rotation to root bone. - FCompactPoseBoneIndex RootBoneIndex(0); - CompactPose[RootBoneIndex].SetRotation(CompactPose[RootBoneIndex].GetRotation() * DeltaQuat); - CompactPose[RootBoneIndex].NormalizeRotation(); - } - // if (IKFootRootBone.IsValidToEvaluate(BoneContainer)) - // { - // // Prepare convert Quat and BoneContainer. - // const FQuat MeshToComponentQuat(FRotator(0.f, 0.f, 0.f)); - - // CSOutput.Pose.InitPose(CompactPose); - - // //Build our desired rotation for IK root bone. - // FRotator DeltaRotation(0.0f, 0.0f, 0.f); - // switch (Settings.YawRotationAxis) - // { - // case EAxis::X: - // DeltaRotation.Roll = Orient; - // case EAxis::Y: - // DeltaRotation.Pitch = Orient; - // case EAxis::Z: - // DeltaRotation.Yaw = Orient; - // default: - // break; - // } - // const FQuat DeltaQuat(DeltaRotation); - // // Convert our rotation from Component Space to Mesh Space. - // const FQuat MeshSpaceDeltaQuat = DeltaQuat; - // // Apply rotation to IK root bone. - // FCompactPoseBoneIndex RotateBoneIndex = IKFootRootBone.GetCompactPoseIndex(BoneContainer); - // CompactPose[RotateBoneIndex].SetRotation(CompactPose[RotateBoneIndex].GetRotation() * MeshSpaceDeltaQuat); - // CompactPose[RotateBoneIndex].NormalizeRotation(); - - - // // Do the same things like IK foot root bone to pelvis, but in the reversed orientation. - // FCompactPoseBoneIndex PelvisBoneIndex(1); - // FTransform PelvisBoneTM = CSOutput.Pose.GetComponentSpaceTransform(PelvisBoneIndex); - - // const FRotator PelvisDeltaRotation(DeltaRotation.Pitch * Settings.BodyOrientationAlpha, DeltaRotation.Yaw * Settings.BodyOrientationAlpha, DeltaRotation.Roll * Settings.BodyOrientationAlpha); - // FQuat PelvisDeltaQuat(PelvisDeltaRotation); - - // //const FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse() *PelvisDeltaQuat * PelvisBoneTM.GetRotation(); - // FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse()*PelvisDeltaQuat * PelvisBoneTM.GetRotation(); - - // CompactPose[PelvisBoneIndex].ConcatenateRotation(MeshSpacePelvisDeltaQuat); - // CompactPose[PelvisBoneIndex].NormalizeRotation(); - - // // Apply rotation to spine - // if (SpineBones.Num()) - // { - // for (int32 j = 0; j < SpineBones.Num(); j++) - // { - // if (SpineBones[j].Bone.IsValidToEvaluate(BoneContainer)) - // { - // FCompactPoseBoneIndex SpineBoneIndex = SpineBones[j].Bone.GetCompactPoseIndex(BoneContainer); - // FTransform SpineBoneTM = CSOutput.Pose.GetComponentSpaceTransform(SpineBoneIndex); - // const FRotator SpineDeltaRotation((-PelvisDeltaRotation.Pitch / SpineBones.Num()), (-PelvisDeltaRotation.Yaw / SpineBones.Num()), (-PelvisDeltaRotation.Roll / SpineBones.Num())); - // const FQuat SpineDeltaQuat(SpineDeltaRotation); - // const FQuat MeshSpaceSpineDeltaQuat = SpineBoneTM.GetRotation().Inverse() * SpineDeltaQuat * SpineBoneTM.GetRotation(); - // CompactPose[SpineBoneIndex].ConcatenateRotation(MeshSpaceSpineDeltaQuat); - // CompactPose[SpineBoneIndex].NormalizeRotation(); - // //GEngine->AddOnScreenDebugMessage(-1, DeltaTime, FColor::Yellow, (FString::Printf(TEXT(" SpineDeltaQuat: %s, MeshSpaceSpineDeltaQuat: %s PelvisDeltaQuat: %s"), *SpineDeltaQuat.ToString(), *MeshSpaceSpineDeltaQuat.ToString(), *PelvisDeltaQuat.ToString()))); - // } - // } - // } - // } - //} -} diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h b/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h deleted file mode 100644 index 1165134..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/AnimNode_BlendLocomotionFour.h +++ /dev/null @@ -1,146 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Animation/AnimationAsset.h" -#include "Animation/AnimNodeBase.h" -#include "AlphaBlend.h" -#include "BoneContainer.h" -#include "OrionInterface.h" -#include "Animation/InputScaleBias.h" -#include "AnimNode_BlendLocomotionFour.generated.h" - -class UBlendProfile; -class UCurveFloat; - -enum class EECardinalDirection : uint8 -{ - N = 0, - SW = 1, - E = 2, - NW = 3, - S = 4, - NE = 5, - W = 6, - SE = 7 -}; -USTRUCT(BlueprintType) -struct FOAxisSettings -{ - GENERATED_BODY() - - UPROPERTY(EditAnywhere, Category = "FAxisSettings") - TEnumAsByte YawRotationAxis; - - UPROPERTY(EditAnywhere, Category = "FAxisSettings") - float BodyOrientationAlpha; - - FOAxisSettings() :YawRotationAxis(EAxis::Z) - , BodyOrientationAlpha(0.5f) {} -}; -USTRUCT() -struct FOBoneRef -{ - GENERATED_BODY() - - UPROPERTY(EditAnywhere, Category = "Settings") - FBoneReference Bone; -}; -// Blend list node; has many children -USTRUCT(BlueprintInternalUseOnly) -struct ORIONANIMATION_API FAnimNode_BlendLocomotionFour : public FAnimNode_Base -{ - GENERATED_USTRUCT_BODY() -public: - UPROPERTY(EditAnywhere, EditFixedSize, BlueprintReadWrite, Category = Links) - TArray BlendPose; - - UPROPERTY(EditAnywhere, EditFixedSize, BlueprintReadWrite, Category = Config, meta = (PinShownByDefault)) - TArray BlendTime; - - UPROPERTY(EditAnywhere, Category = BlendType) - EAlphaBlendOption BlendType; - - UPROPERTY(EditAnywhere, Category = BlendType) - UCurveFloat* CustomBlendCurve; - - UPROPERTY(EditAnywhere, Category = BlendType) - UBlendProfile* BlendProfile; - - UPROPERTY() - TArray Blends; - -protected: - UPROPERTY() - TArray BlendWeights; - - UPROPERTY() - TArray RemainingBlendTimes; - - UPROPERTY() - int32 LastActiveChildIndex; - - UPROPERTY() - TArray PerBoneSampleData; - - //Store which poses we need to evaluate - TArray PosesToEvaluate; - - /** This reinitializes child pose when re-activated. For example, when active child changes */ - UPROPERTY(EditAnywhere, Category = Option) - bool bResetChildOnActivation; - -protected: - int32 CurrentDirection; - EFCardinalDirection OldDirection; - EFCardinalDirection Dir; - float OrientN; - float OrientE; - float OrientS; - float OrientW; - float CurrentOrient; - bool bDirectionChanged; - int32 CurrentPose; - - UPROPERTY(Transient) - mutable float InternalBlendAlpha; - - UPROPERTY(Transient) - class ACharacter* Character; - - UPROPERTY(Transient) - class UCharacterMovementComponent* CMC; - - float RemainingBlendTime; - FAlphaBlend AlphaBlend; - - FAlphaBlend NorthBlend; - FAlphaBlend EastBlend; - - float DotBlendTime; - int32 NDot; - int32 EDot; -public: - FAnimNode_BlendLocomotionFour() - : LastActiveChildIndex(0) - , bResetChildOnActivation(false) - { - BlendTime.SetNum(4); - BlendPose.SetNum(4); - } - - // FAnimNode_Base interface - virtual void Initialize_AnyThread(const FAnimationInitializeContext& Context) override; - virtual void CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) override; - virtual void Update_AnyThread(const FAnimationUpdateContext& Context) override; - virtual void Evaluate_AnyThread(FPoseContext& Output) override; - virtual void GatherDebugData(FNodeDebugData& DebugData) override; - // End of FAnimNode_Base interface - -protected: - virtual int32 GetActiveChildIndex() { return 0; } - virtual FString GetNodeName(FNodeDebugData& DebugData) { return DebugData.GetNodeName(this); } - void Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient); -}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp deleted file mode 100644 index 1cf28be..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.cpp +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "OrionAnimComponent.h" - - -// Sets default values for this component's properties -UOrionAnimComponent::UOrionAnimComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - - // ... -} - - -// Called when the game starts -void UOrionAnimComponent::BeginPlay() -{ - Super::BeginPlay(); - - // ... - -} - - -// Called every frame -void UOrionAnimComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} - diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h deleted file mode 100644 index 93b3c69..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimComponent.h +++ /dev/null @@ -1,29 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "OrionAnimComponent.generated.h" - - -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ORIONANIMATION_API UOrionAnimComponent : public UActorComponent -{ - GENERATED_BODY() - -public: - // Sets default values for this component's properties - UOrionAnimComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - - -}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs index ba1d632..23ca89a 100644 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs +++ b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.Build.cs @@ -8,14 +8,6 @@ public OrionAnimation(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "OrionAnimation/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "OrionAnimation/Private", diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp deleted file mode 100644 index 835b245..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#include "OrionAnimation.h" - -#define LOCTEXT_NAMESPACE "FOrionAnimationModule" - -void FOrionAnimationModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FOrionAnimationModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FOrionAnimationModule, OrionAnimation) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h b/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h deleted file mode 100644 index da88bbe..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionAnimation.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "Modules/ModuleManager.h" - -class FOrionAnimationModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp deleted file mode 100644 index da8cfef..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.cpp +++ /dev/null @@ -1,6 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "OrionInterface.h" - - -// Add default functionality here for any IOrionInterface functions that are not pure virtual. diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h b/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h deleted file mode 100644 index 66aee9d..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/OrionInterface.h +++ /dev/null @@ -1,42 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/Interface.h" -#include "OrionInterface.generated.h" - -enum class EFCardinalDirection : uint8 -{ - N = 0, - E = 1, - S = 2, - W = 3 -}; - -// This class does not need to be modified. -UINTERFACE(MinimalAPI) -class UOrionInterface : public UInterface -{ - GENERATED_BODY() -}; - -/** - * - */ -class ORIONANIMATION_API IOrionInterface -{ - GENERATED_BODY() - - // Add interface functions to this class. This is the class that will be inherited to implement this interface. -public: - - virtual float GetAnimOrient() { return 0; } - - virtual float GetAnimOrientN() { return 0; } - virtual float GetAnimOrientE() { return 0; } - virtual float GetAnimOrientS() { return 0; } - virtual float GetAnimOrientW() { return 0; } - - virtual EFCardinalDirection GetCardianlDirection() { return EFCardinalDirection::N; } -}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp deleted file mode 100644 index 359a7c0..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.cpp +++ /dev/null @@ -1,130 +0,0 @@ -// Copyright 2018 Sean Chen. All Rights Reserved. - -#include "AnimGraphNode_BlendLocomotionFour.h" -#include "OrionAnimationEditor.h" - -#define LOCTEXT_NAMESPACE "A3Nodes" - -UAnimGraphNode_BlendLocomotionFour::UAnimGraphNode_BlendLocomotionFour() -{ - -} - -FLinearColor UAnimGraphNode_BlendLocomotionFour::GetNodeTitleColor() const -{ - return FLinearColor(0.7f, 0.7f, 0.7f); -} - -FText UAnimGraphNode_BlendLocomotionFour::GetTooltipText() const -{ - return LOCTEXT("LocomotionFour", "Locomotion Four Direction"); -} - -FText UAnimGraphNode_BlendLocomotionFour::GetNodeTitle(ENodeTitleType::Type TitleType) const -{ - return LOCTEXT("LocomotionFour", "Locomotion Four Direction"); -} - -FString UAnimGraphNode_BlendLocomotionFour::GetNodeCategory() const -{ - return TEXT("Orion Animation"); -} -void GetPinInformation(const FString& InPinName, int32& Out_PinIndex, bool& Out_bIsPosePin, bool& Out_bIsTimePin) -{ - const int32 UnderscoreIndex = InPinName.Find(TEXT("_"), ESearchCase::CaseSensitive); - if (UnderscoreIndex != INDEX_NONE) - { - const FString ArrayName = InPinName.Left(UnderscoreIndex); - Out_PinIndex = FCString::Atoi(*(InPinName.Mid(UnderscoreIndex + 1))); - - Out_bIsPosePin = (ArrayName == TEXT("BlendPose")); - Out_bIsTimePin = (ArrayName == TEXT("BlendTime")); - } - else - { - Out_bIsPosePin = false; - Out_bIsTimePin = false; - Out_PinIndex = INDEX_NONE; - } -} -void UAnimGraphNode_BlendLocomotionFour::CustomizePinData(UEdGraphPin* Pin, FName SourcePropertyName, int32 ArrayIndex) const -{ - // if pin name starts with BlendPose or BlendWeight, change to enum name - bool bIsPosePin; - bool bIsTimePin; - int32 RawArrayIndex; - GetPinInformation(Pin->PinName.ToString(), /*out*/ RawArrayIndex, /*out*/ bIsPosePin, /*out*/ bIsTimePin); - checkSlow(RawArrayIndex == ArrayIndex); - - - if (bIsPosePin) - { - if (RawArrayIndex == 0) - { - //Pin->PinFriendlyName = FText::FromName("North Pose"); - //FFormatNamedArguments Args; - //Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); - Pin->PinFriendlyName = FText::FromString("N Pose"); - } - else if (RawArrayIndex == 1) - { - Pin->PinFriendlyName = FText::FromString("E Pose"); - } - else if (RawArrayIndex == 2) - { - Pin->PinFriendlyName = FText::FromString("S Pose"); - } - else if (RawArrayIndex == 3) - { - Pin->PinFriendlyName = FText::FromString("W Pose"); - } - } - //if (bIsPosePin || bIsTimePin) - //{ - // if (RawArrayIndex > 0) - // { - // const int32 ExposedEnumPinIndex = RawArrayIndex - 1; - - // // find pose index and see if it's mapped already or not - // if (VisibleEnumEntries.IsValidIndex(ExposedEnumPinIndex) && (BoundEnum != NULL)) - // { - // const FName& EnumElementName = VisibleEnumEntries[ExposedEnumPinIndex]; - // const int32 EnumIndex = BoundEnum->GetIndexByName(EnumElementName); - // if (EnumIndex != INDEX_NONE) - // { - // Pin->PinFriendlyName = BoundEnum->GetDisplayNameTextByIndex(EnumIndex); - // } - // else - // { - // Pin->PinFriendlyName = FText::FromName(EnumElementName); - // } - // } - // else - // { - // Pin->PinFriendlyName = LOCTEXT("InvalidIndex", "Invalid index"); - // } - // } - // else if (ensure(RawArrayIndex == 0)) - // { - // Pin->PinFriendlyName = LOCTEXT("Default", "Default"); - // } - - // // Append the pin type - // if (bIsPosePin) - // { - // FFormatNamedArguments Args; - // Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); - // Pin->PinFriendlyName = FText::Format(LOCTEXT("FriendlyNamePose", "{PinFriendlyName} Pose"), Args); - // } - - // if (bIsTimePin) - // { - // FFormatNamedArguments Args; - // Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); - // Pin->PinFriendlyName = FText::Format(LOCTEXT("FriendlyNameBlendTime", "{PinFriendlyName} Blend Time"), Args); - // } - //} -} - -#undef LOCTEXT_NAMESPACE - diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h b/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h deleted file mode 100644 index 71f79fb..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimationEditor/AnimGraphNode_BlendLocomotionFour.h +++ /dev/null @@ -1,35 +0,0 @@ -// Copyright 2018 Sean Chen. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "AnimGraphNode_Base.h" -#include "AnimNode_BlendLocomotionFour.h" -#include "AnimGraphNode_BlendLocomotionFour.generated.h" - -struct FAnimMode_OrientationWarping; -/** -* -*/ -UCLASS() -class ORIONANIMATIONEDITOR_API UAnimGraphNode_BlendLocomotionFour : public UAnimGraphNode_Base -{ - GENERATED_BODY() - - UPROPERTY(EditAnywhere, Category = "Settings") - FAnimNode_BlendLocomotionFour Node; - - //~ Begin UEdGraphNode Interface. - virtual FLinearColor GetNodeTitleColor() const override; - virtual FText GetTooltipText() const override; - virtual FText GetNodeTitle(ENodeTitleType::Type TitleType) const override; - //~ End UEdGraphNode Interface. - - //~ Begin UAnimGraphNode_Base Interface - virtual FString GetNodeCategory() const override; - //~ End UAnimGraphNode_Base Interface - virtual void CustomizePinData(UEdGraphPin* Pin, FName SourcePropertyName, int32 ArrayIndex) const override; - UAnimGraphNode_BlendLocomotionFour(); - - -}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs index 59aa1b7..83dcc7f 100644 --- a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.Build.cs @@ -7,15 +7,7 @@ public class OrionAnimationEditor : ModuleRules public OrionAnimationEditor(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - - PublicIncludePaths.AddRange( - new string[] { - "OrionAnimationEditor/Public" - // ... add public include paths required here ... - } - ); - - + PrivateIncludePaths.AddRange( new string[] { "OrionAnimationEditor/Private", diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp deleted file mode 100644 index 05b5d7f..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 2018 Sean Chen. All Rights Reserved. - -#include "OrionAnimationEditor.h" - -#define LOCTEXT_NAMESPACE "OrionAnimationEditorModule" - -void FOrionAnimationEditorModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FOrionAnimationEditorModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FOrionAnimationEditorModule, OrionAnimationEditor) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h b/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h deleted file mode 100644 index e60cb6a..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimationEditor/OrionAnimationEditor.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 2018 Sean Chen. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FOrionAnimationEditorModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs index c69bf3f..7611a7c 100644 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs +++ b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.Build.cs @@ -8,14 +8,6 @@ public SpectrAI(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "SpectrAI/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "SpectrAI/Private", diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp deleted file mode 100644 index 44a9f01..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#include "SpectrAI.h" - -#define LOCTEXT_NAMESPACE "FSpectrAIModule" - -void FSpectrAIModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FSpectrAIModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FSpectrAIModule, SpectrAI) \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h deleted file mode 100644 index a266684..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAI.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FSpectrAIModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp deleted file mode 100644 index c5103bd..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.cpp +++ /dev/null @@ -1,12 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrAIController.h" -#include "SpectrBrainComponent.h" - - -ASpectrAIController::ASpectrAIController(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - SpectrBrain = ObjectInitializer.CreateDefaultSubobject(this, TEXT("SpectrBrain")); - AIPerception = ObjectInitializer.CreateDefaultSubobject(this, TEXT("AIPerception")); -} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h deleted file mode 100644 index 19287ea..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAIController.h +++ /dev/null @@ -1,48 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "AIController.h" -#include "Perception/AIPerceptionComponent.h" -#include "SpectrAIController.generated.h" - -//Consideration (calculates score) -//--normalized 0-1 -//--calculated against curve - -//Qualifier -//--Contains Considerations -//--defines how score Considerations should be combined -//--return score. - -//Decision (what should I do?) -//--contain exactly ONE action to execute if decision wins - -//Decision Score Evaluator (Selector) -//--containts multiple considerations -//--all condsiderations are calculated with given context -//--they are summed (or multiplied) -//--contains single decision to execute. - - - -/** - * - */ -UCLASS() -class SPECTRAI_API ASpectrAIController : public AAIController -{ - GENERATED_BODY() -public: - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - class USpectrBrainComponent* SpectrBrain; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - class UAIPerceptionComponent* AIPerception; - - - ASpectrAIController(const FObjectInitializer& ObjectInitializer); - - -}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp deleted file mode 100644 index e57eba5..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.cpp +++ /dev/null @@ -1,60 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrAction.h" -#include "SpectrBrainComponent.h" - - -void USpectrAction::NativeMoveTo(class USpectrBrainComponent* Brain) -{ - MoveTo(Brain); -} -void USpectrAction::NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) -{ - OnMoveFinished(InContext, AIController, Brain); -} -void USpectrAction::FinishMove(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) -{ - NativeOnMoveFinished(InContext, AIController, Brain); -} -void USpectrAction::MoveTo_Implementation(class USpectrBrainComponent* Brain) -{ - -} - -float USpectrAction::NativeScore(class USpectrContext* InContext, class AAIController* AIController) -{ - return Score(InContext, AIController); -} - -float USpectrAction::Score_Implementation(class USpectrContext* InContext, class AAIController* AIController) -{ - return Cost; -} -bool USpectrAction::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) -{ - return EvaluateCondition(InContext, AIController); -} -bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController) -{ - return true; -} - -void USpectrAction::NativeFinished() -{ - OwningBrain->OnActionFinished(this); -} - -void USpectrAction::NativeExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) -{ - OnExecute(InContext, AIController, Brain); -} - -void USpectrAction::ActionFinished() -{ - NativeFinished(); -} - -void USpectrAction::MoveToTarget(AActor* Target, float MinimumDistance) -{ - OwningBrain->MoveToActor(Target, MinimumDistance); -} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h deleted file mode 100644 index b6ac82b..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrAction.h +++ /dev/null @@ -1,94 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "GameplayTags.h" -#include "GameplayTagContainer.h" -#include "SpectrAction.generated.h" - -/** - * Default implmenetations of Native* functions call to either blueprint events - * or blueprint Native functions which can be overriden from blueprint. - * Though they do provide default implementation (where possible). - */ - -UCLASS(BlueprintType, Blueprintable) -class SPECTRAI_API USpectrAction : public UObject -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "State Configuration") - int32 Cost; - /* - Tag Name of requirent condition in agent state, Desiared State Value - */ - UPROPERTY(EditAnywhere, Category = "State Configuration") - TMap PreConditions; - - /* - Tag Name of change applied to agent state is effect is executed, Desiared State Value - */ - UPROPERTY(EditAnywhere, Category = "State Configuration") - TMap Effects; - - UPROPERTY(BlueprintReadOnly, Category = "Spectr AI") - USpectrBrainComponent* OwningBrain; - - /* Override to check if action in rnage of Target/Location to execute */ - virtual bool NativeIsInRange(class AAIController* AIController) - { - return true; - } - - virtual void NativeMoveTo(class USpectrBrainComponent* Brain); - - virtual void NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - - UFUNCTION(BlueprintNativeEvent) - void MoveTo(class USpectrBrainComponent* Brain); - virtual void MoveTo_Implementation(class USpectrBrainComponent* Brain); - - UFUNCTION(BlueprintImplementableEvent, Category = "Spectr AI") - void OnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - - UFUNCTION(BlueprintCallable, Category = "Spectr AI") - void FinishMove(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - - /* - Call Super::NativeExecute if you want to execute OnExecuted BP event, or call it manually. - - Remember to call NativeFinished() somewhere, to indicate that Action finished execution. - */ - virtual void NativeExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - - virtual float NativeScore(class USpectrContext* InContext, class AAIController* AIController); - - virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); - - /* - Remember to call it always after Action has finished execution. Otherwise Action Queue will be stuck. - */ - void NativeFinished(); - - UFUNCTION(BlueprintImplementableEvent, Category = "Spectr AI") - void OnExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); - - UFUNCTION(BlueprintCallable, Category = "Spectr AI") - void ActionFinished(); - - UFUNCTION(BlueprintNativeEvent) - float Score(class USpectrContext* InContext, class AAIController* AIController); - virtual float Score_Implementation(class USpectrContext* InContext, class AAIController* AIController); - - UFUNCTION(BlueprintNativeEvent) - bool EvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); - virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController); - - - - - UFUNCTION(BlueprintCallable) - void MoveToTarget(AActor* Target, float MinimumDistance); -}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp deleted file mode 100644 index 9a38a52..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.cpp +++ /dev/null @@ -1,175 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrBrainComponent.h" -#include "SpectrContext.h" -#include "AIController.h" -#include "Engine/World.h" -#include "TimerManager.h" - -bool operator==(const FSpectrNode& Other, const USpectrAction*& Action) -{ - return Other.Action == Action; -} - -USpectrBrainComponent::USpectrBrainComponent(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ - FSMState = ESpectrState::Idle; - if(Context) - CurrentContext = Cast(CreateDefaultSubobject(TEXT("CurrentContext"), Context, Context, true, false, false)); -} - -void USpectrBrainComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - //check for new goals - //evaluate if new goal is worth pursuing over the current one. -} -void USpectrBrainComponent::BeginPlay() -{ - Super::BeginPlay(); - if (AAIController* AIController = Cast(GetOwner())) - { - AIController->GetPathFollowingComponent()->OnRequestFinished.AddUObject(this, &USpectrBrainComponent::OnMoveFinished); - } - for (const TSubclassOf& ActionClass : ActionList) - { - USpectrAction* Action = NewObject(this, ActionClass); - Action->OwningBrain = this; - Actions.Add(Action); - } -} -void USpectrBrainComponent::StarPlanning() -{ - //no point of running planner on clients. - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - return; - } - - TArray OutActionList; - if (AAIController* AIController = Cast(GetOwner())) - { - SpectrAI.Plan(Goal, CurrentState, OutActionList, Actions, CurrentContext, AIController); - } - for (int32 Idx = OutActionList.Num() - 1; Idx >= 0; Idx--) - { - FString name = OutActionList[Idx]->GetName(); - - PendingPlan.Add(OutActionList[Idx]); - PendingPlan2.Enqueue(OutActionList[Idx]); - - UE_LOG(LogTemp, Log, TEXT("Action Name: %s \n"), *name); - } - if (OutActionList.Num() == 0) - { - FTimerManager& Timer = GetWorld()->GetTimerManager(); - FTimerDelegate del = FTimerDelegate::CreateUObject(this, &USpectrBrainComponent::NextPlan); - Timer.SetTimer(NextPlanTimerHandle, del, 0.2f, false, 0.2f); - } - else - { - ExecutePlan(nullptr); - } - -} -void USpectrBrainComponent::NextPlan() -{ - TArray OutActionList; - if (AAIController* AIController = Cast(GetOwner())) - { - SpectrAI.Plan(Goal, CurrentState, OutActionList, Actions, CurrentContext, AIController); - } - if (OutActionList.Num() == 0) - { - FTimerManager& Timer = GetWorld()->GetTimerManager(); - FTimerDelegate del = FTimerDelegate::CreateUObject(this, &USpectrBrainComponent::NextPlan); - Timer.SetTimer(NextPlanTimerHandle, del, 0.2f, false, 0.2f); - } - else - { - ExecutePlan(nullptr); - } - -} -void USpectrBrainComponent::SelectGoal() -{ - -} - -void USpectrBrainComponent::ExecutePlan(class USpectrAction* PreviousAction) -{ - if (PendingPlan2.IsEmpty()) - { - //plan finished - StarPlanning(); //plan again - //in reality look for new goal. - return; - } - while (!PendingPlan2.IsEmpty()) - { - USpectrAction* OutAction; - PendingPlan2.Dequeue(OutAction); - if (OutAction != PreviousAction) - { - CurrentAction = OutAction; - break; - } - } - /*if (PendingPlan.Num() && PendingPlan[0]) - { - CurrentAction = PendingPlan[0]; - PendingPlan.RemoveAt(0, 1, true); - }*/ - if (AAIController* AIController = Cast(GetOwner())) - { - //Not in range - if (!CurrentAction->NativeIsInRange(AIController)) - { - FSMState = ESpectrState::Move; - CurrentAction->NativeMoveTo(this); - FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(CurrentAction, &USpectrAction::NativeOnMoveFinished, CurrentContext, AIController, this); - PendingMoveEvent = Delegate; - } - else //in range, just execute action. - { - FSMState = ESpectrState::Action; - CurrentAction->NativeExecute(CurrentContext, AIController, this); - } - // - } -} -void USpectrBrainComponent::AbortPlan(const FString& Reason) -{ - -} -void USpectrBrainComponent::OnActionFinished(USpectrAction* InAction) -{ - ExecutePlan(InAction); -} -void USpectrBrainComponent::OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result) -{ - if (AAIController* AIController = Cast(GetOwner())) - { - if (CurrentAction) - { - CurrentAction->NativeOnMoveFinished(CurrentContext, AIController, this); - } - } - //PendingMoveEvent.ExecuteIfBound(); - //PendingMoveEvent.Unbind(); - //ExecutePlan(); -} - -void USpectrBrainComponent::MoveToLocation() -{ - FSMState = ESpectrState::Move; -} -void USpectrBrainComponent::MoveToActor(AActor* Target, float MinDistance) -{ - FSMState = ESpectrState::Move; - if (AAIController* AIController = Cast(GetOwner())) - { - AIController->MoveToActor(Target, MinDistance); - } -} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h deleted file mode 100644 index 332e97b..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrBrainComponent.h +++ /dev/null @@ -1,323 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameplayTasksComponent.h" -#include "GameplayTags.h" -#include "GameplayTagContainer.h" -#include "Queue.h" -#include "SpectrAction.h" -#include "Navigation/PathFollowingComponent.h" -#include "AITypes.h" - -#include "SpectrBrainComponent.generated.h" - -enum class ESpectrState : uint8 -{ - Idle = 0, - Action = 1, - Move = 2 -}; - -//Node representing single step in plan. -struct FSpectrNode -{ - int32 Cost; - float Score; - int32 RemainingCost; - TWeakPtr Parent; - TMap State; - USpectrAction* Action; - TArray> Children; - FSpectrNode() {} - FSpectrNode(const TMap& InState, int32 InCost, int32 InRemainingCost) - : Cost(InCost) - , RemainingCost(InRemainingCost) - , State(InState) - {} - - bool Equals(USpectrAction* InAction) - { - return Action == InAction; - } - - bool operator==(const FSpectrNode& Other) const - { - return Action == Other.Action; - } - bool operator==(const USpectrAction*& Other) const - { - return Action == Other; - } - -}; - -bool operator==(const FSpectrNode& Other, const USpectrAction*& Action); - - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrAI -{ - GENERATED_BODY() -public: - //Precondition, List of action for this precondition; - TMap> > ActionMap; - - bool CheckGoal(const TMap& InEffects, const TMap& InGoal) - { - bool bAchieved = false; - for (TPair Test : InGoal) - { - UE_LOG(LogTemp, Log, TEXT("---Build Plan - Check Current Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); - } - - for (TPair Test : InEffects) - { - if (InGoal.Contains(Test.Key)) - { - if (InGoal[Test.Key] == Test.Value) - { - UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Passed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); - bAchieved = true; - } - else - { - UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Failed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); - bAchieved = false; - break; //all or nothing. - } - } - } - - - return bAchieved; - } - - TMap UpdateState(const TMap& InEffects, - const TMap& InCurrentState) - { - TMap NewState; - NewState.Append(InCurrentState); - for (TPair Effect : InEffects) - { - if (NewState.Contains(Effect.Key)) - { - bool* dd = NewState.Find(Effect.Key); - *dd = Effect.Value; - } - } - return NewState; - } - - TMap AddGoalChanges(const TMap& InCurrentGoal, - const TMap& InGoalChange) - { - TMap NewSet; - - NewSet.Append(InCurrentGoal); - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE START")); - for (TPair Test : InCurrentGoal) - { - UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); - } - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE END")); - for (TPair Change : InGoalChange) - { - if (NewSet.Contains(Change.Key)) - { - /*bool* dd = NewSet.Find(Change.Key); - *dd = Change.Value;*/ - } - else - { - NewSet.Add(Change.Key, Change.Value); - } - } - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST START")); - for (TPair Test : NewSet) - { - UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); - } - UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST END")); - return NewSet; - } - void InitializeMap(const TArray>& ActionList) - { - for (const TSubclassOf Action : ActionList) - { - for (const TPair& Effect : Action.GetDefaultObject()->Effects) - { - TArray>& ActionArray = ActionMap.FindOrAdd(Effect.Key); - ActionArray.Add(Action); - } - - } - } - void Plan(const TMap& InTargetGoal, const TMap& InCurrentState - , TArray& InActionQueue - , const TArray& ActionList - , class USpectrContext* InContext - , class AAIController* AIController) - { - TArray> OpenNodes; - TArray> ClosedNodes; - - TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); - - //actually made action when constructing node path. - //and then execute it in reverse (from last item in array to first). - //so we don't was time traversing node tree and then reordering actions.. - TArray ActionPlan; - - OpenNodes.Push(Node); - - TArray AvailableActions = ActionList; - - //reverse A*, or something similiar to it at least.. - while (OpenNodes.Num()) - { - TSharedPtr CurrentNode = OpenNodes.Pop(); - ClosedNodes.Push(CurrentNode); - - for (USpectrAction*& Action : AvailableActions) - { - //or instead of pushing to closed actions... we can remove them for Available Actions hmm ? - if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) - { - return Item->Equals(Action); - })) - { - continue; - } - - if (!(CurrentNode->Action == Action)) - { - if (CheckGoal(Action->Effects, CurrentNode->State)) - { - //action scored Zero, so it probabaly can't be used anyway. - if (!Action->NativeEvaluateCondition(InContext, AIController)) - { - continue; - } - float Score = Action->NativeScore(InContext, AIController); - - TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action->PreConditions, Action->Cost, 0)); - Node2->Action = Action; - Node2->Score = Score; - OpenNodes.Add(Node2); - - if (CurrentNode->Children.Num() == 0) - { - CurrentNode->Children.Add(Node2); - ActionPlan.Add(Action); - } - else - { - //add new action, only if it is cheaper than current one. - //very primitive we need to check if the actuall path will be cheaper. - //so compare current cost of the path with - if (Score > Node2->Score) - { - ActionPlan.Remove(CurrentNode->Children[0]->Action); - CurrentNode->Children.Empty(); - CurrentNode->Children.Add(Node2); - - ActionPlan.Add(Action); - } - else - { - //action has been discarded, remove it from OpenNodes - OpenNodes.Remove(Node2); - //and add to closed nodes. No reason to ever consider it again. - ClosedNodes.Add(Node2); - } - } - } - } - } - } - - InActionQueue = ActionPlan; - } -}; - -USTRUCT(BlueprintType) -struct FGoalSpec -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Instanced) - class USpectrGoal* Goal; - UPROPERTY(EditAnywhere, Instanced) - TArray Considerations; -}; - -/** - * - */ -UCLASS() -class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent -{ - GENERATED_BODY() -public: - ESpectrState FSMState; - - UPROPERTY(EditAnywhere) - TMap Goal; - UPROPERTY(EditAnywhere) - TMap CurrentState; - UPROPERTY(EditAnywhere) - TArray> ActionList; - UPROPERTY() - TArray Actions; - UPROPERTY(EditAnywhere) - TArray Goals2; - - UPROPERTY(EditAnywhere, Instanced) - TArray Goals; - UPROPERTY() - class USpectrGoal* CurrentGoal; - - - UPROPERTY() - TArray PendingPlan; - - TQueue PendingPlan2; - - UPROPERTY() - USpectrAction* CurrentAction; - - - - UPROPERTY(EditAnywhere) - TSubclassOf Context; - UPROPERTY() - class USpectrContext* CurrentContext; - - FSpectrAI SpectrAI; - - //Map of pending move events. - FSimpleDelegate PendingMoveEvent; - - FTimerHandle NextPlanTimerHandle; - - USpectrBrainComponent(const FObjectInitializer& ObjectInitializer); - virtual void BeginPlay() override; - virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; - UFUNCTION(BlueprintCallable) - void StarPlanning(); - UFUNCTION() - void NextPlan(); - - void SelectGoal(); - void ExecutePlan(class USpectrAction* PreviousAction); - void AbortPlan(const FString& Reason); - void OnActionFinished(USpectrAction* InAction); - void OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result); - - void MoveToLocation(); - void MoveToActor(AActor* Target, float MinDistance); - - -}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp deleted file mode 100644 index 88cf50e..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrConsideration.h" - - - - diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h deleted file mode 100644 index da8ec6e..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrConsideration.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "SpectrConsideration.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class SPECTRAI_API USpectrConsideration : public UObject -{ - GENERATED_BODY() - -public: - virtual float Score() const { return 0; } - -}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp deleted file mode 100644 index 988813d..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrContext.h" - - - - diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h deleted file mode 100644 index 8822a25..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrContext.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "SpectrContext.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAI_API USpectrContext : public UObject -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp deleted file mode 100644 index 37d9944..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrEvaluator.h" - - - - diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h deleted file mode 100644 index 673ff31..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrEvaluator.h +++ /dev/null @@ -1,72 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "SpectrConsideration.h" -#include "SpectrEvaluator.generated.h" - - -//USTRUCT(BlueprintType) -//struct SPECTRAI_API FSpectrConsideration -//{ -// GENERATED_BODY() -//public: -// virtual float Score() const { return 0; } -// virtual ~FSpectrConsideration() -// {} -//}; - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrQualifier -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Instanced) - TArray Considerations; -public: - virtual ~FSpectrQualifier() - {} - virtual float Qualify() const - { - float TotalScore = 0; - for (USpectrConsideration* Consideration : Considerations) - { - TotalScore += Consideration->Score(); - } - return TotalScore; - } -}; - -USTRUCT(BlueprintType) -struct SPECTRAI_API FSpectrEvaluator -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - FSpectrQualifier Qualifier; - - mutable float Score; - - float Evaluate() const - { - Score = 0; - float score = Qualifier.Qualify(); - Score = score; - return score; - } -}; - -/** - * - */ -//UCLASS() -//class SPECTRAI_API USpectrEvaluator : public UObject -//{ -// GENERATED_BODY() -// -// -// -// -//}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp deleted file mode 100644 index 3b2ccbf..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SpectrGoal.h" - - - - diff --git a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h b/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h deleted file mode 100644 index f2b5ca8..0000000 --- a/Plugins/SpectrAI/Source/SpectrAI/SpectrGoal.h +++ /dev/null @@ -1,63 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "UObject/NoExportTypes.h" -#include "GameplayTags.h" -#include "GameplayTagContainer.h" -#include "SpectrEvaluator.h" -#include "SpectrGoal.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable, EditInLineNew) -class SPECTRAI_API USpectrGoal : public UObject -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TMap Goal; - - //What to change in state if goal has been achieved ? - UPROPERTY(EditAnywhere) - TMap FinishedState; - - UPROPERTY(EditAnywhere, Instanced) - TArray Considerations; - - UPROPERTY(EditAnywhere) - FSpectrEvaluator ScoreEvaluator; - - virtual float QualifyGoal(class USpectrContext* InContext) - { - return -1.0f; - } - - //What Should we do if this goal is selected ? - virtual void GoalSelected() - { - - } - - //Called when goal has been selected, just before plan is executed. - virtual void GoalStarted() - { - - } - - //called just after plan finished execution - virtual void GoalFinished() - { - - } - - //called if plan for some reason cannot be finished and is aborted. - virtual void GoalAborted() - { - - } - - -}; diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs index 7ef7a9b..73c1d2c 100644 --- a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.Build.cs @@ -8,15 +8,6 @@ public SpectrAIEditor(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "SpectrAIEditor/Public", - "SpectrAI/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "SpectrAIEditor/Private", diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp deleted file mode 100644 index 7e6a50e..0000000 --- a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "SpectrAIEditor.h" - -#define LOCTEXT_NAMESPACE "FSpectrAIEditor" - -void FSpectrAIEditorModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FSpectrAIEditorModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FSpectrAIEditorModule, SpectrAIEditor) \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h deleted file mode 100644 index 7b2e8e7..0000000 --- a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrAIEditor.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FSpectrAIEditorModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp deleted file mode 100644 index 6269568..0000000 --- a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.cpp +++ /dev/null @@ -1,12 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "SpectrGoalCustomization.h" - -TSharedRef FSpectrGoalCustomization::MakeInstance() -{ - return MakeShareable(new FSpectrGoalCustomization()); -} -void FSpectrGoalCustomization::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) -{ - -} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h b/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h deleted file mode 100644 index 767e7f9..0000000 --- a/Plugins/SpectrAI/Source/SpectrAIEditor/SpectrGoalCustomization.h +++ /dev/null @@ -1,17 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrGoal.h" - -#include "IDetailCustomization.h" -#include "PropertyHandle.h" - -class FSpectrGoalCustomization : public IDetailCustomization -{ -public: - /** Makes a new instance of this detail layout class for a specific detail view requesting it */ - static TSharedRef MakeInstance(); - virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; -}; \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp deleted file mode 100644 index 7b04f84..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAIControllerBase.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h deleted file mode 100644 index f79cf73..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAIControllerBase.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAIController.h" -#include "STestAIControllerBase.generated.h" - -/** - * - */ -UCLASS() -class SPECTRAITEST_API ASTestAIControllerBase : public ASpectrAIController -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp deleted file mode 100644 index 793d1af..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.cpp +++ /dev/null @@ -1,54 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_ChopFirewood.h" -#include "AIController.h" -#include "SpectrBrainComponent.h" -#include "STestTree.h" -#include "EngineUtils.h" - -bool USTestAction_ChopFirewood::NativeIsInRange(class AAIController* AIController) -{ - //We can evaluate again here if we have target, and if it worth going. - //we can either find better fit or abort plan at this point. - bool bInRange = false; - if (TargetTree) - { - APawn* Pawn = AIController->GetPawn(); - FVector Position = Pawn->GetActorLocation(); - FVector TargetPosition = TargetTree->GetActorLocation(); - float Distance = FVector::Dist(Position, TargetPosition); - if (Distance < MinDistance) - { - bInRange = true; - } - } - return bInRange; -} -void USTestAction_ChopFirewood::NativeMoveTo(class USpectrBrainComponent* Brain) -{ - Brain->MoveToActor(TargetTree, MinDistance); -} -void USTestAction_ChopFirewood::NativeOnMoveFinished(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) -{ - NativeExecute(InContext, AIController, Brain); -} -//void USTestAction_ChopFirewood::NativeExecute(class USpectrContext* InContext -// , class AAIController* AIController -// , class USpectrBrainComponent* Brain) -//{ -// NativeFinished(); -//} - -bool USTestAction_ChopFirewood::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) -{ - bool bFound = false; - for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) - { - TargetTree = *ActorIt; - bFound = true; - break; - } - return bFound; -} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h deleted file mode 100644 index d2378c8..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopFirewood.h +++ /dev/null @@ -1,36 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_ChopFirewood.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_ChopFirewood : public USpectrAction -{ - GENERATED_BODY() - - UPROPERTY() - AActor* TargetTree; - UPROPERTY(EditAnywhere) - float MinDistance; - -public: - virtual bool NativeIsInRange(class AAIController* AIController) override; - virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; - virtual void NativeOnMoveFinished(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) override; - - //virtual void NativeExecute(class USpectrContext* InContext - // , class AAIController* AIController - // , class USpectrBrainComponent* Brain) override; - - virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp deleted file mode 100644 index 001a874..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_ChopWood.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h deleted file mode 100644 index 4428927..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_ChopWood.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_ChopWood.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_ChopWood : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp deleted file mode 100644 index 876aefc..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_CollectBranches.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h deleted file mode 100644 index bae50a2..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectBranches.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_CollectBranches.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_CollectBranches : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp deleted file mode 100644 index 3800d2d..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_CollectOre.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h deleted file mode 100644 index 212463b..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_CollectOre.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_CollectOre.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_CollectOre : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp deleted file mode 100644 index e23a260..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.cpp +++ /dev/null @@ -1,52 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_DropFirewood.h" -#include "AIController.h" -#include "SpectrBrainComponent.h" -#include "STestStorage.h" -#include "EngineUtils.h" - -bool USTestAction_DropFirewood::NativeIsInRange(class AAIController* AIController) -{ - bool bInRange = false; - if (TargetDropPoint) - { - APawn* Pawn = AIController->GetPawn(); - FVector Position = Pawn->GetActorLocation(); - FVector TargetPosition = TargetDropPoint->GetActorLocation(); - float Distance = FVector::Dist(Position, TargetPosition); - if (Distance < MinDistance) - { - bInRange = true; - } - } - return bInRange; -} -void USTestAction_DropFirewood::NativeMoveTo(class USpectrBrainComponent* Brain) -{ - Brain->MoveToActor(TargetDropPoint, MinDistance); -} -void USTestAction_DropFirewood::NativeOnMoveFinished(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) -{ - NativeExecute(InContext, AIController, Brain); -} -void USTestAction_DropFirewood::NativeExecute(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) -{ - NativeFinished(); -} - -bool USTestAction_DropFirewood::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) -{ - bool bFound = false; - for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) - { - TargetDropPoint = *ActorIt; - bFound = true; - break; - } - return bFound; -} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h deleted file mode 100644 index 9a8cb95..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropFirewood.h +++ /dev/null @@ -1,36 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_DropFirewood.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_DropFirewood : public USpectrAction -{ - GENERATED_BODY() - - UPROPERTY() - AActor* TargetDropPoint; - UPROPERTY(EditAnywhere) - float MinDistance; - -public: - virtual bool NativeIsInRange(class AAIController* AIController) override; - virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; - virtual void NativeOnMoveFinished(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) override; - - virtual void NativeExecute(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) override; - - virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp deleted file mode 100644 index d017aad..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_DropOre.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h deleted file mode 100644 index 2883ff4..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropOre.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_DropOre.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_DropOre : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp deleted file mode 100644 index 0cafb3b..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_DropWood.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h deleted file mode 100644 index 04fb1c8..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_DropWood.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_DropWood.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_DropWood : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp deleted file mode 100644 index 365c590..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_GoTo.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h deleted file mode 100644 index 393bce0..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_GoTo.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_GoTo.generated.h" - -/** - * - */ -UCLASS() -class SPECTRAITEST_API USTestAction_GoTo : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp deleted file mode 100644 index c9b4702..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_MakeAxe.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h deleted file mode 100644 index 030d66c..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakeAxe.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_MakeAxe.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_MakeAxe : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp deleted file mode 100644 index a50a2b5..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_MakePick.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h deleted file mode 100644 index b694046..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MakePick.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_MakePick.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_MakePick : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp deleted file mode 100644 index 6c91e77..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_MineOre.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h deleted file mode 100644 index 6472f2e..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_MineOre.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_MineOre.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_MineOre : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp deleted file mode 100644 index eeb7171..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.cpp +++ /dev/null @@ -1,52 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_PickItemAxe.h" -#include "AIController.h" -#include "SpectrBrainComponent.h" -#include "STestAxePickup.h" -#include "EngineUtils.h" - -bool USTestAction_PickItemAxe::NativeIsInRange(class AAIController* AIController) -{ - bool bInRange = false; - if (TargetItem) - { - APawn* Pawn = AIController->GetPawn(); - FVector Position = Pawn->GetActorLocation(); - FVector TargetPosition = TargetItem->GetActorLocation(); - float Distance = FVector::Dist(Position, TargetPosition); - if (Distance < MinDistance) - { - bInRange = true; - } - } - return bInRange; -} -void USTestAction_PickItemAxe::NativeMoveTo(class USpectrBrainComponent* Brain) -{ - Brain->MoveToActor(TargetItem, MinDistance); -} -void USTestAction_PickItemAxe::NativeOnMoveFinished(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) -{ - NativeExecute(InContext, AIController, Brain); -} -void USTestAction_PickItemAxe::NativeExecute(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) -{ - NativeFinished(); -} - -bool USTestAction_PickItemAxe::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) -{ - bool bFound = false; - for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) - { - TargetItem = *ActorIt; - bFound = true; - break; - } - return bFound; -} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h deleted file mode 100644 index e1a25f0..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemAxe.h +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_PickItemAxe.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_PickItemAxe : public USpectrAction -{ - GENERATED_BODY() -protected: - /* Minimum distance from item to pick it. */ - UPROPERTY(EditAnywhere) - float MinDistance; - UPROPERTY() - AActor* TargetItem; -public: - virtual bool NativeIsInRange(class AAIController* AIController) override; - virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; - virtual void NativeOnMoveFinished(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) override; - - virtual void NativeExecute(class USpectrContext* InContext - , class AAIController* AIController - , class USpectrBrainComponent* Brain) override; - - virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp deleted file mode 100644 index 4d1578b..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAction_PickItemPick.h" - - - - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h deleted file mode 100644 index a22eaff..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAction_PickItemPick.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SpectrAction.h" -#include "STestAction_PickItemPick.generated.h" - -/** - * - */ -UCLASS(BlueprintType, Blueprintable) -class SPECTRAITEST_API USTestAction_PickItemPick : public USpectrAction -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp deleted file mode 100644 index a25fb52..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestAxePickup.h" - - -// Sets default values -ASTestAxePickup::ASTestAxePickup() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void ASTestAxePickup::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void ASTestAxePickup::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h deleted file mode 100644 index 970ff76..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestAxePickup.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "STestAxePickup.generated.h" - -UCLASS() -class SPECTRAITEST_API ASTestAxePickup : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - ASTestAxePickup(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp deleted file mode 100644 index 9296a87..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestBranch.h" - - -// Sets default values -ASTestBranch::ASTestBranch() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void ASTestBranch::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void ASTestBranch::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h deleted file mode 100644 index 2c1755a..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestBranch.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "STestBranch.generated.h" - -UCLASS() -class SPECTRAITEST_API ASTestBranch : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - ASTestBranch(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp deleted file mode 100644 index 22d4aa4..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestForge.h" - - -// Sets default values -ASTestForge::ASTestForge() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void ASTestForge::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void ASTestForge::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h deleted file mode 100644 index 21f2f0e..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestForge.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "STestForge.generated.h" - -UCLASS() -class SPECTRAITEST_API ASTestForge : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - ASTestForge(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp deleted file mode 100644 index a28db48..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestStorage.h" - - -// Sets default values -ASTestStorage::ASTestStorage() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void ASTestStorage::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void ASTestStorage::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h deleted file mode 100644 index fcf1463..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestStorage.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "STestStorage.generated.h" - -UCLASS() -class SPECTRAITEST_API ASTestStorage : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - ASTestStorage(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp deleted file mode 100644 index cc09e79..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.cpp +++ /dev/null @@ -1,27 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "STestTree.h" - - -// Sets default values -ASTestTree::ASTestTree() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - -} - -// Called when the game starts or when spawned -void ASTestTree::BeginPlay() -{ - Super::BeginPlay(); - -} - -// Called every frame -void ASTestTree::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h b/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h deleted file mode 100644 index 1c0cb6c..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/STestTree.h +++ /dev/null @@ -1,28 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "STestTree.generated.h" - -UCLASS() -class SPECTRAITEST_API ASTestTree : public AActor -{ - GENERATED_BODY() - -public: - // Sets default values for this actor's properties - ASTestTree(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; - - - -}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs index f899150..018c2d4 100644 --- a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs +++ b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.Build.cs @@ -8,14 +8,6 @@ public SpectrAITest(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "SpectrAITest/Public" - // ... add public include paths required here ... - } - ); - - PrivateIncludePaths.AddRange( new string[] { "SpectrAITest/Private", diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp deleted file mode 100644 index ebd2517..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#include "SpectrAITest.h" - -#define LOCTEXT_NAMESPACE "FSpectrAITestModule" - -void FSpectrAITestModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FSpectrAITestModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FSpectrAITestModule, SpectrAITest) \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h b/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h deleted file mode 100644 index 8f51c72..0000000 --- a/Plugins/SpectrAITest/Source/SpectrAITest/SpectrAITest.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "Modules/ModuleManager.h" - -class FSpectrAITestModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 237ef7d..8aca1ef 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -7,40 +7,9 @@ public class ActionRPGGame : ModuleRules public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "AbilityFramework", - "OrionAnimation", - "OrionAnimation/Private", - "OrionAnimation/Public", - "AbilityFramework/Abilities", - "AbilityFramework/Attributes", - "AbilityFramework/Effects", - "AbilityFramework/Public", - "ActionRPGGame/Abilities", - "ActionRPGGame/AI", - "ActionRPGGame/Attributes", - "ActionRPGGame/UI", - "ActionRPGGame/UI/Abilities" - // ... add public include paths required here ... - } - ); - + PrivateIncludePaths.AddRange( new string[] { - "AbilityFramework", - "OrionAnimation", - "OrionAnimation/Private", - "OrionAnimation/Public", - "AbilityFramework/Abilities", - "AbilityFramework/Attributes", - "AbilityFramework/Effects", - "AbilityFramework/Private", - "ActionRPGGame/Abilities", - "ActionRPGGame/AI", - "ActionRPGGame/Attributes", - "ActionRPGGame/UI", - "ActionRPGGame/UI/Abilities" // ... add other private include paths required here ... } ); diff --git a/Source/ActionRPGGame/AI/ARAICharacter.cpp b/Source/ActionRPGGame/Public/AI/ARAICharacter.cpp similarity index 100% rename from Source/ActionRPGGame/AI/ARAICharacter.cpp rename to Source/ActionRPGGame/Public/AI/ARAICharacter.cpp diff --git a/Source/ActionRPGGame/AI/ARAICharacter.h b/Source/ActionRPGGame/Public/AI/ARAICharacter.h similarity index 100% rename from Source/ActionRPGGame/AI/ARAICharacter.h rename to Source/ActionRPGGame/Public/AI/ARAICharacter.h diff --git a/Source/ActionRPGGame/AI/ARAIController.cpp b/Source/ActionRPGGame/Public/AI/ARAIController.cpp similarity index 100% rename from Source/ActionRPGGame/AI/ARAIController.cpp rename to Source/ActionRPGGame/Public/AI/ARAIController.cpp diff --git a/Source/ActionRPGGame/AI/ARAIController.h b/Source/ActionRPGGame/Public/AI/ARAIController.h similarity index 100% rename from Source/ActionRPGGame/AI/ARAIController.h rename to Source/ActionRPGGame/Public/AI/ARAIController.h diff --git a/Source/ActionRPGGame/ARCharacter.cpp b/Source/ActionRPGGame/Public/ARCharacter.cpp similarity index 96% rename from Source/ActionRPGGame/ARCharacter.cpp rename to Source/ActionRPGGame/Public/ARCharacter.cpp index ed544e1..b3eb396 100644 --- a/Source/ActionRPGGame/ARCharacter.cpp +++ b/Source/ActionRPGGame/Public/ARCharacter.cpp @@ -567,4 +567,51 @@ void AARCharacter::OnInventoryReplicated(class UIFInventoryComponent* Inventory) { } -/* IIFInventoryInterface */ \ No newline at end of file +/* IIFInventoryInterface */ + + + +void AARCharacter::CalculateSpatialGrid() +{ + FVector Location = GetActorLocation(); + + auto resFunc = [Location]() + { + int32 MaxH = 100; + int32 MaxV = 20; + float HOffset = 0; + float VOffset = 0; + FPostResult Res; + for (int32 IdxH = 0; IdxH < MaxH; IdxH++) + { + HOffset += 30; + VOffset = 0; + for (int32 IdxV = 0; IdxV < MaxV; IdxV++) + { + VOffset += 30; + FVector Pos = Location + FVector(HOffset, VOffset, 0); + Res.Data.Add(Pos); + } + } + return Res; + }; + Result = Async(EAsyncExecution::TaskGraph, resFunc, SpatialComplete()); +} + +TFunction AARCharacter::SpatialComplete() +{ + + //DrawBox() + auto func = [&]() + { + auto func2 = [&]() + { + for (const FVector& Pos : Result.Get().Data) + { + DrawDebugPoint(GetWorld(), Pos, 20, FColor::Red, true, 10); + } + }; + AsyncTask(ENamedThreads::GameThread, func2); + }; + return func; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/ARCharacter.h b/Source/ActionRPGGame/Public/ARCharacter.h similarity index 97% rename from Source/ActionRPGGame/ARCharacter.h rename to Source/ActionRPGGame/Public/ARCharacter.h index 1df545c..7586627 100644 --- a/Source/ActionRPGGame/ARCharacter.h +++ b/Source/ActionRPGGame/Public/ARCharacter.h @@ -298,5 +298,16 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio virtual void OnInventoryReplicated(class UIFInventoryComponent* Inventory) override; /* IIFInventoryInterface */ + + + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame") + void CalculateSpatialGrid(); + + struct FPostResult + { + TArray Data; + }; + TFuture Result; + TFunction SpatialComplete(); }; diff --git a/Source/ActionRPGGame/ARCharacterMovementComponent.cpp b/Source/ActionRPGGame/Public/ARCharacterMovementComponent.cpp similarity index 100% rename from Source/ActionRPGGame/ARCharacterMovementComponent.cpp rename to Source/ActionRPGGame/Public/ARCharacterMovementComponent.cpp diff --git a/Source/ActionRPGGame/ARCharacterMovementComponent.h b/Source/ActionRPGGame/Public/ARCharacterMovementComponent.h similarity index 100% rename from Source/ActionRPGGame/ARCharacterMovementComponent.h rename to Source/ActionRPGGame/Public/ARCharacterMovementComponent.h diff --git a/Source/ActionRPGGame/ARGameMode.cpp b/Source/ActionRPGGame/Public/ARGameMode.cpp similarity index 100% rename from Source/ActionRPGGame/ARGameMode.cpp rename to Source/ActionRPGGame/Public/ARGameMode.cpp diff --git a/Source/ActionRPGGame/ARGameMode.h b/Source/ActionRPGGame/Public/ARGameMode.h similarity index 100% rename from Source/ActionRPGGame/ARGameMode.h rename to Source/ActionRPGGame/Public/ARGameMode.h diff --git a/Source/ActionRPGGame/ARGlobals.cpp b/Source/ActionRPGGame/Public/ARGlobals.cpp similarity index 100% rename from Source/ActionRPGGame/ARGlobals.cpp rename to Source/ActionRPGGame/Public/ARGlobals.cpp diff --git a/Source/ActionRPGGame/ARGlobals.h b/Source/ActionRPGGame/Public/ARGlobals.h similarity index 100% rename from Source/ActionRPGGame/ARGlobals.h rename to Source/ActionRPGGame/Public/ARGlobals.h diff --git a/Source/ActionRPGGame/ARItemBase.cpp b/Source/ActionRPGGame/Public/ARItemBase.cpp similarity index 100% rename from Source/ActionRPGGame/ARItemBase.cpp rename to Source/ActionRPGGame/Public/ARItemBase.cpp diff --git a/Source/ActionRPGGame/ARItemBase.h b/Source/ActionRPGGame/Public/ARItemBase.h similarity index 100% rename from Source/ActionRPGGame/ARItemBase.h rename to Source/ActionRPGGame/Public/ARItemBase.h diff --git a/Source/ActionRPGGame/ARItemPickupBase.cpp b/Source/ActionRPGGame/Public/ARItemPickupBase.cpp similarity index 100% rename from Source/ActionRPGGame/ARItemPickupBase.cpp rename to Source/ActionRPGGame/Public/ARItemPickupBase.cpp diff --git a/Source/ActionRPGGame/ARItemPickupBase.h b/Source/ActionRPGGame/Public/ARItemPickupBase.h similarity index 100% rename from Source/ActionRPGGame/ARItemPickupBase.h rename to Source/ActionRPGGame/Public/ARItemPickupBase.h diff --git a/Source/ActionRPGGame/ARPlayerController.cpp b/Source/ActionRPGGame/Public/ARPlayerController.cpp similarity index 100% rename from Source/ActionRPGGame/ARPlayerController.cpp rename to Source/ActionRPGGame/Public/ARPlayerController.cpp diff --git a/Source/ActionRPGGame/ARPlayerController.h b/Source/ActionRPGGame/Public/ARPlayerController.h similarity index 100% rename from Source/ActionRPGGame/ARPlayerController.h rename to Source/ActionRPGGame/Public/ARPlayerController.h diff --git a/Source/ActionRPGGame/Abilities/ARAbilityBase.cpp b/Source/ActionRPGGame/Public/Abilities/ARAbilityBase.cpp similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAbilityBase.cpp rename to Source/ActionRPGGame/Public/Abilities/ARAbilityBase.cpp diff --git a/Source/ActionRPGGame/Abilities/ARAbilityBase.h b/Source/ActionRPGGame/Public/Abilities/ARAbilityBase.h similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAbilityBase.h rename to Source/ActionRPGGame/Public/Abilities/ARAbilityBase.h diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.cpp similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.cpp rename to Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.cpp diff --git a/Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAbilityManagerComponent.h rename to Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h diff --git a/Source/ActionRPGGame/Abilities/ARAbilityUIData.cpp b/Source/ActionRPGGame/Public/Abilities/ARAbilityUIData.cpp similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAbilityUIData.cpp rename to Source/ActionRPGGame/Public/Abilities/ARAbilityUIData.cpp diff --git a/Source/ActionRPGGame/Abilities/ARAbilityUIData.h b/Source/ActionRPGGame/Public/Abilities/ARAbilityUIData.h similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAbilityUIData.h rename to Source/ActionRPGGame/Public/Abilities/ARAbilityUIData.h diff --git a/Source/ActionRPGGame/Abilities/ARAvailableAbilities.cpp b/Source/ActionRPGGame/Public/Abilities/ARAvailableAbilities.cpp similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAvailableAbilities.cpp rename to Source/ActionRPGGame/Public/Abilities/ARAvailableAbilities.cpp diff --git a/Source/ActionRPGGame/Abilities/ARAvailableAbilities.h b/Source/ActionRPGGame/Public/Abilities/ARAvailableAbilities.h similarity index 100% rename from Source/ActionRPGGame/Abilities/ARAvailableAbilities.h rename to Source/ActionRPGGame/Public/Abilities/ARAvailableAbilities.h diff --git a/Source/ActionRPGGame/ActionRPGGame.cpp b/Source/ActionRPGGame/Public/ActionRPGGame.cpp similarity index 100% rename from Source/ActionRPGGame/ActionRPGGame.cpp rename to Source/ActionRPGGame/Public/ActionRPGGame.cpp diff --git a/Source/ActionRPGGame/ActionRPGGame.h b/Source/ActionRPGGame/Public/ActionRPGGame.h similarity index 100% rename from Source/ActionRPGGame/ActionRPGGame.h rename to Source/ActionRPGGame/Public/ActionRPGGame.h diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp b/Source/ActionRPGGame/Public/Attributes/ARAbilityAttributes.cpp similarity index 100% rename from Source/ActionRPGGame/Attributes/ARAbilityAttributes.cpp rename to Source/ActionRPGGame/Public/Attributes/ARAbilityAttributes.cpp diff --git a/Source/ActionRPGGame/Attributes/ARAbilityAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARAbilityAttributes.h similarity index 100% rename from Source/ActionRPGGame/Attributes/ARAbilityAttributes.h rename to Source/ActionRPGGame/Public/Attributes/ARAbilityAttributes.h diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp b/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.cpp similarity index 100% rename from Source/ActionRPGGame/Attributes/ARCharacterAttributes.cpp rename to Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.cpp diff --git a/Source/ActionRPGGame/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h similarity index 100% rename from Source/ActionRPGGame/Attributes/ARCharacterAttributes.h rename to Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.cpp b/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.cpp similarity index 100% rename from Source/ActionRPGGame/Attributes/ARGunAttributes.cpp rename to Source/ActionRPGGame/Public/Attributes/ARGunAttributes.cpp diff --git a/Source/ActionRPGGame/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h similarity index 100% rename from Source/ActionRPGGame/Attributes/ARGunAttributes.h rename to Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h diff --git a/Source/ActionRPGGame/Attributes/ARHealthExtension.cpp b/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.cpp similarity index 100% rename from Source/ActionRPGGame/Attributes/ARHealthExtension.cpp rename to Source/ActionRPGGame/Public/Attributes/ARHealthExtension.cpp diff --git a/Source/ActionRPGGame/Attributes/ARHealthExtension.h b/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.h similarity index 100% rename from Source/ActionRPGGame/Attributes/ARHealthExtension.h rename to Source/ActionRPGGame/Public/Attributes/ARHealthExtension.h diff --git a/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.cpp b/Source/ActionRPGGame/Public/Calculations/ARAmmoReloadCalculation.cpp similarity index 100% rename from Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.cpp rename to Source/ActionRPGGame/Public/Calculations/ARAmmoReloadCalculation.cpp diff --git a/Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.h b/Source/ActionRPGGame/Public/Calculations/ARAmmoReloadCalculation.h similarity index 100% rename from Source/ActionRPGGame/Calculations/ARAmmoReloadCalculation.h rename to Source/ActionRPGGame/Public/Calculations/ARAmmoReloadCalculation.h diff --git a/Source/ActionRPGGame/UI/ARHUD.cpp b/Source/ActionRPGGame/Public/UI/ARHUD.cpp similarity index 100% rename from Source/ActionRPGGame/UI/ARHUD.cpp rename to Source/ActionRPGGame/Public/UI/ARHUD.cpp diff --git a/Source/ActionRPGGame/UI/ARHUD.h b/Source/ActionRPGGame/Public/UI/ARHUD.h similarity index 100% rename from Source/ActionRPGGame/UI/ARHUD.h rename to Source/ActionRPGGame/Public/UI/ARHUD.h diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.cpp b/Source/ActionRPGGame/Public/UI/ARHUDWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/ARHUDWidget.cpp rename to Source/ActionRPGGame/Public/UI/ARHUDWidget.cpp diff --git a/Source/ActionRPGGame/UI/ARHUDWidget.h b/Source/ActionRPGGame/Public/UI/ARHUDWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/ARHUDWidget.h rename to Source/ActionRPGGame/Public/UI/ARHUDWidget.h diff --git a/Source/ActionRPGGame/UI/ARUIComponent.cpp b/Source/ActionRPGGame/Public/UI/ARUIComponent.cpp similarity index 100% rename from Source/ActionRPGGame/UI/ARUIComponent.cpp rename to Source/ActionRPGGame/Public/UI/ARUIComponent.cpp diff --git a/Source/ActionRPGGame/UI/ARUIComponent.h b/Source/ActionRPGGame/Public/UI/ARUIComponent.h similarity index 100% rename from Source/ActionRPGGame/UI/ARUIComponent.h rename to Source/ActionRPGGame/Public/UI/ARUIComponent.h diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp b/Source/ActionRPGGame/Public/UI/ARUMGWidgetBase.cpp similarity index 100% rename from Source/ActionRPGGame/UI/ARUMGWidgetBase.cpp rename to Source/ActionRPGGame/Public/UI/ARUMGWidgetBase.cpp diff --git a/Source/ActionRPGGame/UI/ARUMGWidgetBase.h b/Source/ActionRPGGame/Public/UI/ARUMGWidgetBase.h similarity index 100% rename from Source/ActionRPGGame/UI/ARUMGWidgetBase.h rename to Source/ActionRPGGame/Public/UI/ARUMGWidgetBase.h diff --git a/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp b/Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.cpp similarity index 100% rename from Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.cpp rename to Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.cpp diff --git a/Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.h b/Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.h similarity index 100% rename from Source/ActionRPGGame/UI/HUD/AREnemyHealthBar.h rename to Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.h diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp b/Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshair.cpp similarity index 100% rename from Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.cpp rename to Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshair.cpp diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h b/Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshair.h similarity index 100% rename from Source/ActionRPGGame/UI/HUD/ARHUDCrosshair.h rename to Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshair.h diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.cpp b/Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshairInfo.cpp similarity index 100% rename from Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.cpp rename to Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshairInfo.cpp diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h b/Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshairInfo.h similarity index 100% rename from Source/ActionRPGGame/UI/HUD/ARHUDCrosshairInfo.h rename to Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshairInfo.h diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp b/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.cpp similarity index 100% rename from Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.cpp rename to Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.cpp diff --git a/Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h b/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.h similarity index 100% rename from Source/ActionRPGGame/UI/HUD/ARHUDPlayerInfo.h rename to Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.h diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARInventoryScreenWidget.h rename to Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h diff --git a/Source/ActionRPGGame/UI/Inventory/ARItemView.cpp b/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARItemView.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/ARItemView.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/ARItemView.h b/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARItemView.h rename to Source/ActionRPGGame/Public/UI/Inventory/ARItemView.h diff --git a/Source/ActionRPGGame/UI/Inventory/ARListItemView.cpp b/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARListItemView.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/ARListItemView.h b/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARListItemView.h rename to Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.h diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/ARUIInventoryComponent.h rename to Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/ARItemWeaponWidget.h rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARListItemWeaponWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/ARListItemWeaponWidget.h rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARListItemWeaponWidget.h diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponContainerWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/ARWeaponContainerWidget.h rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponContainerWidget.h diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp diff --git a/Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h similarity index 100% rename from Source/ActionRPGGame/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h rename to Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h diff --git a/Source/ActionRPGGame/UI/SARCrosshairBase.cpp b/Source/ActionRPGGame/Public/UI/SARCrosshairBase.cpp similarity index 100% rename from Source/ActionRPGGame/UI/SARCrosshairBase.cpp rename to Source/ActionRPGGame/Public/UI/SARCrosshairBase.cpp diff --git a/Source/ActionRPGGame/UI/SARCrosshairBase.h b/Source/ActionRPGGame/Public/UI/SARCrosshairBase.h similarity index 100% rename from Source/ActionRPGGame/UI/SARCrosshairBase.h rename to Source/ActionRPGGame/Public/UI/SARCrosshairBase.h diff --git a/Source/ActionRPGGame/UI/SARDrawTestWidget.cpp b/Source/ActionRPGGame/Public/UI/SARDrawTestWidget.cpp similarity index 100% rename from Source/ActionRPGGame/UI/SARDrawTestWidget.cpp rename to Source/ActionRPGGame/Public/UI/SARDrawTestWidget.cpp diff --git a/Source/ActionRPGGame/UI/SARDrawTestWidget.h b/Source/ActionRPGGame/Public/UI/SARDrawTestWidget.h similarity index 100% rename from Source/ActionRPGGame/UI/SARDrawTestWidget.h rename to Source/ActionRPGGame/Public/UI/SARDrawTestWidget.h diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARItemWeapon.cpp rename to Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp diff --git a/Source/ActionRPGGame/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARItemWeapon.h rename to Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.cpp b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeEffect.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.cpp rename to Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeEffect.cpp diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.h b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeEffect.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARMagazineUpgradeEffect.h rename to Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeEffect.h diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.cpp b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.cpp rename to Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.cpp diff --git a/Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARMagazineUpgradeItem.h rename to Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.cpp rename to Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.cpp diff --git a/Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponAbilityBase.h rename to Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponBase.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponBase.cpp rename to Source/ActionRPGGame/Public/Weapons/ARWeaponBase.cpp diff --git a/Source/ActionRPGGame/Weapons/ARWeaponBase.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponBase.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponBase.h rename to Source/ActionRPGGame/Public/Weapons/ARWeaponBase.h diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp similarity index 78% rename from Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp rename to Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index 66dd993..723a6a7 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -17,7 +17,7 @@ UARWeaponInventoryComponent::UARWeaponInventoryComponent() MaxSlots = 4; AvailableSlots = 4; - + CurrentWeaponIndex = -1; // ... } @@ -155,7 +155,7 @@ void UARWeaponInventoryComponent::MulticastRemoveWeapon_Implementation(const FAR } -void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(uint8 WeaponIndex, const FARWeaponRPC& WeaponData) +void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(int8 WeaponIndex, const FARWeaponRPC& WeaponData) { if (AARCharacter* Character = Cast(POwner)) { @@ -164,8 +164,22 @@ void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(uint8 Weap } CurrentWeaponIndex = WeaponIndex; } - -void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, const FARWeaponRPC& WeaponData) +void UARWeaponInventoryComponent::MulticastUnequipWeapon_Implementation(int8 OldWeaponIndex, const FARWeaponRPC& WeaponData) +{ + UARItemWeapon* EquipedWeapon = GetItem(OldWeaponIndex); + if (!EquipedWeapon) + return; + if (AARCharacter* Character = Cast(POwner)) + { + if (!Character->GetEquipedMainWeapon()->GetChildActor()) + { + return; + } + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + } + SetWeapon(WeaponData, GroupToComponent[OldWeaponIndex]); +} +void UARWeaponInventoryComponent::Equip(int8 WeaponIndex, const FARWeaponRPC& WeaponData) { if (AARCharacter* Character = Cast(POwner)) { @@ -181,25 +195,28 @@ void UARWeaponInventoryComponent::Equip(uint8 WeaponIndex, const FARWeaponRPC& W CurrentWeaponIndex = WeaponIndex; } } -void UARWeaponInventoryComponent::Unequip(uint8 WeaponIndex) +void UARWeaponInventoryComponent::Unequip(int8 WeaponIndex) { - //MainHandWeapon.Weapon.Reset(); - //MainHandWeapon.Position = FVector(0,0,0); - //MainHandWeapon.Rotation = FRotator(0,0,0); - //MainHandWeapon.NetIndex = 0; - //MainHandWeapon.RepCounter++; - //WeaponHelper[WeaponIndex]->Weapon.Reset(); - //WeaponHelper[WeaponIndex]->RepCounter++; - - //if (AARCharacter* Character = Cast(POwner)) - //{ - // SetWeapon(MainHandWeapon, Character->GetEquipedMainWeapon()); - // GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); - // if (AARPlayerController* PC = Cast(Character->Controller)) - // { - // PC->WeaponManager->RemoveAbility(static_cast(WeaponIndex), EAMSlot::Slot001); - // } - //} + UARItemWeapon* EquipedWeapon = GetItem(WeaponIndex); + if (!EquipedWeapon) + return; + if (AARCharacter* Character = Cast(POwner)) + { + if (!Character->GetEquipedMainWeapon()->GetChildActor()) + { + return; + } + Character->GetAbilityComp()->RemoveAbilitiesFromActions(EquipedWeapon->Ability); + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + } + FARWeaponRPC Data; + Data.Weapon = EquipedWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = EquipedWeapon->HolsteredPosition; + Data.Rotation = EquipedWeapon->HolsteredRotation; + Data.AttachSlot = static_cast(WeaponIndex); + SetWeapon(Data, GroupToComponent[WeaponIndex]); + ServerHolster(Data); } void UARWeaponInventoryComponent::Holster() { @@ -219,6 +236,7 @@ void UARWeaponInventoryComponent::Holster() Data.AttachSlot = static_cast(CurrentWeaponIndex); SetWeapon(Data, GroupToComponent[CurrentWeaponIndex]); ServerHolster(Data); + CurrentWeaponIndex = -1; } void UARWeaponInventoryComponent::ServerHolster_Implementation(const FARWeaponRPC& WeaponData) { @@ -231,20 +249,21 @@ bool UARWeaponInventoryComponent::ServerHolster_Validate(const FARWeaponRPC& Wea void UARWeaponInventoryComponent::MulticastHolster_Implementation(const FARWeaponRPC& WeaponData) { SetWeapon(WeaponData, GroupToComponent[CurrentWeaponIndex]); + CurrentWeaponIndex = -1; } -void UARWeaponInventoryComponent::SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility) +void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility) { } void UARWeaponInventoryComponent::NextWeapon() { - uint8 OldGroup = CurrentWeaponIndex; + int8 OldGroup = CurrentWeaponIndex; ENetMode NetMode = GetOwner()->GetNetMode(); if (NetMode == ENetMode::NM_Client || NetMode == ENetMode::NM_Standalone) { - uint8 CurrentIndex = CurrentWeaponIndex; + int8 CurrentIndex = CurrentWeaponIndex; CurrentIndex++; if (CurrentIndex > 4) { @@ -267,6 +286,9 @@ void UARWeaponInventoryComponent::NextWeapon() Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; Data.AttachSlot = EARWeaponPosition::Equiped; + if(OldGroup > -1) + Unequip(OldGroup); + Equip(CurrentWeaponIndex, Data); if (GetOwnerRole() < ENetRole::ROLE_Authority) { @@ -275,9 +297,9 @@ void UARWeaponInventoryComponent::NextWeapon() } void UARWeaponInventoryComponent::PreviousWeapon() { - uint8 OldGroup = CurrentWeaponIndex; + int8 OldGroup = CurrentWeaponIndex; - uint8 CurrentIndex = CurrentWeaponIndex; + int8 CurrentIndex = CurrentWeaponIndex; CurrentIndex--; CurrentWeaponIndex = CurrentIndex; if (CurrentIndex < 0) @@ -299,11 +321,11 @@ void UARWeaponInventoryComponent::HolsterWeapon() { Holster(); } -void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIndex) +void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(int8 WeaponIndex) { - uint8 OldGroup = CurrentWeaponIndex; + int8 OldGroup = CurrentWeaponIndex; - uint8 CurrentIndex = CurrentWeaponIndex; + int8 CurrentIndex = CurrentWeaponIndex; //if (WeaponIndex > CurrentIndex) CurrentIndex++; @@ -316,6 +338,20 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIn CurrentWeaponIndex = CurrentIndex; } + if (OldGroup > -1) + { + UARItemWeapon* OldWeapon = GetItem(OldGroup); + if (OldWeapon) + { + FARWeaponRPC OldData; + OldData.Weapon = OldWeapon->Weapon; + OldData.Position = OldWeapon->HolsteredPosition; + OldData.Rotation = OldWeapon->HolsteredRotation; + OldData.AttachSlot = static_cast(OldGroup); + MulticastUnequipWeapon(OldGroup, OldData); + } + } + UARItemWeapon* InWeapon = GetItem(CurrentWeaponIndex); if (!InWeapon) { @@ -323,11 +359,9 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIn } FARWeaponRPC Data; Data.Weapon = InWeapon->Weapon; - //Data.SocketName = InWeapon->Socket; Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; Data.AttachSlot = EARWeaponPosition::Equiped; - MulticastEquipWeapon(CurrentWeaponIndex, Data); if (WeaponIndex == CurrentWeaponIndex) { @@ -338,11 +372,11 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(uint8 WeaponIn ClientNextWeapon(CurrentWeaponIndex, false); } } -bool UARWeaponInventoryComponent::ServerNextWeapon_Validate(uint8 WeaponIndex) +bool UARWeaponInventoryComponent::ServerNextWeapon_Validate(int8 WeaponIndex) { return true; } -void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess) +void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess) { if (bPredictionSuccess) return; @@ -352,9 +386,9 @@ void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(uint8 WeaponIn //Equip(WeaponIndex, NextWeaponAbility); } -void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 WeaponIndex) +void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(int8 WeaponIndex) { - uint8 CurrentIndex = CurrentWeaponIndex; + int8 CurrentIndex = CurrentWeaponIndex; if (CurrentIndex > WeaponIndex) CurrentIndex--; @@ -367,11 +401,29 @@ void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 Weap CurrentWeaponIndex = CurrentIndex; } - UARItemWeapon* NextWeaponAbility = GetItem(CurrentWeaponIndex); - if (!NextWeaponAbility) + UARItemWeapon* OldWeapon = GetItem(CurrentIndex); + if (OldWeapon) { - NextWeaponAbility = FindPreviousValid(); + FARWeaponRPC OldData; + OldData.Weapon = OldWeapon->Weapon; + OldData.Position = OldWeapon->HolsteredPosition; + OldData.Rotation = OldWeapon->HolsteredRotation; + OldData.AttachSlot = static_cast(CurrentIndex); + MulticastUnequipWeapon(CurrentIndex, OldData); } + + UARItemWeapon* InWeapon = GetItem(CurrentWeaponIndex); + if (!InWeapon) + { + InWeapon = FindNextValid(); + } + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + Data.Position = InWeapon->EquipedPosition; + Data.Rotation = InWeapon->EquipedRotation; + Data.AttachSlot = EARWeaponPosition::Equiped; + MulticastEquipWeapon(CurrentWeaponIndex, Data); + //so Server index is different. Client might tried to cheat //or sometrhing. We will override it. //situation where client can chage multiple weapons within second @@ -387,11 +439,11 @@ void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(uint8 Weap ClientPreviousWeapon(CurrentWeaponIndex, true); } } -bool UARWeaponInventoryComponent::ServerPreviousWeapon_Validate(uint8 WeaponIndex) +bool UARWeaponInventoryComponent::ServerPreviousWeapon_Validate(int8 WeaponIndex) { return true; } -void UARWeaponInventoryComponent::ClientPreviousWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess) +void UARWeaponInventoryComponent::ClientPreviousWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess) { if (bPredictionSuccess) return; @@ -403,7 +455,7 @@ UARItemWeapon* UARWeaponInventoryComponent::FindNextValid() { UARItemWeapon* WeaponAbilityTag = nullptr; - uint8 Idx = CurrentWeaponIndex; + int8 Idx = CurrentWeaponIndex; while (!WeaponAbilityTag) { Idx++; @@ -429,7 +481,7 @@ UARItemWeapon* UARWeaponInventoryComponent::FindNextValid() UARItemWeapon* UARWeaponInventoryComponent::FindPreviousValid() { UARItemWeapon* WeaponAbilityTag = nullptr; - uint8 Idx = CurrentWeaponIndex; + int8 Idx = CurrentWeaponIndex; while (!WeaponAbilityTag) { Idx--; @@ -462,7 +514,7 @@ void UARWeaponInventoryComponent::AsynWeaponLoaded(UChildActorComponent* Compone Component->SetRelativeLocation(InWeapon.Position); Component->SetRelativeRotation(InWeapon.Rotation); } -void UARWeaponInventoryComponent::AddMagazineMod(uint8 WeaponIdx, uint8 MagazineModIndex) +void UARWeaponInventoryComponent::AddMagazineMod(int8 WeaponIdx, int8 MagazineModIndex) { if (GetOwnerRole() < ENetRole::ROLE_Authority) { @@ -489,7 +541,7 @@ void UARWeaponInventoryComponent::AddMagazineMod(uint8 WeaponIdx, uint8 Magazine } } } -void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(uint8 WeaponIdx, uint8 MagazineModIndex) +void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex) { if (AARCharacter* Character = Cast(GetOwner())) { @@ -510,7 +562,7 @@ void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(uint8 Weap } } } -bool UARWeaponInventoryComponent::ServerAddMagazineMod_Validate(uint8 WeaponIdx, uint8 MagazineModIndex) +bool UARWeaponInventoryComponent::ServerAddMagazineMod_Validate(int8 WeaponIdx, int8 MagazineModIndex) { return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h similarity index 71% rename from Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h rename to Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index b6fcbff..662634b 100644 --- a/Source/ActionRPGGame/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -31,10 +31,10 @@ struct FARWeapon UPROPERTY(EditAnywhere, Category = "Attachment Test") FRotator Rotation; UPROPERTY(EditAnywhere, Category = "Attachment Test") - uint8 NetIndex; + int8 NetIndex; UPROPERTY(EditAnywhere, Category = "Attachment Test") - uint8 RepCounter; + int8 RepCounter; }; UENUM() @@ -76,10 +76,10 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone UPROPERTY() class APawn* POwner; - TMap GroupToComponent; + TMap GroupToComponent; TMap GroupToItem; - uint8 CurrentWeaponIndex; + int8 CurrentWeaponIndex; public: // Sets default values for this component's properties @@ -108,11 +108,15 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void MulticastRemoveWeapon_Implementation(const FARWeaponRPC& WeaponData); UFUNCTION(NetMulticast, Reliable) - void MulticastEquipWeapon(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); - void MulticastEquipWeapon_Implementation(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); + void MulticastEquipWeapon(int8 WeaponIndex, const FARWeaponRPC& WeaponData); + void MulticastEquipWeapon_Implementation(int8 WeaponIndex, const FARWeaponRPC& WeaponData); - void Equip(uint8 WeaponIndex, const FARWeaponRPC& WeaponData); - void Unequip(uint8 WeaponIndex); + UFUNCTION(NetMulticast, Reliable) + void MulticastUnequipWeapon(int8 OldWeaponIndex, const FARWeaponRPC& WeaponData); + void MulticastUnequipWeapon_Implementation(int8 OldWeaponIndex, const FARWeaponRPC& WeaponData); + + void Equip(int8 WeaponIndex, const FARWeaponRPC& WeaponData); + void Unequip(int8 WeaponIndex); void Holster(); UFUNCTION(Server, Reliable, WithValidation) @@ -127,7 +131,7 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone { POwner = InPawn; } - void SetAbilityToItem(uint8 InLocalIndex, class UGAAbilityBase* InAbility); + void SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility); UFUNCTION(BlueprintCallable) void NextWeapon(); UFUNCTION(BlueprintCallable) @@ -138,20 +142,20 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone protected: UFUNCTION(Server, Reliable, WithValidation) - void ServerNextWeapon(uint8 WeaponIndex); - void ServerNextWeapon_Implementation(uint8 WeaponIndex); - bool ServerNextWeapon_Validate(uint8 WeaponIndex); + void ServerNextWeapon(int8 WeaponIndex); + void ServerNextWeapon_Implementation(int8 WeaponIndex); + bool ServerNextWeapon_Validate(int8 WeaponIndex); UFUNCTION(Client, Reliable) - void ClientNextWeapon(uint8 WeaponIndex, bool bPredictionSuccess); - void ClientNextWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess); + void ClientNextWeapon(int8 WeaponIndex, bool bPredictionSuccess); + void ClientNextWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess); UFUNCTION(Server, Reliable, WithValidation) - void ServerPreviousWeapon(uint8 WeaponIndex); - void ServerPreviousWeapon_Implementation(uint8 WeaponIndex); - bool ServerPreviousWeapon_Validate(uint8 WeaponIndex); + void ServerPreviousWeapon(int8 WeaponIndex); + void ServerPreviousWeapon_Implementation(int8 WeaponIndex); + bool ServerPreviousWeapon_Validate(int8 WeaponIndex); UFUNCTION(Client, Reliable) - void ClientPreviousWeapon(uint8 WeaponIndex, bool bPredictionSuccess); - void ClientPreviousWeapon_Implementation(uint8 WeaponIndex, bool bPredictionSuccess); + void ClientPreviousWeapon(int8 WeaponIndex, bool bPredictionSuccess); + void ClientPreviousWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess); UARItemWeapon* FindNextValid(); UARItemWeapon* FindPreviousValid(); @@ -164,11 +168,11 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone public: //Local Indexes - void AddMagazineMod(uint8 WeaponIdx, uint8 MagazineModIndex); + void AddMagazineMod(int8 WeaponIdx, int8 MagazineModIndex); UFUNCTION(Server, Reliable, WithValidation) - void ServerAddMagazineMod(uint8 WeaponIdx, uint8 MagazineModIndex); + void ServerAddMagazineMod(int8 WeaponIdx, int8 MagazineModIndex); - void ServerAddMagazineMod_Implementation(uint8 WeaponIdx, uint8 MagazineModIndex); - bool ServerAddMagazineMod_Validate(uint8 WeaponIdx, uint8 MagazineModIndex); + void ServerAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex); + bool ServerAddMagazineMod_Validate(int8 WeaponIdx, int8 MagazineModIndex); }; diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.cpp rename to Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.cpp diff --git a/Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponManagerComponent.h rename to Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.h diff --git a/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponUpgradeItem.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.cpp rename to Source/ActionRPGGame/Public/Weapons/ARWeaponUpgradeItem.cpp diff --git a/Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponUpgradeItem.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponUpgradeItem.h rename to Source/ActionRPGGame/Public/Weapons/ARWeaponUpgradeItem.h diff --git a/Source/ActionRPGGame/Weapons/ARWeaponsTypes.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponsTypes.cpp similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponsTypes.cpp rename to Source/ActionRPGGame/Public/Weapons/ARWeaponsTypes.cpp diff --git a/Source/ActionRPGGame/Weapons/ARWeaponsTypes.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponsTypes.h similarity index 100% rename from Source/ActionRPGGame/Weapons/ARWeaponsTypes.h rename to Source/ActionRPGGame/Public/Weapons/ARWeaponsTypes.h From 316fa4484087d6559d408e81d7fae3496b77c281 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 14:11:22 +0200 Subject: [PATCH 152/187] weaponm abilities are now instanced trough weapon inventory component --- .../Public/ARPlayerController.cpp | 7 +- .../Weapons/ARWeaponInventoryComponent.cpp | 119 +++++++++++++++--- .../Weapons/ARWeaponInventoryComponent.h | 11 +- 3 files changed, 115 insertions(+), 22 deletions(-) diff --git a/Source/ActionRPGGame/Public/ARPlayerController.cpp b/Source/ActionRPGGame/Public/ARPlayerController.cpp index c9974f6..fd6dc29 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.cpp +++ b/Source/ActionRPGGame/Public/ARPlayerController.cpp @@ -6,6 +6,7 @@ #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "ARAbilityBase.h" +#include "ARCharacter.h" #include "Weapons/ARWeaponManagerComponent.h" #include "Abilities/ARAbilityManagerComponent.h" @@ -50,7 +51,11 @@ void AARPlayerController::BeginPlay() AbilityManager->BindInputs(InputComponent, AbilityComp); - WeaponManager->BindInputs(InputComponent, AbilityComp); + AARCharacter* Character = Cast(GetPawn()); + + Character->WeaponInventory->BindInputs(InputComponent, AbilityComp); + + //WeaponManager->BindInputs(InputComponent, AbilityComp); bInputBount = true; } //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index 723a6a7..7210457 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -5,6 +5,7 @@ #include "ARItemWeapon.h" #include "ARCharacter.h" #include "ARPlayerController.h" +#include "AFAbilityComponent.h" #include "Weapons/ARWeaponManagerComponent.h" // Sets default values for this component's properties @@ -30,7 +31,16 @@ void UARWeaponInventoryComponent::BeginPlay() // ... } +void UARWeaponInventoryComponent::BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent) +{ + if (!AbilityComponent) + return; + for (const FGameplayTag& Input : WeaponInput) + { + AbilityComponent->BindAbilityToAction(InputComponent, Input); + } +} void UARWeaponInventoryComponent::InitializeWeapons(APawn* Pawn) { if (AARCharacter* Character = Cast(Pawn)) @@ -79,10 +89,38 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde SetWeapon(Data, GroupToComponent[LocalIndex]); if (AARCharacter* Character = Cast(POwner)) { - if (AARPlayerController* PC = Cast(Character->Controller)) + TArray NoInput; + FAFOnAbilityReady del; + { + del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability); + Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); + } + Character->GetAbilityComp()->NativeAddAbility(InWeapon->Ability, NoInput); + /*if (AARPlayerController* PC = Cast(Character->Controller)) { PC->WeaponManager->NativeEquipAbility(InWeapon->Ability, static_cast(LocalIndex), EAMSlot::Slot001, false); + }*/ + } +} +void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr InAbilityTag) +{ + AARCharacter* Character = Cast(POwner); + if (!Character) + return; + + UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); + + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + + AARPlayerController* PC = Cast(GetOwner()); + if (PC) + { + if (AARCharacter* Character = Cast(PC->GetPawn())) + { + //UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); + Character->WeaponInventory->SetAbilityToItem(CurrentWeaponIndex, Ability); } + } } void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) @@ -157,6 +195,7 @@ void UARWeaponInventoryComponent::MulticastRemoveWeapon_Implementation(const FAR void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(int8 WeaponIndex, const FARWeaponRPC& WeaponData) { + ENetRole Role = GetOwnerRole(); if (AARCharacter* Character = Cast(POwner)) { SetWeapon(WeaponData, Character->GetEquipedMainWeapon()); @@ -181,17 +220,13 @@ void UARWeaponInventoryComponent::MulticastUnequipWeapon_Implementation(int8 Old } void UARWeaponInventoryComponent::Equip(int8 WeaponIndex, const FARWeaponRPC& WeaponData) { + if (WeaponIndex < 0) + return; + if (AARCharacter* Character = Cast(POwner)) { SetWeapon(WeaponData, Character->GetEquipedMainWeapon()); GroupToComponent[WeaponIndex]->SetChildActorClass(nullptr); - if (AARPlayerController* PC = Cast(Character->Controller)) - { - UARItemWeapon* ItemWeapon = GetItem(WeaponIndex); - FSoftObjectPath Path = ItemWeapon->Ability.ToSoftObjectPath(); - TSoftClassPtr ab(Path); - PC->WeaponManager->EquipWeapon(ab); - } CurrentWeaponIndex = WeaponIndex; } } @@ -217,6 +252,7 @@ void UARWeaponInventoryComponent::Unequip(int8 WeaponIndex) Data.AttachSlot = static_cast(WeaponIndex); SetWeapon(Data, GroupToComponent[WeaponIndex]); ServerHolster(Data); + CurrentWeaponIndex = -1; } void UARWeaponInventoryComponent::Holster() { @@ -248,8 +284,13 @@ bool UARWeaponInventoryComponent::ServerHolster_Validate(const FARWeaponRPC& Wea } void UARWeaponInventoryComponent::MulticastHolster_Implementation(const FARWeaponRPC& WeaponData) { - SetWeapon(WeaponData, GroupToComponent[CurrentWeaponIndex]); - CurrentWeaponIndex = -1; + ENetRole Role = GetOwnerRole(); + if (Role != ENetRole::ROLE_AutonomousProxy + && Role != ENetRole::ROLE_Authority) + { + SetWeapon(WeaponData, GroupToComponent[CurrentWeaponIndex]); + CurrentWeaponIndex = -1; + } } void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility) { @@ -257,15 +298,40 @@ void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAA } void UARWeaponInventoryComponent::NextWeapon() { + ENetMode NetMode = GetOwner()->GetNetMode(); + bool bProceed = false; + switch (NetMode) + { + case NM_Standalone: + bProceed = true; + break; + case NM_DedicatedServer: + break; + case NM_ListenServer: + break; + case NM_Client: + bProceed = true; + break; + case NM_MAX: + break; + default: + break; + } + + if (!bProceed) + { + return; + } int8 OldGroup = CurrentWeaponIndex; + if (OldGroup > -1) + Unequip(OldGroup); - ENetMode NetMode = GetOwner()->GetNetMode(); if (NetMode == ENetMode::NM_Client || NetMode == ENetMode::NM_Standalone) { int8 CurrentIndex = CurrentWeaponIndex; CurrentIndex++; - if (CurrentIndex > 4) + if (CurrentIndex > 4 || CurrentIndex < 0) { CurrentWeaponIndex = 0; } @@ -286,8 +352,7 @@ void UARWeaponInventoryComponent::NextWeapon() Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; Data.AttachSlot = EARWeaponPosition::Equiped; - if(OldGroup > -1) - Unequip(OldGroup); + Equip(CurrentWeaponIndex, Data); if (GetOwnerRole() < ENetRole::ROLE_Authority) @@ -329,7 +394,7 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(int8 WeaponInd //if (WeaponIndex > CurrentIndex) CurrentIndex++; - if (CurrentIndex > 4) + if (CurrentIndex > 4 || CurrentIndex < 0) { CurrentWeaponIndex = 0; } @@ -379,11 +444,29 @@ bool UARWeaponInventoryComponent::ServerNextWeapon_Validate(int8 WeaponIndex) void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess) { if (bPredictionSuccess) - return; + { + UARItemWeapon* NextWeaponAbility = GetItem(WeaponIndex); + if (AARCharacter* Character = Cast(POwner)) + { + UARItemWeapon* Item = GetItem(WeaponIndex); + + UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); + if (!AbilityComp) + return; + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); + } + else + { + AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); + } + } + return; + } CurrentWeaponIndex = WeaponIndex; - UARItemWeapon* NextWeaponAbility = GetItem(WeaponIndex); - //Equip(WeaponIndex, NextWeaponAbility); + } void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(int8 WeaponIndex) diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 662634b..944dd8f 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -10,7 +10,7 @@ #include "IFInventoryComponent.h" #include "IFEquipmentComponent.h" #include "AMTypes.h" - +#include "Weapons/ARWeaponAbilityBase.h" #include "ARWeaponInventoryComponent.generated.h" USTRUCT() @@ -76,6 +76,9 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone UPROPERTY() class APawn* POwner; + UPROPERTY(EditAnywhere, CAtegory = "Input") + TArray WeaponInput; + TMap GroupToComponent; TMap GroupToItem; @@ -84,11 +87,11 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone public: // Sets default values for this component's properties UARWeaponInventoryComponent(); - + void BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent); protected: // Called when the game starts virtual void BeginPlay() override; - + public: void InitializeWeapons(APawn* Pawn); // Called every frame @@ -99,6 +102,8 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; virtual void OnServerItemRemoved(uint8 LocalIndex) override; + void OnWeaponReady(TSoftClassPtr InAbilityTag); + UFUNCTION(NetMulticast, Reliable) void MulticastAddWeapon(const FARWeaponRPC& WeaponData); void MulticastAddWeapon_Implementation(const FARWeaponRPC& WeaponData); From 8a6f373edc9556e6581c8d0cf545121880ea2cb8 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 15:19:30 +0200 Subject: [PATCH 153/187] removing weapon manager component --- .../Public/ARPlayerController.cpp | 5 - .../ActionRPGGame/Public/ARPlayerController.h | 2 - .../Weapons/ARWeaponInventoryComponent.cpp | 146 ++++++++++++------ .../Weapons/ARWeaponInventoryComponent.h | 4 + .../Weapons/ARWeaponManagerComponent.cpp | 129 ---------------- .../Public/Weapons/ARWeaponManagerComponent.h | 91 ----------- 6 files changed, 100 insertions(+), 277 deletions(-) delete mode 100644 Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.cpp delete mode 100644 Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.h diff --git a/Source/ActionRPGGame/Public/ARPlayerController.cpp b/Source/ActionRPGGame/Public/ARPlayerController.cpp index fd6dc29..1833727 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.cpp +++ b/Source/ActionRPGGame/Public/ARPlayerController.cpp @@ -8,7 +8,6 @@ #include "ARAbilityBase.h" #include "ARCharacter.h" -#include "Weapons/ARWeaponManagerComponent.h" #include "Abilities/ARAbilityManagerComponent.h" #include "UI/ARHUD.h" @@ -17,7 +16,6 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial : Super(ObjectInitializer) { UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); - WeaponManager = ObjectInitializer.CreateDefaultSubobject(this, "WeaponManager"); AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); MainInventory = ObjectInitializer.CreateDefaultSubobject(this, "MainInventory"); MainInventory->SetIsReplicated(true); @@ -55,7 +53,6 @@ void AARPlayerController::BeginPlay() Character->WeaponInventory->BindInputs(InputComponent, AbilityComp); - //WeaponManager->BindInputs(InputComponent, AbilityComp); bInputBount = true; } //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. @@ -121,8 +118,6 @@ void AARPlayerController::Possess(APawn* aPawn) { ClientPossesed(aPawn); } - - WeaponManager->POwner = aPawn; } void AARPlayerController::ClientPossesed_Implementation(APawn* InPawn) diff --git a/Source/ActionRPGGame/Public/ARPlayerController.h b/Source/ActionRPGGame/Public/ARPlayerController.h index e294c8f..b1b2bde 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.h +++ b/Source/ActionRPGGame/Public/ARPlayerController.h @@ -19,8 +19,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I public: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIComponent* UIComponent; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") - class UARWeaponManagerComponent* WeaponManager; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARAbilityManagerComponent* AbilityManager; diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index 7210457..2ce5245 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -6,7 +6,6 @@ #include "ARCharacter.h" #include "ARPlayerController.h" #include "AFAbilityComponent.h" -#include "Weapons/ARWeaponManagerComponent.h" // Sets default values for this component's properties UARWeaponInventoryComponent::UARWeaponInventoryComponent() @@ -18,6 +17,7 @@ UARWeaponInventoryComponent::UARWeaponInventoryComponent() MaxSlots = 4; AvailableSlots = 4; + WeaponAbilities.SetNum(4); CurrentWeaponIndex = -1; // ... } @@ -96,10 +96,7 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); } Character->GetAbilityComp()->NativeAddAbility(InWeapon->Ability, NoInput); - /*if (AARPlayerController* PC = Cast(Character->Controller)) - { - PC->WeaponManager->NativeEquipAbility(InWeapon->Ability, static_cast(LocalIndex), EAMSlot::Slot001, false); - }*/ + WeaponAbilities[LocalIndex] = InWeapon->Ability; } } void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr InAbilityTag) @@ -117,7 +114,6 @@ void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr(PC->GetPawn())) { - //UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); Character->WeaponInventory->SetAbilityToItem(CurrentWeaponIndex, Ability); } @@ -125,13 +121,10 @@ void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr(POwner)) - { - if (AARPlayerController* PC = Cast(Character->Controller)) - { - PC->WeaponManager->NativeRemoveAbility(TSoftClassPtr(), static_cast(LocalIndex), EAMSlot::Slot001); - } - } + AARCharacter* Character = Cast(POwner); + + Character->GetAbilityComp()->NativeRemoveAbility(WeaponAbilities[LocalIndex]); + FARWeaponRPC Data; Data.Weapon.Reset(); //Data.SocketName = InWeapon->Socket; @@ -322,23 +315,20 @@ void UARWeaponInventoryComponent::NextWeapon() { return; } + int8 OldGroup = CurrentWeaponIndex; if (OldGroup > -1) Unequip(OldGroup); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) + int8 CurrentIndex = CurrentWeaponIndex; + CurrentIndex++; + if (CurrentIndex > 4 || CurrentIndex < 0) { - int8 CurrentIndex = CurrentWeaponIndex; - CurrentIndex++; - if (CurrentIndex > 4 || CurrentIndex < 0) - { - CurrentWeaponIndex = 0; - } - else - { - CurrentWeaponIndex = CurrentIndex; - } + CurrentWeaponIndex = 0; + } + else + { + CurrentWeaponIndex = CurrentIndex; } UARItemWeapon* InWeapon = GetItem(CurrentWeaponIndex); @@ -362,6 +352,30 @@ void UARWeaponInventoryComponent::NextWeapon() } void UARWeaponInventoryComponent::PreviousWeapon() { + ENetMode NetMode = GetOwner()->GetNetMode(); + bool bProceed = false; + switch (NetMode) + { + case NM_Standalone: + bProceed = true; + break; + case NM_DedicatedServer: + break; + case NM_ListenServer: + break; + case NM_Client: + bProceed = true; + break; + case NM_MAX: + break; + default: + break; + } + + if (!bProceed) + { + return; + } int8 OldGroup = CurrentWeaponIndex; int8 CurrentIndex = CurrentWeaponIndex; @@ -443,30 +457,7 @@ bool UARWeaponInventoryComponent::ServerNextWeapon_Validate(int8 WeaponIndex) } void UARWeaponInventoryComponent::ClientNextWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess) { - if (bPredictionSuccess) - { - UARItemWeapon* NextWeaponAbility = GetItem(WeaponIndex); - if (AARCharacter* Character = Cast(POwner)) - { - UARItemWeapon* Item = GetItem(WeaponIndex); - - UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); - if (!AbilityComp) - return; - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); - } - else - { - AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); - } - } - return; - } - CurrentWeaponIndex = WeaponIndex; - + HandleClientPrediction(WeaponIndex, bPredictionSuccess); } void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(int8 WeaponIndex) @@ -527,12 +518,67 @@ bool UARWeaponInventoryComponent::ServerPreviousWeapon_Validate(int8 WeaponIndex return true; } void UARWeaponInventoryComponent::ClientPreviousWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess) +{ + HandleClientPrediction(WeaponIndex, bPredictionSuccess); +} + +void UARWeaponInventoryComponent::HandleClientPrediction(int8 WeaponIndex, bool bPredictionSuccess) { if (bPredictionSuccess) + { + if (AARCharacter* Character = Cast(POwner)) + { + UARItemWeapon* Item = GetItem(WeaponIndex); + + UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); + if (!AbilityComp) + return; + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); + } + else + { + AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); + } + } return; -} + } + else //override client decision. + { + CurrentWeaponIndex = WeaponIndex; + UARItemWeapon* InWeapon = GetItem(CurrentWeaponIndex); + if (!InWeapon) + { + InWeapon = FindNextValid(); + } + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = InWeapon->EquipedPosition; + Data.Rotation = InWeapon->EquipedRotation; + Data.AttachSlot = EARWeaponPosition::Equiped; + + Equip(CurrentWeaponIndex, Data); + if (AARCharacter* Character = Cast(POwner)) + { + UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); + if (!AbilityComp) + return; + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + AbilityComp->SetAbilityToAction(InWeapon->Ability, WeaponInput, FAFOnAbilityReady()); + } + else + { + AbilityComp->SetAbilityToAction(InWeapon->Ability, WeaponInput, FAFOnAbilityReady()); + } + } + } +} UARItemWeapon* UARWeaponInventoryComponent::FindNextValid() { diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 944dd8f..0a89d4a 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -82,6 +82,8 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone TMap GroupToComponent; TMap GroupToItem; + TArray> WeaponAbilities; + int8 CurrentWeaponIndex; public: @@ -162,6 +164,8 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void ClientPreviousWeapon(int8 WeaponIndex, bool bPredictionSuccess); void ClientPreviousWeapon_Implementation(int8 WeaponIndex, bool bPredictionSuccess); + void HandleClientPrediction(int8 WeaponIndex, bool bPredictionSuccess); + UARItemWeapon* FindNextValid(); UARItemWeapon* FindPreviousValid(); diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.cpp deleted file mode 100644 index 6dfde29..0000000 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.cpp +++ /dev/null @@ -1,129 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARWeaponManagerComponent.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "ARWeaponAbilityBase.h" -#include "ARItemWeapon.h" -#include "ARCharacter.h" -#include "ARPlayerController.h" - -#include "DWBPFunctionLibrary.h" -#include "SDraggableWindowWidget.h" - -#include "Engine/World.h" - -// Sets default values for this component's properties -UARWeaponManagerComponent::UARWeaponManagerComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - // ... -} - - -// Called when the game starts -void UARWeaponManagerComponent::BeginPlay() -{ - Super::BeginPlay(); - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - -} - - -// Called every frame -void UARWeaponManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} -void UARWeaponManagerComponent::EquipWeapon(TSoftClassPtr WeaponAbility) -{ - if (WeaponAbility.IsNull()) - { - return; - } - - TArray WeaponInput = GetInputTag(EAMGroup::Group001, EAMSlot::Slot001); - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); - if (!AbilityComp) - return; - - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(WeaponAbility)); - AARCharacter* Character = Cast(POwner); - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARWeaponManagerComponent::OnWeaponInputRead, - WeaponAbility, WeaponInput); - - AbilityComp->SetAbilityToAction(WeaponAbility, WeaponInput, ReadyDelegate); - } - else - { - AbilityComp->SetAbilityToAction(WeaponAbility, WeaponInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(WeaponAbility); - } -} -UGAAbilityBase* UARWeaponManagerComponent::GetCurrentWeapon() -{ - return GetAbility(ActiveGroup, EAMSlot::Slot001); -} - -void UARWeaponManagerComponent::AddToWeaponInventory(TSubclassOf InWeapon) -{ -} - -void UARWeaponManagerComponent::BP_AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) -{ - AddWeaponToManager(Group, Slot, Idx); -} -void UARWeaponManagerComponent::AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx) -{ -} -void UARWeaponManagerComponent::ServerAddWeaponToManager_Implementation(EAMGroup Group, EAMSlot Slot, int32 Idx) -{ - AddWeaponToManager(Group, Slot, Idx); -} -bool UARWeaponManagerComponent::ServerAddWeaponToManager_Validate(EAMGroup Group, EAMSlot Slot, int32 Idx) -{ - return true; -} - - - -void UARWeaponManagerComponent::OnWeaponInputRead(TSoftClassPtr WeaponAbilityTag, TArray InInputTags) -{ - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); - - //AbilityComp->SetAbilityToAction(NextWeaponAbility, WeaponInput, FAFOnAbilityReady()); -} - - -void UARWeaponManagerComponent::OnAbilityReady(TSoftClassPtr InAbilityTag - , const TArray& InAbilityInput - , EAMGroup InGroup, EAMSlot InSlot) -{ - AARPlayerController* PC = Cast(GetOwner()); - if (PC) - { - if (AARCharacter* Character = Cast(PC->GetPawn())) - { - UGAAbilityBase* AbilityInstance = GetAbility(InGroup, InSlot); - Character->WeaponInventory->SetAbilityToItem(static_cast(InGroup), AbilityInstance); - } - - } -} \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.h deleted file mode 100644 index b84d576..0000000 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponManagerComponent.h +++ /dev/null @@ -1,91 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "GameplayTags.h" -#include "ARWeaponsTypes.h" -#include "AMAbilityManagerComponent.h" -#include "ARWeaponManagerComponent.generated.h" - -DECLARE_DELEGATE_OneParam(FAROnWeaponReady, class UARWeaponAbilityBase*); - -USTRUCT(BlueprintType) -struct FARWeaponAttachment -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - EAMGroup Group; - - UPROPERTY(EditAnywhere) - FName SocketName; - - - bool operator==(int32 InGroup) const - { - return Group == AMIntToEnum(InGroup); - } - - bool operator==(const FARWeaponAttachment& Other) const - { - return Group == Other.Group; - } - bool operator==(EAMGroup InGroup) const - { - return Group == InGroup; - } -}; -/* Add On Character. */ -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARWeaponManagerComponent : public UAMAbilityManagerComponent -{ - GENERATED_BODY() -protected: - static constexpr int32 MAX_WEAPONS = 4; //maximum weapon + empty hands -public: - UPROPERTY(EditAnywhere, Category = "Attachment Config") - FName EquipSocketName; - - //maybe not reference directly ? - TWeakObjectPtr WeaponToModify; - - -public: - UPROPERTY() - class APawn* POwner; - // Sets default values for this component's properties - UARWeaponManagerComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - void EquipWeapon(TSoftClassPtr WeaponAbility); - UGAAbilityBase* GetCurrentWeapon(); - - UFUNCTION(BlueprintCallable, Category = "Weapon Manager") - void AddToWeaponInventory(TSubclassOf InWeapon); - - UFUNCTION(BlueprintCallable, meta=(DisplayName="Add Weapon To Manager"), Category = "Weapon Manager") - void BP_AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); - - virtual void AddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerAddWeaponToManager(EAMGroup Group, EAMSlot Slot, int32 Idx); - virtual void ServerAddWeaponToManager_Implementation(EAMGroup Group, EAMSlot Slot, int32 Idx); - bool ServerAddWeaponToManager_Validate(EAMGroup Group, EAMSlot Slot, int32 Idx); - - UFUNCTION() - void OnWeaponInputRead(TSoftClassPtr WeaponAbilityTag, TArray InInputTags); -protected: - virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) override; -}; From 5718e13287bd21daeb01945eebbf3e8da0d97467 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 15:46:12 +0200 Subject: [PATCH 154/187] adding missing files from last folder reorganizaion --- .../Private/AFAbilityComponent.cpp | 610 ++++++++ .../Private/AFAbilityInterface.cpp | 25 + .../Private/AFAbilityTypes.cpp | 226 +++ .../Private/AFAttributeComponent.cpp | 35 + .../Private/AFBlueprintFunctionLibrary.cpp | 46 + .../Private/AFCueInterface.cpp | 7 + .../AbilityFramework/Private/AFCueManager.cpp | 341 +++++ .../Private/AFEffectsComponent.cpp | 502 ++++++ .../Abilities/AFAbilityActivationSpec.cpp | 13 + .../Abilities/AFAbilityCooldownSpec.cpp | 14 + .../AFAbilityInfiniteDurationSpec.cpp | 13 + .../Private/Abilities/AFAbilityPeriodSpec.cpp | 13 + .../AFAbilityPeriodicInfiniteSpec.cpp | 14 + .../Private/Abilities/GAAbilityBase.cpp | 950 ++++++++++++ .../Private/Abilities/GAAbilityBlueprint.cpp | 33 + .../Tasks/AFAbilityTask_SpawnProjectile.cpp | 30 + .../Private/Abilities/Tasks/GAAbilityTask.cpp | 12 + .../Tasks/GAAbilityTask_CreateObject.cpp | 64 + .../Tasks/GAAbilityTask_PlayMontage.cpp | 50 + .../Abilities/Tasks/GAAbilityTask_Repeat.cpp | 15 + .../Tasks/GAAbilityTask_SpawnActor.cpp | 70 + .../Tasks/GAAbilityTask_TargetData.cpp | 154 ++ .../Tasks/GAAbilityTask_TargetDataCircle.cpp | 64 + .../GAAbilityTask_TargetDataLineTrace.cpp | 218 +++ .../Tasks/GAAbilityTask_WaitForConfirm.cpp | 33 + .../Tasks/GAAbilityTask_WaitTargetData.cpp | 84 + .../Private/AbilityFramework.cpp | 213 +++ .../AnimNotify/AFAbilityNotifyState.cpp | 33 + .../Private/AnimNotify/AFAnimNotify.cpp | 19 + .../Private/Attributes/GAAttributeBase.cpp | 248 +++ .../Attributes/GAAttributeExtension.cpp | 23 + .../Private/Attributes/GAAttributeGlobals.cpp | 5 + .../Private/Attributes/GAAttributesBase.cpp | 297 ++++ .../GAAttributesBlueprintFunctionLibrary.cpp | 72 + .../Private/Attributes/GAAttributesStats.cpp | 4 + .../AFEffectApplicationRequirement.cpp | 8 + .../Effects/AFEffectCustomApplication.cpp | 26 + .../Effects/AFEffectCustomStackingRule.cpp | 14 + .../Effects/AFEffectSpecFunctionLibrary.cpp | 50 + .../AFAttributeStongerOverride.cpp | 39 + .../AFEffectAlreadyApplied.cpp | 20 + .../AFAtributeDurationAdd.cpp | 25 + .../AFAtributeDurationUnique.cpp | 38 + .../AFAttributeDurationInfinite.cpp | 17 + .../AFAttributeDurationOverride.cpp | 27 + .../AFPeriodApplicationAdd.cpp | 32 + .../AFPeriodApplicationExtend.cpp | 53 + .../AFPeriodApplicationInfiniteAdd.cpp | 24 + .../AFPeriodApplicationOverride.cpp | 34 + .../AFPeriodicApplInfiniteOverride.cpp | 8 + .../Effects/EffectTasks/AFEffectTask.cpp | 8 + .../AFEffectTask_AppliedEffectEvent.cpp | 82 + .../AFEffectTask_AttributeChange.cpp | 70 + .../AFEffectTask_EffectAppliedToSelf.cpp | 80 + .../AFEffectTask_EffectAppliedToTarget.cpp | 85 ++ .../EffectTasks/AFEffectTask_EffectEvent.cpp | 84 + .../AFEffectTask_ExecutedEffectEvent.cpp | 84 + .../Private/Effects/GABlueprintLibrary.cpp | 371 +++++ .../Private/Effects/GACustomCalculation.cpp | 11 + .../Private/Effects/GAEffectBlueprint.cpp | 33 + .../Private/Effects/GAEffectCue.cpp | 162 ++ .../GAEffectCueBlueprintGeneratedClass.cpp | 13 + .../Private/Effects/GAEffectCueGlobals.cpp | 51 + .../Private/Effects/GAEffectCueSequence.cpp | 130 ++ .../Private/Effects/GAEffectExecution.cpp | 24 + .../Private/Effects/GAEffectExtension.cpp | 70 + .../Private/Effects/GAEffectField.cpp | 48 + .../Private/Effects/GAEffectGlobalTypes.cpp | 143 ++ .../Private/Effects/GAGameEffect.cpp | 847 +++++++++++ .../Private/GAGlobalTypes.cpp | 353 +++++ .../Private/GAHelperTemplates.cpp | 5 + .../Private/GAPhysicalMaterial.cpp | 8 + .../AbilityFramework/Private/GAUIData.cpp | 8 + .../LatentActions/AFLatentInterface.cpp | 8 + .../Private/LatentActions/AFTaskBase.cpp | 100 ++ .../Private/LatentActions/AFTaskManager.cpp | 25 + .../Private/LatentActions/GAWaitAction.cpp | 51 + .../Private/Mods/GAAttributeMod.cpp | 11 + .../Public/AFAbilityComponent.h | 613 ++++++++ .../Public/AFAbilityInterface.h | 75 + .../AbilityFramework/Public/AFAbilityTypes.h | 109 ++ .../Public/AFAttributeComponent.h | 29 + .../Public/AFBlueprintFunctionLibrary.h | 17 + .../AbilityFramework/Public/AFCueInterface.h | 26 + .../AbilityFramework/Public/AFCueManager.h | 53 + .../Public/AFEffectsComponent.h | 227 +++ .../Abilities/AFAbilityActivationSpec.h | 21 + .../Public/Abilities/AFAbilityCooldownSpec.h | 20 + .../Abilities/AFAbilityInfiniteDurationSpec.h | 21 + .../Public/Abilities/AFAbilityPeriodSpec.h | 20 + .../Abilities/AFAbilityPeriodicInfiniteSpec.h | 18 + .../Public/Abilities/GAAbilityBase.h | 622 ++++++++ .../Public/Abilities/GAAbilityBlueprint.h | 31 + .../Tasks/AFAbilityTask_SpawnProjectile.h | 58 + .../Public/Abilities/Tasks/GAAbilityTask.h | 95 ++ .../Tasks/GAAbilityTask_CreateObject.h | 32 + .../Tasks/GAAbilityTask_PlayMontage.h | 45 + .../Abilities/Tasks/GAAbilityTask_Repeat.h | 24 + .../Tasks/GAAbilityTask_SpawnActor.h | 34 + .../Tasks/GAAbilityTask_TargetData.h | 64 + .../Tasks/GAAbilityTask_TargetDataCircle.h | 40 + .../Tasks/GAAbilityTask_TargetDataLineTrace.h | 107 ++ .../Tasks/GAAbilityTask_WaitForConfirm.h | 30 + .../Tasks/GAAbilityTask_WaitTargetData.h | 34 + .../Public/AbilityFramework.h | 152 ++ .../Public/AnimNotify/AFAbilityNotifyState.h | 28 + .../Public/AnimNotify/AFAnimNotify.h | 23 + .../Public/Attributes/GAAttributeBase.h | 148 ++ .../Public/Attributes/GAAttributeExtension.h | 32 + .../Public/Attributes/GAAttributeGlobals.h | 15 + .../Public/Attributes/GAAttributesBase.h | 136 ++ .../GAAttributesBlueprintFunctionLibrary.h | 58 + .../Public/Attributes/GAAttributesStats.h | 2 + .../Effects/AFEffectApplicationRequirement.h | 29 + .../Effects/AFEffectCustomApplication.h | 44 + .../Effects/AFEffectCustomStackingRule.h | 22 + .../Effects/AFEffectSpecFunctionLibrary.h | 57 + .../AFAttributeStongerOverride.h | 25 + .../AFEffectAlreadyApplied.h | 27 + .../AFAtributeDurationAdd.h | 32 + .../AFAtributeDurationUnique.h | 34 + .../AFAttributeDurationInfinite.h | 33 + .../AFAttributeDurationOverride.h | 34 + .../AFPeriodApplicationAdd.h | 39 + .../AFPeriodApplicationExtend.h | 39 + .../AFPeriodApplicationInfiniteAdd.h | 39 + .../AFPeriodApplicationOverride.h | 38 + .../AFPeriodicApplInfiniteOverride.h | 26 + .../Public/Effects/EffectTasks/AFEffectTask.h | 37 + .../AFEffectTask_AppliedEffectEvent.h | 49 + .../AFEffectTask_AttributeChange.h | 50 + .../AFEffectTask_EffectAppliedToSelf.h | 50 + .../AFEffectTask_EffectAppliedToTarget.h | 50 + .../EffectTasks/AFEffectTask_EffectEvent.h | 48 + .../AFEffectTask_ExecutedEffectEvent.h | 49 + .../Public/Effects/GABlueprintLibrary.h | 111 ++ .../Public/Effects/GACustomCalculation.h | 30 + .../Public/Effects/GAEffectBlueprint.h | 31 + .../Public/Effects/GAEffectCue.h | 85 ++ .../GAEffectCueBlueprintGeneratedClass.h | 17 + .../Public/Effects/GAEffectCueGlobals.h | 26 + .../Public/Effects/GAEffectCueSequence.h | 69 + .../Public/Effects/GAEffectExecution.h | 22 + .../Public/Effects/GAEffectExtension.h | 79 + .../Public/Effects/GAEffectField.h | 60 + .../Public/Effects/GAEffectGlobalTypes.h | 155 ++ .../Public/Effects/GAGameEffect.h | 1346 +++++++++++++++++ .../AbilityFramework/Public/GAGlobalTypes.h | 790 ++++++++++ .../Public/GAHelperTemplates.h | 59 + .../Public/GAPhysicalMaterial.h | 19 + .../Source/AbilityFramework/Public/GAUIData.h | 16 + .../Public/IAbilityFramework.h | 37 + .../Public/LatentActions/AFLatentInterface.h | 25 + .../Public/LatentActions/AFTaskBase.h | 102 ++ .../Public/LatentActions/AFTaskManager.h | 17 + .../Public/LatentActions/GAWaitAction.h | 42 + .../Public/Mods/GAAttributeMod.h | 32 + .../Public/AFAbilityActionSpecDetails.cpp | 75 + .../Public/AFAbilityActionSpecDetails.h | 31 + .../Public/AFAbilityCooldownSpecDetails.cpp | 75 + .../Public/AFAbilityCooldownSpecDetails.h | 30 + .../AFAbilityInfiniteDurationSpecDetails.cpp | 83 + .../AFAbilityInfiniteDurationSpecDetails.h | 31 + .../AFAbilityInfinitePeriodSpecDetails.cpp | 83 + .../AFAbilityInfinitePeriodSpecDetails.h | 31 + .../Public/AFAbilityPeriodSpecDetails.cpp | 81 + .../Public/AFAbilityPeriodSpecDetails.h | 31 + .../Public/AFEK2Node_AsyncEffectTaskCall.cpp | 79 + .../Public/AFEK2Node_AsyncEffectTaskCall.h | 20 + .../Public/AFEffectCustomizationCommon.cpp | 111 ++ .../Public/AFEffectCustomizationCommon.h | 19 + .../AssetTypeActions_GAAbilityBlueprint.cpp | 57 + .../AssetTypeActions_GAAbilityBlueprint.h | 27 + .../GAAbilityBlueprintFactory.cpp | 334 ++++ .../AbilityEditor/GAAbilityBlueprintFactory.h | 32 + .../Public/AbilityEditor/GAAbilityEditor.cpp | 142 ++ .../Public/AbilityEditor/GAAbilityEditor.h | 64 + .../Public/AbilityEditor/GAAbilityGraph.cpp | 16 + .../Public/AbilityEditor/GAAbilityGraph.h | 15 + .../AbilityEditor/GAAbilityGraphSchema.cpp | 22 + .../AbilityEditor/GAAbilityGraphSchema.h | 38 + .../Public/AbilityFrameworkEditor.cpp | 161 ++ .../Public/AbilityFrameworkEditor.h | 60 + .../GACurveTableDetailCustomization.cpp | 28 + .../GACurveTableDetailCustomization.h | 23 + .../EffectCueEditor/AFEffectCueDetails.cpp | 353 +++++ .../EffectCueEditor/AFEffectCueDetails.h | 36 + .../AssetTypeActions_GAEffectCueBlueprint.cpp | 57 + .../AssetTypeActions_GAEffectCueBlueprint.h | 27 + .../EffectCueEditor/GAEffectCueBlueprint.cpp | 33 + .../EffectCueEditor/GAEffectCueBlueprint.h | 32 + .../GAEffectCueBlueprintFactory.cpp | 334 ++++ .../GAEffectCueBlueprintFactory.h | 32 + .../EffectCueEditor/GAEffectCueEditor.cpp | 210 +++ .../EffectCueEditor/GAEffectCueEditor.h | 79 + .../EffectCueEditor/GAEffectCueGraph.cpp | 16 + .../Public/EffectCueEditor/GAEffectCueGraph.h | 15 + .../GAEffectCueGraphSchema.cpp | 22 + .../EffectCueEditor/GAEffectCueGraphSchema.h | 38 + .../AssetTypeActions_GAEffectBlueprint.cpp | 57 + .../AssetTypeActions_GAEffectBlueprint.h | 27 + .../EffectEditor/GAEffectBlueprintFactory.cpp | 347 +++++ .../EffectEditor/GAEffectBlueprintFactory.h | 32 + .../Public/EffectEditor/GAEffectEditor.cpp | 124 ++ .../Public/EffectEditor/GAEffectEditor.h | 53 + .../Public/EffectEditor/GAEffectGraph.cpp | 16 + .../Public/EffectEditor/GAEffectGraph.h | 15 + .../EffectEditor/GAEffectGraphSchema.cpp | 22 + .../Public/EffectEditor/GAEffectGraphSchema.h | 38 + .../Public/GAAttributeDetailCustomization.cpp | 90 ++ .../Public/GAAttributeDetailCustomization.h | 33 + .../GAAttributePanelGraphPinFactory.cpp | 16 + .../Public/GAAttributePanelGraphPinFactory.h | 23 + .../Public/GAAttributePin.cpp | 105 ++ .../Public/GAAttributePin.h | 27 + .../GAEK2Node_LatentAbilityTaskCall.cpp | 79 + .../Public/GAEK2Node_LatentAbilityTaskCall.h | 20 + .../Public/GAEK2Node_LatentAction.cpp | 76 + .../Public/GAEK2Node_LatentAction.h | 19 + .../Public/GAEffectClassStructWidget.cpp | 856 +++++++++++ .../Public/GAEffectClassStructWidget.h | 58 + .../Public/GAEffectDetails.cpp | 112 ++ .../Public/GAEffectDetails.h | 32 + .../GAEffectPropertyStructCustomization.cpp | 96 ++ .../GAEffectPropertyStructCustomization.h | 28 + .../Public/GAGlobalTypesEditor.h | 35 + .../Public/IAbilityFrameworkEditor.h | 36 + .../Public/SGAAttributeWidget.cpp | 151 ++ .../Public/SGAAttributeWidget.h | 64 + .../Public/AFDAbilityGiveTrigger.cpp | 107 ++ .../Public/AFDAbilityGiveTrigger.h | 83 + .../Public/AFDBlueprintFunctionLibrary.cpp | 11 + .../Public/AFDBlueprintFunctionLibrary.h | 20 + .../Public/AFDManager.cpp | 41 + .../Public/AFDManager.h | 38 + .../Public/Abilities/AFDAbilityBase.cpp | 7 + .../Public/Abilities/AFDAbilityBase.h | 20 + .../Public/AbilityFrameworkDebugger.cpp | 45 + .../Public/AbilityFrameworkDebugger.h | 22 + .../Public/SAFDAttributes.cpp | 74 + .../Public/SAFDAttributes.h | 39 + .../Public/SAFDDesktopWidget.cpp | 203 +++ .../Public/SAFDDesktopWidget.h | 54 + .../Public/SAFDEffectInspector.cpp | 16 + .../Public/SAFDEffectInspector.h | 20 + .../Public/SAFDEffects.cpp | 105 ++ .../Public/SAFDEffects.h | 82 + .../Public/SAFDViewportMouseCapture.cpp | 22 + .../Public/SAFDViewportMouseCapture.h | 24 + .../Public/AMAbilityManagerComponent.cpp | 451 ++++++ .../Public/AMAbilityManagerComponent.h | 201 +++ .../Source/AbilityManager/Public/AMTypes.cpp | 3 + .../Source/AbilityManager/Public/AMTypes.h | 95 ++ .../AbilityManager/Public/AbilityManager.cpp | 20 + .../AbilityManager/Public/AbilityManager.h | 15 + .../Public/AMAbilityInputProperty.cpp | 36 + .../Public/AMAbilityInputProperty.h | 18 + .../Public/AbilityManagerEditor.cpp | 20 + .../Public/AbilityManagerEditor.h | 15 + .../Public/DWBPFunctionLibrary.cpp | 14 + .../Public/DWBPFunctionLibrary.h | 26 + .../DraggableWindow/Public/DWManager.cpp | 72 + .../Source/DraggableWindow/Public/DWManager.h | 38 + .../Source/DraggableWindow/Public/DWTypes.cpp | 3 + .../Source/DraggableWindow/Public/DWTypes.h | 41 + .../Public/DraggableWindow.cpp | 33 + .../DraggableWindow/Public/DraggableWindow.h | 21 + .../Public/SDraggableWindowWidget.cpp | 706 +++++++++ .../Public/SDraggableWindowWidget.h | 195 +++ .../Private/IFEquipmentComponent.cpp | 86 ++ .../InventoryFramework/Private/IFTypes.cpp | 11 + .../Public/IFEquipmentComponent.h | 83 + .../InventoryFramework/Public/IFTypes.h | 42 + .../Public/AnimNode_BlendLocomotionFour.cpp | 548 +++++++ .../Public/AnimNode_BlendLocomotionFour.h | 146 ++ .../Public/OrionAnimComponent.cpp | 34 + .../Public/OrionAnimComponent.h | 29 + .../OrionAnimation/Public/OrionAnimation.cpp | 20 + .../OrionAnimation/Public/OrionAnimation.h | 15 + .../OrionAnimation/Public/OrionInterface.cpp | 6 + .../OrionAnimation/Public/OrionInterface.h | 42 + .../AnimGraphNode_BlendLocomotionFour.cpp | 130 ++ .../Private/OrionAnimationEditor.cpp | 20 + .../AnimGraphNode_BlendLocomotionFour.h | 35 + .../Public/OrionAnimationEditor.h | 15 + .../Source/SpectrAI/Public/SpectrAI.cpp | 20 + .../Source/SpectrAI/Public/SpectrAI.h | 15 + .../SpectrAI/Public/SpectrAIController.cpp | 12 + .../SpectrAI/Public/SpectrAIController.h | 48 + .../Source/SpectrAI/Public/SpectrAction.cpp | 60 + .../Source/SpectrAI/Public/SpectrAction.h | 94 ++ .../SpectrAI/Public/SpectrBrainComponent.cpp | 175 +++ .../SpectrAI/Public/SpectrBrainComponent.h | 323 ++++ .../SpectrAI/Public/SpectrConsideration.cpp | 7 + .../SpectrAI/Public/SpectrConsideration.h | 20 + .../Source/SpectrAI/Public/SpectrContext.cpp | 7 + .../Source/SpectrAI/Public/SpectrContext.h | 20 + .../SpectrAI/Public/SpectrEvaluator.cpp | 7 + .../Source/SpectrAI/Public/SpectrEvaluator.h | 72 + .../Source/SpectrAI/Public/SpectrGoal.cpp | 7 + .../Source/SpectrAI/Public/SpectrGoal.h | 63 + .../SpectrAIEditor/Public/SpectrAIEditor.cpp | 20 + .../SpectrAIEditor/Public/SpectrAIEditor.h | 15 + .../Public/SpectrGoalCustomization.cpp | 12 + .../Public/SpectrGoalCustomization.h | 17 + .../Public/STestAIControllerBase.cpp | 7 + .../Public/STestAIControllerBase.h | 20 + .../Public/STestAction_ChopFirewood.cpp | 54 + .../Public/STestAction_ChopFirewood.h | 36 + .../Public/STestAction_ChopWood.cpp | 7 + .../Public/STestAction_ChopWood.h | 20 + .../Public/STestAction_CollectBranches.cpp | 7 + .../Public/STestAction_CollectBranches.h | 20 + .../Public/STestAction_CollectOre.cpp | 7 + .../Public/STestAction_CollectOre.h | 20 + .../Public/STestAction_DropFirewood.cpp | 52 + .../Public/STestAction_DropFirewood.h | 36 + .../Public/STestAction_DropOre.cpp | 7 + .../SpectrAITest/Public/STestAction_DropOre.h | 20 + .../Public/STestAction_DropWood.cpp | 7 + .../Public/STestAction_DropWood.h | 20 + .../SpectrAITest/Public/STestAction_GoTo.cpp | 7 + .../SpectrAITest/Public/STestAction_GoTo.h | 20 + .../Public/STestAction_MakeAxe.cpp | 7 + .../SpectrAITest/Public/STestAction_MakeAxe.h | 20 + .../Public/STestAction_MakePick.cpp | 7 + .../Public/STestAction_MakePick.h | 20 + .../Public/STestAction_MineOre.cpp | 7 + .../SpectrAITest/Public/STestAction_MineOre.h | 20 + .../Public/STestAction_PickItemAxe.cpp | 52 + .../Public/STestAction_PickItemAxe.h | 34 + .../Public/STestAction_PickItemPick.cpp | 7 + .../Public/STestAction_PickItemPick.h | 20 + .../SpectrAITest/Public/STestAxePickup.cpp | 27 + .../SpectrAITest/Public/STestAxePickup.h | 28 + .../SpectrAITest/Public/STestBranch.cpp | 27 + .../Source/SpectrAITest/Public/STestBranch.h | 28 + .../Source/SpectrAITest/Public/STestForge.cpp | 27 + .../Source/SpectrAITest/Public/STestForge.h | 28 + .../SpectrAITest/Public/STestStorage.cpp | 27 + .../Source/SpectrAITest/Public/STestStorage.h | 28 + .../Source/SpectrAITest/Public/STestTree.cpp | 27 + .../Source/SpectrAITest/Public/STestTree.h | 28 + .../SpectrAITest/Public/SpectrAITest.cpp | 20 + .../Source/SpectrAITest/Public/SpectrAITest.h | 15 + .../Source/TimeOfDay/Private/TimeOfDay.cpp | 20 + .../Source/TimeOfDay/Public/TimeOfDay.h | 15 + .../Source/TimeOfDay/TimeOfDay.Build.cs | 47 + .../Private/WeaponFramework.cpp | 20 + .../WeaponFramework/Public/WeaponFramework.h | 15 + .../WeaponFramework/WeaponFramework.Build.cs | 48 + .../WALandscapeGraphAssetEditor.cpp | 610 ++++++++ .../WALandscapeGraphAssetEditor.h | 116 ++ .../WALandscapeGraphAssetEditorToolbar.cpp | 51 + .../WALandscapeGraphAssetEditorToolbar.h | 28 + .../WALandscapeGraphColors.h | 43 + ...ALandscapeGraphConnectionDrawingPolicy.cpp | 117 ++ .../WALandscapeGraphConnectionDrawingPolicy.h | 25 + .../WALandscapeGraphEdGraph.cpp | 76 + .../WALandscapeGraphEdGraph.h | 19 + .../WALandscapeGraphEdNode.cpp | 65 + .../WALandscapeGraphEdNode.h | 33 + .../WALandscapeGraphEdNode_Multiply.cpp | 79 + .../WALandscapeGraphEdNode_Multiply.h | 26 + .../WALandscapeGraphEdNode_Output.cpp | 55 + .../WALandscapeGraphEdNode_Output.h | 23 + .../WALandscapeGraphEditorCommands.cpp | 12 + .../WALandscapeGraphEditorCommands.h | 17 + .../WALandscapeGraphSchema.cpp | 344 +++++ .../WALandscapeGraphSchema.h | 63 + .../Public/Runtime/WALandscapeGraph.cpp | 26 + .../Public/Runtime/WALandscapeGraph.h | 41 + .../Public/Runtime/WALandscapeNode.cpp | 31 + .../Public/Runtime/WALandscapeNode.h | 45 + .../Public/WALGEdNode_Combine.cpp | 7 + .../Public/WALGEdNode_Combine.h | 20 + .../Public/WALGEdNode_PerlinNoise.cpp | 64 + .../Public/WALGEdNode_PerlinNoise.h | 40 + .../Public/WALGEdNode_Start.cpp | 12 + .../Public/WALGEdNode_Start.h | 21 + .../WALandscapeGraphAssetTypeActions.cpp | 47 + .../Public/WALandscapeGraphAssetTypeActions.h | 18 + .../Public/WALandscapeGraphEditorTypes.cpp | 19 + .../Public/WALandscapeGraphEditorTypes.h | 21 + .../Public/WALandscapeGraphFactory.cpp | 22 + .../Public/WALandscapeGraphFactory.h | 15 + .../Public/WALandscapeNode_Multiply.cpp | 28 + .../Public/WALandscapeNode_Multiply.h | 29 + .../Public/WALandscapeNode_Output.cpp | 16 + .../Public/WALandscapeNode_Output.h | 24 + .../Public/WALandscapeNode_PerlinNoise.cpp | 18 + .../Public/WALandscapeNode_PerlinNoise.h | 38 + .../WorldArchitectEditor/Public/WANoise.cpp | 29 + .../WorldArchitectEditor/Public/WANoise.h | 459 ++++++ .../Public/WorldArchitectEdMode.cpp | 50 + .../Public/WorldArchitectEdMode.h | 24 + .../Public/WorldArchitectEdModeToolkit.cpp | 857 +++++++++++ .../Public/WorldArchitectEdModeToolkit.h | 91 ++ .../Public/WorldArchitectEditor.cpp | 41 + .../Public/WorldArchitectEditor.h | 18 + .../WorldArchitectEditor.Build.cs | 59 + .../UI/Inventory/ARUIInventoryComponent.cpp | 1 + 402 files changed, 31181 insertions(+) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityActivationSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityCooldownSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityInfiniteDurationSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodicInfiniteSpec.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_CreateObject.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_Repeat.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetData.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAbilityNotifyState.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAnimNotify.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeGlobals.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesStats.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectApplicationRequirement.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomApplication.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomStackingRule.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectSpecFunctionLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationAdd.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationInfinite.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationAdd.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GACustomCalculation.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueGlobals.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectField.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectGlobalTypes.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/GAHelperTemplates.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/GAPhysicalMaterial.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/GAUIData.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFLatentInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskBase.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskManager.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/GAWaitAction.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Mods/GAAttributeMod.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeComponent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityActivationSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityCooldownSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityInfiniteDurationSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodicInfiniteSpec.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_CreateObject.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_PlayMontage.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_Repeat.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_SpawnActor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitTargetData.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAbilityNotifyState.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAnimNotify.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeGlobals.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesStats.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectApplicationRequirement.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomApplication.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomStackingRule.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectSpecFunctionLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFAttributeStongerOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationAdd.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationUnique.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationInfinite.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationAdd.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationExtend.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AttributeChange.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectEvent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GACustomCalculation.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueGlobals.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueSequence.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectField.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectGlobalTypes.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/GAHelperTemplates.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/GAPhysicalMaterial.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/GAUIData.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFLatentInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskManager.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/GAWaitAction.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Mods/GAAttributeMod.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAGlobalTypesEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/IAbilityFrameworkEditor.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp create mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h create mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h create mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h create mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp create mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.h create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.cpp create mode 100644 Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.h create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h create mode 100644 Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/AnimGraphNode_BlendLocomotionFour.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/OrionAnimationEditor.cpp create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/AnimGraphNode_BlendLocomotionFour.h create mode 100644 Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/OrionAnimationEditor.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.h create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.h create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.h create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.cpp create mode 100644 Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.h create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.cpp create mode 100644 Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.h create mode 100644 Plugins/TimeOfDay/Source/TimeOfDay/Private/TimeOfDay.cpp create mode 100644 Plugins/TimeOfDay/Source/TimeOfDay/Public/TimeOfDay.h create mode 100644 Plugins/TimeOfDay/Source/TimeOfDay/TimeOfDay.Build.cs create mode 100644 Plugins/WeaponFramework/Source/WeaponFramework/Private/WeaponFramework.cpp create mode 100644 Plugins/WeaponFramework/Source/WeaponFramework/Public/WeaponFramework.h create mode 100644 Plugins/WeaponFramework/Source/WeaponFramework/WeaponFramework.Build.cs create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphColors.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.cpp create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.h create mode 100644 Plugins/WorldArchitect/Source/WorldArchitectEditor/WorldArchitectEditor.Build.cs diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp new file mode 100644 index 0000000..4f1273d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -0,0 +1,610 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" + +#include "Abilities/GAAbilityBase.h" +#include "Abilities/Tasks/GAAbilityTask.h" +#include "IAbilityFramework.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" +#include "Animation/AnimInstance.h" +#include "Animation/AnimMontage.h" +#include "Attributes/GAAttributesBase.h" +#include "AFAbilityInterface.h" +#include "Effects/GAEffectExecution.h" +#include "Effects/GAGameEffect.h" + +#include "Effects/GAEffectExtension.h" +#include "Effects/GAEffectCue.h" +#include "AFCueManager.h" +#include "Effects/GABlueprintLibrary.h" +#include "Async.h" + +#include "AFAbilityComponent.h" +#include "AFEffectsComponent.h" +#include "AFAbilityInterface.h" + +DEFINE_STAT(STAT_ApplyEffect); +DEFINE_STAT(STAT_ModifyAttribute); + + + +void FAFReplicatedAttributeItem::PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer) +{ + FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); + ArraySerializer.AttributeMap.Remove(AttributeTag); +} +void FAFReplicatedAttributeItem::PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer) +{ + FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); + UGAAttributesBase*& Attribute = ArraySerializer.AttributeMap.FindOrAdd(AttributeTag); + Attribute = Attributes; + InArraySerializer.OnAttributeReplicated(AttributeTag); +} +void FAFReplicatedAttributeItem::PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer) +{ + +} +UGAAttributesBase* FAFReplicatedAttributeContainer::Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter) +{ + UGAAttributesBase* AttributesDup = DuplicateObject(InAttributes, InOuter); + FAFReplicatedAttributeItem Item; + Item.AttributeTag = InTag; + Item.Attributes = AttributesDup; + Attributes.Add(Item); + MarkItemDirty(Item); + UGAAttributesBase*& Added = AttributeMap.FindOrAdd(InTag); + Added = AttributesDup; + return AttributesDup; +} +UAFAbilityComponent::UAFAbilityComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bWantsInitializeComponent = true; + bIsAnyAbilityActive = false; + bAutoActivate = true; + bAutoRegister = true; + PrimaryComponentTick.bCanEverTick = true; + PrimaryComponentTick.bStartWithTickEnabled = true; + PrimaryComponentTick.bRunOnAnyThread = false; + PrimaryComponentTick.bAllowTickOnDedicatedServer = true; + PrimaryComponentTick.TickGroup = ETickingGroup::TG_DuringPhysics; +} + +void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData) +{ + FAFAttributeChangedDelegate* Delegate = AttributeChanged.Find(InAttribute); + if (Delegate) + { + Delegate->Broadcast(InData); + } +} + +void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn + ,FGAEffectProperty& InProperty) +{ + //OnAttributePreModifed.Broadcast(ModIn, 0); + //Add log. + if (!DefaultAttributes) + { + return; + } + float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); + FAFAttributeChangedData Data; + FGAEffectContext& Context = InProperty.GetContext(HandleIn).GetRef(); + Data.Mod = ModIn; + Data.Target = Context.Target; + Data.Location = Context.HitResult.Location; + OnAttributeModifed.Broadcast(Data); + NotifyInstigatorTargetAttributeChanged(Data, Context); + //add default replication (PropertyRep) that attribute changed. +}; +void UAFAbilityComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext) +{ + InContext.InstigatorComp->OnTargetAttributeModifed.Broadcast(InData); +} +void UAFAbilityComponent::GetAttributeStructTest(FGAAttribute Name) +{ + DefaultAttributes->GetAttribute(Name); +} + +void UAFAbilityComponent::OnRep_GameEffectContainer() +{ + float test = 0; +} +void UAFAbilityComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + UActorComponent::TickComponent(DeltaTime, TickType, ThisTickFunction); + if (DefaultAttributes) + { + DefaultAttributes->Tick(DeltaTime); + } +} + +void UAFAbilityComponent::BeginPlay() +{ + Super::BeginPlay(); + //FAFEffectTimerManager::Get(); +} +void UAFAbilityComponent::EndPlay(const EEndPlayReason::Type EndPlayReason) +{ + Super::EndPlay(EndPlayReason); + +} +void UAFAbilityComponent::DestroyComponent(bool bPromoteChildren) +{ + Super::DestroyComponent(bPromoteChildren); + +} + +void UAFAbilityComponent::OnAttributeModified(const FGAEffectMod& InMod, + const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet) +{ + +} + +void UAFAbilityComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly replicate it to everyone + //to allow prediction for UI. + DOREPLIFETIME(UAFAbilityComponent, DefaultAttributes); + DOREPLIFETIME(UAFAbilityComponent, RepAttributes); + + DOREPLIFETIME(UAFAbilityComponent, ActiveCues); + DOREPLIFETIME_CONDITION(UAFAbilityComponent, AbilityContainer, COND_OwnerOnly); + DOREPLIFETIME_CONDITION(UAFAbilityComponent, RepMontage, COND_SkipOwner); +} +void UAFAbilityComponent::OnRep_ActiveEffects() +{ + +} +void UAFAbilityComponent::OnRep_ActiveCues() +{ + +} + +bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) +{ + bool WroteSomething = Super::ReplicateSubobjects(Channel, Bunch, RepFlags); + + if (DefaultAttributes) + { + WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); + } + for (const FAFAbilityItem& Ability : AbilityContainer.AbilitiesItems) + { + //if (Set.InputOverride) + // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); + + if (Ability.Ability) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Ability.Ability), *Bunch, *RepFlags); + } + + for (const FAFReplicatedAttributeItem& Attribute : RepAttributes.Attributes) + { + //if (Set.InputOverride) + // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); + + if (Attribute.Attributes) + WroteSomething |= Channel->ReplicateSubobject(const_cast(Attribute.Attributes), *Bunch, *RepFlags); + } + + return WroteSomething; +} +void UAFAbilityComponent::GetSubobjectsWithStableNamesForNetworking(TArray& Objs) +{ + if (DefaultAttributes && DefaultAttributes->IsNameStableForNetworking()) + { + Objs.Add(const_cast(DefaultAttributes)); + } +} + +void UAFAbilityComponent::GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const +{ + if (IAFAbilityInterface* ABInterface = Cast(GetOwner())) + { + TagContainer = ABInterface->NativeGetEffectsComponent()->AppliedTags.AllTags; + } +} + + + +void UAFAbilityComponent::InitializeComponent() +{ + Super::InitializeComponent(); + //PawnInterface = Cast(GetOwner()); + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + AbilityContainer.AbilitiesComp = this; + //EffectTimerManager = MakeShareable(new FAFEffectTimerManager()); + + //EffectTimerManager.InitThread(); + if (DefaultAttributes) + { + DefaultAttributes->InitializeAttributes(this); + DefaultAttributes->InitializeAttributesFromTable(); + } + ActiveCues.OwningComp = this; + //ActiveCues.OwningComponent = this; + AppliedTags.AddTagContainer(DefaultTags); + InitializeInstancedAbilities(); + + AActor* MyOwner = GetOwner(); + if (!MyOwner || !MyOwner->IsTemplate()) + { + ULevel* ComponentLevel = (MyOwner ? MyOwner->GetLevel() : GetWorld()->PersistentLevel); + } +} +void UAFAbilityComponent::UninitializeComponent() +{ + Super::UninitializeComponent(); + //EffectTimerManager.Deinitialize(); + //EffectTimerManager.Reset(); + //GameEffectContainer +} +void UAFAbilityComponent::BindInputs(class UInputComponent* InputComponent) +{ + for (const FGameplayTag& Tag : AbilityInputs) + { + BindAbilityToAction(InputComponent, Tag); + } +} +void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) +{ + AbilityContainer.SetBlockedInput(InActionName, bBlock); +} +void UAFAbilityComponent::BP_BindAbilityToAction(FGameplayTag ActionName) +{ + UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); + check(InputComponent); + + BindAbilityToAction(InputComponent, ActionName); +} +void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName) +{ + check(InputComponent); + + if (!InputComponent) + return; + + { + FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputPressed, ActionName); + InputComponent->AddActionBinding(AB); + } + + // Released event + { + FInputActionBinding AB(ActionName.GetTagName(), IE_Released); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputReleased, ActionName); + InputComponent->AddActionBinding(AB); + } + SetBlockedInput(ActionName, false); +} +void UAFAbilityComponent::SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag + , const FAFOnAbilityReady& InputDelegate) +{ + AbilityContainer.SetAbilityToAction(InAbilityPtr, InInputTag); + ENetRole role = GetOwnerRole(); + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + && role == ENetRole::ROLE_AutonomousProxy) + { + if (InputDelegate.IsBound()) + { + AddOnAbilityInputReadyDelegate(InAbilityPtr, InputDelegate); + } + ServerSetAbilityToAction(InAbilityPtr, InInputTag); + } +} + +TSoftClassPtr UAFAbilityComponent::IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) +{ + for (const FGameplayTag& Tag : InInputTag) + { + return AbilityContainer.IsAbilityBoundToAction(Tag); + break; + } + return TSoftClassPtr(); +} + +void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + SetAbilityToAction(InAbilityPtr, InInputTag, FAFOnAbilityReady()); + } +} +bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) +{ + return true; +} +void UAFAbilityComponent::RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr) +{ + AbilityContainer.RemoveAbilityFromAction(InAbilityPtr); + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerRemoveAbilitiesFromActions(InAbilityPtr.ToSoftObjectPath()); + } +} +void UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr) +{ + AbilityContainer.RemoveAbilityFromAction(TSoftClassPtr(InAbilityPtr)); +} +bool UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr) +{ + return true; +} +void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr) +{ + NotifyOnAbilityInputReady(InAbilityPtr); + UGAAbilityBase* Ability = AbilityContainer.TagToAbility.FindRef(InAbilityPtr); + if (Ability) + { + Ability->OnAbilityInputReady(); + } +} + +void UAFAbilityComponent::SetAbilitiesToActions(const TArray& InAbilitiesActions + , const TArray& InputDelegate) +{ + for (const FAFAbilityActionSet& Set : InAbilitiesActions) + { + AbilityContainer.SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs); + } + ENetRole role = GetOwnerRole(); + + if (GetOwner()->GetNetMode() == ENetMode::NM_Client + && role == ENetRole::ROLE_AutonomousProxy) + { + for (int32 Idx = 0; Idx < InAbilitiesActions.Num(); Idx++) + { + if (InputDelegate[Idx].IsBound()) + { + AddOnAbilityInputReadyDelegate(InAbilitiesActions[Idx].AbilityTag, InputDelegate[Idx]); + } + } + + ServerSetAbilitiesToActions(InAbilitiesActions); + } +} + +void UAFAbilityComponent::ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions) +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + for (const FAFAbilityActionSet& Set : InAbilitiesActions) + { + SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs, FAFOnAbilityReady()); + } + } +} +bool UAFAbilityComponent::ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions) +{ + return true; +} + +void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) +{ + NativeInputPressed(ActionName); +} +void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) +{ + FAFPredictionHandle PredHandle; + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + PredHandle = FAFPredictionHandle::GenerateClientHandle(this); + AbilityContainer.HandleInputPressed(ActionName, PredHandle); + } + ServerNativeInputPressed(ActionName, PredHandle); + +} + +void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) +{ + AbilityContainer.HandleInputPressed(ActionName, InPredictionHandle); + //NativeInputPressed(ActionName); +} +bool UAFAbilityComponent::ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) +{ + return true; +} + +void UAFAbilityComponent::BP_InputReleased(FGameplayTag ActionName) +{ + NativeInputReleased(ActionName); +} + +void UAFAbilityComponent::NativeInputReleased(FGameplayTag ActionName) +{ + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + AbilityContainer.HandleInputReleased(ActionName); + } + ServerNativeInputReleased(ActionName); +} + +void UAFAbilityComponent::ServerNativeInputReleased_Implementation(FGameplayTag ActionName) +{ + AbilityContainer.HandleInputReleased(ActionName); +} +bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag ActionName) +{ + return true; +} + +void UAFAbilityComponent::BP_AddAbility(TSoftClassPtr InAbility, + TArray InInputTag) +{ + NativeAddAbility(InAbility, InInputTag); +} + +void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbility, + const TArray& InInputTag) +{ + //FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeAddAbility(InAbility.ToSoftObjectPath(), InInputTag); + /*if (AlreadyBound.IsValid()) + { + for (const FGameplayTag& Input : InInputTag) + { + AbilityContainer.RemoveAbilityFromAction(AlreadyBound); + } + }*/ + } + else + { + /*if (AlreadyBound.IsValid()) + { + AbilityContainer.RemoveAbilityFromAction(AlreadyBound); + }*/ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + FStreamableManager& StreamManager = UAssetManager::GetStreamableManager(); + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbility); + + StreamManager.RequestAsyncLoad(InAbility.ToSoftObjectPath() + , del); + } + } + } +} + + +void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, + const TArray& InInputTag) +{ + NativeAddAbility(TSoftClassPtr(InAbility), InInputTag); +} + +bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, + const TArray& InInputTag) +{ + return true; +} +void UAFAbilityComponent::OnFinishedLoad(TSoftClassPtr InAbility) +{ + if (AbilityContainer.AbilityExists(InAbility)) + { + return; + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + return; + } + + + FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + + TSubclassOf cls = InAbility.Get(); + if (cls) + { + InstanceAbility(cls, InAbility); + } + + { + Manager.Unload(InAbility.ToSoftObjectPath()); + } +} + +void UAFAbilityComponent::BP_RemoveAbility(TSoftClassPtr TagIn) +{ + +} +void UAFAbilityComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNativeRemoveAbility(InAbilityTag.ToSoftObjectPath()); + } + AbilityContainer.RemoveAbility(InAbilityTag); +} +void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag) +{ + AbilityContainer.RemoveAbility(TSoftClassPtr(InAbilityTag)); +} + +bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag) +{ + return true; +} + +UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(TSoftClassPtr TagIn) +{ + UGAAbilityBase* retVal = AbilityContainer.GetAbility(TagIn); + return retVal; +} +UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass + , TSoftClassPtr InClassPtr) +{ + if (AbilityClass) + { + UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InClassPtr); + AbilityContainer.MarkArrayDirty(); + return ability; + } + return nullptr; +} + +void UAFAbilityComponent::OnRep_InstancedAbilities() +{ +} +void UAFAbilityComponent::NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag) +{ + OnAbilityAdded.Broadcast(InAbilityTag); + +} +void UAFAbilityComponent::InitializeInstancedAbilities() +{ +} + +void UAFAbilityComponent::OnRep_PlayMontage() +{ + ACharacter* MyChar = Cast(GetOwner()); + if (MyChar) + { + UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); + AnimInst->Montage_Play(RepMontage.CurrentMontage); + if (RepMontage.SectionName != NAME_None) + { + AnimInst->Montage_JumpToSection(RepMontage.SectionName, RepMontage.CurrentMontage); + } + UE_LOG(AbilityFramework, Log, TEXT("OnRep_PlayMontage MontageName: %s SectionNAme: %s ForceRep: %s"), *RepMontage.CurrentMontage->GetName(), *RepMontage.SectionName.ToString(), *FString::FormatAsNumber(RepMontage.ForceRep)); + } +} + +void UAFAbilityComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) +{ + //if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + //Probabaly want to do something different here for client non authority montage plays. + //return; + } + ACharacter* MyChar = Cast(GetOwner()); + if (MyChar) + { + UAnimInstance* AnimInst = MyChar->GetMesh()->GetAnimInstance(); + AnimInst->Montage_Play(MontageIn, Speed); + if (SectionName != NAME_None) + { + //AnimInst->Montage_JumpToSection(SectionName, MontageIn); + } + + UE_LOG(AbilityFramework, Log, TEXT("PlayMontage MontageName: %s SectionNAme: %s Where: %s"), *MontageIn->GetName(), *SectionName.ToString(), (GetOwnerRole() < ENetRole::ROLE_Authority ? TEXT("Client") : TEXT("Server"))); + RepMontage.SectionName = SectionName; + RepMontage.CurrentMontage = MontageIn; + RepMontage.ForceRep++; + } +} +void UAFAbilityComponent::MulticastPlayMontage_Implementation(UAnimMontage* MontageIn, FName SectionName, float Speed = 1) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp new file mode 100644 index 0000000..134412e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp @@ -0,0 +1,25 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "AFEffectsComponent.h" +#include "AFAttributeComponent.h" +UAFAbilityInterface::UAFAbilityInterface(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +//class UGAAttributesBase* IAFAbilityInterface::GetAttributes() +//{ +// return nullptr;// GetAbilityComp()->DefaultAttributes; +//} + +FGAEffectHandle IAFAbilityInterface::ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, InHandle, Params, Modifier); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp new file mode 100644 index 0000000..981b61a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp @@ -0,0 +1,226 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityComponent.h" +#include "Abilities/GAAbilityBase.h" +#include "AFAbilityTypes.h" + +void FAFAbilityItem::PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer) +{ + if (InArraySerializer.AbilitiesComp.IsValid()) + { + FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + //remove attributes + //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); + Ability->Attributes = nullptr; + InArraySerializerC.AbilityToAction.Remove(AbilityClass); + InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); + InArraySerializerC.TagToAbility.Remove(AbilityClass); + } +} +void FAFAbilityItem::PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer) +{ + if (InArraySerializer.AbilitiesComp.IsValid()) + { + //should be safe, since we only modify the non replicated part of struct. + FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + Ability->AbilityComponent = InArraySerializer.AbilitiesComp.Get(); + if (InArraySerializer.AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(InArraySerializer.AbilitiesComp->GetOwner()); + Ability->POwner = POwner; + Ability->PCOwner = Cast(POwner->Controller); + Ability->OwnerCamera = nullptr; + } + Ability->InitAbility(); + Ability->Attributes = nullptr; + + //TODO - CHANGE ATTRIBUTE HANDLING + UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); + Ability->Attributes = attr; + + InArraySerializerC.AbilitiesInputs.Add(AbilityClass, Ability); //.Add(Ability->AbilityTag, Ability); + InArraySerializerC.TagToAbility.Add(AbilityClass, Ability); + InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(AbilityClass); + } +} +void FAFAbilityItem::PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer) +{ + +} + + +void FAFAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) +{ + if (BlockedInput.Contains(InActionName)) + { + BlockedInput[InActionName] = bBlock; + } + else + { + BlockedInput.Add(InActionName, bBlock); + } +} +UGAAbilityBase* FAFAbilityContainer::AddAbility(TSubclassOf AbilityIn + , TSoftClassPtr InClassPtr) +{ + if (AbilityIn && AbilitiesComp.IsValid()) + { + + UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); + ability->AbilityComponent = AbilitiesComp.Get(); + if (AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(AbilitiesComp->GetOwner()); + ability->POwner = POwner; + ability->PCOwner = Cast(POwner->Controller); + ability->OwnerCamera = nullptr; + } + ability->InitAbility(); + FGameplayTag Tag = ability->AbilityTag; + + AbilitiesInputs.Add(InClassPtr, ability); + FAFAbilityItem AbilityItem(ability, InClassPtr); + MarkItemDirty(AbilityItem); + AbilityItem.Ability = ability; + AbilitiesItems.Add(AbilityItem); + TagToAbility.Add(InClassPtr, ability); + + MarkArrayDirty(); + if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone + || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) + { + AbilitiesComp->NotifyOnAbilityReady(InClassPtr); + } + /* if (ActionName.IsValid()) + { + UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); + AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); + }*/ + return ability; + } + return nullptr; +} +void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& AbilityIn) +{ + int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); + + if (Index == INDEX_NONE) + return; + + UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); + + + for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) + { + AbilitiesComp->ReplicatedTasks.Remove(It->Value); + } + Ability->AbilityTasks.Reset(); + + AbilityToAction.Remove(AbilityIn); + AbilitiesInputs.Remove(AbilityIn); + TagToAbility.Remove(AbilityIn); + MarkItemDirty(AbilitiesItems[Index]); + AbilitiesItems.RemoveAt(Index); + MarkArrayDirty(); +} +TSoftClassPtr FAFAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) +{ + TSoftClassPtr Ability; + TSoftClassPtr* AbilityTag = ActionToAbility.Find(InInputTag); + if (AbilityTag) + { + Ability = *AbilityTag; + } + + return Ability; +} + +void FAFAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) +{ + for (const FGameplayTag& InputTag : InInputTag) + { + TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); + AbilityClassPtr = InAbiltyPtr; + TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); + ActionTag.Add(InputTag); + } + if (!AbilitiesComp.IsValid()) + return; + + UGAAbilityBase* Ability = TagToAbility.FindRef(InAbiltyPtr); + if (Ability) + { + Ability->OnAbilityInputReady(); + } + + if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) + { + AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); + } +} +void FAFAbilityContainer::RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr) +{ + TArray* Inputs = AbilityToAction.Find(InAbiltyPtr); + + if (Inputs) + { + for (const FGameplayTag& Input : *Inputs) + { + ActionToAbility.Remove(Input); + } + + AbilityToAction.Remove(InAbiltyPtr); + } +} +UGAAbilityBase* FAFAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) +{ + UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); + return retAbility; +} +void FAFAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) +{ + if (BlockedInput.FindRef(ActionName)) + { + return; + } + TSoftClassPtr AbiltyPtr = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(AbiltyPtr); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + ability->OnNativeInputPressed(ActionName, InPredictionHandle); + } +} +void FAFAbilityContainer::HandleInputReleased(FGameplayTag ActionName) +{ + if (BlockedInput.FindRef(ActionName)) + { + return; + } + TSoftClassPtr abilityTag = ActionToAbility.FindRef(ActionName); + UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); + if (ability) + { + ability->OnNativeInputReleased(ActionName); + } +} + +void FAFAbilityContainer::TriggerAbylityByTag(TSoftClassPtr InTag) +{ + UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); + if (ability) + { + if (ability->IsWaitingForConfirm()) + { + ability->ConfirmAbility(); + return; + } + FAFPredictionHandle PredHandle = FAFPredictionHandle::GenerateClientHandle(AbilitiesComp.Get()); + ability->OnNativeInputPressed(FGameplayTag(), PredHandle); + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeComponent.cpp new file mode 100644 index 0000000..3362503 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeComponent.cpp @@ -0,0 +1,35 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAttributeComponent.h" + + +// Sets default values for this component's properties +UAFAttributeComponent::UAFAttributeComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UAFAttributeComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UAFAttributeComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..96bb5a8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp @@ -0,0 +1,46 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" + +#include "Abilities/GAAbilityBase.h" +#include "Effects/GAEffectField.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "AFBlueprintFunctionLibrary.h" + +void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, + const FGameplayTag& AbilityTag, FGameplayTag ActionTag) +{ + IAFAbilityInterface* Interface = Cast(Target); + if (!Interface) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Invalid Target")); + return; + } + UAFAbilityComponent* Comp = Interface->GetAbilityComp(); + if (!Comp) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityPressedByTag: Target %s InvalidComponent"), *Target->GetName()); + return; + } + + Comp->NativeInputPressed(ActionTag); +} +void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, + const FGameplayTag& AbilityTag, FGameplayTag ActionTag) +{ + IAFAbilityInterface* Interface = Cast(Target); + if (!Interface) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Invalid Target")); + return; + } + UAFAbilityComponent* Comp = Interface->GetAbilityComp(); + if (!Comp) + { + UE_LOG(AbilityFramework, Log, TEXT("TriggerAbilityReleasedByTag: Target %s InvalidComponent"), *Target->GetName()); + return; + } + + Comp->NativeInputReleased(ActionTag); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueInterface.cpp new file mode 100644 index 0000000..2fac5ab --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueInterface.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFCueInterface.h" + + +// Add default functionality here for any IAFCueInterface functions that are not pure virtual. diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp new file mode 100644 index 0000000..c988060 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp @@ -0,0 +1,341 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/GAEffectCue.h" +#include "AFCueManager.h" +#if WITH_EDITOR +#include "Editor.h" +#endif + +UAFCueManager* UAFCueManager::ManagerInstance = nullptr; +//UWorld* UAFCueManager::CurrentWorld = nullptr; + +UAFCueManager* UAFCueManager::Get() +{ + if (ManagerInstance) + { + return ManagerInstance; + } + ManagerInstance = NewObject(GEngine, UAFCueManager::StaticClass(), "UAFCueManagerInstance", + RF_MarkAsRootSet); + ManagerInstance->AddToRoot(); + ManagerInstance->Initialize(); + + return ManagerInstance; +} +void UAFCueManager::Initialize() +{ +#if WITH_EDITORONLY_DATA + FEditorDelegates::EndPIE.AddUObject(this, &UAFCueManager::HandleOnPIEEnd); +#endif //WITH_EDITORONLY_DATA + FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); + FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); +} +#if WITH_EDITOR +void UAFCueManager::HandleOnPIEEnd(bool InVal) +{ + CurrentWorld = nullptr; + for (auto It = InstancedCues.CreateIterator(); It; ++It) + { + if (It->Value.IsValid()) + { + while (!It->Value->IsEmpty()) + { + AGAEffectCue* ToDestroy = nullptr; + It->Value->Dequeue(ToDestroy); + if (ToDestroy) + { + ToDestroy->Destroy(); + } + } + } + } + for (auto It = UsedCues.CreateIterator(); It; ++It) + { + if (It->Value.Num() <= 0) + { + UsedCues.Remove(It->Key); + } + for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) + { + if (QIt->Value.IsValid()) + { + while (!QIt->Value->IsEmpty()) + { + AGAEffectCue* ToDestroy = nullptr; + QIt->Value->Dequeue(ToDestroy); + if (ToDestroy) + { + ToDestroy->Destroy(); + } + } + } + if (It->Value.Num() <= 0) + { + UsedCues.Remove(It->Key); + } + } + + } + ActiveCues.Empty(); + InstancedCues.Empty(); + UsedCues.Empty(); +} +#endif //WITH_EDITOR +void UAFCueManager::HandlePreLoadMap(const FString& InMapName) +{ + CurrentWorld = nullptr; + + InstancedCues.Reset(); + InstancedCues.Compact(); + UsedCues.Reset(); + UsedCues.Compact(); + //for (auto It = InstancedCues.CreateIterator(); It; ++It) + //{ + // if (It->Value.IsValid()) + // { + // while (!It->Value->IsEmpty()) + // { + // AGAEffectCue* ToDestroy = nullptr; + // It->Value->Dequeue(ToDestroy); + // if (ToDestroy) + // { + // ToDestroy->Destroy(); + // } + // } + // } + //} + //for (auto It = UsedCues.CreateIterator(); It; ++It) + //{ + // if (It->Value.Num() <= 0) + // { + // UsedCues.Remove(It->Key); + // } + // for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) + // { + // if (QIt->Value.IsValid()) + // { + // while (!QIt->Value->IsEmpty()) + // { + // AGAEffectCue* ToDestroy = nullptr; + // QIt->Value->Dequeue(ToDestroy); + // if (ToDestroy) + // { + // ToDestroy->Destroy(); + // } + // } + // } + // if (It->Value.Num() <= 0) + // { + // UsedCues.Remove(It->Key); + // } + // } + + //} +} +void UAFCueManager::HandlePostLoadMap(UWorld* InWorld) +{ + CurrentWorld = InWorld; +} + + +void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) +{ + if (!CurrentWorld) + CurrentWorld = CueParams.Instigator->GetWorld(); + + + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + for (const FGameplayTag& CueTag : Tags) + { + + AGAEffectCue* actor = nullptr; + ENetRole mode = CueParams.Instigator->GetRemoteRole(); + TUniquePtr>& Cues = InstancedCues.FindOrAdd(CueTag); + if (Cues.IsValid()) + { + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(CueTag); + + if (!UseCuesQueue.IsValid()) + { + UseCuesQueue = MakeUnique>(); + } + { + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); + } + if (actor) + { + ActiveCues.Add(InHandle, actor); + actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.GetActor(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); + } + return;//don't try to load asset, we already have pooled instance. + } + + + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("EffectCueTagSearch", CueTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("EffectCue"), AssetData[0].AssetName); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams, InHandle); + + Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } + } + } +} +void UAFCueManager::HandleExecuteCue(FAFCueHandle InHandle) +{ + AGAEffectCue** Cue = ActiveCues.Find(InHandle); + if (Cue) + { + AGAEffectCue* cue = *Cue; + + cue->NativeOnExecuted(); + } +} +void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag + , FPrimaryAssetId InPrimaryAssetId + , FGAEffectCueParams CueParams + , FAFCueHandle InHandle) +{ + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); + TSubclassOf cls = Cast(loaded); + if (cls) + { + TSubclassOf CueClass = cls; + if (!CueClass) + return; + + ENetRole mode = CueParams.Instigator->GetRemoteRole(); + FString role; + switch (mode) + { + case ROLE_None: + role = "ROLE_None"; + break; + case ROLE_SimulatedProxy: + role = "ROLE_SimulatedProxy"; + break; + case ROLE_AutonomousProxy: + role = "ROLE_AutonomousProxy"; + break; + case ROLE_Authority: + role = "ROLE_Authority"; + break; + case ROLE_MAX: + role = "ROLE_MAX"; + break; + default: + break; + } + + FString prefix = ""; + //if (mode == ENetMode::NM_Client) + //{ + // prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); + //} + + UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), + *prefix, + *InCueTag.ToString(), + CueParams.Instigator.IsValid() ? *CueParams.Instigator->GetName() : TEXT("Invalid Instigator"), + *CueParams.HitResult.Location.ToString(), + *CurrentWorld->GetName(), + *role + ); + + FActorSpawnParameters SpawnParams; + FVector Location = CueParams.HitResult.Location; + FRotator Rotation = FRotator::ZeroRotator; + AGAEffectCue* actor = nullptr; + + TUniquePtr>& Cues = InstancedCues.FindOrAdd(InCueTag); + if (!Cues.IsValid()) + { + Cues = MakeUnique>(); + } + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(InCueTag); + + if (!UseCuesQueue.IsValid()) + { + UseCuesQueue = MakeUnique>(); + } + + if (Cues->IsEmpty()) + { + actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); + Cues->Enqueue(actor); + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); + } + else + { + Cues->Dequeue(actor); + UseCuesQueue->Enqueue(actor); + } + + if (actor) + { + ActiveCues.Add(InHandle, actor); + actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), + CueParams.Causer.Get(), CueParams.HitResult, CueParams); + } + } + + { + Manager->UnloadPrimaryAsset(InPrimaryAssetId); + } + } +} + +void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) +{ + if (!CurrentWorld) + CurrentWorld = CueParams.Instigator->GetWorld(); + for (const FGameplayTag& Tag : CueParams.CueTags) + { + AGAEffectCue* actor = nullptr; + TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); + if (!Cues.IsValid()) + { + Cues = MakeUnique>(); + } + FObjectKey InstigatorKey(CueParams.Instigator.Get()); + TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); + TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(Tag); + + if (!UseCuesQueue.IsValid()) + { + UseCuesQueue = MakeUnique>(); + } + + UseCuesQueue->Dequeue(actor); + + + if (actor) + { + ActiveCues.Remove(InHandle); + Cues->Enqueue(actor); + actor->NativeOnRemoved(); + } + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp new file mode 100644 index 0000000..87b6110 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp @@ -0,0 +1,502 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectsComponent.h" + +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + +#include "AFAbilityInterface.h" +#include "Effects/GAEffectExecution.h" +#include "Effects/GAGameEffect.h" +#include "Effects/GAEffectExtension.h" +#include "Effects/GAEffectCue.h" +#include "AFCueManager.h" +#include "Effects/GABlueprintLibrary.h" + +// Sets default values for this component's properties +UAFEffectsComponent::UAFEffectsComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UAFEffectsComponent::BeginPlay() +{ + Super::BeginPlay(); + GameEffectContainer.OwningComponent = this; + // ... + +} +void UAFEffectsComponent::InitializeComponent() +{ + Super::InitializeComponent(); + + GameEffectContainer.OwningComponent = this; +} + +// Called every frame +void UAFEffectsComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + FGAEffectProperty& InProperty = Params.GetProperty(); + const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; + + FAFEventData Data; + + for (const FGameplayTag& Tag : AppliedEventTags) + { + if (TArray* Events = EffectEvents.Find(Tag)) + { + for (const FAFEventDelegate& Event : *Events) + Event.Execute(Data); + } + + } + OnAppliedToSelf.Broadcast(Params.Context, Params.Property, Params.EffectSpec); + + if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) + { + Delegate->ExecuteIfBound(); + } + + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InHandle, Params, Modifier); + GameEffectContainer.MarkArrayDirty(); + return Handle; +} + +FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + FGAEffectProperty& InProperty = Params.GetProperty(); + FGAEffectContext& InContext = Params.GetContext(); + if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) + { + Delegate->ExecuteIfBound(); + } + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + + FAFCueHandle CueHandle = FAFCueHandle::GenerateHandle(); + + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams(InContext, InProperty); + MulticastApplyEffectCue(CueParams, CueHandle); + } + + OnAppliedToTarget.Broadcast(Params.Context, Params.Property, Params.EffectSpec); + + if (InContext.TargetComp.IsValid()) + { + FGAEffectHandle Handle; + Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InHandle, Params, Modifier); + //if (!PropertyByHandle.Contains(Handle)) + // PropertyByHandle.Add(Handle, &InProperty); + + EffectToCue.Add(Handle, CueHandle); + + return Handle; + } + return FGAEffectHandle(); +} + + +/* Have to to copy handle around, because timer delegates do not support references. */ +void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn + , FAFEffectParams Params + , FAFFunctionModifier Modifier) +{ + FGAEffectContext& Context = Params.Context.GetRef(); + FGAEffectProperty& Property = Params.Property.GetRef(); + FAFEffectSpec& EffectSpec = Params.GetSpec(); + /* + this patth will give effects chance to do any replicated events, like applying cues. + WE do not make any replication at the ApplyEffect because some effect might want to apply cues + on periods on expiration etc, and all those will go trouch ExecuteEffect path. + */ + const FGameplayTagContainer& RequiredTags = Property.GetSpec()->RequiredTags; + if (RequiredTags.Num() > 0) + { + if (!HasAll(RequiredTags)) + { + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *Property.GetSpec()->GetName(), *RequiredTags.ToString()); + return; + } + } + + //apply execution events: + const FGameplayTagContainer& ExecuteEventTags = Property.GetSpec()->ExecuteEventTags; + FAFEventData Data(Params); + for (const FGameplayTag& Tag : ExecuteEventTags) + { + TriggerExecuteEvent(Tag, Data); + } + + //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *Property.GetSpec()->GetName()); + + FGAEffectMod Mod = FAFStatics::GetAttributeModifier(Property.GetAttributeModifier() + , Property.GetSpec() + , Context + , HandleIn); + + EffectSpec.OnExecuted(); + ExecuteEffectEvent(Property.GetSpec()->OnPeriodEvent); + + FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + if (CueHandle) + MulticastExecuteEffectCue(*CueHandle); + + Property.ExecuteEffect(HandleIn, Mod, Params, Modifier); + PostExecuteEffect(); +} + +void UAFEffectsComponent::PostExecuteEffect() +{ + +} +/* ExpireEffect is used to remove existing effect naturally when their time expires. */ +void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn + , FAFEffectParams Params) +{ + //call effect internal delegate: + FGAEffectProperty& InProperty = Params.GetProperty(); + FGAEffectContext& InContext = Params.GetContext(); + FAFEffectSpec& EffectSpec = Params.GetSpec(); + FGAEffect* Effect = GameEffectContainer.GetEffect(HandleIn); + EffectSpec.OnExpired(); + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); + if (mode == ENetMode::NM_DedicatedServer + || mode == ENetMode::NM_ListenServer) + { + ClientExpireEffect(InProperty.GetPredictionHandle()); + } + + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams(InContext, InProperty); + + FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + if (CueHandle) + { + MulticastRemoveEffectCue(CueParams, *CueHandle); + } + } + + TArray handles = GameEffectContainer.RemoveEffect(Params.Property); +} + +void UAFEffectsComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) +{ + +} + +void UAFEffectsComponent::RemoveEffect(const FAFPropertytHandle& InProperty + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + if (!InProperty.IsValid()) + { + UE_LOG(AFEffects, Log, TEXT("RemoveEffect - Trying to Remove invalid effect.")); + return; + } + //if (GetOwnerRole() == ENetRole::ROLE_Authority + // || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) + { + InternalRemoveEffect(InProperty, InContext); + } + ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); + FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); + + FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); + if (CueHandle) + { + MulticastRemoveEffectCue(CueParams, *CueHandle); + } +} +void UAFEffectsComponent::InternalRemoveEffect(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext) +{ + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); + + //MulticastRemoveEffectCue(HandleIn); + if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + { + FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role >= ENetRole::ROLE_Authority) + { + //MulticastRemoveEffectCue(CueParams); + } + } + + TArray handles = GameEffectContainer.RemoveEffect(InProperty); +} + +void UAFEffectsComponent::AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) +{ + if (!InEventTag.IsValid()) + return; + if (!OnEffectEvent.Contains(InEventTag)) + { + UE_LOG(AbilityFramework, Log, TEXT("AddEffectEvent: %s"), *InEventTag.ToString()); + OnEffectEvent.Add(InEventTag, InEvent); + } +} +void UAFEffectsComponent::ExecuteEffectEvent(const FGameplayTag& InEventTag) +{ + if (!InEventTag.IsValid()) + return; + FSimpleDelegate* Delegate = OnEffectEvent.Find(InEventTag); + if (Delegate) + { + UE_LOG(AbilityFramework, Log, TEXT("ExecuteEffectEvent: %s"), *InEventTag.ToString()); + Delegate->ExecuteIfBound(); + } +} +void UAFEffectsComponent::RemoveEffectEvent(const FGameplayTag& InEventTag) +{ + if (!InEventTag.IsValid()) + return; + UE_LOG(AbilityFramework, Log, TEXT("RemoveEffectEvent: %s"), *InEventTag.ToString()); + OnEffectEvent.Remove(InEventTag); +} +TArray& UAFEffectsComponent::GetTagEvent(FGameplayTag TagIn) +{ + TArray& Delegate = EffectEvents.FindChecked(TagIn); + return Delegate; +} + +void UAFEffectsComponent::NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + TArray* Delegate = EffectEvents.Find(TagIn); + if (Delegate) + { + for (const FAFEventDelegate& Event : *Delegate) + { + if (Event.IsBound()) + { + Event.Execute(InEventData); + } + } + } +} + +void UAFEffectsComponent::AddAppliedEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) +{ + TArray& Events = AppliedEvents.FindOrAdd(EventTag); + Events.Add(EventDelegate); +} +void UAFEffectsComponent::RemoveAppliedEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) +{ + TArray* Events = AppliedEvents.Find(EventTag); + if (Events) + { + int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) + { + return Other.GetHandle() == EventDelegate; + }); + + Events->RemoveAt(Idx, 1, true); + } +} +void UAFEffectsComponent::TriggerAppliedEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + TArray* Delegate = AppliedEvents.Find(TagIn); + if (Delegate) + { + for (const FAFEventDelegate& Event : *Delegate) + { + if (Event.IsBound()) + { + Event.Execute(InEventData); + } + } + } +} + +void UAFEffectsComponent::AddExecuteEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) +{ + TArray& Events = ExecutedEvents.FindOrAdd(EventTag); + Events.Add(EventDelegate); +} +void UAFEffectsComponent::RemoveExecuteEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) +{ + TArray* Events = ExecutedEvents.Find(EventTag); + if (Events) + { + int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) + { + return Other.GetHandle() == EventDelegate; + }); + + Events->RemoveAt(Idx, 1, true); + } +} +void UAFEffectsComponent::TriggerExecuteEvent(FGameplayTag TagIn, const FAFEventData& InEventData) +{ + TArray* Delegate = ExecutedEvents.Find(TagIn); + if (Delegate) + { + for (const FAFEventDelegate& Event : *Delegate) + { + if (Event.IsBound()) + { + Event.Execute(InEventData); + } + } + } +} + + +void UAFEffectsComponent::AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate) +{ + TArray& Events = EffectEvents.FindOrAdd(EventTag); + Events.Add(EventDelegate); +} + +void UAFEffectsComponent::RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate) +{ + TArray* Events = EffectEvents.Find(EventTag); + if (Events) + { + + int32 Idx = Events->IndexOfByPredicate([&](const FAFEventDelegate& Other) + { + return Other.GetHandle() == EventDelegate; + }); + + Events->RemoveAt(Idx, 1, true); + } +} + +bool UAFEffectsComponent::IsEffectActive(const FGAEffectHandle& InHandle) const +{ + return GameEffectContainer.IsEffectActive(InHandle); +} + +bool UAFEffectsComponent::DenyEffectApplication(const FGameplayTagContainer& InTags) +{ + bool bDenyApplication = false; + if (InTags.Num() > 0) + { + bDenyApplication = HasAll(InTags); + } + return bDenyApplication; +} + +bool UAFEffectsComponent::HaveEffectRquiredTags(const FGameplayTagContainer& InTags) +{ + bool bAllowApplication = true; + if (InTags.Num() > 0) + { + bAllowApplication = HasAll(InTags); + } + return bAllowApplication; +} + +FGAEffect* UAFEffectsComponent::GetEffect(const FGAEffectHandle& InHandle) +{ + return *GameEffectContainer.ActiveEffects.Find(InHandle); +} + +/* +Need prediction for spawning effects on client, +and then on updateing them predicitvely on all other clients. +*/ +/* + +*/ +void UAFEffectsComponent::MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); + } +} +void UAFEffectsComponent::MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleExecuteCue(InHandle); + } +} + +void UAFEffectsComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle) +{ + ENetRole role = GetOwnerRole(); + ENetMode mode = GetOwner()->GetNetMode(); + if (mode == ENetMode::NM_Standalone + || role != ENetRole::ROLE_Authority) + { + UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams, InHandle); + } +} + +void UAFEffectsComponent::MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} + +void UAFEffectsComponent::MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn) +{ + +} + +void UAFEffectsComponent::MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn) +{ + +} + +void UAFEffectsComponent::MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn) +{ + +} + + +/*Network Functions - BEGIN */ + +void UAFEffectsComponent::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + + DOREPLIFETIME(UAFEffectsComponent, GameEffectContainer); + DOREPLIFETIME(UAFEffectsComponent, AppliedTags); + DOREPLIFETIME(UAFEffectsComponent, ImmunityTags); +} + +void UAFEffectsComponent::OnRep_GameEffectContainer() +{ + +} + +/*Network Functions - END */ \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityActivationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityActivationSpec.cpp new file mode 100644 index 0000000..dbb9013 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityActivationSpec.cpp @@ -0,0 +1,13 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../Effects/CustomApplications/AFAtributeDurationAdd.h" +#include "AFAbilityActivationSpec.h" + + + +UAFAbilityActivationSpec::UAFAbilityActivationSpec() + :Super() +{ + Application = UAFAtributeDurationAdd::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityCooldownSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityCooldownSpec.cpp new file mode 100644 index 0000000..045614d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityCooldownSpec.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/CustomApplications/AFAtributeDurationAdd.h" +#include "AFAbilityCooldownSpec.h" + + + + +UAFAbilityCooldownSpec::UAFAbilityCooldownSpec() + : Super() +{ + Application = UAFAtributeDurationAdd::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityInfiniteDurationSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityInfiniteDurationSpec.cpp new file mode 100644 index 0000000..19cf6ce --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityInfiniteDurationSpec.cpp @@ -0,0 +1,13 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/CustomApplications/AFAttributeDurationInfinite.h" +#include "AFAbilityInfiniteDurationSpec.h" + + + +UAFAbilityInfiniteDurationSpec::UAFAbilityInfiniteDurationSpec() + :Super() +{ + Application = UAFAttributeDurationInfinite::StaticClass(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodSpec.cpp new file mode 100644 index 0000000..49cb210 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodSpec.cpp @@ -0,0 +1,13 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityPeriodSpec.h" +#include "../Effects/CustomApplications/AFPeriodApplicationAdd.h" + + + +UAFAbilityPeriodSpec::UAFAbilityPeriodSpec() + :Super() +{ + Application = UAFPeriodApplicationAdd::StaticClass(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodicInfiniteSpec.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodicInfiniteSpec.cpp new file mode 100644 index 0000000..a77c62a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/AFAbilityPeriodicInfiniteSpec.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h" +#include "AFAbilityPeriodicInfiniteSpec.h" + + + + +UAFAbilityPeriodicInfiniteSpec::UAFAbilityPeriodicInfiniteSpec() + :Super() +{ + Application = UAFPeriodApplicationInfiniteAdd::StaticClass(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp new file mode 100644 index 0000000..9b5a023 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp @@ -0,0 +1,950 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + + +#include "AbilityFramework.h" +#include "Tasks/GAAbilityTask.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Effects/GAEffectGlobalTypes.h" +#include "AFAbilityComponent.h" +#include "AFEffectsComponent.h" + +#include "GameplayTagContainer.h" +#include "Net/UnrealNetwork.h" +#include "Animation/AnimMontage.h" +#include "Effects/GABlueprintLibrary.h" +#include "Camera/CameraComponent.h" +#include "Kismet/KismetSystemLibrary.h" + +#include "GAAbilityBase.h" +FAFPredictionHandle UGAAbilityBase::GetPredictionHandle() { return PredictionHandle; } + +UGAAbilityBase::UGAAbilityBase(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bReplicate = true; + bIsNameStable = false; +} + +void UGAAbilityBase::PostInitProperties() +{ + UpdateAssetRegistryInfo(); + Super::PostInitProperties(); +} + +void UGAAbilityBase::Serialize(FArchive& Ar) +{ + if (Ar.IsSaving()) + { + UpdateAssetRegistryInfo(); + } + + Super::Serialize(Ar); + + if (Ar.IsLoading()) + { + UpdateAssetRegistryInfo(); + } +} +#if WITH_EDITORONLY_DATA +void UGAAbilityBase::UpdateAssetBundleData() +{ + AssetBundleData.Reset(); + + // By default parse the metadata + if (UAssetManager::IsValid()) + { + UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); + } +} + +void UGAAbilityBase::PreSave(const class ITargetPlatform* TargetPlatform) +{ + Super::PreSave(TargetPlatform); + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid()) + { + // Bundles may have changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +} +#endif + +FPrimaryAssetId UGAAbilityBase::GetPrimaryAssetId() const +{ + //FName Name = GetFName(); + //FName clsNam = GetClass()->GetFName(); + FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); + //FName dupa2 = FPackageName::GetShortFName(GetFName()); + const UGAAbilityBase* A = this; + return FPrimaryAssetId(FPrimaryAssetType("Ability"), dupa1); + //if (HasAnyFlags(RF_ClassDefaultObject)) + { + UClass* SearchNativeClass = GetClass(); + + while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) + { + SearchNativeClass = SearchNativeClass->GetSuperClass(); + } + + if (SearchNativeClass && SearchNativeClass != GetClass()) + { + // If blueprint, return native class and asset name + + } + + // Native CDO, return nothing + return FPrimaryAssetId(); + } + + // Data assets use Class and ShortName by default, there's no inheritance so class works fine + //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); +} + +void UGAAbilityBase::PostLoad() +{ + Super::PostLoad(); + +#if WITH_EDITORONLY_DATA + FAssetBundleData OldData = AssetBundleData; + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid() && OldData != AssetBundleData) + { + // Bundles changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +#endif +} +#if WITH_EDITOR +void UGAAbilityBase::PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) +{ + Super::PostEditChangeProperty(PropertyChangedEvent); +} +#endif // WITH_EDITOR + +void UGAAbilityBase::UpdateAssetRegistryInfo() +{ + AbilityTagSearch = AbilityTag.GetTagName(); +} + +void UGAAbilityBase::InitAbility() +{ + //still want to initialize, as Spec is used in multiple places. + DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); + ActivationEffect.InitializeIfNotInitialized(DefaultContext); + CooldownEffect.InitializeIfNotInitialized(DefaultContext); + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + AttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + } + AttributeCostHandle.AddZeroed(AttributeCost.Num()); + + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + } + AbilityAttributeCostHandle.AddZeroed(AbilityAttributeCost.Num()); + if (AbilityComponent) + { + World = AbilityComponent->GetWorld(); + } + + if (!AbilityComponent) + { + AbilityComponent = GetAbilityComp(); + } + if (Attributes) + { + Attributes->InitializeAttributes(GetAbilityComp()); + Attributes->InitializeAttributesFromTable(); + } + + ENetRole role = AbilityComponent->GetOwnerRole(); + ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); + + if (role < ENetRole::ROLE_Authority) + { + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); + AbilityComponent->RepAttributes.RegisterAttributeRepEvent(AbilityTag, Delegate); + } + + //AbilityComponent->RepAttributes.AttributeMap.Add(AbilityTag, Attributes); + if (role == ENetRole::ROLE_Authority || + mode == ENetMode::NM_Standalone) + { + if (AbilityComponent && Attributes) + { + UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes);; + Attributes = nullptr; + Attributes = NewAttributes; + } + } + + if (!OwnerCamera) + { + OwnerCamera = POwner->FindComponentByClass(); + } + + OnAbilityInited(); +} +void UGAAbilityBase::OnAttributeSetReplicated() +{ + UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); + Attributes = attributes; +} + +void UGAAbilityBase::OnAbilityInited() +{ + +} +void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) +{ + { + UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); + PredictionHandle = InPredictionHandle; + OnInputPressed(ActionName); + OnInputPressedDelegate.Broadcast(); + } +} + +void UGAAbilityBase::OnNativeInputReleased(FGameplayTag ActionName) +{ + { + UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputReleased in ability %s"), *GetName()); + OnInputReleased(ActionName); + OnInputReleasedDelegate.Broadcast(); + } +} + +void UGAAbilityBase::StartActivation(bool bApplyActivationEffect) +{ + if (!CanUseAbility()) + { + UE_LOG(AbilityFramework, Log, TEXT("Cannot use Ability: %s"), *GetName()); + return; + } + //AbilityComponent->ExecutingAbility = this; + AbilityState = EAFAbilityState::Activating; + NativeOnBeginAbilityActivation(bApplyActivationEffect); +} + +void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) +{ + UE_LOG(AbilityFramework, Log, TEXT("Begin Executing Ability: %s"), *GetName()); + + if (OnConfirmCastingEndedDelegate.IsBound()) + { + OnConfirmCastingEndedDelegate.Broadcast(); + } + //ActivationInfo.SetActivationInfo(); + ApplyActivationEffect(bApplyActivationEffect); + OnActivate(); + OnActivateBeginDelegate.Broadcast(); + AbilityComponent->AppliedTags.AddTagContainer(ActivationAddedTags); + //OnAbilityExecuted(); +} + +void UGAAbilityBase::OnCooldownEffectExpired() +{ + UE_LOG(AFAbilities, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); + + if (CooldownEffectHandle.IsValid()) + { + //CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); + } +} +/* Functions for activation effect delegates */ +void UGAAbilityBase::NativeOnAbilityActivationFinish(FGAEffectHandle InHandle) +{ + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); + OnActivationFinished(); + OnActivationFinishedDelegate.Broadcast(); +} +void UGAAbilityBase::NativeOnAbilityActivationCancel() +{ + //OnAbilityExecutedNative(); + //this works under assumption that current state == activation state. + UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Removed In Ability: %s"), *GetName()); + //AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + + OnActivationCancel(); + //AbilityActivatedCounter++; +} +void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) +{ + UE_LOG(AFAbilities, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); + + OnPeriod(); +} +void UGAAbilityBase::FinishAbility() +{ + UE_LOG(AFAbilities, Log, TEXT("FinishExecution in ability %s"), *GetName()); + OnAbilityFinished(); + NativeFinishAbility(); + AbilityState = EAFAbilityState::Waiting; + GetEffectsComponent()->AppliedTags.RemoveTagContainer(ActivationAddedTags); +} +void UGAAbilityBase::NativeFinishAbility() +{ + UE_LOG(AFAbilities, Log, TEXT("NativeFinishExecution in ability %s"), *GetName()); + AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + if (!ActivationEffectHandle.IsValid()) + { + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + ActivationEffectHandle.Reset(); + } + //remove effect. +} +/* Functions for activation effect delegates */ +void UGAAbilityBase::CancelActivation() +{ + NativeCancelActivation(); +} +void UGAAbilityBase::NativeCancelActivation() +{ + if (!ActivationEffectHandle.IsValid()) + return; + + UAFAbilityComponent* AttrComp = DefaultContext.InstigatorComp.Get(); + AbilityComponent->ExecutingAbility = nullptr; + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); + if (GetEffectsComponent()) + { + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + AbilityState = EAFAbilityState::Waiting; + ActivationEffectHandle.Reset(); + } + OnActivationCancel(); +} + +bool UGAAbilityBase::IsWaitingForConfirm() +{ + if (OnConfirmDelegate.IsBound()) + return true; + else + return false; +} +void UGAAbilityBase::ConfirmAbility() +{ + if (OnConfirmDelegate.IsBound()) + OnConfirmDelegate.Broadcast(); + OnConfirmDelegate.Clear(); + OnConfirmDelegate.RemoveAll(this); +} + +bool UGAAbilityBase::ApplyCooldownEffect() +{ + if (!CooldownEffect.GetSpec()) + { + return false; + } + FAFFunctionModifier Modifier; + + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); + GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); + + CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + CooldownEffect + , CooldownEffectHandle + , this + , POwner + , this + , Modifier); + ENetMode nm = AbilityComponent->GetOwner()->GetNetMode(); + ENetRole role = AbilityComponent->GetOwnerRole(); + + if (role >= ENetRole::ROLE_Authority) + { + ClientSetCooldownHandle(CooldownEffectHandle); + } + OnCooldownStart(); + + //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); + return false; +} +void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) +{ + //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); + OnCooldownEnd(InHandle); + CooldownEffectHandle.Reset(); +} +void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) +{ + //CooldownEffectHandle = InCooldownHandle; +} +bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) +{ + if (!ActivationEffect.GetSpec()) + return false; + FHitResult Hit(ForceInit); + + UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); + float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); + float PeriodCheck = Spec->Period.GetFloatValue(DefaultContext); + if (DurationCheck > 0 || PeriodCheck > 0) + { + bApplyActivationEffect = true; + } + + if (bApplyActivationEffect) + { + FHitResult HitIn; + if (ActivationEffectHandle.IsValid()) + ActivationEffectHandle.Reset(); + + FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); + + FAFFunctionModifier Modifier; + ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( + ActivationEffect + , ActivationEffectHandle + , this + , POwner + , this + , Modifier); + + //if(!ActivationEffectHandle.GetEffectRef().OnEffectExpired.) + // ActivationEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); + + + if (PeriodCheck > 0) + { + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); + //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) + // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); + } + } + else + { + NativeOnAbilityActivationFinish(FGAEffectHandle()); + } + return false; +} + +bool UGAAbilityBase::CanUseAbility() +{ + bool CanUse = true; + bool bIsOnCooldown = IsOnCooldown(); + bool bIsActivating = IsActivating(); + //if (!AbilityComponent->ExecutingAbility) + // UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility AbilityComponent->ExecutingAbility is true")); + + CanUse = !bIsOnCooldown && !bIsActivating; + UE_LOG(AbilityFramework, Log, TEXT("CanUseAbility Ability, Cooldown: %s, Activating: %s \n"), bIsOnCooldown ? TEXT("true") : TEXT("false"), bIsActivating ? TEXT("true") : TEXT("false") ); + //now Lets check tags + if (CanUse) + { + if (GetEffectsComponent()->HasAll(ActivationRequiredTags)) + { + CanUse = true; + } + //blocking takes precedence. + if (GetEffectsComponent()->HasAny(ActivationBlockedTags)) + { + CanUse = false; + } + } + + return CanUse; +} +bool UGAAbilityBase::BP_CanUseAbility() +{ + return CanUseAbility(); +} +bool UGAAbilityBase::CanReleaseAbility() +{ + bool bCanUse = true; + /*if (AbilityComponent->ExecutingAbility == this) + { + bCanUse = true; + }*/ + if (IsOnCooldown()) + { + bCanUse = false; + UE_LOG(AbilityFramework, Log, TEXT("CanReleaseAbility can't release ability is on cooldown")); + } + return bCanUse; +} + +class UGAAttributesBase* UGAAbilityBase::GetAttributes() +{ + return Attributes; +} +UAFAbilityComponent* UGAAbilityBase::GetAbilityComp() +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->GetAbilityComp(); + } + return nullptr; +} + +UAFEffectsComponent* UGAAbilityBase::GetEffectsComponent() +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->GetEffectsComponent(); + } + return nullptr; +} +UAFEffectsComponent* UGAAbilityBase::NativeGetEffectsComponent() const +{ + IAFAbilityInterface* OwnerAttributes = Cast(POwner); + if (OwnerAttributes) + { + return OwnerAttributes->NativeGetEffectsComponent(); + } + return nullptr; +} +float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const +{ + return NativeGetAttributeValue(AttributeIn); +} +float UGAAbilityBase::NativeGetAttributeValue(const FGAAttribute AttributeIn) const +{ + return Attributes->GetCurrentAttributeValue(AttributeIn); +} +float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const +{ + return Attributes->GetCurrentAttributeValue(AttributeIn); +} + +bool UGAAbilityBase::ApplyAttributeCost() +{ + FAFFunctionModifier Modifier; + if (CheckAttributeCost()) + { + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + AttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( + AttributeCost[Idx] + , AttributeCostHandle[Idx] + , POwner + , POwner + , this + , Modifier); + } + return true; + } + return false; +} +bool UGAAbilityBase::ApplyAbilityAttributeCost() +{ + //add checking if attribute goes below zero + //maybe let game specific code handle it.. + FAFFunctionModifier Modifier; + + if (CheckAbilityAttributeCost()) + { + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + AbilityAttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( + AbilityAttributeCost[Idx] + , AbilityAttributeCostHandle[Idx] + , this + , POwner + , this + , Modifier); + } + return true; + } + return false; +} +bool UGAAbilityBase::BP_ApplyAttributeCost() +{ + return ApplyAttributeCost(); +} +bool UGAAbilityBase::BP_CheckAttributeCost() +{ + return CheckAttributeCost(); +} + +bool UGAAbilityBase::BP_ApplyAbilityAttributeCost() +{ + return ApplyAbilityAttributeCost(); +} +bool UGAAbilityBase::BP_CheckAbilityAttributeCost() +{ + return CheckAbilityAttributeCost(); +} +bool UGAAbilityBase::CheckAbilityAttributeCost() +{ + for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) + { + float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Attributes->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + } + return true; +} +bool UGAAbilityBase::CheckAttributeCost() +{ + IAFAbilityInterface* Interface = Cast(POwner); + + for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) + { + float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float AttributeVal = Interface->GetAttributes()->GetFloatValue(Attribute); + if (ModValue > AttributeVal) + return false; + } + return true; +} +bool UGAAbilityBase::IsOnCooldown() +{ + bool bOnCooldown = false; + bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle); + if (bOnCooldown) + { + OnNotifyOnCooldown.Broadcast(); + } + return bOnCooldown; //temp +} +bool UGAAbilityBase::IsActivating() +{ + bool bAbilityActivating = false; + bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffect.GetHandle(this)); + bool bInActivatingState = AbilityState == EAFAbilityState::Activating; + UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); + bAbilityActivating = bHaveEffect || bInActivatingState; + + return bAbilityActivating; //temp +} +bool UGAAbilityBase::BP_IsOnCooldown() +{ + return IsOnCooldown(); +} +void UGAAbilityBase::BP_ApplyCooldown() +{ + ApplyCooldownEffect(); +} + +float UGAAbilityBase::GetCurrentActivationTime() +{ + if (ActivationEffectHandle.IsValid()) + { + if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) + { + FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); + if (Effect) + { + return Effect->GetCurrentDuration(); + } + } + //return ActivationEffectHandle.GetEffectPtr()->GetCurrentDuration(); + } + return 0; +} + +float UGAAbilityBase::CalculateAnimationSpeed(UAnimMontage* MontageIn) +{ + float ActivationTime = MontageIn->GetPlayLength(); + UGAGameEffectSpec* Spec = ActivationEffect.GetClass().GetDefaultObject(); + float DurationCheck = Spec->Duration.GetFloatValue(DefaultContext); + if (DurationCheck > 0) + { + ActivationTime = DurationCheck; + } + float Duration = MontageIn->GetPlayLength(); + + float PlaySpeed = Duration / ActivationTime; + return PlaySpeed; +} + + +bool UGAAbilityBase::IsNameStableForNetworking() const +{ + return bIsNameStable; +} + +void UGAAbilityBase::SetNetAddressable() +{ + bIsNameStable = true; +} + +class UWorld* UGAAbilityBase::GetWorld() const +{ + return World; +} +void UGAAbilityBase::PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed) +{ + AbilityComponent->PlayMontage(MontageIn, SectionName, Speed); +} + +//replication +void UGAAbilityBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly can be infered upon replication. + //does other players need info about this ? + DOREPLIFETIME(UGAAbilityBase, POwner); + DOREPLIFETIME(UGAAbilityBase, PCOwner); + DOREPLIFETIME(UGAAbilityBase, AICOwner); + DOREPLIFETIME(UGAAbilityBase, AvatarActor); + //probabaly should be SKIP_Owner, and I'm not really sure if Multicast wouldn't be better. + +} +int32 UGAAbilityBase::GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) +{ + if (HasAnyFlags(RF_ClassDefaultObject)) + { + return FunctionCallspace::Local; + } + check(POwner != NULL); + return POwner->GetFunctionCallspace(Function, Parameters, Stack); +} +bool UGAAbilityBase::CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) +{ + check(!HasAnyFlags(RF_ClassDefaultObject)); + check(POwner != NULL); + + + UNetDriver* NetDriver = POwner->GetNetDriver(); + if (NetDriver) + { + NetDriver->ProcessRemoteFunction(POwner, Function, Parameters, OutParms, Stack, this); + return true; + } + + return false; +} + +void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) +{ + AbilityComponent->NativeInputPressed(ActionName); +} +void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) +{ + AbilityComponent->NativeInputReleased(ActionName); +} + +bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) +{ + bool bHaveTag = false; + if (IAFAbilityInterface* Interface = Cast(Target)) + { + if (UAFEffectsComponent* Comp = GetEffectsComponent()) + { + if (Comp->HasTag(Tag)) + { + bHaveTag = true; + } + } + } + return bHaveTag; +} +bool UGAAbilityBase::HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag) +{ + bool bHaveTag = false; + if (IAFAbilityInterface* Interface = Cast(Target)) + { + if (UAFEffectsComponent* Comp = GetEffectsComponent()) + { + if (Comp->HasAny(Tag)) + { + bHaveTag = true; + } + } + } + return bHaveTag; +} +/* Tracing Helpers Start */ +bool UGAAbilityBase::LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit) +{ + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); + FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); + + bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); + return bHit; +} +bool UGAAbilityBase::LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + FVector Start = FVector::ZeroVector; + if (OwnerCamera) + { + Start = OwnerCamera->GetComponentLocation(); + } + else + { + FRotator UnusedRot; + POwner->GetActorEyesViewPoint(Start, UnusedRot); + } + FVector End = (POwner->GetBaseAimRotation().Vector() * Range) + Start; + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + static const FName LineTraceSingleName(TEXT("AbilityLineTraceSingle")); + FCollisionQueryParams Params(LineTraceSingleName, bTraceComplex); + bool bHit = World->LineTraceSingleByChannel(OutHit, Start, End, CollisionChannel, Params); +#if ENABLE_DRAW_DEBUG + if (DrawDebugType != EDrawDebugTrace::None) + { + bool bPersistent = DrawDebugType == EDrawDebugTrace::Persistent; + float LifeTime = (DrawDebugType == EDrawDebugTrace::ForDuration) ? DrawTime : 0.f; + + // @fixme, draw line with thickness = 2.f? + if (bHit && OutHit.bBlockingHit) + { + // Red up to the blocking hit, green thereafter + ::DrawDebugLine(World, Start, OutHit.ImpactPoint, TraceColor.ToFColor(true), bPersistent, LifeTime); + ::DrawDebugLine(World, OutHit.ImpactPoint, End, TraceHitColor.ToFColor(true), bPersistent, LifeTime); + ::DrawDebugPoint(World, OutHit.ImpactPoint, 16, TraceColor.ToFColor(true), bPersistent, LifeTime); + } + else + { + // no hit means all red + ::DrawDebugLine(World, Start, End, TraceColor.ToFColor(true), bPersistent, LifeTime); + } + } +#endif + return bHit; +} +bool UGAAbilityBase::LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + return false; +} +bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime) +{ + return false; +} +/* Tracing Helpers End */ + +//Helpers +float UGAAbilityBase::GetActivationRemainingTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationRemainingTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationCurrentTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationCurrentTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); +} +float UGAAbilityBase::GetActivationEndTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle); +} +float UGAAbilityBase::BP_GetActivationRemainingTime() +{ + return GetActivationRemainingTime(); +} +float UGAAbilityBase::BP_GetActivationRemainingTimeNormalized() +{ + return GetActivationRemainingTimeNormalized(); +} +float UGAAbilityBase::BP_GetActivationCurrentTime() +{ + return GetActivationCurrentTime(); +} +float UGAAbilityBase::BP_GetActivationCurrentTimeNormalized() +{ + return GetActivationCurrentTimeNormalized(); +} +float UGAAbilityBase::BP_GetActivationEndTime() +{ + return GetActivationEndTime(); +} + + +float UGAAbilityBase::GetCooldownRemainingTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownCurrentTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); +} +float UGAAbilityBase::GetCooldownEndTime() const +{ + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle); +} +float UGAAbilityBase::BP_GetCooldownRemainingTime() +{ + return GetCooldownRemainingTime(); +} +float UGAAbilityBase::BP_GetCooldownRemainingTimeNormalized() +{ + return GetCooldownRemainingTimeNormalized(); +} +float UGAAbilityBase::BP_GetCooldownCurrentTime() +{ + return GetCooldownCurrentTime(); +} +float UGAAbilityBase::BP_GetCooldownCurrentTimeNormalized() +{ + return GetCooldownCurrentTimeNormalized(); +} +float UGAAbilityBase::BP_GetCooldownEndTime() +{ + return GetCooldownEndTime(); +} + +AActor* UGAAbilityBase::BP_GetAvatar() +{ + return AvatarActor; +} + + +void UGAAbilityBase::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) +{ + if (!InstanceName.IsNone()) + { + AbilityTasks.Add(InstanceName, TaskIn); + } +}; +void UGAAbilityBase::AddReplicatedTask(class UAFTaskBase* TaskIn) +{ + AbilityComponent->ReplicatedTasks.Add(TaskIn); +} +void UGAAbilityBase::OnLatentTaskRemoved(class UAFTaskBase* TaskIn) +{ +}; + +void UGAAbilityBase::OnLatentTaskActivated(class UAFTaskBase* TaskIn) +{ +}; +void UGAAbilityBase::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) +{ +}; + +class UAFTaskBase* UGAAbilityBase::GetCachedLatentAction(FName TaskName) +{ + return AbilityTasks.FindRef(TaskName); +} +class UGAAbilityTask* UGAAbilityBase::GetAbilityTask(const FName& InName) +{ + UAFTaskBase* result = AbilityTasks.FindRef(InName); + return Cast(result); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBlueprint.cpp new file mode 100644 index 0000000..71133ea --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAAbilityBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAAbilityBlueprint::UGAAbilityBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAAbilityBlueprint* UGAAbilityBlueprint::FindRootGameplayAbilityBlueprint(UGAAbilityBlueprint* DerivedBlueprint) +{ + UGAAbilityBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAAbilityBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp new file mode 100644 index 0000000..dee0062 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/AFAbilityTask_SpawnProjectile.cpp @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityTask_SpawnProjectile.h" + + + + +UAFAbilityTask_SpawnProjectile* UAFAbilityTask_SpawnProjectile::Ability_SpawnProjectile(UGAAbilityBase* WorldContextObject, + FName InTaskName, + FVector InStartLocation, + FVector InEndLocation, + float InLaunchSpeed, + float InOverrideGravityZ, + EAFPRojectileSpawnTraceOption InTraceOption, + float InCollisionRadius, + bool InbFavorHighArc, + bool InbDrawDebug) +{ + auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); + MyObj->StartLocation = InStartLocation; + MyObj->EndLocation = InEndLocation; + MyObj->LaunchSpeed = InLaunchSpeed; + MyObj->OverrideGravityZ = InOverrideGravityZ; + MyObj->TraceOption = InTraceOption; + MyObj->CollisionRadius = InCollisionRadius; + MyObj->bFavorHighArc = InbFavorHighArc; + MyObj->bDrawDebug = InbDrawDebug; + return MyObj; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask.cpp new file mode 100644 index 0000000..190da1a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask.cpp @@ -0,0 +1,12 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../../AbilityFramework.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask.h" + +UGAAbilityTask::UGAAbilityTask(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + bIsReplicated = false; + SetFlags(RF_StrongRefOnFrame); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_CreateObject.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_CreateObject.cpp new file mode 100644 index 0000000..c82011a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_CreateObject.cpp @@ -0,0 +1,64 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_CreateObject.h" + +UGAAbilityTask_CreateObject* UGAAbilityTask_CreateObject::CreateObject(UGAAbilityBase* WorldContextObject, + FName InTaskName, TSubclassOf Class, UObject* Outer) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + //if(MyObj) + // MyObj->SpawnObject(WorldContextObject, InClass, Outer); + //MyObj->CachedTargetDataHandle = TargetData; + return MyObj; +} + +// --------------------------------------------------------------------------------------- + +bool UGAAbilityTask_CreateObject::BeginSpawningActor(UGAAbilityBase* WorldContextObject, + TSubclassOf Class, UObject*& SpawnedActor) +{ + //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) + //{ + //UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject); + //if (World) + //{ + SpawnedActor = NewObject(WorldContextObject, Class); + //} + //} + + if (SpawnedActor == nullptr) + { + Failure.Broadcast(nullptr); + return false; + } + UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); + return true; +} + +void UGAAbilityTask_CreateObject::FinishSpawningActor(UGAAbilityBase* WorldContextObject, UObject* SpawnedActor) +{ + if (SpawnedActor) + { + FTransform SpawnTransform;// = AbilitySystemComponent->GetOwner()->GetTransform(); + + //if (FGameplayAbilityTargetData* LocationData = CachedTargetDataHandle.Get(0)) //Hardcode to use data 0. It's OK if data isn't useful/valid. + //{ + // //Set location. Rotation is unaffected. + // if (LocationData->HasHitResult()) + // { + // SpawnTransform.SetLocation(LocationData->GetHitResult()->Location); + // } + // else if (LocationData->HasEndPoint()) + // { + // SpawnTransform.SetLocation(LocationData->GetEndPoint()); + // } + //} + + //SpawnedActor->FinishSpawning(SpawnTransform); + + Success.Broadcast(SpawnedActor); + } + UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); + EndTask(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp new file mode 100644 index 0000000..3ab4e2e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_PlayMontage.cpp @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../../AFAbilityComponent.h" +#include "GAAbilityTask_PlayMontage.h" + +UGAAbilityTask_PlayMontage* UGAAbilityTask_PlayMontage::AbilityPlayMontage(UGAAbilityBase* WorldContextObject, + FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, + bool bInUseActivationTime) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + MyObj->Montage = MontageIn; + MyObj->SectionName = SectionNameIn; + MyObj->PlayRate = PlayRateIn; + MyObj->bUseActivationTime = bInUseActivationTime; + return MyObj; +} + +void UGAAbilityTask_PlayMontage::Activate() +{ + AbilityComponent->OnAbilityNotifyBegin.Unbind(); + AbilityComponent->OnAbilityNotifyTick.Unbind(); + AbilityComponent->OnAbilityNotifyEnd.Unbind(); + + AbilityComponent->OnAbilityNotifyBegin.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastStartNotifyState); + AbilityComponent->OnAbilityNotifyTick.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastTickNotifyState); + AbilityComponent->OnAbilityNotifyEnd.BindUObject(this, &UGAAbilityTask_PlayMontage::BroadcastEndNotifyState); + if (bUseActivationTime) + { + PlayRate = Ability->CalculateAnimationSpeed(Montage); + Ability->PlayMontage(Montage, SectionName, PlayRate); + } + else + { + Ability->PlayMontage(Montage, SectionName, PlayRate); + } +} + +void UGAAbilityTask_PlayMontage::BroadcastStartNotifyState(const FGameplayTag& InTag, const FName& InName) +{ + NotifyBegin.Broadcast(InTag, InName); +} +void UGAAbilityTask_PlayMontage::BroadcastEndNotifyState(const FGameplayTag& InTag, const FName& InName) +{ + NotifyTick.Broadcast(InTag, InName); +} +void UGAAbilityTask_PlayMontage::BroadcastTickNotifyState(const FGameplayTag& InTag, const FName& InName) +{ + NotifyEnd.Broadcast(InTag, InName); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_Repeat.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_Repeat.cpp new file mode 100644 index 0000000..1ee4cbb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_Repeat.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_Repeat.h" + + + + +UGAAbilityTask_Repeat* UGAAbilityTask_Repeat::CreateRepeatTask(UGAAbilityBase* WorldContextObject, + FName InTaskName) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + //MyObj->CachedTargetDataHandle = TargetData; + return MyObj; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp new file mode 100644 index 0000000..a075365 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_SpawnActor.cpp @@ -0,0 +1,70 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_SpawnActor.h" + + + + + +UGAAbilityTask_SpawnActor* UGAAbilityTask_SpawnActor::SpawnActor(UGAAbilityBase* WorldContextObject, + FName InTaskName, TSubclassOf InClass) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + //MyObj->CachedTargetDataHandle = TargetData; + return MyObj; +} + +// --------------------------------------------------------------------------------------- +void UGAAbilityTask_SpawnActor::Activate() +{ + UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); + //EndTask(); +} + +bool UGAAbilityTask_SpawnActor::BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf InClass, AActor*& SpawnedActor) +{ + //if (Ability.IsValid() && Ability.Get()->GetCurrentActorInfo()->IsNetAuthority()) + //{ + UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); + if (World) + { + SpawnedActor = World->SpawnActorDeferred(InClass, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); + } + //} + + if (SpawnedActor == nullptr) + { + Failure.Broadcast(nullptr); + return false; + } + UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); + return true; +} + +void UGAAbilityTask_SpawnActor::FinishSpawningActor(UGAAbilityBase* WorldContextObject, AActor* SpawnedActor) +{ + if (SpawnedActor) + { + FTransform SpawnTransform;// = AbilitySystemComponent->GetOwner()->GetTransform(); + + //if (FGameplayAbilityTargetData* LocationData = CachedTargetDataHandle.Get(0)) //Hardcode to use data 0. It's OK if data isn't useful/valid. + //{ + // //Set location. Rotation is unaffected. + // if (LocationData->HasHitResult()) + // { + // SpawnTransform.SetLocation(LocationData->GetHitResult()->Location); + // } + // else if (LocationData->HasEndPoint()) + // { + // SpawnTransform.SetLocation(LocationData->GetEndPoint()); + // } + //} + + SpawnedActor->FinishSpawning(SpawnTransform); + + Success.Broadcast(SpawnedActor); + } + UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); + //EndTask(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetData.cpp new file mode 100644 index 0000000..9221e99 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetData.cpp @@ -0,0 +1,154 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask_TargetData.h" + + +UGAAbilityTask_TargetData* UGAAbilityTask_TargetData::CreateTargetDataTask(UGAAbilityBase* WorldContextObject, + FName InTaskName, + bool bDrawDebug, + bool bDrawCorrectedDebug, + bool bUseCorrectedTrace, + EGASConfirmType ConfirmTypeIn, + float Range) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + + if (MyObj) + { + MyObj->Range = Range; + MyObj->ConfirmType = ConfirmTypeIn; + MyObj->bIsTickable = false; + MyObj->bDrawDebug = bDrawDebug; + MyObj->bDrawCorrectedDebug = bDrawCorrectedDebug; + MyObj->bUseCorrectedTrace = bUseCorrectedTrace; + } + return MyObj; +} + +void UGAAbilityTask_TargetData::Activate() +{ + switch (ConfirmType) + { + case EGASConfirmType::Instant: + { + FHitResult Hit = LineTrace(); + OnReceiveTargetData.Broadcast(Hit); + EndTask(); + break; + } + case EGASConfirmType::WaitForConfirm: + { + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetData::OnConfirm); + bIsTickable = true; + } + if (!Ability->OnConfirmCastingEndedDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmCastingEndedDelegate.AddUObject(this, &UGAAbilityTask_TargetData::OnCastEndedConfirm); + } + } + break; + } + } +} + +// --------------------------------------------------------------------------------------- + +void UGAAbilityTask_TargetData::OnConfirm() +{ + FHitResult Hit(ForceInit);// = LineTrace(); + OnConfirmed.Broadcast(Hit); + Ability->OnConfirmDelegate.RemoveAll(this); +} +void UGAAbilityTask_TargetData::OnCastEndedConfirm() +{ + FHitResult Hit = LineTrace(); + OnReceiveTargetData.Broadcast(Hit); + bIsTickable = false; + EndTask(); +} +void UGAAbilityTask_TargetData::Tick(float DeltaTime) +{ + //FHitResult HitOut = LineTrace(); +} + +FHitResult UGAAbilityTask_TargetData::LineTrace() +{ + FHitResult HitOut; + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + UCameraComponent* Camera = Ability->OwnerCamera; + FVector TraceStart; + FRotator UnusedRot; + if (PC) + { + PC->PlayerCameraManager->GetCameraViewPoint(TraceStart, UnusedRot); +// TraceStart = Camera->GetComponentLocation(); + } + else + { + UnusedRot = P->GetBaseAimRotation(); + TraceStart = P->GetPawnViewLocation(); + } + + FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; + UWorld* World = GetWorld(); + FCollisionQueryParams ColParams; + ColParams.AddIgnoredActor(P); + FCollisionResponseParams ColResp; + World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + if (HitOut.bBlockingHit) + { + FHitResult NewHit; + FVector Start = P->GetPawnViewLocation(); + FVector NewDir = (HitOut.Location - Start).GetSafeNormal(); + float Distance = FVector::Dist(Start, HitOut.Location); + FVector End = Start + (NewDir * Range); + World->LineTraceSingleByChannel(NewHit, Start, End, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + + if (bDrawCorrectedDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, true, 2);// GetWorld()->DeltaTimeSeconds); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + } + } + } + else + { + FHitResult NewHit; + FVector Start = P->GetPawnViewLocation(); + FVector NewDir = (TraceEnd - Start).GetSafeNormal(); + float Distance = Range - FVector::Dist(TraceStart, Start); + FVector End = Start + (NewDir * Distance); + + World->LineTraceSingleByChannel(NewHit, Start, End, ECollisionChannel::ECC_WorldStatic, ColParams, ColResp); + + if (bDrawCorrectedDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, true, 2);//GetWorld()->DeltaTimeSeconds); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, true, 2);//GetWorld()->DeltaTimeSeconds); + } + } + } + if (bDrawDebug) + { + if (HitOut.bBlockingHit) + { + DrawDebugLine(GetWorld(), TraceStart, HitOut.ImpactPoint, FColor::Red, true, 2);//GetWorld()->DeltaTimeSeconds); + DrawDebugPoint(GetWorld(), HitOut.Location, 8, FColor::Red, true, 2);//GetWorld()->DeltaTimeSeconds); + } + DrawDebugLine(GetWorld(), TraceStart, TraceEnd, FColor::Green, true, 2);//GetWorld()->DeltaTimeSeconds); + } + return HitOut; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp new file mode 100644 index 0000000..1d539b4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataCircle.cpp @@ -0,0 +1,64 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask_TargetDataCircle.h" + + +UGAAbilityTask_TargetDataCircle* UGAAbilityTask_TargetDataCircle::TargetCircleDataTask(UGAAbilityBase* WorldContextObject, + FName InTaskName, EGASConfirmType ConfirmTypeIn) +{ + auto MyObj = NewAbilityTask(WorldContextObject); + + if (MyObj) + { + MyObj->ConfirmType = ConfirmTypeIn; + } + return MyObj; +} + +void UGAAbilityTask_TargetDataCircle::Activate() +{ + switch (ConfirmType) + { + case EGASConfirmType::Instant: + { + + } + case EGASConfirmType::WaitForConfirm: + { + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetDataCircle::OnConfirm); + } + } + } + } + //EndTask(); +} + +// --------------------------------------------------------------------------------------- + +//bool UGAAbilityTask_TargetDataCircle::BeginSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject*& SpawnedActor) +//{ +// SpawnedActor = Class.GetDefaultObject();//NewObject(WorldContext +// return true; +//} +// +//void UGAAbilityTask_TargetDataCircle::FinishSpawningActor(UObject* WorldContextObject, UGASAbilityTargetingObject* SpawnedActor) +//{ +// if (SpawnedActor) +// { +// //Success.Broadcast(SpawnedActor); +// } +// UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); +// ReadyForActivation(); +//} + +void UGAAbilityTask_TargetDataCircle::OnConfirm() +{ + //TargetObj2->GetTarget(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp new file mode 100644 index 0000000..38115e5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp @@ -0,0 +1,218 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "Abilities/GAAbilityBase.h" +#include "GAAbilityTask_TargetDataLineTrace.h" + + +UGAAbilityTask_TargetDataLineTrace* UGAAbilityTask_TargetDataLineTrace::CreateTargetDataLineTrace(UGAAbilityBase* WorldContextObject + , FName InTaskName + , ETraceTypeQuery InTraceChannel + , USkeletalMeshComponent* InSocketComponent + , FName InSocketName + , bool bDrawDebug + , EAFConfirmType ConfirmTypeIn + , float Range) +{ + auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); + + if (MyObj) + { + MyObj->TraceChannel = InTraceChannel; + MyObj->Range = Range; + MyObj->ConfirmType = ConfirmTypeIn; + MyObj->SocketComponent = InSocketComponent; + MyObj->SocketName = InSocketName; + MyObj->bIsTickable = false; + MyObj->bDrawDebug = bDrawDebug; + } + return MyObj; +} +UGAAbilityTask_TargetDataLineTrace::UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bIsReplicated = true; +} +void UGAAbilityTask_TargetDataLineTrace::Activate() +{ + LocalHitResult.Reset(1, false); + FHitResult HitData; + switch (ConfirmType) + { + case EAFConfirmType::Instant: + { + HitData = LineTrace(); + LocalHitResult = HitData; + //OnClient... Is called on both Client and server and is result of local simulation + //unconfirmed by server. This result might get overrided when data from server arrive to client + //it's good to spawn some cosmetic effects, but shouldn't be used to actually confirm hit result on client. + + //OnServer.. is confirmed by server that we got hit (or not), and should be used to show client confirmation + //for hits. + if (IsServerOrStandalone()) + { + OnClientReceiveTargetData.Broadcast(HitData); + OnServerReceiveTargetData.Broadcast(HitData); + EndTask(); + } + else + { + OnClientReceiveTargetData.Broadcast(HitData); + } + break; + } + case EAFConfirmType::WaitForConfirm: + { + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_TargetDataLineTrace::OnConfirm); + bIsTickable = true; + } + if (!Ability->OnConfirmCastingEndedDelegate.IsBoundToObject(this)) + { + Ability->OnConfirmCastingEndedDelegate.AddUObject(this, &UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm); + } + } + break; + } + } + if (HitData.IsValidBlockingHit()) + { + if (AbilityComponent->GetOwnerRole() < ROLE_Authority) + { + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + + PC->PlayerState->RecalculateAvgPing(); + float ExactPing = PC->PlayerState->ExactPing; + + FAFLineTraceData TraceData; + TraceData.ExactPing = ExactPing; + TraceData.HitActor = HitData.GetActor(); + TraceData.HitLocation = HitData.Location; + + ServerConfirmHitInfo(TraceData); + } + } +} + +void UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData) +{ + int test = 0; + FAFLineTraceConfirmData ConfirmData; + ConfirmData.bConfirmed = true; + ConfirmData.HitActor = LocalHitResult.GetActor(); + ConfirmData.HitLocation = LocalHitResult.Location; + ClientConfirmHitInfo(ConfirmData); +} +bool UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Validate(FAFLineTraceData TraceData) +{ + return true; +} + +void UGAAbilityTask_TargetDataLineTrace::ClientConfirmHitInfo_Implementation(FAFLineTraceConfirmData ConfirmData) +{ + if (ConfirmData.bConfirmed) + { + OnServerReceiveTargetData.Broadcast(LocalHitResult); + } + else + { + LocalHitResult.Actor = ConfirmData.HitActor; + LocalHitResult.Location = ConfirmData.HitLocation; + LocalHitResult.ImpactPoint = ConfirmData.HitLocation; + OnServerReceiveTargetData.Broadcast(LocalHitResult); + } +} + +// --------------------------------------------------------------------------------------- + +void UGAAbilityTask_TargetDataLineTrace::OnConfirm() +{ + FHitResult Hit = LineTrace(); + OnConfirmed.Broadcast(Hit); + Ability->OnConfirmDelegate.RemoveAll(this); +} +void UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm() +{ + FHitResult Hit = LineTrace(); + OnClientReceiveTargetData.Broadcast(Hit); + bIsTickable = false; + EndTask(); +} +void UGAAbilityTask_TargetDataLineTrace::Tick(float DeltaTime) +{ + //FHitResult HitOut = LineTrace(); +} + +FHitResult UGAAbilityTask_TargetDataLineTrace::LineTrace() +{ + FHitResult HitOut; + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + + + UCameraComponent* Camera = Ability->OwnerCamera; + FVector TraceStart; + FRotator UnusedRot; + if (PC) + { + PC->PlayerCameraManager->GetCameraViewPoint(TraceStart, UnusedRot); +// TraceStart = Camera->GetComponentLocation(); + } + else + { + UnusedRot = P->GetBaseAimRotation(); + TraceStart = P->GetPawnViewLocation(); + } + + FVector TraceEnd = UnusedRot.Vector() * Range + TraceStart; + UWorld* World = GetWorld(); + FCollisionQueryParams ColParams; + ColParams.AddIgnoredActor(P); + FCollisionResponseParams ColResp; + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(TraceChannel); + World->LineTraceSingleByChannel(HitOut, TraceStart, TraceEnd, CollisionChannel, ColParams, ColResp); + if (HitOut.bBlockingHit) + { + FHitResult NewHit; + FVector Start = SocketComponent->GetSocketLocation(SocketName); + FVector NewDir = (HitOut.Location - Start).GetSafeNormal(); + float Distance = FVector::Dist(Start, HitOut.Location); + FVector End = Start + (NewDir * Range); + World->LineTraceSingleByChannel(NewHit, Start, End, CollisionChannel, ColParams, ColResp); + UE_LOG(AbilityFramework, Log, TEXT("UGAAbilityTask_TargetDataLineTrace::LineTrace Corrected")); + if (bDrawDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1.0f); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, false, 1.0f); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, false, 1.0f); + } + } + } + else + { + FHitResult NewHit; + FVector Start = SocketComponent->GetSocketLocation(SocketName); + FVector NewDir = (TraceEnd - Start).GetSafeNormal(); + float Distance = Range - FVector::Dist(TraceStart, Start); + FVector End = Start + (NewDir * Distance); + + World->LineTraceSingleByChannel(NewHit, Start, End, CollisionChannel, ColParams, ColResp); + UE_LOG(AbilityFramework, Log, TEXT("UGAAbilityTask_TargetDataLineTrace::LineTrace")); + if (bDrawDebug) + { + DrawDebugLine(GetWorld(), Start, End, FColor::Green, false, 1.0f); + if (NewHit.bBlockingHit) + { + DrawDebugLine(GetWorld(), Start, NewHit.Location, FColor::Magenta, false, 1.0f); + DrawDebugPoint(GetWorld(), NewHit.Location, 8, FColor::Magenta, false, 1.0f); + } + } + } + return HitOut; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp new file mode 100644 index 0000000..58e48ce --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitForConfirm.cpp @@ -0,0 +1,33 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "../GAAbilityBase.h" +#include "GAAbilityTask_WaitForConfirm.h" + + + + +UGAAbilityTask_WaitForConfirm* UGAAbilityTask_WaitForConfirm::CreateWaitConfirmTask(UGAAbilityBase* WorldContextObject, + FName InTaskName) +{ + auto MyObj = NewAbilityTask(WorldContextObject, InTaskName); + return MyObj; +} +void UGAAbilityTask_WaitForConfirm::Activate() +{ + if (AbilityComponent.IsValid() && Ability.IsValid()) + { + GetOuterUGAAbilityBase()->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_WaitForConfirm::OnConfirm); + } +} +void UGAAbilityTask_WaitForConfirm::Initialize() +{ + +} + +void UGAAbilityTask_WaitForConfirm::OnConfirm() +{ + Ability->OnConfirmDelegate.Clear(); + OnConfirmed.Broadcast(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp new file mode 100644 index 0000000..38f2151 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_WaitTargetData.cpp @@ -0,0 +1,84 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "GAAbilityTask_WaitTargetData.h" + + +UGAAbilityTask_WaitTargetData::UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + + +//UGAAbilityTask_WaitTargetData* UGAAbilityTask_WaitTargetData::WaitTargetData(UObject* WorldContextObject, +// FName InTaskName, TSubclassOf InClass, float InRange, ETraceTypeQuery InTraceChannel) +//{ +// auto MyObj = NewAbilityTask(WorldContextObject, "UGAAbilityTask_WaitTargetData"); +// MyObj->Range = InRange; +// MyObj->TraceChannel = InTraceChannel; +// return MyObj; +//} + +// --------------------------------------------------------------------------------------- +void UGAAbilityTask_WaitTargetData::Activate() +{ + UE_LOG(AbilityFramework, Log, TEXT("TArget object spawned")); + if (Ability.IsValid()) + { + if (!Ability->OnConfirmDelegate.IsBoundToObject(this)) + Ability->OnConfirmDelegate.AddUObject(this, &UGAAbilityTask_WaitTargetData::OnConfirm); + //Ability->ConfirmDelegate.CreateUObject(this, &UGAAbilityTask_WaitForConfirm::OnConfirm); + } +} + +//bool UGAAbilityTask_WaitTargetData::BeginSpawningActor(UObject* WorldContextObject, TSubclassOf Class, AGATargetingActor*& SpawnedActor) +//{ +// UWorld* const World = GEngine->GetWorldFromContextObject(WorldContextObject, EGetWorldErrorMode::LogAndReturnNull); +// if (World) +// { +// SpawnedActor = World->SpawnActorDeferred(Class, FTransform::Identity, NULL, NULL, ESpawnActorCollisionHandlingMethod::AlwaysSpawn); +// } +// +// if (SpawnedActor == nullptr) +// { +// return false; +// } +// UE_LOG(AbilityFramework, Log, TEXT("Begin Spawning Actor in GAAbilityTask_SpawnActor")); +// return true; +//} +// +//void UGAAbilityTask_WaitTargetData::FinishSpawningActor(UObject* WorldContextObject, AGATargetingActor* SpawnedActor) +//{ +// if (SpawnedActor) +// { +// FTransform SpawnTransform; +// SpawnedActor->FinishSpawning(SpawnTransform); +// TargetActor = SpawnedActor; +// } +// ReadyForActivation(); +// UE_LOG(AbilityFramework, Log, TEXT("Finish Spawning Actor in GAAbilityTask_SpawnActor")); +//} +void UGAAbilityTask_WaitTargetData::TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) +{ + //if (TargetActor && Ability.IsValid()) + //{ + // FHitResult OutHit; + // bool bHit = Ability->LineTraceSingleByChannelFromCamera(Range, TraceChannel, false, OutHit, + // EDrawDebugTrace::Type::None, true, FLinearColor::Green, FLinearColor::Red, 2); + // if (bHit) + // { + // TargetActor->SetActorLocation(OutHit.Location); + // } + // else + // { + // TargetActor->SetActorLocation(OutHit.TraceEnd); + // } + //} +} + +void UGAAbilityTask_WaitTargetData::OnConfirm() +{ + Ability->OnConfirmDelegate.Clear(); + OnConfirmed.Broadcast(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp new file mode 100644 index 0000000..25f3d4f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp @@ -0,0 +1,213 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "AbilityFramework.h" + +DEFINE_LOG_CATEGORY(AbilityFramework); +DEFINE_LOG_CATEGORY(GameAttributesGeneral); +DEFINE_LOG_CATEGORY(GameAttributes); +DEFINE_LOG_CATEGORY(GameAttributesEffects); + +DEFINE_LOG_CATEGORY(AFAttributes); +DEFINE_LOG_CATEGORY(AFEffects); +DEFINE_LOG_CATEGORY(AFAbilities); + +FAFEffectTimerManager* FAFEffectTimerManager::Instance = nullptr; + +DECLARE_CYCLE_STAT(TEXT("EffectTimer.Run"), STAT_EffectTimerRun, STATGROUP_EffectTimer); +FAFEffectTimer::FAFEffectTimer() +{ + +} +FAFEffectTimerWorker::FAFEffectTimerWorker() +{ + bActive = true; + Timers.Reset(); + Timers.SetNumZeroed(0); + InternalTime = FPlatformTime::ToSeconds64(FPlatformTime::Cycles64()); + for (int Idx = 0; Idx < 10000; Idx++) + { + float Duration = FMath::RandRange(15, 25); + AddTimer(Duration, 0.2); + } +} +FAFEffectTimerManager::FAFEffectTimerManager() +{ + TimerWorker = new FAFEffectTimerWorker(); + TimerThread = FRunnableThread::Create(TimerWorker, TEXT("EffectTimerThread"), 512*1024, TPri_Normal); + + check(TimerWorker != nullptr); +} +FAFEffectTimerManager::~FAFEffectTimerManager() +{ + //if (TimerThread) + //{ + // TimerThread->Kill(); + // delete TimerThread; + // TimerThread = nullptr; + //} +} +uint32 FAFEffectTimerWorker::Run() +{ + while (1) + { + SCOPE_CYCLE_COUNTER(STAT_EffectTimerRun); + InternalTime = FPlatformTime::ToSeconds64(FPlatformTime::Cycles64()); + //while (Timers.Num() > 0) + { +//#if UE_BUILD_DEVELOPTMENT || UE_BUILD_DEBUG + +//#endif // UE_BUILD_DEVELOPTMENT || UE_BUILD_DEBUG + + //for (FAFEffectTimer& Timer : Timers) + { + //auto It = Timers.CreateIterator(); + //for (; It; ++It) + //{ + + // if (It->bHavePeriod && (InternalTime > It->NextPeriodTime)) + // { + // double asdasd = It->ExpireTime - InternalTime; + // double FinalTime = InternalTime - It->StartTime; + // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Period TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + + // It->NextPeriodTime = InternalTime + It->PeriodTime; + // //It->PeriodDelegate.ExecuteIfBound(); + + // } + // if (It->bHaveDuration && (InternalTime > It->ExpireTime)) + // { + // double asdasd = It->ExpireTime - InternalTime; + // double FinalTime = InternalTime - It->StartTime; + // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + // //It->ExpireDelegate.ExecuteIfBound(); + + // //FAFEffectTimer Out; + // //Timers.Remove(*It); + // //Timers.Shrink(); + // } + //} + for (FAFEffectTimer& Timer : Timers) + { + if (!Timer.bActive) + continue; + + if (Timer.bHavePeriod && (InternalTime > Timer.NextPeriodTime)) + { + double asdasd = Timer.ExpireTime - InternalTime; + double FinalTime = InternalTime - Timer.StartTime; + //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Period TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + + Timer.NextPeriodTime = InternalTime + Timer.PeriodTime; + //Timer.PeriodDelegate.ExecuteIfBound(); + + } + if (Timer.bHaveDuration && (InternalTime > Timer.ExpireTime)) + { + double asdasd = Timer.ExpireTime - InternalTime; + double FinalTime = InternalTime - Timer.StartTime; + //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + //Timer.ExpireDelegate.ExecuteIfBound(); + //Timer.bActive = false; + //FAFEffectTimer Out; + //Timers.Remove(*It); + //Timers.Shrink(); + } + } + //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer TimeRemaining: %f"), asdasd); + //FAFEffectTimer& Top = Timers.HeapTop(); + + //if (Timer.bActive) + //{ + // if (Top.bHaveDuration && (InternalTime > Top.ExpireTime)) + // { + // double asdasd = Top.ExpireTime - InternalTime; + // double FinalTime = InternalTime - Top.StartTime; + // //UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Finish TimeDifference: %f FinalTime: %f"), asdasd, FinalTime); + // Top.ExpireDelegate.ExecuteIfBound(); + + // FAFEffectTimer Out; + // Timers.HeapPop(Out); + // Timers.Shrink(); + // } + //} + } + } + FPlatformProcess::Sleep(0.01); + } + return 0; +} +bool FAFEffectTimerWorker::Init() +{ + return true; +} +void FAFEffectTimerWorker::Stop() +{ + bActive = false; +} + +/** +* Exits the runnable object. +* +* Called in the context of the aggregating thread to perform any cleanup. +* @see Init, Run, Stop +*/ +void FAFEffectTimerWorker::Exit() +{ + //Timers.Empty(); + //bActive = false; +} + +FAFEffectTimeHandle FAFEffectTimerWorker::AddTimer(double InDuration, double InPeriod) +{ + FScopeLock lock(&CS); + //bActive = false; + FAFEffectTimer Timer; + Timer.Duration = InDuration; + Timer.PeriodTime = InPeriod; + Timer.bHaveDuration = InDuration <= 0 ? false : true; + Timer.bHavePeriod = InPeriod <= 0 ? false : true; + Timer.StartTime = InternalTime; // FPlatformTime::ToSeconds64(FPlatformTime::Cycles64());// InternalTime; + + Timer.ExpireTime = InternalTime + Timer.Duration; + Timer.NextPeriodTime = InternalTime + Timer.PeriodTime; + Timer.bActive = true; + Timers.Add(Timer); + int32 idx = Timers.Num() - 1; + //Timers.Push(Timer); + //Timers.Heapify(); + FAFEffectTimeHandle Handle; + Handle.Index = idx; + Timers[idx].Handle = Handle; + UE_LOG(GameAttributesEffects, Log, TEXT("AsyncTimer Start TimeDifference: %f"), (Timer.ExpireTime - InternalTime)); + + //since there is at least one timer, set timer manager to be active. + + bActive = true; + return Handle; +} + +FAFEffectTimeHandle FAFEffectTimerManager::AddTimer(double InDuration, double InPeriod) +{ + + return TimerWorker->AddTimer(InDuration, InPeriod); +} + +void FAbilityFramework::StartupModule() +{ +#if WITH_EDITOR + //FModuleManager::Get().LoadModule(TEXT("AbilityFrameworkEditor")); +#endif //WITH_EDITOR + //FAFEffectTimerManager::Get(); + // This code will execute after your module is loaded into memory (but after global variables are initialized, of course.) +} + + +void FAbilityFramework::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + + + +IMPLEMENT_MODULE(FAbilityFramework, AbilityFramework) \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAbilityNotifyState.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAbilityNotifyState.cpp new file mode 100644 index 0000000..10e8534 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAbilityNotifyState.cpp @@ -0,0 +1,33 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "AFAbilityNotifyState.h" + + + + +void UAFAbilityNotifyState::NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) +{ + IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); + if (IAbilities) + { + CachedAbilitiesComp = IAbilities->GetAbilityComp(); + CachedAbilitiesComp->OnAbilityNotifyBegin.ExecuteIfBound(Tag, Name); + } +} +void UAFAbilityNotifyState::NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) +{ + if (CachedAbilitiesComp) + { + CachedAbilitiesComp->OnAbilityNotifyTick.ExecuteIfBound(Tag, Name); + } +} +void UAFAbilityNotifyState::NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) +{ + if (CachedAbilitiesComp) + { + CachedAbilitiesComp->OnAbilityNotifyEnd.ExecuteIfBound(Tag, Name); + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAnimNotify.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAnimNotify.cpp new file mode 100644 index 0000000..26e0f2d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AnimNotify/AFAnimNotify.cpp @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" +#include "AFAnimNotify.h" + + + + +void UAFAnimNotify::Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) +{ + IAFAbilityInterface* IAbilities = Cast(MeshComp->GetOwner()); + if (!IAbilities) + return; + + UAFAbilityComponent* Comp = IAbilities->GetAbilityComp(); + Comp->OnAbilityNotifyBegin.ExecuteIfBound(Tag, Name); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp new file mode 100644 index 0000000..77ff541 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -0,0 +1,248 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GameplayTagContainer.h" +#include "../AFAbilityComponent.h" +#include "GAAttributesBase.h" +#include "../AFAbilityInterface.h" +#include "GAAttributeExtension.h" + +#include "GAAttributeBase.h" +DEFINE_STAT(STAT_CalculateBonus); +DEFINE_STAT(STAT_CurrentBonusByTag); +DEFINE_STAT(STAT_FinalBonusByTag); +//UGAAttributeBase::UGAAttributeBase(const FObjectInitializer& ObjectInitializer) +// : Super(ObjectInitializer) +//{ +// +//} +FAFAttributeBase::FAFAttributeBase() + : CurrentValue(0), + BonusValue(0) +{ + Modifiers.AddDefaulted(7); +}; +FAFAttributeBase::FAFAttributeBase(float BaseValueIn) + : BaseValue(BaseValueIn), + CurrentValue(BaseValue), + BonusValue(0) +{ + Modifiers.AddDefaulted(7); +}; + + +void FAFAttributeBase::InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName) +{ + CurrentValue = BaseValue; + CalculateBonus(); + CurrentValue = GetFinalValue(); + Modifiers.Empty(); + Modifiers.AddDefaulted(7);// static_cast(EGAAttributeMod::Invalid)); + //Modifiers.AddDefaulted(static_cast(EGAAttributeMod::Invalid)); + if (ExtensionClass) + { + ExtensionClass.GetDefaultObject()->Initialize(InComponent, InAttributeName); + } +} + +void FAFAttributeBase::CalculateBonus() +{ + SCOPE_CYCLE_COUNTER(STAT_CalculateBonus); + float AdditiveBonus = 0; + float SubtractBonus = 0; + float MultiplyBonus = 1; + float DivideBonus = 1; + //auto ModIt = Modifiers.CreateConstIterator(); + TMap& Additive = Modifiers[static_cast(EGAAttributeMod::Add)]; + TMap& Subtractive = Modifiers[static_cast(EGAAttributeMod::Subtract)]; + TMap& Multiplicative = Modifiers[static_cast(EGAAttributeMod::Multiply)]; + TMap& Divide = Modifiers[static_cast(EGAAttributeMod::Divide)]; + for (auto ModIt = Additive.CreateConstIterator(); ModIt; ++ModIt) + { + AdditiveBonus += ModIt->Value.Value; + } + for (auto ModIt = Subtractive.CreateConstIterator(); ModIt; ++ModIt) + { + SubtractBonus += ModIt->Value.Value; + } + for (auto ModIt = Multiplicative.CreateConstIterator(); ModIt; ++ModIt) + { + MultiplyBonus += ModIt->Value.Value; + } + for (auto ModIt = Divide.CreateConstIterator(); ModIt; ++ModIt) + { + DivideBonus += ModIt->Value.Value; + } + //for (ModIt; ModIt; ++ModIt) + //{ + // const FGAEffectMod& mod = ModIt->Value; + // switch (mod.AttributeMod) + // { + // case EGAAttributeMod::Add: + // AdditiveBonus += mod.Value; + // break; + // case EGAAttributeMod::Subtract: + // SubtractBonus += mod.Value; + // break; + // case EGAAttributeMod::Multiply: + // MultiplyBonus += mod.Value; + // break; + // case EGAAttributeMod::Divide: + // DivideBonus += mod.Value; + // break; + // default: + // break; + // } + //} + float OldBonus = BonusValue; + //calculate final bonus from modifiers values. + //we don't handle stacking here. It's checked and handled before effect is added. + BonusValue = (AdditiveBonus - SubtractBonus); + BonusValue = (BonusValue * MultiplyBonus); + BonusValue = (BonusValue / DivideBonus); + //this is absolute maximum (not clamped right now). + float addValue = BonusValue - OldBonus; + //reset to max = 200 + CurrentValue = CurrentValue + addValue; + /* + BaseValue = 200; + CurrentValue = 200; + BonusValue = 50; + CurrentValue = 200 + 50; + CurentValue == 250; + + Damage taken. + CurrentValue = 250 - 25; + CurrentValue == 225; + Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; + Expected Result : 175; (225 - 50) + OldBonusValue = 50; + BonusValue = 0; + CurrentValue == 225; + BonusValue - OldBonusValue = -50; + CurrentValue = CurrentValue + (-50); ?? + + TwoBonuses 50 + 50; + CurrentValue = 300 - 25; + CurrentValue == 275; + Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; + Expected Result : 225; (275 - 50) + OldBonusValue = 100; + BonusValue = 50; + CurrentValue == 225; + BonusValue - OldBonusValue = -50; + CurrentValue = CurrentValue + (-50); ?? + + Inverse Bonus is going to be Increased: + TwoBonuses 50 + 50; + CurrentValue = 300 - 25; + CurrentValue == 275; + Bonus Ended - THERE IS NO SUBTRACTION ONLY FULL STATCK RECALCULATION; + Expected Result : 325; (275 + 50) + OldBonusValue = 100; + new BonusValue = 150; (new bonus gives +50) + CurrentValue == 275; + BonusValue - OldBonusValue = 50; (150 - 100) = 50 + CurrentValue = CurrentValue + (50); ?? + */ +} + +bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) +{ + TMap& mods = Modifiers[static_cast(InMod.AttributeMod)]; + auto It = mods.CreateConstIterator(); + for (; It; ++It) + { + if (InMod > It->Value) + { + return true; + } + } + if (mods.Num() <= 0) + { + return true; + } + return false; +} +float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + FGAEffectProperty& InProperty) +{ + //FString name = GetTypeName(); + if (ExtensionClass) + { + ExtensionClass.GetDefaultObject()->OnPreAttributeModify(CurrentValue); + } + float returnValue = -1; + bool isPeriod = InProperty.GetPeriod() > 0; + bool IsDuration = InProperty.GetDuration() > 0; + if ( !InProperty.GetIsInstant()) + { + FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); + AttrMod.Tags.AppendTags(InProperty.GetSpec()->AttributeTags); + AddBonus(ModIn, HandleIn); + return ModIn.Value; + } + else + { + switch (ModIn.AttributeMod) + { + case EGAAttributeMod::Add: + { + float OldCurrentValue = CurrentValue; + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: OldCurrentValue: %f"), OldCurrentValue); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: AddValue: %f"), ModIn.Value); + float Val = CurrentValue - (OldCurrentValue + ModIn.Value); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: ActuallAddVal: %f"), Val); + CurrentValue -= Val; + CurrentValue = FMath::Clamp(CurrentValue, 0, GetFinalValue()); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Add:: CurrentValue: %f"), CurrentValue); + returnValue = CurrentValue; + break; + } + case EGAAttributeMod::Subtract: + { + float OldCurrentValue = CurrentValue; + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: OldCurrentValue: %f"), OldCurrentValue); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: SubtractValue: %f"), ModIn.Value); + float Val = CurrentValue - (OldCurrentValue - ModIn.Value); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: ActuallSubtractVal: %f"), Val); + CurrentValue -= Val; + CurrentValue = FMath::Clamp(CurrentValue, 0, GetFinalValue()); + UE_LOG(GameAttributes, Log, TEXT("FAFAttributeBase::Subtract:: CurrentValue: %f"), CurrentValue); + + returnValue = CurrentValue; + break; + } + case EGAAttributeMod::Multiply: + { + returnValue = -1; + break; + } + case EGAAttributeMod::Divide: + { + returnValue = -1; + break; + } + } + } + if (ExtensionClass) + { + ExtensionClass.GetDefaultObject()->OnPreAttributeModify(returnValue); + } + return returnValue; +} + +void FAFAttributeBase::AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle) +{ + TMap& mods = Modifiers[static_cast(ModIn.AttributeMod)]; + FGAEffectMod& modsTemp = mods.FindOrAdd(Handle); + modsTemp = ModIn; + CalculateBonus(); +} +void FAFAttributeBase::RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod) +{ + TMap& mods = Modifiers[static_cast(InMod)]; + mods.Remove(Handle); + //Modifiers.Remove(Handle); + CalculateBonus(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp new file mode 100644 index 0000000..6066955 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "../AFAbilityComponent.h" +#include "GAAttributeExtension.h" + + + + +void UGAAttributeExtension::Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName) +{ + AbilityComponent = InAbilityComponent; + Attribute = FGAAttribute(InAttributeName); +} + +void UGAAttributeExtension::OnPreAttributeModify(float InValue) +{ + AbilityComponent->NotifyOnPreAttributeModified(Attribute); +} +void UGAAttributeExtension::OnPostAttributeModify(float InValue) +{ + AbilityComponent->NotifyOnPostAttributeModified(Attribute); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeGlobals.cpp new file mode 100644 index 0000000..de1a982 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeGlobals.cpp @@ -0,0 +1,5 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAAttributeGlobals.h" + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp new file mode 100644 index 0000000..4a59378 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp @@ -0,0 +1,297 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAGlobalTypes.h" +#include "../AFAbilityComponent.h" +#include "Net/UnrealNetwork.h" +#include "GAAttributesBase.h" + +UGAAttributesBase::UGAAttributesBase(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + bNetAddressable = false; + LastAttributeProp = nullptr; + CachedFloatPropety = nullptr; +} +UGAAttributesBase::~UGAAttributesBase() +{ + LastAttributeProp = nullptr; //make sure we clear this pointer. + CachedFloatPropety = nullptr; +} +//void UGAAttributesBase::PostNetReceive() +//{ +// Super::PostNetReceive(); +//} +void UGAAttributesBase::InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp) +{ + OwningAttributeComp = InOwningAttributeComp; + for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) + { + FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); + if (attr) + { + attr->InitializeAttribute(InOwningAttributeComp, StrIt->GetFName()); + TickableAttributes.Add(attr); + } + } + /* + Bind Delegates to map > For each attribute, so we don't store them inside attribute + but in this class. + */ + /*for (TFieldIterator PropIt(GetClass(), EFieldIteratorFlags::IncludeSuper); PropIt; ++PropIt) + { + int32 FoundIndex = -1; + FoundIndex = PropIt->GetName().Find("PostAttribute"); + FAFAttributeBase* attrPtr = GetAttribute(FGAAttribute(PropIt->GetFName())); + if (attrPtr) + { + return attrPtr->InitializeAttribute(); + } + }*/ + BP_InitializeAttributes(); +} + +void UGAAttributesBase::InitializeAttributesFromTable() +{ + if (!AttributeValues) + return; + + for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) + { + FAFAttributeBase* attr = StrIt->ContainerPtrToValuePtr(this); + if (attr) + { + FName fieldName = StrIt->GetFName(); + FString OutString; + FAFAtributeRowData* row = AttributeValues->FindRow(fieldName, OutString); + if (row) + { + attr->SetBaseValue(row->BaseValue); + attr->SetMaxValue(row->MaxValue); + attr->SetMinValue(row->MinValue); + attr->SetCurrentValue(row->CurrentValue); + attr->SetExtensionClass(row->Extension); + attr->InitializeAttribute(OwningAttributeComp, StrIt->GetFName()); + } + //TickableAttributes.Add(attr); + } + } +} + +void UGAAttributesBase::Tick(float DeltaTime) +{ + for (FAFAttributeBase* Attribute : TickableAttributes) + { + } +} + + +UProperty* UGAAttributesBase::FindProperty(const FGAAttribute& AttributeIn) +{ + //if new attribute name is the same as last attribute name and pointer to last property + //is not null, then we just return last pointer instead of performing new search. + if ((AttributeIn.AttributeName == LastAttributeName) && LastAttributeProp) + return LastAttributeProp; + + LastAttributeName = AttributeIn.AttributeName; + LastAttributeProp = FindFieldChecked(this->GetClass(), LastAttributeName); + return LastAttributeProp; + return nullptr; +} +UStructProperty* UGAAttributesBase::GetStructAttribute(const FGAAttribute& Name) +{ + return FindField(this->GetClass(), Name.AttributeName); +} +FAFAttributeBase* UGAAttributesBase::GetAttribute(const FGAAttribute& Name) +{ + if (!Name.IsValid()) + { + UE_LOG(GameAttributesEffects, Log, TEXT("GetAttribute INVALID NAME")); + return nullptr; + } + UStructProperty* tempStruct = FindField(this->GetClass(), Name.AttributeName); + + FAFAttributeBase* attr = nullptr; + if (tempStruct) + { + attr = tempStruct->ContainerPtrToValuePtr(this); + return attr; + } + return attr; +} +void UGAAttributesBase::SetAttribute(const FGAAttribute& NameIn, UObject* NewVal) +{ + //UStructProperty* tempStruct = FindField(this->GetClass(), NameIn.AttributeName); +} +void UGAAttributesBase::SetAttributeAdditiveBonus(const FGAAttribute& NameIn, float NewValue) +{ + UStructProperty* tempStruct = FindField(this->GetClass(), NameIn.AttributeName); + UScriptStruct* scriptStruct = tempStruct->Struct; + + uint8* StructData = tempStruct->ContainerPtrToValuePtr(this); + + //omg figured it out! + //for (TFieldIterator It(scriptStruct); It; ++It) + //{ + // if (UProperty* Prop = *It) + // { + // if (Prop->GetFName() == "AdditiveBonus") + // { + // if (Prop->IsA(UFloatProperty::StaticClass())) + // { + // float testValue = NewValue; + // Cast(Prop)->SetPropertyValue_InContainer(StructData, testValue); + // break; + // } + // } + // } + //} +} + +float UGAAttributesBase::GetFinalAttributeValue(const FGAAttribute& Name) +{ + FAFAttributeBase* attrPtr = GetAttribute(Name); + if (attrPtr) + { + return attrPtr->GetFinalValue(); + } + return 0; +} +float UGAAttributesBase::GetCurrentAttributeValue(const FGAAttribute& Name) +{ + FAFAttributeBase* attrPtr = GetAttribute(Name); + if (attrPtr) + { + return attrPtr->GetCurrentValue(); + } + return 0; +} +float UGAAttributesBase::GetFloatValue(const FGAAttribute& AttributeIn) +{ + FAFAttributeBase* Attribute = GetAttribute(AttributeIn); + + if (!Attribute) + return 0; + return Attribute->GetCurrentValue(); +} + +float UGAAttributesBase::SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn) +{ + if ((AttributeIn.AttributeName == LastAttributeName)) + { + if (CachedFloatPropety) + { + void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); + CachedFloatPropety->SetFloatingPointPropertyValue(ValuePtr, ValueIn); + return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); + } + } + //LastAttributeName = AttributeIn.AttributeName; + UNumericProperty* NumericProperty = CastChecked(FindProperty(AttributeIn)); + CachedFloatPropety = NumericProperty; + void* ValuePtr = CachedFloatPropety->ContainerPtrToValuePtr(this); + NumericProperty->SetFloatingPointPropertyValue(ValuePtr, ValueIn); + return CachedFloatPropety->GetFloatingPointPropertyValue(ValuePtr); + return 0; +} + +float UGAAttributesBase::AttributeOperation(const FGAAttribute& AttributeIn, float ValueIn, EGAAttributeMod Operation) +{ + switch (Operation) + { + case EGAAttributeMod::Add: + return AddAttributeFloat(GetFloatValue(AttributeIn), ValueIn); //don't want to set. + case EGAAttributeMod::Subtract: + return SubtractAttributeFloat(GetFloatValue(AttributeIn), ValueIn); + case EGAAttributeMod::Multiply: + return MultiplyAttributeFloat(GetFloatValue(AttributeIn), ValueIn); + case EGAAttributeMod::Divide: + return DivideAttributeFloat(GetFloatValue(AttributeIn), ValueIn); + case EGAAttributeMod::Set: + return SetFloatValue(AttributeIn, ValueIn); + default: + return 0; + } + return 0; +} + +float UGAAttributesBase::AddAttributeFloat(float ValueA, float ValueB) +{ + return ValueA + ValueB; +} +float UGAAttributesBase::SubtractAttributeFloat(float ValueA, float ValueB) +{ + return ValueA - ValueB; +} +float UGAAttributesBase::MultiplyAttributeFloat(float ValueA, float ValueB) +{ + return ValueA * ValueB; +} +float UGAAttributesBase::DivideAttributeFloat(float ValueA, float ValueB) +{ + return ValueA / ValueB; +} + +bool UGAAttributesBase::IsNameStableForNetworking() const +{ + /** + * IsNameStableForNetworking means an attribute set can be referred to its path name (relative to owning AActor*) over the network + * + * Attribute sets are net addressable if: + * -They are Default Subobjects (created in C++ constructor) + * -They were loaded directly from a package (placed in map actors) + * -They were explicitly set to bNetAddressable + */ + + return bNetAddressable;// || Super::IsNameStableForNetworking(); +} + + +void UGAAttributesBase::SetNetAddressable() +{ + bNetAddressable = true; +} +void UGAAttributesBase::ModifyAttribute(const FGAEffect& EffectIn) +{ + +} + +float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn, + const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty) +{ + FAFAttributeBase* attr = nullptr; + + attr = GetAttribute(ModIn.Attribute); + float OutVal = -1; + if (attr) + { + OutVal = attr->Modify(ModIn, HandleIn, InProperty); + } + OnAttributeModified(ModIn, HandleIn); + return OutVal; +} + +void UGAAttributesBase::RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) +{ + FAFAttributeBase* attr = nullptr; + + attr = GetAttribute(AttributeIn); + if (attr) + { + return attr->RemoveBonus(HandleIn, InMod); + } +} + +void UGAAttributesBase::OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle) +{ + OwningAttributeComp->OnAttributeModified(InMod, InHandle, this); + FAFAttributeChangedData Data; + OwningAttributeComp->BroadcastAttributeChange(InMod.Attribute, Data); +} +void UGAAttributesBase::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const +{ + Super::GetLifetimeReplicatedProps(OutLifetimeProps); + //possibly replicate it to everyone + //to allow prediction for UI. + DOREPLIFETIME(UGAAttributesBase, OwningAttributeComp); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..3a194a8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp @@ -0,0 +1,72 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" + +#include "../AFAbilityInterface.h" +#include "GAAttributesBase.h" +#include "../AFAbilityComponent.h" +#include "GABlueprintLibrary.h" +#include "GAAttributesBlueprintFunctionLibrary.h" + + + +UGAAttributesBlueprintFunctionLibrary::UGAAttributesBlueprintFunctionLibrary(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} + +bool UGAAttributesBlueprintFunctionLibrary::EqualAttribute(const FGAAttribute& Compare, FGAAttribute Against) +{ + return Compare == Against; +} +FName UGAAttributesBlueprintFunctionLibrary::GetAttribute(FGAAttribute AttributeIn) +{ + return AttributeIn.AttributeName; +} +float UGAAttributesBlueprintFunctionLibrary::GetFinalAttributeValue(AActor* Target, FGAAttribute Name) +{ + IAFAbilityInterface* attributeInt = Cast(Target); + if (!attributeInt) + return 0; + if (!attributeInt->GetAttributes()) + return 0; + + return attributeInt->GetAttributes()->GetFinalAttributeValue(Name); +} +float UGAAttributesBlueprintFunctionLibrary::GetCurrentAttributeValue(AActor* Target, FGAAttribute Name) +{ + IAFAbilityInterface* attributeInt = Cast(Target); + if (!attributeInt) + return 0; + return attributeInt->GetAttributes()->GetCurrentAttributeValue(Name); +} +float UGAAttributesBlueprintFunctionLibrary::GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn) +{ + IAFAbilityInterface* attributeInt = Cast(Target); + if (!attributeInt) + return 0; + + return attributeInt->GetAttributes()->GetFloatValue(AttributeIn); +} + +void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues( + APawn* Instigator + , UObject* Causer + , FAFPropertytHandle From + , FGAEffectHandle FromHandle + , UObject* FromTarget + , FAFPropertytHandle To + , FGAEffectHandle ToHandle + , UObject* ToTarget) +{ + IAFAbilityInterface* FromInterface = Cast(FromTarget); + IAFAbilityInterface* ToInterface = Cast(ToTarget); + + if (!FromInterface || !ToInterface) + return; + + FAFFunctionModifier ModF; + UGABlueprintLibrary::ApplyGameEffectToObject(From, FromHandle, FromTarget, Instigator, Causer, ModF); + UGABlueprintLibrary::ApplyGameEffectToObject(To, ToHandle, ToTarget, Instigator, Causer, ModF); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesStats.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesStats.cpp new file mode 100644 index 0000000..110fd10 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesStats.cpp @@ -0,0 +1,4 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAAttributesStats.h" diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectApplicationRequirement.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectApplicationRequirement.cpp new file mode 100644 index 0000000..a6e6ad6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectApplicationRequirement.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectApplicationRequirement.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomApplication.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomApplication.cpp new file mode 100644 index 0000000..8f04be7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomApplication.cpp @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../AFAbilityComponent.h" +#include "AFEffectCustomApplication.h" + + + + +bool UAFEffectCustomApplication::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + return true; +} + +void UAFEffectCustomApplication::ApplyExecute( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + Params.GetContext().GetTargetEffectsComponent()->ExecuteEffect(InHandle, Params, Modifier); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomStackingRule.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomStackingRule.cpp new file mode 100644 index 0000000..bc4b54b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectCustomStackingRule.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectCustomStackingRule.h" + + + + +bool UAFEffectCustomStackingRule::CanStack(class UAFAbilityComponent* InComp, struct FGAEffectContainer* InContainer, + const FGAEffectHandle& InHandle) +{ + //InHandle.GetContext().TargetComp->ExecuteEffect(InHandle); + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectSpecFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectSpecFunctionLibrary.cpp new file mode 100644 index 0000000..5d1704c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFEffectSpecFunctionLibrary.cpp @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectSpecFunctionLibrary.h" + + + +void UAFEffectSpecFunctionLibrary::AppendOwnedTags(FAFEffectSpecHandle Spec, const FGameplayTagContainer& InTags) +{ + Spec.GetPtr()->OwnedTags.AppendTags(InTags); +} + +void UAFEffectSpecFunctionLibrary::CompareOwnedTags(FAFEffectSpecHandle Spec + , EAFTagContainerCompare Mode + , const FGameplayTagContainer& InTags + , EAFTagCompareResult& Result) +{ + switch (Mode) + { + case EAFTagContainerCompare::HasAny: + Spec.GetPtr()->OwnedTags.HasAny(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagContainerCompare::HasAnyExact: + Spec.GetPtr()->OwnedTags.HasAnyExact(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagContainerCompare::HasAll: + Spec.GetPtr()->OwnedTags.HasAll(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagContainerCompare::HasAllExact: + Spec.GetPtr()->OwnedTags.HasAllExact(InTags) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + default: + break; + } +} + +void UAFEffectSpecFunctionLibrary::CompareOwnedTag(FAFEffectSpecHandle Spec + , EAFTagCompare Mode + , FGameplayTag InTag + , EAFTagCompareResult& Result) +{ + switch (Mode) + { + case EAFTagCompare::HasTag: + Spec.GetPtr()->OwnedTags.HasTag(InTag) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + case EAFTagCompare::HasTagExact: + Spec.GetPtr()->OwnedTags.HasTagExact(InTag) ? Result = EAFTagCompareResult::Match : Result = EAFTagCompareResult::NoMatch; + break; + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp new file mode 100644 index 0000000..46e7ee3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../../Attributes/GAAttributeBase.h" +#include "../../AFAbilityInterface.h" +#include "AFAttributeStongerOverride.h" + + + + +bool UAFAttributeStongerOverride::CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) +{ + bool bCanApply = true; + FGAAttribute Attribute = Params.GetProperty().GetSpec()->AtributeModifier.Attribute; + FAFAttributeBase* AttributePtr = Params.GetContext().TargetInterface->GetAttribute(Attribute); + FGAEffectProperty& InProperty = Params.GetProperty(); + + if (AttributePtr) + { + FGAEffectMod mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() + , InProperty.GetSpec() + , Params.GetContext() + , InHandle); + + if (AttributePtr->CheckIfStronger(mod)) + { + bCanApply = true; + } + else + { + bCanApply = false; + } + } + return bCanApply; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp new file mode 100644 index 0000000..9e44f37 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFEffectAlreadyApplied.cpp @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectAlreadyApplied.h" + + + + +bool UAFEffectAlreadyApplied::CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) +{ + if (InContainer->ContainsEffectOfClass(Params.Property)) + { + return false; + } + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationAdd.cpp new file mode 100644 index 0000000..a96c24c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationAdd.cpp @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFAtributeDurationAdd.h" + + + + +bool UAFAtributeDurationAdd::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp new file mode 100644 index 0000000..d38c4e1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFAbilityInterface.h" +#include "AFAtributeDurationUnique.h" + + + + +bool UAFAtributeDurationUnique::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + if (InContainer->IsEffectActive(Params.GetSpec().GetEffectClass())) + { + return false; + } + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + return true; +} + +bool UAFAtributeDurationUnique::CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) +{ + if (!Target) + return false; + + return !Target->GetEffectsComponent()->IsEffectActive(EffectClass); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationInfinite.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationInfinite.cpp new file mode 100644 index 0000000..373b41c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationInfinite.cpp @@ -0,0 +1,17 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAttributeDurationInfinite.h" + + + + +bool UAFAttributeDurationInfinite::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp new file mode 100644 index 0000000..145e7bf --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFAttributeDurationOverride.h" + + + + +bool UAFAttributeDurationOverride::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + InContainer->RemoveEffect(Params.Property); + + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationAdd.cpp new file mode 100644 index 0000000..a7bab63 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationAdd.cpp @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFPeriodApplicationAdd.h" + + +bool UAFPeriodApplicationAdd::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); + + //InContainer->AddEffect(InProperty, InHandle); + + return true; +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp new file mode 100644 index 0000000..c6b461d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -0,0 +1,53 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFPeriodApplicationExtend.h" + + + + +bool UAFPeriodApplicationExtend::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + TSet handles = InContainer->GetHandlesByClass(Params.GetProperty(), Params.GetContext()); + for (const FGAEffectHandle& handle : handles) + { + FGAEffect& ExtEffect = *InContainer->GetEffect(handle); + FGAEffect& Effect = const_cast(EffectIn); + + FGAEffectContext& ExtContext = const_cast(Params).GetProperty().GetContext(handle).GetRef(); + + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + float RemainingTime = DurationTimer.GetTimerRemaining(ExtEffect.DurationTimerHandle); + float NewDuration = RemainingTime + Effect.GetDurationTime(); + DurationTimer.ClearTimer(ExtEffect.DurationTimerHandle); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(ExtContext.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(ExtEffect.DurationTimerHandle, delDuration, + NewDuration, false); + } + if (handles.Num() <= 0) + { + FGAEffect& Effect = const_cast(EffectIn);; + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(Effect.DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(Effect.PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); + } + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp new file mode 100644 index 0000000..7fc9e0a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.cpp @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFPeriodApplicationInfiniteAdd.h" + + +bool UAFPeriodApplicationInfiniteAdd::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); + + return true; +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp new file mode 100644 index 0000000..db10dbe --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../GAGameEffect.h" +#include "AFEffectsComponent.h" +#include "AFPeriodApplicationOverride.h" + + + + +bool UAFPeriodApplicationOverride::ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + + InContainer->RemoveEffect(Params.Property); + + FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate delDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExpireEffect, InHandle, Params); + DurationTimer.SetTimer(const_cast(EffectIn).DurationTimerHandle, delDuration, + Params.GetProperty().GetDuration(), false); + + FTimerManager& PeriodTimer = const_cast(Params).GetTargetTimerManager(); + + FTimerDelegate PeriodDuration = FTimerDelegate::CreateUObject(Params.GetTargetEffectsComponent(), &UAFEffectsComponent::ExecuteEffect, InHandle, Params, Modifier); + PeriodTimer.SetTimer(const_cast(EffectIn).PeriodTimerHandle, PeriodDuration, + Params.GetProperty().GetPeriod(), true); + + return true; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp new file mode 100644 index 0000000..4585496 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFPeriodicApplInfiniteOverride.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask.cpp new file mode 100644 index 0000000..d24b545 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../../AbilityFramework.h" +#include "AFEffectTask.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp new file mode 100644 index 0000000..df86500 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.cpp @@ -0,0 +1,82 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_AppliedEffectEvent.h" + + + + +UAFEffectTask_AppliedEffectEvent::UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_AppliedEffectEvent* UAFEffectTask_AppliedEffectEvent::ListenAppliedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->Tag = Tag; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_AppliedEffectEvent::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_AppliedEffectEvent::GameplayEventCallback + FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_AppliedEffectEvent::GameplayEventCallback); + MyHandle = Delegate.GetHandle(); + ASC->AddAppliedEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_AppliedEffectEvent::GameplayEventCallback(FAFEventData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} +void UAFEffectTask_AppliedEffectEvent::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->RemoveAppliedEvent(Tag, MyHandle); + } +} +void UAFEffectTask_AppliedEffectEvent::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_AppliedEffectEvent::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp new file mode 100644 index 0000000..1e91f68 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_AttributeChange.cpp @@ -0,0 +1,70 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFEffectTask_AttributeChange.h" + + +UAFEffectTask_AttributeChange::UAFEffectTask_AttributeChange(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_AttributeChange* UAFEffectTask_AttributeChange::ListenAttributeChanged(UGAEffectExtension* OwningExtension, + FGAAttribute InAttribute, + AActor* OptionalExternalTarget, + bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension); + MyObj->Attribute = InAttribute; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_AttributeChange::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + // MyHandle = ASC->AttributeChanged.FindOrAdd(Attribute).AddUObject(this, &UAFEffectTask_AttributeChange::AttributeChangedCallback); + } + + Super::Activate(); +} + +void UAFEffectTask_AttributeChange::AttributeChangedCallback(FAFAttributeChangedData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_AttributeChange::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_AttributeChange::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp new file mode 100644 index 0000000..584eaed --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp @@ -0,0 +1,80 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_EffectAppliedToSelf.h" + + + + +UAFEffectTask_EffectAppliedToSelf::UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_EffectAppliedToSelf* UAFEffectTask_EffectAppliedToSelf::ListenEffectAppliedToSelf(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_EffectAppliedToSelf::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + MyHandle = ASC->OnAppliedToSelf.AddUObject(this, &UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback);//AddExecuteEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Context, Property, Spec); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} +void UAFEffectTask_EffectAppliedToSelf::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->OnAppliedToSelf.Remove(MyHandle); + } +} +void UAFEffectTask_EffectAppliedToSelf::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_EffectAppliedToSelf::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp new file mode 100644 index 0000000..9c8b566 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp @@ -0,0 +1,85 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_EffectAppliedToTarget.h" + + + + +UAFEffectTask_EffectAppliedToTarget::UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_EffectAppliedToTarget* UAFEffectTask_EffectAppliedToTarget::ListenEffectAppliedToTarget(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_EffectAppliedToTarget::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback + //FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback); + //MyHandle = Delegate.GetHandle(); + MyHandle = ASC->OnAppliedToTarget.AddUObject(this, &UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback);//AddExecuteEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Context, Property, Spec); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_EffectAppliedToTarget::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->OnAppliedToTarget.Remove(MyHandle); + } +} + +void UAFEffectTask_EffectAppliedToTarget::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_EffectAppliedToTarget::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp new file mode 100644 index 0000000..c59cda4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectEvent.cpp @@ -0,0 +1,84 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "../../AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_EffectEvent.h" + + + + +UAFEffectTask_EffectEvent::UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_EffectEvent* UAFEffectTask_EffectEvent::ListenEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->Tag = Tag; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_EffectEvent::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_EffectEvent::GameplayEventCallback + FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_EffectEvent::GameplayEventCallback); + MyHandle = Delegate.GetHandle(); + ASC->AddEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_EffectEvent::GameplayEventCallback(FAFEventData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_EffectEvent::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->RemoveEvent(Tag, MyHandle); + } +} + +void UAFEffectTask_EffectEvent::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_EffectEvent::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp new file mode 100644 index 0000000..cdeaaa0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.cpp @@ -0,0 +1,84 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAbilityInterface.h" +#include "AFEffectsComponent.h" +#include "AFEffectTask_ExecutedEffectEvent.h" + + + + +UAFEffectTask_ExecutedEffectEvent::UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +UAFEffectTask_ExecutedEffectEvent* UAFEffectTask_ExecutedEffectEvent::ListenExecutedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag Tag, AActor* OptionalExternalTarget, bool OnlyTriggerOnce) +{ + auto MyObj = NewEffectTask(OwningExtension, TaskName); + MyObj->Tag = Tag; + MyObj->SetExternalTarget(OptionalExternalTarget); + MyObj->OnlyTriggerOnce = OnlyTriggerOnce; + + return MyObj; +} + +void UAFEffectTask_ExecutedEffectEvent::Activate() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + //(this, &UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback + FAFEventDelegate Delegate = FAFEventDelegate::CreateUObject(this, &UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback); + MyHandle = Delegate.GetHandle(); + ASC->AddExecuteEvent(Tag, Delegate); + } + + Super::Activate(); +} + +void UAFEffectTask_ExecutedEffectEvent::GameplayEventCallback(FAFEventData Payload) +{ + //if (ShouldBroadcastAbilityTaskDelegates()) + { + OnEvent.Broadcast(Payload); + } + if (OnlyTriggerOnce) + { + EndTask(); + } +} + +void UAFEffectTask_ExecutedEffectEvent::OnTaskEnded() +{ + UAFEffectsComponent* ASC = GetTargetASC(); + if (ASC) + { + ASC->RemoveExecuteEvent(Tag, MyHandle); + } +} + +void UAFEffectTask_ExecutedEffectEvent::SetExternalTarget(AActor* Actor) +{ + if (Actor) + { + + if (IAFAbilityInterface* interface = Cast(Actor)) + { + UseExternalTarget = true; + OptionalExternalTarget = interface->GetEffectsComponent(); + } + + } +} + +UAFEffectsComponent* UAFEffectTask_ExecutedEffectEvent::GetTargetASC() +{ + if (UseExternalTarget) + { + return OptionalExternalTarget; + } + + return EffectsComponent; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp new file mode 100644 index 0000000..b8c4ed5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp @@ -0,0 +1,371 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFAbilityComponent.h" + + +#include "GABlueprintLibrary.h" + +#include "AFAbilityInterface.h" +#include "GAGameEffect.h" +#include "AFEffectCustomApplication.h" + +#include "GAEffectExtension.h" + +UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} + + +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToObject( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffectToObject(InEffect, Handle, Target, Instigator, Causer, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToActor( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffectToActor(InEffect, Handle, Target, Instigator, Causer, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffectFromHit(InEffect, Handle, Target, Instigator, Causer, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffect( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier) +{ + IAFAbilityInterface* Ability = Cast(Causer); + if (!Ability) + { + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); + return FGAEffectHandle(); + } + + IAFAbilityInterface* TargetInterface = Cast(Target); + if (!InEffect.GetClass().GetDefaultObject()->Application.GetDefaultObject()->CanApply(TargetInterface, InEffect.GetClass())) + { + return FGAEffectHandle(); + } + bool bReusedParams = false; + bool bPeriodicEffect = false; + bool bReusedSpec = false; + if (Handle.IsValid() && (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) + { + bPeriodicEffect = true; + } + + FAFContextHandle Context; + FAFEffectSpecHandle EffectSpecHandle; + + //only reused Spec and Context if effect is instant ? + if (Handle.IsValid() && !bPeriodicEffect) + { + FAFContextHandle ExistingContext = InEffect.GetContext(Handle); + if (ExistingContext.IsValid()) + { + Context = ExistingContext; + Context.SetTarget(Target); + bReusedParams = true; + } + FAFEffectSpecHandle SpecHandle = InEffect.GetEffectSpec(Handle); + EffectSpecHandle = SpecHandle; + bReusedParams = true; + bReusedSpec = true; + } + else + { + Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + } + + InEffect.InitializeIfNotInitialized(Context.GetRef()); + UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); + + + if ((InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) + { + bPeriodicEffect = true; + } + + if (!InEffect.IsInitialized()) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + return FGAEffectHandle(); + } + + + if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) + { + return FGAEffectHandle(); + } + if (Target2->DenyEffectApplication(InEffect.GetSpec()->DenyTags)) + { + return FGAEffectHandle(); + } + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); + + FGAEffect effect; + effect.World = Instigator->GetWorld(); + if (Ability) + { + //InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); + + effect.PredictionHandle = Ability->GetPredictionHandle(); + } + IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + + FAFEffectParams Params(InEffect); + + if (!bReusedSpec) + { + FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); + AddTagsToEffect(EffectSpec); + Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); + } + else + { + Params.EffectSpec = EffectSpecHandle; + } + Params.bRecreated = bReusedParams; + Params.bPeriodicEffect = bPeriodicEffect; + Params.Context = Context; + + FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); + + return NewHandle; +} +FGAEffectHandle UGABlueprintLibrary::ApplyEffect( + FGAEffectProperty* InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier) +{ + //IAFAbilityInterface* Ability = Cast(Causer); + //if (!Ability) + //{ + // UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); + // return FGAEffectHandle(); + //} + //bool bReusedParams = false; + //bool bPeriodicEffect = false; + //bool bReusedSpec = false; + //if (Handle.IsValid() && (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0)) + //{ + // bPeriodicEffect = true; + //} + + //FAFContextHandle Context; + //FAFEffectSpecHandle EffectSpecHandle; + + //if (Handle.IsValid()) + //{ + // if (bPeriodicEffect) + // { + // FAFContextHandle* ExistingContext = InEffect->GetContext(Handle); + // if (ExistingContext) + // { + // Context = *ExistingContext; + // Context.SetTarget(Target); + // bReusedParams = true; + // } + // FAFEffectSpecHandle* SpecHandle = InEffect->GetEffectSpec(Handle); + // EffectSpecHandle = *SpecHandle; + // bReusedSpec = true; + // } + // else + // { + // Context = InEffect->GetInstantContext(); + // Context.SetTarget(Target); + + // EffectSpecHandle = InEffect->GetInstantEffectSpec(); + // bReusedParams = true; + // bReusedSpec = true; + // } + //} + //else + //{ + // Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + //} + + //InEffect->InitializeIfNotInitialized(Context.GetRef()); + + //if (!InEffect->IsInitialized()) + //{ + // UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + // return FGAEffectHandle(); + //} + + //UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); + //if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) + //{ + // return FGAEffectHandle(); + //} + //if (Target2->DenyEffectApplication(InEffect->GetSpec()->DenyTags)) + //{ + // return FGAEffectHandle(); + //} + //UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); + + //FGAEffect effect; + //effect.World = Instigator->GetWorld(); + //if (Ability) + //{ + // InEffect->SetPredictionHandle(Ability->GetPredictionHandle()); + // effect.PredictionHandle = Ability->GetPredictionHandle(); + // + //} + // + //FAFPropertytHandle Property = FAFPropertytHandle::Generate(*InEffect); + //FAFEffectParams Params(Property); + //FAFEffectSpec* EffectSpec = new FAFEffectSpec(); + ////AddTagsToEffect(EffectSpec); + //Params.Context = Context; + // + //Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); + + //IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + //FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); + FGAEffectHandle NewHandle; + return NewHandle; +} +FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffect(InEffect, Handle, Target.GetActor(), Instigator, Causer, Target, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffectToActor( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + FHitResult Hit(ForceInit); + return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); +} + +FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + FHitResult Hit(ForceInit); + return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); +} + +FAFContextHandle UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, + AActor* InAvatar, UObject* Causer, const FHitResult& HitIn) +{ + IAFAbilityInterface* targetAttr = Cast(Target); + IAFAbilityInterface* instiAttr = Cast(Instigator); + if (!targetAttr && !instiAttr) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Target and Instigator does not implement IAFAbilityInterface interface")); + return FAFContextHandle(); + } + UAFAbilityComponent* targetComp = nullptr; + UAFAbilityComponent* instiComp = nullptr; + if (targetAttr) + { + targetComp = targetAttr->GetAbilityComp(); + } + if (instiAttr) + { + instiComp = instiAttr->GetAbilityComp(); + } + + FVector location = targetComp ? targetComp->GetOwner()->GetActorLocation() : FVector(HitIn.ImpactPoint.X, HitIn.ImpactPoint.Y, HitIn.ImpactPoint.Z); + FGAEffectContext* Context = new FGAEffectContext( + targetAttr ? targetAttr->GetAttributes() : nullptr + , instiAttr ? instiAttr->GetAttributes() : nullptr + , location + , Target + , Causer + , Instigator + , targetComp + , instiComp + , InAvatar); + + Context->HitResult = HitIn; + + FAFContextHandle Handle = FAFContextHandle::Generate(Context); + + return Handle; +} + +void UGABlueprintLibrary::AddTagsToEffect(FAFEffectSpec* EffectIn) +{ + if (EffectIn) + { + EffectIn->AddOwnedTags(EffectIn->GetSpec()->OwnedTags); + EffectIn->AddApplyTags(EffectIn->GetSpec()->ApplyTags); + } +} + +FGAEffectContext& UGABlueprintLibrary::GetContext(const FAFContextHandle& InHandle) +{ + return InHandle.GetRef(); +} + +UAFAbilityComponent* UGABlueprintLibrary::GetTargetComponent(const FGAEffectHandle& InHandle) +{ + return nullptr;// InHandle.GetContextRef().InstigatorComp.Get(); +} + +UAFAbilityComponent* UGABlueprintLibrary::GetInstigatorComponent(const FGAEffectHandle& InHandle) +{ + return nullptr;// InHandle.GetContextRef().TargetComp.Get(); +} + +void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag) +{ + IAFAbilityInterface* targetAttr = Cast(Target); + if (!targetAttr) + return; + + UAFAbilityComponent* TargetComp = targetAttr->GetAbilityComp(); + if (!TargetComp) + return; + + //FAFEventData EventData; + //TargetComp->NativeTriggerTagEvent(EventTag, EventData); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GACustomCalculation.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GACustomCalculation.cpp new file mode 100644 index 0000000..2fa6e5d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GACustomCalculation.cpp @@ -0,0 +1,11 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAGlobalTypes.h" +#include "GACustomCalculation.h" + +UGACustomCalculation::UGACustomCalculation(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectBlueprint.cpp new file mode 100644 index 0000000..1edd0b9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAEffectBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectBlueprint::UGAEffectBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAEffectBlueprint* UGAEffectBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectBlueprint* DerivedBlueprint) +{ + UGAEffectBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAEffectBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp new file mode 100644 index 0000000..0564782 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp @@ -0,0 +1,162 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "MovieScene.h" +#include "GAEffectCueSequence.h" +#include "ActorSequencePlayer.h" +#include "GAEffectCue.h" + +AGAEffectCue::AGAEffectCue(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + PrimaryActorTick.bCanEverTick = true; + PrimaryActorTick.bStartWithTickEnabled = true; + StartTime = 0; + EndTime = 5; + if (HasAnyFlags(RF_ClassDefaultObject) || GetArchetype() == GetDefault()) + { + Sequence = ObjectInitializer.CreateDefaultSubobject(this, "Sequence"); + Sequence->SetFlags(RF_Public | RF_Transactional); + SequencePlayer = ObjectInitializer.CreateDefaultSubobject(this, "SequencePlayer"); + } +} +void AGAEffectCue::PostInitProperties() +{ + UpdateAssetRegistryInfo(); + Super::PostInitProperties(); +} + +void AGAEffectCue::Serialize(FArchive& Ar) +{ + if (Ar.IsSaving()) + { + UpdateAssetRegistryInfo(); + } + + Super::Serialize(Ar); + + if (Ar.IsLoading()) + { + UpdateAssetRegistryInfo(); + } +} +#if WITH_EDITORONLY_DATA +void AGAEffectCue::UpdateAssetBundleData() +{ + AssetBundleData.Reset(); + UpdateAssetRegistryInfo(); + + // By default parse the metadata + if (UAssetManager::IsValid()) + { + UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); + } +} + +void AGAEffectCue::PreSave(const class ITargetPlatform* TargetPlatform) +{ + Super::PreSave(TargetPlatform); + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid()) + { + // Bundles may have changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +} +#endif +void AGAEffectCue::PostLoad() +{ + Super::PostLoad(); + +#if WITH_EDITORONLY_DATA + FAssetBundleData OldData = AssetBundleData; + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid() && OldData != AssetBundleData) + { + // Bundles changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +#endif +} +FPrimaryAssetId AGAEffectCue::GetPrimaryAssetId() const +{ + FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); + + const AGAEffectCue* A = this; + return FPrimaryAssetId(FPrimaryAssetType("EffectCue"), dupa1); + //if (HasAnyFlags(RF_ClassDefaultObject)) + { + UClass* SearchNativeClass = GetClass(); + + while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) + { + SearchNativeClass = SearchNativeClass->GetSuperClass(); + } + + if (SearchNativeClass && SearchNativeClass != GetClass()) + { + // If blueprint, return native class and asset name + + } + + // Native CDO, return nothing + return FPrimaryAssetId(); + } + + // Data assets use Class and ShortName by default, there's no inheritance so class works fine + //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); +} + +void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) +{ + Sequence = InSequence; +} +// Called when the game starts or when spawned +void AGAEffectCue::BeginPlay() +{ + if (!SequencePlayer) + { + SequencePlayer = NewObject(this, UActorSequencePlayer::StaticClass(), "SequencerPlayer"); + } + SequencePlayer->Initialize(Sequence, PlaybackSettings); + + Super::BeginPlay(); + //NativeBeginCue(); +} + +// Called every frame +void AGAEffectCue::Tick( float DeltaTime ) +{ + Super::Tick( DeltaTime ); + if (SequencePlayer) + { + SequencePlayer->Update(DeltaTime); + } +} +void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, + const FHitResult& HitInfo, const FGAEffectCueParams& CueParams) +{ + BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); + if (!SequencePlayer) + { + SequencePlayer->Play(); + } +} + +void AGAEffectCue::NativeOnExecuted() +{ + OnExecuted(); +} +void AGAEffectCue::NativeOnRemoved() +{ + OnRemoved(); +} + +void AGAEffectCue::UpdateAssetRegistryInfo() +{ + EffectCueTagSearch = CueTag.GetTagName(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp new file mode 100644 index 0000000..580daab --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp @@ -0,0 +1,13 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAEffectCueBlueprintGeneratedClass.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectCueBlueprintGeneratedClass::UGAEffectCueBlueprintGeneratedClass(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueGlobals.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueGlobals.cpp new file mode 100644 index 0000000..3f57b12 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueGlobals.cpp @@ -0,0 +1,51 @@ +#pragma once +#include "../AbilityFramework.h" +#include "../AFAbilityComponent.h" +#include "GAEffectCueGlobals.h" + +void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn) +{ + //if (!CueIn) + //{ + // return; + //} + //UGAEffectCue* Cue = NewObject(OwningComponent.Get(), CueIn); + //Cues.Add(HandleIn, Cue); + //Cue->SetParameters(OwningComponent->GetOwner(), CueParamsIn); + //Cue->BeginCue(); +} +void FGACueContainer::AddCue(const FGAEffectHandle& HandleIn) +{ + //Cues.Add(HandleIn, CueIn); +} +class UGAEffectCue* FGACueContainer::GetCue(const FGAEffectHandle& HandleIn) +{ + //UGAEffectCue* Cue = nullptr; + //Cue = Cues.FindRef(HandleIn); + return nullptr; +} +void FGACueContainer::ExecuteCue(const FGAEffectHandle& HandleIn) +{ + //UGAEffectCue* Cue = GetCue(HandleIn); + //if (Cue) + //{ + // Cue->ExecuteCue(); + //} +} +void FGACueContainer::RemoveCue(const FGAEffectHandle& HandleIn) +{ + //UGAEffectCue* Cue; + //if (Cues.Num() > 0) + //{ + // Cues.RemoveAndCopyValue(HandleIn, Cue); + // if (Cue) + // { + // Cue->EndCue(); + // Cue->MarkPendingKill(); + // } + //} +} +void FGACueContainer::CueExpired(const FGAEffectHandle& HandleIn) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp new file mode 100644 index 0000000..b373f14 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp @@ -0,0 +1,130 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "../AbilityFramework.h" +#include "GAEffectCue.h" +#include "MovieScene.h" +#include "MovieSceneCommonHelpers.h" +#include "Modules/ModuleManager.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Engine/Blueprint.h" +#include "GameFramework/Actor.h" +#include "Classes/Engine/SCS_Node.h" +#include "Classes/Engine/SimpleConstructionScript.h" +#include "Engine/Blueprint.h" +#include "UObject/Package.h" +#include "ActorSequenceObjectReference.h" +#include "GAEffectCueSequence.h" + + +#if WITH_EDITOR +UGAEffectCueSequence::FOnInitialize UGAEffectCueSequence::OnInitializeSequenceEvent; +#endif + +UGAEffectCueSequence::UGAEffectCueSequence(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) + , MovieScene(nullptr) +#if WITH_EDITOR + , bHasBeenInitialized(false) +#endif +{ + bParentContextsAreSignificant = true; + + MovieScene = ObjectInitializer.CreateDefaultSubobject(this, "MovieScene"); + MovieScene->SetFlags(RF_Transactional); +} + +void UGAEffectCueSequence::PostInitProperties() +{ +#if WITH_EDITOR && WITH_EDITORONLY_DATA + AGAEffectCue* OwnerCue = Cast(GetOuter()); + if (!bHasBeenInitialized && !HasAnyFlags(RF_ClassDefaultObject) && OwnerCue && !OwnerCue->HasAnyFlags(RF_ClassDefaultObject)) + { + FGuid BindingID = MovieScene->AddPossessable(OwnerCue ? OwnerCue->GetActorLabel() : TEXT("Owner"), OwnerCue ? OwnerCue->GetClass() : AGAEffectCue::StaticClass()); + //ObjectReferences.CreateBinding(BindingID, FActorSequenceObjectReference::CreateForContextActor()); + + OnInitializeSequenceEvent.Broadcast(this); + bHasBeenInitialized = true; + } +#endif + + Super::PostInitProperties(); +} +#if WITH_EDITOR +UGAEffectCueSequence* UGAEffectCueSequence::GetNullAnimation() +{ + static UGAEffectCueSequence* NullAnimation = nullptr; + + if (!NullAnimation) + { + NullAnimation = NewObject(GetTransientPackage(), NAME_None); + NullAnimation->AddToRoot(); + NullAnimation->MovieScene = NewObject(NullAnimation, FName("No Animation")); + NullAnimation->MovieScene->AddToRoot(); + } + + return NullAnimation; +} +#endif //WITH_EDITOR +FFrameNumber UGAEffectCueSequence::GetStartTime() const +{ + return MovieScene->GetPlaybackRange().GetLowerBoundValue(); +} + + +FFrameNumber UGAEffectCueSequence::GetEndTime() const +{ + return MovieScene->GetPlaybackRange().GetUpperBoundValue(); +} + + +/* UMovieSceneAnimation overrides +*****************************************************************************/ + + +void UGAEffectCueSequence::BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) +{ + AActor* ActorContext = CastChecked(Context); + + if (AActor* Actor = Cast(&PossessedObject)) + { + //ObjectReferences.CreateBinding(ObjectId, FActorSequenceObjectReference::CreateForActor(Actor, ActorContext)); + } +} + + +bool UGAEffectCueSequence::CanPossessObject(UObject& Object, UObject* InPlaybackContext) const +{ + AActor* ActorContext = CastChecked(InPlaybackContext); + + if (AActor* Actor = Cast(&Object)) + { + return Actor == InPlaybackContext || Actor->GetLevel() == ActorContext->GetLevel(); + } + return true; +} + +void UGAEffectCueSequence::LocateBoundObjects(const FGuid& ObjectId, UObject* Context, TArray>& OutObjects) const +{ + if (Context) + { + //ObjectReferences.ResolveBinding(ObjectId, CastChecked(Context), OutObjects); + } +} + + +UMovieScene* UGAEffectCueSequence::GetMovieScene() const +{ + return MovieScene; +} + + +UObject* UGAEffectCueSequence::GetParentObject(UObject* Object) const +{ + + return GetOuter(); +} + +void UGAEffectCueSequence::UnbindPossessableObjects(const FGuid& ObjectId) +{ + //ObjectReferences.RemoveBinding(ObjectId); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp new file mode 100644 index 0000000..bcfbe5e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp @@ -0,0 +1,24 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "../GAGlobalTypes.h" +#include "../Attributes/GAAttributeBase.h" +#include "../AFAbilityComponent.h" +#include "GAEffectExecution.h" + +UGAEffectExecution::UGAEffectExecution(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} +void UGAEffectExecution::PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context) +{ + UE_LOG(GameAttributesEffects, Log, TEXT("Sample execution class implementation")); +} +void UGAEffectExecution::ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, + const FAFEffectParams& Params, + const FAFFunctionModifier& Modifier) +{ + PreModifyAttribute(HandleIn, ModIn, Params.GetContext()); + Params.GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty()); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp new file mode 100644 index 0000000..8bd4fac --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp @@ -0,0 +1,70 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFEffectsComponent.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "GAEffectExtension.h" + +UGAEffectExtension::UGAEffectExtension(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} +void UGAEffectExtension::SetParameters(const FGAEffectContext& ContextIn) +{ + Context = ContextIn; +} +void UGAEffectExtension::BeginEffect() +{ +} + +void UGAEffectExtension::NativeOnEffectApplied() +{ + OnEffectApplied(); +} +void UGAEffectExtension::NativeOnEffectExecuted() +{ + OnEffectExecuted(); +} +void UGAEffectExtension::NativeOnEffectExpired() +{ + OnEffectExpired(); +} +void UGAEffectExtension::NativeOnEffectRemoved() +{ + OnEffectRemoved(); +} + +UWorld* UGAEffectExtension::GetWorld() const +{ + if (Context.Target.IsValid()) + return Context.Target->GetWorld(); + + return nullptr; +} + +void UGAEffectExtension::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) +{ + if (!InstanceName.IsNone()) + { + Tasks.Add(InstanceName, TaskIn); + } +}; +void UGAEffectExtension::AddReplicatedTask(class UAFTaskBase* TaskIn) +{ + //AbilityComponent->ReplicatedTasks.Add(TaskIn); +} +void UGAEffectExtension::OnLatentTaskRemoved(class UAFTaskBase* TaskIn) +{ +}; + +void UGAEffectExtension::OnLatentTaskActivated(class UAFTaskBase* TaskIn) +{ +}; +void UGAEffectExtension::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) +{ +}; + +class UAFTaskBase* UGAEffectExtension::GetCachedLatentAction(FName TaskName) +{ + return Tasks.FindRef(TaskName); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectField.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectField.cpp new file mode 100644 index 0000000..30e0213 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectField.cpp @@ -0,0 +1,48 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" + +#include "../Abilities/GAAbilityBase.h" + +#include "GAEffectField.h" + +AGAEffectField::AGAEffectField(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + bReplicates = true; + SetReplicates(true); +} + +void AGAEffectField::InitializeField() +{ + //if (bIsFieldPersistent && AbilityInstigator) + //{ + + //} + //else if (!bIsFieldPersistent && AbilityInstigator) + //{ + // AbilityInstigator->OnAbilityCastEnd.AddUObject(this, &AGAEffectField::DestroyField); + //} + + //1. Automaticallt gather all collision componenets from blueprinted version. + // don't want to hardcode any kind of collision inside base class + // let designer decide what exactly he wants to do with it. + // but on other hand encapsulate this functionality so + // designer won't have to deal with binding/assiging events inside blueprint. + //2. Bind Events from them. +} + +void AGAEffectField::DestroyField() +{ + +} + +void AGAEffectField::OnAbilityExecuted_Implementation() +{ + +} + +void AGAEffectField::OnOtherFieldOverlap_Implementation() +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectGlobalTypes.cpp new file mode 100644 index 0000000..a099560 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectGlobalTypes.cpp @@ -0,0 +1,143 @@ +#pragma once +#include "../AbilityFramework.h" +#include "../AFAbilityComponent.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAEffectExecution.h" +#include "AFAbilityInterface.h" +#include "GAGameEffect.h" +#include "GACustomCalculation.h" + + + +float FGADirectModifier::GetValue() { return Value; } +float FGADirectModifier::GetValue() const { return Value; } +float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + switch (Source) + { + case EGAAttributeSource::Instigator: + { + IAFAbilityInterface* AttrInt = Cast(Context.Instigator.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes(); + attr = Attributes->GetAttribute(Attribute); + //attr = Context.InstigatorComp->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Target: + { + IAFAbilityInterface* AttrInt = Cast(Context.Target.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; + attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Causer: + { + IAFAbilityInterface* AttrInt = Cast(Context.Causer.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; + attr = Attributes->GetAttribute(Attribute);//Context.TargetComp->GetAttribute(Attribute); + break; + } + default: + return 0; + } + Result = (Coefficient * (PreMultiply + attr->GetFinalValue()) + PostMultiply) * PostCoefficient; + if (!bUseSecondaryAttribute) + return Result; + + return 0; +} +float FGAAttributeBasedModifier::GetValue(const FGAEffectContext& Context) const +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + + switch (Source) + { + case EGAAttributeSource::Instigator: + { + IAFAbilityInterface* AttrInt = Cast(Context.Instigator.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes(); + attr = Attributes->GetAttribute(Attribute); + //attr = Context.InstigatorComp->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Target: + { + IAFAbilityInterface* AttrInt = Cast(Context.Target.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes(); + attr = Attributes->GetAttribute(Attribute); + break; + } + case EGAAttributeSource::Causer: + { + IAFAbilityInterface* AttrInt = Cast(Context.Causer.Get()); + UGAAttributesBase* Attributes = AttrInt->GetAttributes();// nullptr; + attr = Attributes->GetAttribute(Attribute); + break; + } + default: + return 0; + } + Result = (Coefficient * (PreMultiply + attr->GetFinalValue()) + PostMultiply) * PostCoefficient; + if (!bUseSecondaryAttribute) + return Result; + + return 0; +} + +float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + switch (Source) + { + case EGAAttributeSource::Instigator: + attr = ContextIn.InstigatorComp->GetAttribute(Attribute); + break; + case EGAAttributeSource::Target: + attr = ContextIn.TargetComp->GetAttribute(Attribute); + break; + default: + return 0; + } + FString ContextString(TEXT("Evaluating modifier value.")); + Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); + return Result; +} +float FGACurveBasedModifier::GetValue(const FGAEffectContext& ContextIn) const +{ + FAFAttributeBase* attr = nullptr; + float Result = 0; + switch (Source) + { + case EGAAttributeSource::Instigator: + attr = ContextIn.InstigatorComp->GetAttribute(Attribute); + break; + case EGAAttributeSource::Target: + attr = ContextIn.TargetComp->GetAttribute(Attribute); + break; + default: + return 0; + } + FString ContextString(TEXT("Evaluating modifier value.")); + Result = CurveTable.Eval(attr->GetFinalValue(), ContextString); + return Result; +} +float FGACustomCalculationModifier::GetValue(const FGAEffectContext& ContextIn) +{ + if (CustomCalculation) + { + return CustomCalculation->NativeCalculateMagnitude(ContextIn); + } + return 0; +} +float FGACustomCalculationModifier::GetValue(const FGAEffectContext& ContextIn) const +{ + if (CustomCalculation) + { + return CustomCalculation->NativeCalculateMagnitude(ContextIn); + } + return 0; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp new file mode 100644 index 0000000..64304ce --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp @@ -0,0 +1,847 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "GameplayTagContainer.h" +#include "AFEffectsComponent.h" +#include "Attributes/GAAttributesBase.h" +#include "AFAbilityInterface.h" + +#include "GAEffectExecution.h" +#include "GAEffectExtension.h" +#include "GAGlobalTypes.h" + +#include "AFEffectApplicationRequirement.h" +#include "AFEffectCustomApplication.h" +#include "GAGameEffect.h" +#include "GABlueprintLibrary.h" + +DEFINE_STAT(STAT_GatherModifiers); + + +void FAFEffectSpec::OnApplied() +{ + if (Extension) + { + Extension->NativeOnEffectApplied(); + } +} +void FAFEffectSpec::OnExpired() +{ + if (Extension) + { + Extension->NativeOnEffectExpired(); + } +} +void FAFEffectSpec::OnRemoved() +{ + if (Extension) + { + Extension->NativeOnEffectRemoved(); + } +} +void FAFEffectSpec::OnExecuted() +{ + if (Extension) + { + Extension->NativeOnEffectExecuted(); + } +} +FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass) + : SpecClass(InSpecClass) +{ + Context = InContext; + Extension = nullptr; + if (InSpecClass.GetDefaultObject()->Extension) + { + Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); + Extension->OwningComponent = Context.GetPtr()->TargetInterface->GetEffectsComponent(); + } + OwnedTags.AppendTags(InSpecClass.GetDefaultObject()->OwnedTags); +} + +float FAFEffectSpec::GetFloatFromAttributeMagnitude( + const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext) const +{ + switch (AttributeIn.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return AttributeIn.DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeIn.AttributeBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CurveBased: + { + return AttributeIn.CurveBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return AttributeIn.Custom.GetValue(InContext); + } + default: + break; + } + + return 0; +} +float FAFEffectSpec::GetDuration(const FGAEffectContext& InContext) +{ + return GetFloatFromAttributeMagnitude(GetSpec()->Duration, InContext); +} +float FAFEffectSpec::GetPeriod(const FGAEffectContext& InContext) +{ + return GetFloatFromAttributeMagnitude(GetSpec()->Period, InContext); +} +FGAEffectProperty::FGAEffectProperty() + : ApplicationRequirement(nullptr) + , Application(nullptr) + , Execution(nullptr) + , Spec(nullptr) + , Duration(0) + , Period(0) + , bInstant(true) +{ + ApplicationRequirement = nullptr; + Application = nullptr; + Execution = nullptr; + Spec = nullptr; + Duration= 0; + Period = 0; +}; +FGAEffectProperty::FGAEffectProperty(TSubclassOf InClass) + : ApplicationRequirement(nullptr) + , Application(nullptr) + , Execution(nullptr) + , Spec(nullptr) + , Duration(0) + , Period(0) + , bInstant(true) +{ +}; +void FGAEffectProperty::PostScriptConstruct() +{ + ApplicationRequirement = nullptr; + Application = nullptr; + Execution = nullptr; + Spec = nullptr; + Duration = 0; + Period = 0; +} +void FGAEffectProperty::Initialize(TSubclassOf EffectClass) +{ + if (EffectClass) + { + Spec = EffectClass->GetDefaultObject(); + ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); + Application = GetSpec()->Application.GetDefaultObject(); + Execution = GetSpec()->ExecutionType.GetDefaultObject(); + } +} +void FGAEffectProperty::InitializeIfNotInitialized(const FGAEffectContext& InContext + , TSubclassOf EffectClass) +{ + if (!IsInitialized()) + { + Initialize(EffectClass); + } + if (Spec.IsValid()) + { + Duration = GetSpec()->Duration.GetFloatValue(InContext); + Period = GetSpec()->Period.GetFloatValue(InContext); + + if ((Duration > 0) || (Period > 0)) + { + bInstant = false; + } + } +} +bool FGAEffectProperty::CanApply( + const struct FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& InParams + , const FGAEffectHandle& InHandle) +{ + return ApplicationRequirement->CanApply(EffectIn, InParams, InHandle, InContainer); +} +bool FGAEffectProperty::ApplyEffect( + const FGAEffectHandle& InHandle + , const struct FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& InParams + , const FAFFunctionModifier& Modifier) +{ + return Application->ApplyEffect(InHandle, EffectIn, InContainer, InParams, Modifier); +} +void FGAEffectProperty::ApplyExecute(const FGAEffectHandle& InHandle + , const FAFEffectParams& InParams + , const FAFFunctionModifier& Modifier) +{ + Application->ApplyExecute(InHandle, InParams, Modifier); +} + +void FGAEffectProperty::ExecuteEffect( + const FGAEffectHandle& HandleIn + , FGAEffectMod& ModIn + , const FAFEffectParams& InParams + , const FAFFunctionModifier& Modifier) +{ + Execution->ExecuteEffect(HandleIn, ModIn, InParams, Modifier); +} + +void FGAEffect::PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer) +{ + //const_cast(InArraySerializer).RemoveFromReplication(Handle, PredictionHandle); +} +void FGAEffect::PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer) +{ + World = InArraySerializer.OwningComponent->GetWorld(); + AppliedTime = World->TimeSeconds; + LastTickTime = World->TimeSeconds; + + + Handle = FGAEffectHandle::GenerateHandle(); + + //const_cast(InArraySerializer).ApplyFromReplication(Handle, PredictionHandle); +} +void FGAEffect::PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer) +{ + +} + +float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) +{ + switch (CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeBased.GetValue(Context); + } + case EGAMagnitudeCalculation::CurveBased: + { + return CurveBased.GetValue(Context); + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return Custom.GetValue(Context); + } + default: + return 0; + } + + return 0; +} + +float FAFStatics::GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + switch (AttributeIn.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return AttributeIn.DirectModifier.GetValue(); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return AttributeIn.AttributeBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CurveBased: + { + return AttributeIn.CurveBased.GetValue(InContext); + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return AttributeIn.Custom.GetValue(InContext); + } + default: + break; + } + + return 0; +} +FGAEffectMod FAFStatics::GetAttributeModifier(FGAAttributeModifier& ModInfoIn + , class UGAGameEffectSpec* InSpec + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle) +{ + FGAEffectMod ModOut; + if (InSpec) + { + switch (ModInfoIn.Magnitude.CalculationType) + { + case EGAMagnitudeCalculation::Direct: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.DirectModifier.GetValue(), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + } + case EGAMagnitudeCalculation::AttributeBased: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.AttributeBased.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + + } + case EGAMagnitudeCalculation::CurveBased: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.CurveBased.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + + } + case EGAMagnitudeCalculation::CustomCalculation: + { + return FGAEffectMod(ModInfoIn.Attribute, + ModInfoIn.Magnitude.Custom.GetValue(InContext), ModInfoIn.AttributeMod, InHandle, InSpec->AttributeTags); + + } + default: + break; + } + } + return ModOut; +} + +FGAEffect::~FGAEffect() +{ +} + + +float FGAEffect::GetDurationTime() const +{ + return Duration;// GetFloatFromAttributeMagnitude(GetEffect()->Duration); +} +float FGAEffect::GetPeriodTime() const +{ + return Period;// GetFloatFromAttributeMagnitude(GetEffect()->Period); +} + +float FGAEffect::GetCurrentDuration() const +{ + if (World) + { + float CurrentTime = World->TimeSeconds; + return CurrentTime - AppliedTime; + } + + return 0; +} +FTimerManager& FAFEffectParams::GetTargetTimerManager() +{ + return Context.GetPtr()->TargetComp->GetWorld()->GetTimerManager(); +} +UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() +{ + return Context.GetPtr()->GetTargetEffectsComponent(); +} +UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() const +{ + return Context.GetPtr()->GetTargetEffectsComponent(); +} +void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams) +{ + /*if (!EffectCue) + { + return; + } + AActor* Instigator = EffectHandle.GetContext().Instigator.Get(); + UGAEffectCue* NewCue = NewObject(Instigator, EffectCue); + if (NewCue && Instigator) + { + NewCue->SetParameters(Instigator, CueParams); + NewCue->Context = EffectHandle.GetContext(); + NewCue->BeginCue(); + }*/ +} + +FGAEffectHandle FGAEffectContainer::ApplyEffect( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier) +{ + FGAEffectHandle Handle; + FGAEffectProperty& InProperty = Params.GetProperty(); + + bool bHasDuration = InProperty.GetDuration() > 0; + bool bHasPeriod = InProperty.GetPeriod() > 0; + + //InProperty.DataTest->ID++; + + ENetRole role = OwningComponent->GetOwnerRole(); + ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); + if (!Params.bRecreated) + { + Handle = FGAEffectHandle::GenerateHandle(); + } + else + { + Handle = InHandle; + } + if (InProperty.CanApply(EffectIn, this, Params, Handle)) + { + if(!Params.bPeriodicEffect) //instatnt effect. + { + const_cast(EffectIn).SetHandle(Handle); + if (InProperty.ApplyEffect(Handle, + EffectIn, this, Params)) + { + Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() + , Handle + , Params.Context + , Params.EffectSpec); + + InProperty.ApplyExecute(Handle, Params, Modifier); + + // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); + } + } + else + { + const_cast(EffectIn).SetHandle(Handle); + if (InProperty.ApplyEffect(Handle, + EffectIn, this, Params)) + { + FAFEffectSpec& Spec = Params.GetSpec(); + FGAEffectContext& Context = Params.GetContext(); + + Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() + , Handle + , Params.Context + , Params.EffectSpec); + + const_cast(EffectIn).AppliedTime = OwningComponent->GetWorld()->TimeSeconds; + const_cast(EffectIn).LastTickTime = OwningComponent->GetWorld()->TimeSeconds; + const_cast(EffectIn).Duration = Spec.GetDuration(Context); + const_cast(EffectIn).Period = Spec.GetPeriod(Context); + MarkItemDirty(const_cast(EffectIn)); + int32 newItem = ActiveEffectInfos.Add(EffectIn); + MarkArrayDirty(); + AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &ActiveEffectInfos[newItem], InProperty); + + //InProperty.ApplyExecute(Handle, Params, Modifier); + //generate it only on client, and apply prediction key from client. + //if server replicates with valid key, then nothing happens. + //if not we try to rewind effect application. + //we probabaly don't need to unwind attribute changes, since next replication from + //server will overridem them anyway. + + bool bIsServer = GEngine->GetNetMode(OwningComponent->GetWorld()) == ENetMode::NM_DedicatedServer; + } + } + + } + //right place ? + Params.GetSpec().OnApplied(); + + FAFEventData EventData; + const FGameplayTagContainer& AppliedEvents = InProperty.GetSpec()->AppliedEventTags; + for(const FGameplayTag& Event : AppliedEvents) + OwningComponent->TriggerAppliedEvent(Event, EventData); + + FGAEffectContext& InContext = Params.GetContext(); + TArray& Effects = InProperty.GetSpec()->IfHaveTagEffect.Effects; + for (FAFConditionalEffect& Effect : Effects) + { + if (Effect.RequiredTag.IsValid() + && InContext.GetTargetEffectsComponent()->HasTag(Effect.RequiredTag)) + { + //Hack. We need a way store handles for conditional effects. + FAFPropertytHandle PropertyNew(Effect.Effect); + FGAEffectHandle Handle; + Handle = UGABlueprintLibrary::ApplyEffect(PropertyNew + , Handle + , InContext.Target.Get() + , InContext.Instigator.Get() + , InContext.Causer.Get() + , InContext.HitResult); + } + } + + + return Handle; + +} + +TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectProperty& InProperty +, const FGAEffectContext& InContext) +{ + TSet Handles; + UGAGameEffectSpec* Spec = InProperty.GetSpec(); + EGAEffectAggregation Aggregation = Spec->EffectAggregation; + UClass* EffectClass = Spec->GetClass(); + + switch (Aggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + UAFAbilityComponent* Instigator = InContext.InstigatorComp.Get(); + TMap>* EffectByClassMap = InstigatorEffectByClass.Find(Instigator); + //TSet* EffectByClass; + if (EffectByClassMap) + { + return EffectByClassMap->FindRef(EffectClass); + } + + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + UAFAbilityComponent* Target = InContext.TargetComp.Get(); + TSet* TargetEffect = TargetEffectByClass.Find(EffectClass); + if (TargetEffect) + { + return *TargetEffect; + } + break; + } + default: + break; + } + return Handles; +} + +void FGAEffectContainer::AddEffect( + const FGAEffectHandle& InHandle + , const FAFPredictionHandle& InPredHandle + , FGAEffect* InEffect + , const FGAEffectProperty& InProperty + , bool bInfinite) +{ + HandleByPrediction.Add(InPredHandle, InHandle); + PredictionByHandle.Add(InHandle, InPredHandle); + PredictedEffectInfos.Add(InPredHandle, InEffect); + UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UClass* SpecClass = Spec->GetClass(); + FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); + + TSet& Effects = EffectByAttribute.FindOrAdd(Spec->AtributeModifier.Attribute); + Effects.Add(InHandle); + + FObjectKey EffectKey(SpecClass); + TArray& EffectClass = EffectByClass.FindOrAdd(EffectKey); + EffectClass.Add(InHandle); + + switch (Spec->EffectAggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + TMap>& InstEffectClass = InstigatorEffectByClass.FindOrAdd(Context.Instigator.Get()); + TSet& EffectClass2 = InstEffectClass.FindOrAdd(SpecClass); + EffectClass2.Add(InHandle); + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + TSet& EffectClass = TargetEffectByClass.FindOrAdd(SpecClass); + EffectClass.Add(InHandle); + break; + } + } + + ActiveEffects.Add(InHandle, InEffect); + FGAEffectContainer* sss = this; + int dbg = 0; +} + +void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty) +{ + RemoveEffectInternal(InProperty, InHandle); +} + +TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num) +{ + UGAGameEffectSpec* Spec = HandleIn.GetSpec(); + EGAEffectAggregation Aggregation = Spec->EffectAggregation; + FObjectKey key(HandleIn.GetClass()); + TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); + FGAEffectContainer* sss = this; + if (!handles) + return TArray(); + TArray copy = *handles; + + for (int32 idx = 0; idx < Num; idx++) + { + if (handles->IsValidIndex(0)) + { + FGAEffectHandle OutHandle = (*handles)[idx]; + RemoveEffectInternal(HandleIn, OutHandle); + const_cast(HandleIn).CleanUp(OutHandle); + } + } + + + + return copy; +} + +bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) +{ + if (ActiveEffects.Contains(HandleIn)) + { + return true; + } + return false; +} +bool FGAEffectContainer::IsEffectActive(const FGAEffectHandle& HandleIn) const +{ + if (ActiveEffects.Contains(HandleIn)) + { + return true; + } + return false; +} +bool FGAEffectContainer::ContainsEffectOfClass(const FAFPropertytHandle& InProperty) +{ + FObjectKey key(InProperty.GetClass()); + if (EffectByClass.Contains(key)) + { + return true; + } + return false; +} + +void FGAEffectContainer::ApplyFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle, FGAEffect* InEffect) +{ + //AddEffect(InHandle, InPredHandle, InEffect); +} +void FGAEffectContainer::RemoveFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle) +{ + //FGAEffect* Effect = ActiveEffects[InHandle]; + //APawn* Instigator = Effect->GetContext().Instigator.Get(); + //UObject* Target = Effect->GetContext().Target.Get(); + + //HandleByPrediction.Remove(InPredHandle); + //PredictionByHandle.Remove(InHandle); + //PredictedEffectInfos.Remove(InPredHandle); + + //FGAAttribute Attribute = Effect->GetEffect()->AtributeModifier.Attribute; + + //TSet* Effects = EffectByAttribute.Find(Attribute); + //if (Effects) + //{ + // Effects->Remove(InHandle); + // if (Effects->Num() == 0) + // { + // EffectByAttribute.Remove(Attribute); + // } + //} + + //FObjectKey EffectKey(Effect->GameEffectClass); + //TArray* EffectClass = EffectByClass.Find(EffectKey); + //if (EffectClass) + //{ + // EffectClass->Remove(InHandle); + // if (EffectClass->Num() == 0) + // { + // EffectByClass.Remove(EffectKey); + // } + //} + + //switch (Effect->GetEffect()->EffectAggregation) + //{ + //case EGAEffectAggregation::AggregateByInstigator: + //{ + // TMap>* InstEffectClass = InstigatorEffectByClass.Find(Instigator); + // if (InstEffectClass) + // { + // TSet* EffectClass2 = InstEffectClass->Find(Effect->GameEffectClass); + // if (EffectClass2) + // { + // EffectClass2->Remove(InHandle); + // if (EffectClass2->Num() == 0) + // { + // InstEffectClass->Remove(Effect->GameEffectClass); + // } + // } + // if (InstEffectClass->Num() == 0) + // { + // InstigatorEffectByClass.Remove(Instigator); + // } + // } + // + // break; + //} + //case EGAEffectAggregation::AggregateByTarget: + //{ + // TSet* EffectClass2 = TargetEffectByClass.Find(Effect->GameEffectClass); + // if (EffectClass2) + // { + // EffectClass2->Remove(InHandle); + // if (EffectClass2->Num() == 0) + // { + // TargetEffectByClass.Remove(Effect->GameEffectClass); + // } + // } + // break; + //} + //} +} +UWorld* FGAEffectContainer::GetWorld() const +{ + if (OwningComponent) + { + return OwningComponent->GetWorld(); + } + return nullptr; +} + +UGAGameEffectSpec::UGAGameEffectSpec() +{ + ExecutionType = UGAEffectExecution::StaticClass(); + ApplicationRequirement = UAFEffectApplicationRequirement::StaticClass(); + Application = UAFEffectCustomApplication::StaticClass(); +} + +float FGAEffectContainer::GetRemainingTime(const FGAEffectHandle& InHandle) const +{ + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) + { + const FGAEffect* Ptr = *Effect; + float Duration = Ptr->GetDurationTime(); + return FMath::Clamp(Duration - Ptr->GetCurrentDuration(), 0, Duration); + } + return 0; +} +float FGAEffectContainer::GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const +{ + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) + { + const FGAEffect* Ptr = *Effect; + float CurrentDuration = Ptr->GetCurrentDuration(); + float MaxDuration = Ptr->GetDurationTime(); + + float CurrentTime = ((CurrentDuration / MaxDuration) - 1) * (-1); + + return CurrentTime;// FMath::Clamp(CurrentTime, 1, 0); + } + return 0; +} +float FGAEffectContainer::GetCurrentTime(const FGAEffectHandle& InHandle) const +{ + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) + { + const FGAEffect* Ptr = *Effect; + return Ptr->GetCurrentDuration(); + } + return 0; +} +float FGAEffectContainer::GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const +{ + const FGAEffect* const * Effect = ActiveEffects.Find(InHandle); + if (Effect) + { + const FGAEffect* Ptr = *Effect; + float CurrentDuration = Ptr->GetCurrentDuration(); + float MaxDuration = Ptr->GetDurationTime(); + return CurrentDuration * 1 / MaxDuration; + } + return 0; +} +float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const +{ + return 0; +} + +void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle) +{ + FGAEffect* Effect = ActiveEffects[InHandle]; + UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UClass* SpecClass = Spec->GetClass(); + FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); + + FTimerManager& DurationTimer = Context.TargetComp->GetWorld()->GetTimerManager(); + DurationTimer.ClearTimer(Effect->DurationTimerHandle); + DurationTimer.ClearTimer(Effect->PeriodTimerHandle); + + APawn* Instigator = Context.Instigator.Get(); + UObject* Target = Context.Target.Get(); + FAFPredictionHandle PredHandle = PredictionByHandle[InHandle]; + + HandleByPrediction.Remove(PredHandle); + PredictionByHandle.Remove(InHandle); + PredictedEffectInfos.Remove(PredHandle); + + FGAAttribute Attribute = Spec->AtributeModifier.Attribute; + EGAAttributeMod AttributeMod = Spec->AtributeModifier.AttributeMod;; + + TSet* Effects = EffectByAttribute.Find(Spec->AtributeModifier.Attribute); + if (Effects) + { + IAFAbilityInterface* Target = Context.TargetInterface; + Target->RemoveBonus(Attribute, InHandle, AttributeMod); + Effects->Remove(InHandle); + if (Effects->Num() == 0) + { + EffectByAttribute.Remove(Spec->AtributeModifier.Attribute); + } + } + + FObjectKey EffectKey(SpecClass); + TArray* EffectClass = EffectByClass.Find(EffectKey); + if (EffectClass) + { + EffectClass->Remove(InHandle); + if (EffectClass->Num() == 0) + { + EffectByClass.Remove(EffectKey); + } + } + + switch (Spec->EffectAggregation) + { + case EGAEffectAggregation::AggregateByInstigator: + { + TMap>* InstEffectClass = InstigatorEffectByClass.Find(Instigator); + if (InstEffectClass) + { + TSet* EffectClass2 = InstEffectClass->Find(SpecClass); + if (EffectClass2) + { + EffectClass2->Remove(InHandle); + if (EffectClass2->Num() == 0) + { + InstEffectClass->Remove(SpecClass); + } + } + if (InstEffectClass->Num() == 0) + { + InstigatorEffectByClass.Remove(Instigator); + } + } + + break; + } + case EGAEffectAggregation::AggregateByTarget: + { + TSet* EffectClass2 = TargetEffectByClass.Find(SpecClass); + if (EffectClass2) + { + EffectClass2->Remove(InHandle); + if (EffectClass2->Num() == 0) + { + TargetEffectByClass.Remove(SpecClass); + } + } + break; + } + } + ActiveEffects.Remove(InHandle); +} + +bool FGAEffectContainer::IsEffectActive(TSubclassOf EffectClass) +{ + FObjectKey EffectKey(EffectClass); + if (EffectByClass.Contains(EffectKey)) + { + return true; + } + return false; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp new file mode 100644 index 0000000..ff8bdb1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp @@ -0,0 +1,353 @@ +#pragma once +#include "AbilityFramework.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "GameplayTagContainer.h" +#include "AFAbilityComponent.h" +#include "Attributes/GAAttributeBase.h" +#include "Effects/GAEffectExecution.h" +#include "AFAbilityInterface.h" +#include "Effects/GACustomCalculation.h" + +void AddLogDebugInfo(FString Text, UWorld* World) +{ + bool bIsServer = GEngine->GetNetMode(World) == ENetMode::NM_DedicatedServer; + UE_LOG(AbilityFramework, Log, TEXT("%s :: %s"), bIsServer ? TEXT("Server") : TEXT("Client"), *Text); +} + +FGAEffectContext::FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, + const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, + TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, + TWeakObjectPtr TargetCompIn, + TWeakObjectPtr InstigatorCompIn, + TWeakObjectPtr InAvatar) + : TargetHitLocation(TargetHitLocationIn), + TargetAttributes(TargetAttributesIn), + InstigatorAttributes(InstigatorAttributesIn), + Target(TargetIn), + Causer(CauserIn), + Instigator(InstigatorIn), + Avatar(InAvatar), + TargetComp(TargetCompIn), + InstigatorComp(InstigatorCompIn) +{ + TargetInterface = Cast(TargetIn.Get()); + InstigatorInterface = Cast(Instigator.Get()); + IAFAbilityInterface* CauserInterface = Cast(Causer.Get()); +} +void FGAEffectContext::SetTarget(UObject* NewTarget) +{ + IAFAbilityInterface* ATI = Cast(NewTarget); + if (!ATI) + { + return; + } + + TargetComp = ATI->GetAbilityComp(); + Target = NewTarget; + TargetInterface = ATI; + TargetAttributes = ATI->GetAttributes(); +} +FGAEffectHandle::FGAEffectHandle() + : Handle(0) +{ + Handle = 0; +} +FGAEffectHandle::FGAEffectHandle(uint32 HandleIn) + : Handle(HandleIn) +{ +} +void FGAEffectHandle::PostScriptConstruct() +{ + Handle = 0; +} +FGAEffectHandle::~FGAEffectHandle() +{ +} + +/* Executes effect trough provided execution class. */ + +FGAEffectHandle FGAEffectHandle::GenerateHandle() +{ + static int32 Handle; + Handle++; + return FGAEffectHandle(Handle); +} + +bool FGAEffectHandle::IsValid() const +{ + return (Handle > 0);// && EffectPtr->Context.IsValid(); +} +void FGAEffectHandle::Reset() +{ + Handle = 0; +} + +FAFPredictionHandle FAFPredictionHandle::GenerateClientHandle(UAFAbilityComponent* InComponent) +{ + if (InComponent->GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + static uint32 Counter = 1; + Counter++; + FAFPredictionHandle Handle; + Handle.Handle = Counter; + return Handle; + } + return FAFPredictionHandle(); +} + +FGAHashedGameplayTagContainer::FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn) + : Tags(TagsIn) +{ + GenerateFNameKey(); +} +void FGAHashedGameplayTagContainer::GenerateFNameKey() +{ + FString RetString; + for (const FGameplayTag& tag : Tags) + { + RetString += TEXT("."); + RetString += tag.ToString(); + RetString += TEXT("."); + } + Key = *RetString; +} + +void FGAEffectContext::operator=(const FGAEffectContext& Other) +{ + HitResult = Other.HitResult; + TargetHitLocation = Other.TargetHitLocation; + TargetAttributes = Other.TargetAttributes; + InstigatorAttributes = Other.InstigatorAttributes; + Target = Other.Target; + Causer = Other.Causer; + Instigator = Other.Instigator; + Avatar = Other.Avatar; + TargetComp = Other.TargetComp; + InstigatorComp = Other.InstigatorComp; + TargetInterface = Other.TargetInterface; + InstigatorInterface = Other.InstigatorInterface; +} +FGAEffectContext::FGAEffectContext(const FGAEffectContext& Other) +{ + HitResult = Other.HitResult; + TargetHitLocation = Other.TargetHitLocation; + TargetAttributes = Other.TargetAttributes; + InstigatorAttributes = Other.InstigatorAttributes; + Target = Other.Target; + Causer = Other.Causer; + Instigator = Other.Instigator; + Avatar = Other.Avatar; + TargetComp = Other.TargetComp; + InstigatorComp = Other.InstigatorComp; + TargetInterface = Other.TargetInterface; + InstigatorInterface = Other.InstigatorInterface; +} +void FGAEffectContext::Reset() +{ + Target.Reset(); + Causer.Reset(); + Instigator.Reset(); + TargetComp.Reset(); + InstigatorComp.Reset(); + TargetInterface = nullptr; + InstigatorInterface = nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() +{ + if (TargetAttributes.IsValid()) + return TargetAttributes.Get(); + else + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() +{ + if(InstigatorComp.IsValid()) + return InstigatorComp->DefaultAttributes; + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() +{ + IAFAbilityInterface* AttrInt = Cast(Causer.Get()); + if (AttrInt) + { + return AttrInt->GetAttributes(); + } + return nullptr; +} + +class UGAAttributesBase* FGAEffectContext::GetTargetAttributes() const +{ + if (TargetAttributes.IsValid()) + return TargetAttributes.Get(); + else + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetInstigatorAttributes() const +{ + if (InstigatorComp.IsValid()) + return InstigatorComp->DefaultAttributes; + return nullptr; +} +class UGAAttributesBase* FGAEffectContext::GetCauserAttributes() const +{ + IAFAbilityInterface* AttrInt = Cast(Causer.Get()); + if (AttrInt) + { + return AttrInt->GetAttributes(); + } + return nullptr; +} + +class UAFEffectsComponent* FGAEffectContext::GetTargetEffectsComponent() +{ + IAFAbilityInterface* AttrInt = Cast(Target.Get()); + if (AttrInt) + { + return AttrInt->GetEffectsComponent(); + } + return nullptr; +} + +class UAFEffectsComponent* FGAEffectContext::GetTargetEffectsComponent() const +{ + IAFAbilityInterface* AttrInt = Cast(Target.Get()); + if (AttrInt) + { + return AttrInt->GetEffectsComponent(); + } + return nullptr; +} + +FGAEffectContext::~FGAEffectContext() +{ + Target.Reset(); + Causer.Reset(); + Instigator.Reset(); + TargetComp.Reset(); + InstigatorComp.Reset(); +} + +void FGACountedTagContainer::AddTag(const FGameplayTag& TagIn) +{ + int32& count = CountedTags.FindOrAdd(TagIn); + //if (count) + //{ + // *count += 1; + // return; + //} + count++; + //CountedTags.Add(TagIn, 1); + AllTags.AddTag(TagIn); +} +void FGACountedTagContainer::AddTagContainer(const FGameplayTagContainer& TagsIn) +{ + for (auto TagIt = TagsIn.CreateConstIterator(); TagIt; ++TagIt) + { + int32* count = CountedTags.Find(*TagIt); + if (count) + { + *count += 1; + } + else + { + CountedTags.Add(*TagIt, 1); + AllTags.AddTag(*TagIt); + } + } +} +void FGACountedTagContainer::RemoveTag(const FGameplayTag& TagIn) +{ + int32* count = CountedTags.Find(TagIn); + if (count) + { + *count -= 1; + if (*count <= 0) + { + CountedTags.Remove(TagIn); + AllTags.RemoveTag(TagIn); + } + } +} +void FGACountedTagContainer::RemoveTagContainer(const FGameplayTagContainer& TagsIn) +{ + for (auto TagIt = TagsIn.CreateConstIterator(); TagIt; ++TagIt) + { + int32* count = CountedTags.Find(*TagIt); + if (count) + { + *count -= 1; + } + if (*count <= 0) + { + CountedTags.Remove(*TagIt); + AllTags.RemoveTag(*TagIt); + } + } +} +bool FGACountedTagContainer::HasTag(const FGameplayTag& TagIn) +{ + return AllTags.HasTag(TagIn); +} +bool FGACountedTagContainer::HasTagExact(const FGameplayTag TagIn) +{ + return AllTags.HasTagExact(TagIn); +} +bool FGACountedTagContainer::HasAny(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAny(TagsIn); +} +bool FGACountedTagContainer::HasAnyExact(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAnyExact(TagsIn); +} +bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAll(TagsIn); +} +bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) +{ + return AllTags.HasAllExact(TagsIn); +} + +bool FGACountedTagContainer::HasTag(const FGameplayTag& TagIn) const +{ + return AllTags.HasTag(TagIn); +} +bool FGACountedTagContainer::HasTagExact(const FGameplayTag TagIn) const +{ + return AllTags.HasTagExact(TagIn); +} +bool FGACountedTagContainer::HasAny(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAny(TagsIn); +} +bool FGACountedTagContainer::HasAnyExact(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAnyExact(TagsIn); +} +bool FGACountedTagContainer::HasAll(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAll(TagsIn); +} +bool FGACountedTagContainer::HasAllExact(const FGameplayTagContainer& TagsIn) const +{ + return AllTags.HasAllExact(TagsIn); +} + +FAFCueHandle FAFCueHandle::GenerateHandle() +{ + static uint32 HandleIndex = 0; + HandleIndex++; + + FAFCueHandle NewHandle(HandleIndex); + + return NewHandle; +} + +FGAEffectCueParams::FGAEffectCueParams(const FGAEffectContext& InContext, const struct FGAEffectProperty& InProperty) + : HitResult(InContext.HitResult) + , Instigator(InContext.Instigator) + , Causer(InContext.Causer) + , CueTags(InProperty.GetSpec()->Cues.CueTags) +{}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAHelperTemplates.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAHelperTemplates.cpp new file mode 100644 index 0000000..0451e0e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAHelperTemplates.cpp @@ -0,0 +1,5 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAHelperTemplates.h" + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAPhysicalMaterial.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAPhysicalMaterial.cpp new file mode 100644 index 0000000..05718f4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAPhysicalMaterial.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAPhysicalMaterial.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAUIData.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAUIData.cpp new file mode 100644 index 0000000..6e90d29 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAUIData.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "GAUIData.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFLatentInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFLatentInterface.cpp new file mode 100644 index 0000000..abdf620 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFLatentInterface.cpp @@ -0,0 +1,8 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFLatentInterface.h" +UAFLatentInterface::UAFLatentInterface(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskBase.cpp new file mode 100644 index 0000000..7b0fce9 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskBase.cpp @@ -0,0 +1,100 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFLatentInterface.h" + +#include "AFTaskBase.h" + +void FGALatentFunctionTick::ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) +{ + if (Target && !Target->IsPendingKillOrUnreachable()) + { + FScopeCycleCounterUObject ActorScope(Target); + Target->TickTask(DeltaTime, TickType, *this); + } +} + +FString FGALatentFunctionTick::DiagnosticMessage() +{ + return Target->GetFullName() + TEXT("[TickAction]"); +} + +UAFTaskBase::UAFTaskBase(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + TickFunction.TickGroup = TG_PrePhysics; + // Default to no tick function, but if we set 'never ticks' to false (so there is a tick function) it is enabled by default + TickFunction.bCanEverTick = false; + TickFunction.bStartWithTickEnabled = true; + TickFunction.bAllowTickOnDedicatedServer = true; + TickFunction.bRunOnAnyThread = true; + + TickFunction.SetTickFunctionEnable(true); + SetFlags(RF_StrongRefOnFrame); + TaskState = EState::Waiting; +} + +void UAFTaskBase::Initialize() +{ + if (GetWorld()) + { + TickFunction.Target = this; + ULevel* level = GetWorld()->GetCurrentLevel(); + if (level) + { + TickFunction.RegisterTickFunction(level); + } + } +} + +void UAFTaskBase::ReadyForActivation() +{ + if (TaskOwner) + { + if (TaskState != EState::Active) + { + TaskState = EState::Active; + Activate(); + Cast(TaskOwner)->OnLatentTaskActivated(this); + } + + } + else + { + EndTask(); + } +} + +void UAFTaskBase::EndTask() +{ + if (TickFunction.bCanEverTick && TickFunction.IsTickFunctionRegistered()) + { + TickFunction.UnRegisterTickFunction(); + TickFunction.SetTickFunctionEnable(false); + } + OnTaskEnded(); + Cast(TaskOwner)->OnLatentTaskDeactivated(this); + TaskState = EState::Finished; + //MarkPendingKill(); +} +void UAFTaskBase::BeginDestroy() +{ + Super::BeginDestroy(); +} + +bool UAFTaskBase::IsNameStableForNetworking() const +{ + return false; +} +void UAFTaskBase::SetNetAddressable() +{ + +} +UWorld* UAFTaskBase::GetWorld() const +{ + if (TaskOwner) + { + return TaskOwner->GetWorld(); + } + return nullptr; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskManager.cpp new file mode 100644 index 0000000..10382b4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/AFTaskManager.cpp @@ -0,0 +1,25 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "AFTaskManager.h" + +UAFTaskManager* UAFTaskManager::Instance = nullptr; + +UAFTaskManager::UAFTaskManager(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UAFTaskManager* UAFTaskManager::Get() +{ + if (Instance) + { + return Instance; + } + else + { + Instance = NewObject(); + Instance->AddToRoot(); + return Instance; + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/GAWaitAction.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/GAWaitAction.cpp new file mode 100644 index 0000000..be34c49 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/LatentActions/GAWaitAction.cpp @@ -0,0 +1,51 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFramework.h" +#include "GAWaitAction.h" + +UGAWaitAction::UGAWaitAction(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + TickFunction.bCanEverTick = true; + TickFunction.bStartWithTickEnabled = true; + TickFunction.bAllowTickOnDedicatedServer = true; + TickFunction.bRunOnAnyThread = true; + SetFlags(RF_StrongRefOnFrame); +} + +UGAWaitAction* UGAWaitAction::NewGAWaitAction(UObject* InTaskOwner, float Time) +{ + UGAWaitAction* MyTask = nullptr;/*NewTask(InTaskOwner, InTaskOwner); + if (MyTask) + { + MyTask->Time = Time; + }*/ + return MyTask; +} + +void UGAWaitAction::Activate() +{ + OnInitialized.Broadcast(); + if (GEngine) + { + GEngine->AddOnScreenDebugMessage(0, 1, FColor::Red, FString("ObjectName: ") + GetName()); + } + if (TaskOwner && TaskOwner->GetWorld()) + { + UWorld* World = TaskOwner->GetWorld(); + TimeStarted = World->GetTimeSeconds(); + + // Use a dummy timer handle as we don't need to store it for later but we don't need to look for something to clear + FTimerHandle TimerHandle; + World->GetTimerManager().SetTimer(TimerHandle, this, &UGAWaitAction::OnTimeFinish, Time, false); + } +} +void UGAWaitAction::TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) +{ + OnTick.Broadcast(); +}; +void UGAWaitAction::OnTimeFinish() +{ + OnFinish.Broadcast(); + EndTask(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Mods/GAAttributeMod.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Mods/GAAttributeMod.cpp new file mode 100644 index 0000000..8069c17 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Mods/GAAttributeMod.cpp @@ -0,0 +1,11 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "GAGlobalTypes.h" +#include "GAAttributeMod.h" + +UGAAttributeMod::UGAAttributeMod(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h new file mode 100644 index 0000000..30f8ae0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -0,0 +1,613 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "GameplayTags.h" +#include "AFAbilityTypes.h" + +#include "Attributes/GAAttributeBase.h" +#include "Attributes/GAAttributesBase.h" +#include "Effects/GAEffectCueGlobals.h" + +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" + +#include "GameplayTagAssetInterface.h" + +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" + +#include "AFAbilityComponent.generated.h" + +DECLARE_STATS_GROUP(TEXT("AttributeComponent"), STATGROUP_AttributeComponent, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentApplyEffect"), STAT_ApplyEffect, STATGROUP_AttributeComponent, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("AttributeComponentModifyAttribute"), STAT_ModifyAttribute, STATGROUP_AttributeComponent, ); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAOnAttributeChanged); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGAOnAttributeModifed, const FAFAttributeChangedData&, Mod); + +DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); + + +DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); + +DECLARE_DELEGATE(FAFOnAbilityReady); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); +DECLARE_DELEGATE(FAFGenericAttributeDelegate); + + +//UAFAssetManager* GetAssetManager() +//{ +// return Cast(UAssetManager::GetIfValid()); +//}; + +USTRUCT() +struct FGAModifiedAttributeData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + TArray Mods; + UPROPERTY() + int32 ForceUpdate; + + FGAModifiedAttributeData() + : ForceUpdate(0) + {} +}; + +USTRUCT(BlueprintType) +struct FGAEffectUIData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "UI") + float RemainingTime; + + FGAEffectUIData() + : RemainingTime(0) + {}; +}; +struct FGAContextSetup +{ +public: + UGAAttributesBase* IntigatorAttributes; + UGAAttributesBase* TargetAttributes; + UAFAbilityComponent* InstigatorComp; + UAFAbilityComponent* TargetComp; + + FGAContextSetup() + {}; + FGAContextSetup(UGAAttributesBase* IntigatorAttributesIn, UGAAttributesBase* TargetAttributesIn, + UAFAbilityComponent* InstigatorCompIn, UAFAbilityComponent* TargetCompIn) + : IntigatorAttributes(IntigatorAttributesIn), + TargetAttributes(TargetAttributesIn), + InstigatorComp(InstigatorCompIn), + TargetComp(TargetCompIn) + {}; +}; +DECLARE_MULTICAST_DELEGATE_TwoParams(FGASOnActiveAbilityAdded, int32, int32); +DECLARE_DELEGATE_TwoParams(FAFMontageGenericDelegate, const FGameplayTag&, const FName&); +/* TODO:: Implement fast serialization for structs. */ +/* TODO:: REmove all those structs for customization and replace it with something sane like tmap. */ +/**/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGASMontageRepData +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + UAnimMontage* CurrentMontage; + + UPROPERTY() + FName SectionName; + + UPROPERTY() + uint8 ForceRep; +}; + +USTRUCT() +struct FAFReplicatedAttributeItem : public FFastArraySerializerItem +{ + GENERATED_BODY() +public: + UPROPERTY() + FGameplayTag AttributeTag; + UPROPERTY() + UGAAttributesBase* Attributes; + + void PreReplicatedRemove(const struct FAFReplicatedAttributeContainer& InArraySerializer); + void PostReplicatedAdd(const struct FAFReplicatedAttributeContainer& InArraySerializer); + void PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer); +}; + +USTRUCT() +struct FAFReplicatedAttributeContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + UPROPERTY() + TArray Attributes; + + UPROPERTY() + TMap AttributeMap; + + + TMap AttributeReplicatedEvent; + + void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FSimpleDelegate& InDelegate) + { + if (!AttributeReplicatedEvent.Contains(InTag)) + return; + + AttributeReplicatedEvent.Add(InTag, InDelegate); + } + + void OnAttributeReplicated(const FGameplayTag& InTag) const + { + if (const FSimpleDelegate* Delegate = AttributeReplicatedEvent.Find(InTag)) + { + Delegate->Execute(); + //AttributeReplicatedEvent.Remove(InTag); + } + } + + UGAAttributesBase* Add(const FGameplayTag InTag, UGAAttributesBase* InAttributes, class UAFAbilityComponent* InOuter); + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(Attributes, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FAFReplicatedAttributeContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAbilityActionSet +{ + GENERATED_BODY() +public: + UPROPERTY() + TSoftClassPtr AbilityTag; + UPROPERTY() + TArray AbilityInputs; +}; + +UCLASS(hidecategories = (Object, LOD, Lighting, Transform, Sockets, TextureStreaming), editinlinenew, meta = (BlueprintSpawnableComponent)) +class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public IGameplayTagAssetInterface +{ + GENERATED_BODY() + /* Attributes handling */ +public: + //Only for base testing and prototyping cue application. + //will be removed when Cue Manager will be more functional. + + //FAFEffectTimerManager EffectTimerManager; + + UPROPERTY(EditAnywhere, Category = "Test") + FGameplayTag TagTest; + /* + Set attribute which will be considered for indicating whether or not actor is dead. + */ + UPROPERTY(EditAnywhere, Category = "Config") + FGAAttribute DeathAttribute; + + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray AbilityInputs; + + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DefaultTags; + + UPROPERTY() + FGACountedTagContainer AppliedTags; + + UPROPERTY() + FGACountedTagContainer ImmunityTags; + + UFUNCTION() + void OnRep_ActiveEffects(); + + UPROPERTY(ReplicatedUsing = OnRep_ActiveCues) + FGameCueContainer ActiveCues; + UFUNCTION() + void OnRep_ActiveCues(); + /* + Could make it array. But realistically. How many times do you really need more, than one + attribute set for actor ? + + Of course array of attributes would allow to compose attributes from small discreete + attribute sets. On the other hand similiar funcionality can be achieved by using + inheritance. + + And I think that using inheritance in this case will be easier. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Replicated) + class UGAAttributesBase* DefaultAttributes; + + //probabaly replace FGameplayTag with FObjectKey + TMap AdditionalAttributes; + + UPROPERTY(Replicated) + FAFReplicatedAttributeContainer RepAttributes; + + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnAttributeModifed; + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed OnTargetAttributeModifed; + + + TMap AttributeChanged; + + + void BroadcastAttributeChange(const FGAAttribute& InAttribute, + const FAFAttributeChangedData& InData); + + UFUNCTION() + void OnRep_GameEffectContainer(); + + template + T* GetAttributes() + { + return CastChecked(DefaultAttributes); + } + + template + T* GetAttributeSet(FGameplayTag InOwner) + { + UGAAttributesBase* AttributeSet = AdditionalAttributes.FindRef(InOwner); + return Cast(AttributeSet); + } + UGAAttributesBase* AddAddtionalAttributes(FGameplayTag InOwner, UGAAttributesBase* InAttributes) + { + if (!InAttributes) + return nullptr; + UGAAttributesBase* retVal = RepAttributes.Add(InOwner, InAttributes, this); + RepAttributes.MarkArrayDirty(); + + return retVal; + } + UFUNCTION(BlueprintCallable, Category = "Test") + void GetAttributeStructTest(FGAAttribute Name); + + /** UActorComponent Interface - Begin */ + virtual void BeginPlay() override; + virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; + virtual void DestroyComponent(bool bPromoteChildren = false) override; + virtual void InitializeComponent() override; + virtual void UninitializeComponent() override; + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + /* UActorComponent Interface - End **/ +public: + ///////////////////////////////////////////////// + //////////// ATTRIBUTES HANDLING + + /* + Two functions, They will allow to apply any static numerical mods from player who + initiated attribute change, and from player who will be affected by change. + + Mods will be appiled by small objects, and changed against tags. + For example there might be physical armor mod, which will apply changes only + to attributes tagged as Damage.Physical and only if you are reciving change, not causing it. + */ + + inline float GetFinalAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetFinalAttributeValue(Name); + } + inline float GetCurrentAttributeValue(const FGAAttribute& Name) + { + return DefaultAttributes->GetCurrentAttributeValue(Name); + } + //////////// ATTRIBUTES HANDLING + ///////////////////////////////////////////////// + /* + Attribute replication. + */ + void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle, UGAAttributesBase* InAttributeSet); + //Helper functions: +public: + /* + IGameplayTagAssetInterface Start + */ + /** + * Get any owned gameplay tags on the asset + * + * @param OutTags [OUT] Set of tags on the asset + */ + UFUNCTION(BlueprintCallable, Category = GameplayTags) + virtual void GetOwnedGameplayTags(FGameplayTagContainer& TagContainer) const override; + + /* + IGameplayTagAssetInterface End + */ + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + class UGAAttributesBase* GetAttributes() { return DefaultAttributes; }; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; + + void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, + const FGAEffectContext& InContext); + FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; + float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + +private: + class IAFAbilityInterface* AttributeInterface; + +public: + UAFAbilityComponent(const FObjectInitializer& ObjectInitializer); + + UFUNCTION() + void OnRep_InstancedAbilities(); + UPROPERTY(Replicated) + FAFAbilityContainer AbilityContainer; + UPROPERTY() + TArray AbilitiesRefs; + + UPROPERTY() + APlayerController* PCOwner; + + /* Ability which is currently being executed. */ + UPROPERTY(BlueprintReadOnly, Category = "Game Abilities") + class UGAAbilityBase* ExecutingAbility; + + + + /*UFUNCTION(NetMulticast, Reliable) + MulticastExecuteEffect()*/ + + + + + /* + True if player is currently casting/channeling/activating(?) + any ability. + */ + bool bIsAnyAbilityActive; + + //AbilityTag, Delegate + TMap, FAFOnAbilityReady> OnAbilityReadyMap; + + void AddOnAbilityReadyDelegate(const TSoftClassPtr& InAbilityPtr, FAFOnAbilityReady& InDelegate) + { + if(InDelegate.IsBound()) + OnAbilityReadyMap.Add(InAbilityPtr, InDelegate); + } + + void NotifyOnAbilityReady(const TSoftClassPtr& InAbilityPtr) + { + if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityPtr)) + { + Ready->ExecuteIfBound(); + OnAbilityReadyMap.Remove(InAbilityPtr); + } + } + + TMap, FAFOnAbilityReady> OnAbilityInputReadyMap; + + void AddOnAbilityInputReadyDelegate(const TSoftClassPtr& InAbilityPtr, const FAFOnAbilityReady& InDelegate) + { + if(InDelegate.IsBound()) + OnAbilityInputReadyMap.Add(InAbilityPtr, InDelegate); + } + + void NotifyOnAbilityInputReady(const TSoftClassPtr& InAbilityPtr) + { + if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityPtr)) + { + Ready->ExecuteIfBound(); + OnAbilityInputReadyMap.Remove(InAbilityPtr); + } + } + + TMap> OnPreAttributeModifiedMap; + void AddOnPreAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) + { + TArray& delegates = OnPreAttributeModifiedMap.FindOrAdd(InAttribute); + delegates.Add(InDelegate); + } + + void NotifyOnPreAttributeModified(const FGAAttribute& InAttribute) + { + if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) + { + for(const FAFGenericAttributeDelegate& delegate : *Ready) + delegate.ExecuteIfBound(); + } + } + + void RemoveOnPreAttributeModified(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& Delegate) + { + if (TArray* Ready = OnPreAttributeModifiedMap.Find(InAttribute)) + { + //Ready->RemoveSingle(Delegate); + if (Ready->Num() <= 0) + { + OnPreAttributeModifiedMap.Remove(InAttribute); + } + } + } + + TMap> OnPostAttributeModifiedMap; + void AddOnPostAttributeModifiedDelegate(const FGAAttribute& InAttribute, const FAFGenericAttributeDelegate& InDelegate) + { + TArray& delegates = OnPostAttributeModifiedMap.FindOrAdd(InAttribute); + delegates.Add(InDelegate); + } + + void NotifyOnPostAttributeModified(const FGAAttribute& InAttribute) + { + if (TArray* Ready = OnPostAttributeModifiedMap.Find(InAttribute)) + { + for (const FAFGenericAttributeDelegate& delegate : *Ready) + delegate.ExecuteIfBound(); + } + } + + + + FAFOnAbilityReady OnAbilityReady; + + UPROPERTY(BlueprintAssignable, Category = "AbilityFramework") + FAFOnAbilityAdded OnAbilityAdded; + + FAFMontageGenericDelegate OnAbilityNotifyBegin; + FAFMontageGenericDelegate OnAbilityNotifyTick; + FAFMontageGenericDelegate OnAbilityNotifyEnd; + +private: + + + UPROPERTY(ReplicatedUsing=OnRep_PlayMontage) + FGASMontageRepData RepMontage; + UFUNCTION() + void OnRep_PlayMontage(); + +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + UFUNCTION(NetMulticast, Unreliable) + void MulticastPlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); +public: + inline class UGAAbilityBase* GetGASAbility(int32 IndexIn) + { + return nullptr; + } + + TMap BlockedInput; + + + + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); + void BindInputs(class UInputComponent* InputComponent); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") + void BP_BindAbilityToAction(FGameplayTag ActionName); + void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); + + //need to be called on both client and server. + //Change InInputTag To Array, clear previous binds on the same tag. + void SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); + + TSoftClassPtr IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); + +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerSetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); + void ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); + bool ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); +public: + /* Called when ability action has been binded on server. */ + UFUNCTION(Client, Reliable) + void ClientNotifyAbilityInputReady(const TSoftClassPtr& InAbilityPtr); + void ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr); + + + void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); + UFUNCTION(Server, Reliable, WithValidation) + void ServerSetAbilitiesToActions(const TArray& InAbilitiesActions); + void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); + bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); + + void RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr); + UFUNCTION(Server, Reliable, WithValidation) + void ServerRemoveAbilitiesFromActions(const FSoftObjectPath& InAbilityPtr); + void ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr); + bool ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr); + + UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") + void BP_InputPressed(FGameplayTag ActionName); + + void NativeInputPressed(FGameplayTag ActionName); +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + + +public: + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") + void BP_InputReleased(FGameplayTag ActionName); + + void NativeInputReleased(FGameplayTag ActionName); +protected: + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeInputReleased(FGameplayTag ActionName); + virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); + virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); +public: + /* + Finds ability using asset registry and then gives it to component. + Only valid on server. + Does not check if component can or can't have given ability. + So it must be checked before this function is called. + */ + + UFUNCTION(BlueprintCallable, meta=(DisplayName = "Add Ability"), Category = "AbilityFramework|Ability Component") + void BP_AddAbility(TSoftClassPtr InAbility, + TArray InInputTag); + + void NativeAddAbility(TSoftClassPtr InAbility, + const TArray& InInputTag); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeAddAbility(const FSoftObjectPath& InAbility, + const TArray& InInputTag); + + void ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, + const TArray& InInputTag); + + bool ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, + const TArray& InInputTag); + + void OnFinishedLoad(TSoftClassPtr InAbility); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") + void BP_RemoveAbility(TSoftClassPtr TagIn); + + void NativeRemoveAbility(TSoftClassPtr InAbilityTag); + UFUNCTION(Server, Reliable, WithValidation) + void ServerNativeRemoveAbility(const FSoftObjectPath& InAbilityTag); + + void ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag); + + bool ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag); + + //TODO: Make it procted + + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") + UGAAbilityBase* BP_GetAbilityByTag(TSoftClassPtr TagIn); + + + bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; + void GetSubobjectsWithStableNamesForNetworking(TArray& Objs) override; + + void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); +protected: + void InitializeInstancedAbilities(); + UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass + , TSoftClassPtr InClassPtr); + + +public: + /* + Latent Tasks Handling + */ + + UPROPERTY(Replicated) + TArray ReplicatedTasks; +}; + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h new file mode 100644 index 0000000..f5ede8f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h @@ -0,0 +1,75 @@ +#pragma once +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypes.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.generated.h" + + +struct FAFAttributeBase; +struct FGAEffectHandle; +UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) +class ABILITYFRAMEWORK_API UAFAbilityInterface : public UInterface +{ + GENERATED_UINTERFACE_BODY() +}; + +class IAFAbilityInterface +{ + GENERATED_IINTERFACE_BODY() +public: + virtual FVector GetSocketLocation(FName SocketNameIn){ return FVector::ZeroVector; }; + + + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UAFAbilityComponent* GetAbilityComp() = 0; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual class UAFEffectsComponent* GetEffectsComponent() = 0; + + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const = 0; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; + + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, + struct FGAEffectProperty& InProperty) {}; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; + + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; + + virtual void RemoveTagContainer(const FGameplayTagContainer& TagsIn) {}; + //override to allow gathering tags from causer + //those tags will be merged into effect owned tags. + virtual FGameplayTagContainer GetCauserTags() { return FGameplayTagContainer(); } + + virtual FAFPredictionHandle GetPredictionHandle() { return FAFPredictionHandle(); } + + + FGAEffectHandle ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual class UGAAttributesBase* GetAttributes() { return GetAbilityComp()->DefaultAttributes; }; + + template + T* GetAttributesTyped() + { + return Cast(GetAttributes()); + } + template + T* GetComponentTyped() + { + return Cast(GetAbilityComp()); + } + template + T* GetAttributeTyped(FGAAttribute InAttribute) + { + return static_cast(GetAttribute(InAttribute)); + } +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h new file mode 100644 index 0000000..a976afb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h @@ -0,0 +1,109 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "AFAbilityTypes.generated.h" + +class UGAAbilityBase; + +USTRUCT() +struct ABILITYFRAMEWORK_API FAFAbilityItem : public FFastArraySerializerItem +{ + GENERATED_BODY() + +public: + UPROPERTY() + UGAAbilityBase* Ability; + UPROPERTY() + TSoftClassPtr AbilityClass; + + FAFAbilityItem() + {}; + + FAFAbilityItem(UGAAbilityBase* InAbility, TSoftClassPtr InAbilityClass) + : Ability(InAbility) + , AbilityClass(InAbilityClass) + {} + + void PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer); + void PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer); + void PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer); + + const bool operator==(const TSoftClassPtr& OtherAbility) const + { + return AbilityClass == OtherAbility; + } + + const bool operator==(UGAAbilityBase* OtherAbility) const + { + return Ability == OtherAbility; + } + const bool operator==(const FAFAbilityItem& OtherItem) const + { + return Ability == OtherItem.Ability; + } +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + + UPROPERTY() + TArray AbilitiesItems; + + TWeakObjectPtr AbilitiesComp; + TMap BlockedInput; + + TMap, FGameplayTag> AbilityToInput; + + //Custom binding, for server side validation. + + //ActionInput, AbilityClassPtr + TMap> ActionToAbility; + + //AbilityTag, ActionInput + TMap, TArray> AbilityToAction; + + //abilityTag, Ability Ptr + TMap, UGAAbilityBase*> AbilitiesInputs; + + TMap, UGAAbilityBase*> TagToAbility; + + void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn + , TSoftClassPtr InClassPtr); + + void RemoveAbility(const TSoftClassPtr& AbilityIn); + + void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); + void RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr); + TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); + + UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); + + void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); + void HandleInputReleased(FGameplayTag ActionName); + + void TriggerAbylityByTag(TSoftClassPtr InTag); + + bool AbilityExists(TSoftClassPtr InAbiltyPtr) const + { + return AbilityToInput.Contains(InAbiltyPtr); + } + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); + } +}; + +template<> +struct TStructOpsTypeTraits< FAFAbilityContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + }; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeComponent.h new file mode 100644 index 0000000..1140809 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeComponent.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "AFAttributeComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ABILITYFRAMEWORK_API UAFAttributeComponent : public UActorComponent +{ + GENERATED_BODY() + +public: + // Sets default values for this component's properties + UAFAttributeComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFBlueprintFunctionLibrary.h new file mode 100644 index 0000000..700bfb5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFBlueprintFunctionLibrary.h @@ -0,0 +1,17 @@ +#pragma once +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "AFBlueprintFunctionLibrary.generated.h" +/* + Some static helper functions, to interact with Attribute system. +*/ +UCLASS() +class ABILITYFRAMEWORK_API UAFBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + static void TriggerAbilityPressedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + static void TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueInterface.h new file mode 100644 index 0000000..26baa08 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueInterface.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AFCueInterface.generated.h" + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UAFCueInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class ABILITYFRAMEWORK_API IAFCueInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h new file mode 100644 index 0000000..86bb9c7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h @@ -0,0 +1,53 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "GAGlobalTypes.h" +#include "Effects/GAEffectCue.h" +#include "AFCueManager.generated.h" + +/** + * + */ +UCLASS(config = Game) +class ABILITYFRAMEWORK_API UAFCueManager : public UObject +{ + GENERATED_BODY() +protected: + //UPROPERTY() + static UAFCueManager* ManagerInstance; + UWorld* CurrentWorld; + + //store per instigator ? Causer ? or global pool ? + //stores unused instanced cues. + TMap>> InstancedCues; + //store per instigator ? Causer ? + //stores used cues. + TMap>>> UsedCues; + + TMap ActiveCues; + +public: + void Initialize(); +#if WITH_EDITOR + //handle clearing up cache when PIE mode is ending. + void HandleOnPIEEnd(bool InVal); +#endif //WITH_EDITOR + void HandlePreLoadMap(const FString& InMapName); + void HandlePostLoadMap(UWorld* InWorld); +public: + static UAFCueManager* Get(); + void HandleCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); + void HandleExecuteCue(FAFCueHandle InHandle); + void HandleRemoveCue(const FGameplayTagContainer& Tags, + const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); +protected: + void OnFinishedLoad(FGameplayTag InCueTag + , FPrimaryAssetId InPrimaryAssetId + , FGAEffectCueParams CueParams + , FAFCueHandle InHandle); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h new file mode 100644 index 0000000..0a5c7b1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h @@ -0,0 +1,227 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "GameplayTags.h" +#include "GameplayTagAssetInterface.h" + +#include "Attributes/GAAttributeBase.h" +#include "Attributes/GAAttributesBase.h" +#include "Effects/GAEffectCueGlobals.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" + +#include "AFEffectsComponent.generated.h" + +DECLARE_DELEGATE(FAFEffectEvent); +DECLARE_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); + +DECLARE_MULTICAST_DELEGATE_ThreeParams(FAFApplicationDelegate, FAFContextHandle, FAFPropertytHandle, FAFEffectSpecHandle); + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent +{ + GENERATED_BODY() +private: + friend class UGAAbilityBase; + friend class IAFAbilityInterface; + friend class UAFAbilityComponent; + friend class UAFEffectTask_EffectEvent; + +private: + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DefaultTags; + + UPROPERTY(Replicated) + FGACountedTagContainer AppliedTags; + + UPROPERTY(Replicated) + FGACountedTagContainer ImmunityTags; + + UPROPERTY(ReplicatedUsing = OnRep_GameEffectContainer) + FGAEffectContainer GameEffectContainer; + + TMap OnEffectApplyToTarget; + TMap OnEffectApplyToSelf; + TMap> EffectEvents; + + TMap EffectToCue; + + TMap OnEffectEvent; + + TMap> AppliedEvents; + TMap> ExecutedEvents; +public: + FAFApplicationDelegate OnAppliedToTarget; + FAFApplicationDelegate OnAppliedToSelf; + FAFApplicationDelegate OnEffectExecuted; +public: + // Sets default values for this component's properties + UAFEffectsComponent(const FObjectInitializer& ObjectInitializer); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + + /** UActorComponent Interface - Begin */ + virtual void InitializeComponent() override; + /* UActorComponent Interface - End **/ + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + +protected: + + /* + * @call Order: + * Previous Function: UAFAbilityComponent::ApplyEffectToTarget + * Next Function: FGAEffectContainer::ApplyEffect + * Apply target to Me. Try to apply effect to container and launch Events in: + * TMap OnEffectEvent - event is called before application; + * TMap OnEffectApplyToSelf - event is called before application; + * + * @param EffectIn& - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect; + */ + FGAEffectHandle ApplyEffectToSelf( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + /* + * @call Order: + * Previous Function: UGABlueprintLibrary::ApplyEffect + * Next Function: UAFAbilityComponent::ApplyEffectToSelf + * Apply effect to target provided inside Context. + * Try launch events: + * TMap OnEffectApplyToTarget - event is called before application + * + * @param EffectIn& - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect; + */ + FGAEffectHandle ApplyEffectToTarget( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + +public: + /* Have to to copy handle around, because timer delegates do not support references. */ + void ExecuteEffect(FGAEffectHandle HandleIn + , FAFEffectParams Params + , FAFFunctionModifier Modifier); + + virtual void PostExecuteEffect(); + /* ExpireEffect is used to remove existing effect naturally when their time expires. */ +public: + void ExpireEffect(FGAEffectHandle HandleIn + , FAFEffectParams Params); + +protected: + UFUNCTION(Client, Reliable) + void ClientExpireEffect(FAFPredictionHandle PredictionHandle); + void ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle); + + /* RemoveEffect is used to remove effect by force. */ + void RemoveEffect(const FAFPropertytHandle& InProperty + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle); + void InternalRemoveEffect(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext); + + void AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent); + void ExecuteEffectEvent(const FGameplayTag& InEventTag); + void RemoveEffectEvent(const FGameplayTag& InEventTag); + bool IsEffectActive(const FGAEffectHandle& InHandle) const; + +public: + void AddEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); + void RemoveEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); + TArray& GetTagEvent(FGameplayTag TagIn); + void NativeTriggerTagEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + + void AddAppliedEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); + void RemoveAppliedEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); + void TriggerAppliedEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + + + void AddExecuteEvent(const FGameplayTag& EventTag, FAFEventDelegate& EventDelegate); + void RemoveExecuteEvent(const FGameplayTag& EventTag, const FDelegateHandle& EventDelegate); + void TriggerExecuteEvent(FGameplayTag TagIn, const FAFEventData& InEventData); + +public: + bool DenyEffectApplication(const FGameplayTagContainer& InTags); + bool HaveEffectRquiredTags(const FGameplayTagContainer& InTags); +protected: + /* + + */ + UFUNCTION(NetMulticast, Unreliable) + void MulticastApplyEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExecuteEffectCue(FAFCueHandle InHandle); + void MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastRemoveEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + void MulticastRemoveEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + void MulticastUpdateDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdatePeriodCue(FGAEffectHandle EffectHandle, float NewPeriodIn); + void MulticastUpdatePeriodCue_Implementation(FGAEffectHandle EffectHandle, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastUpdateTimersCue(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); + void MulticastUpdateTimersCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn, float NewPeriodIn); + + UFUNCTION(NetMulticast, Unreliable) + void MulticastExtendDurationCue(FGAEffectHandle EffectHandle, float NewDurationIn); + void MulticastExtendDurationCue_Implementation(FGAEffectHandle EffectHandle, float NewDurationIn); +public: + FGAEffect* GetEffect(const FGAEffectHandle& InHandle); + + /* Counted Tag Container Wrapper Start */ + inline void AddTag(const FGameplayTag& TagIn) { AppliedTags.AddTag(TagIn); }; + inline void AddTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.AddTagContainer(TagsIn); }; + inline void RemoveTag(const FGameplayTag& TagIn) { AppliedTags.RemoveTag(TagIn); }; + inline void RemoveTagContainer(const FGameplayTagContainer& TagsIn) { AppliedTags.RemoveTagContainer(TagsIn); }; + inline bool HasTag(const FGameplayTag& TagIn) const { return AppliedTags.HasTag(TagIn); } + inline bool HasTagExact(const FGameplayTag TagIn) const { return AppliedTags.HasTagExact(TagIn); }; + inline bool HasAny(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAny(TagsIn); }; + inline bool HasAnyExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAnyExact(TagsIn); }; + inline bool HasAll(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAll(TagsIn); }; + inline bool HasAllExact(const FGameplayTagContainer& TagsIn) const { return AppliedTags.HasAllExact(TagsIn); }; + inline int32 GetTagCount(const FGameplayTag& TagIn) const { return AppliedTags.GetTagCount(TagIn); } + /* Counted Tag Container Wrapper Start */ + + + /* Game Effect Container WRAPPER */ + bool IsEffectActive(TSubclassOf EffectClass) + { + return GameEffectContainer.IsEffectActive(EffectClass); + } + + /* Game Effect Container WRAPPER */ + + /*Network Functions - BEGIN */ +protected: + UFUNCTION() + void OnRep_GameEffectContainer(); + + /*Network Functions - END */ +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityActivationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityActivationSpec.h new file mode 100644 index 0000000..d9d6bfb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityActivationSpec.h @@ -0,0 +1,21 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityActivationSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityActivationSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() + +public: + UAFAbilityActivationSpec(); + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityCooldownSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityCooldownSpec.h new file mode 100644 index 0000000..238e495 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityCooldownSpec.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityCooldownSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityCooldownSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityCooldownSpec(); + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityInfiniteDurationSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityInfiniteDurationSpec.h new file mode 100644 index 0000000..89b59a2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityInfiniteDurationSpec.h @@ -0,0 +1,21 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityInfiniteDurationSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityInfiniteDurationSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityInfiniteDurationSpec(); + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodSpec.h new file mode 100644 index 0000000..7c6f1eb --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodSpec.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityPeriodSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityPeriodSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityPeriodSpec(); + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodicInfiniteSpec.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodicInfiniteSpec.h new file mode 100644 index 0000000..57158e4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/AFAbilityPeriodicInfiniteSpec.h @@ -0,0 +1,18 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityPeriodicInfiniteSpec.generated.h" + +/** + * + */ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFAbilityPeriodicInfiniteSpec : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: + UAFAbilityPeriodicInfiniteSpec(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h new file mode 100644 index 0000000..91519ad --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h @@ -0,0 +1,622 @@ +#pragma once +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" +#include "GameplayTasksComponent.h" +#include "GameplayTask.h" +#include "GameplayTaskOwnerInterface.h" +#include "Attributes/GAAttributesBase.h" +#include "AFAbilityInterface.h" +#include "AFAbilityActivationSpec.h" +#include "AssetBundleData.h" +#include "SubclassOf.h" +#include "LatentActions/AFLatentInterface.h" + +#include "GAAbilityBase.generated.h" + +/* + TODO:: + 1. Add virtual functions, for default behaviours inside ability. + And figure out some clever names for them. Functions like: + ExecuteAbility() + Possibly default input functions. + The interface for it, is not yet fully determined. + It would be best if the functions and names of them, made sense.. For both AI and player + pawns. + 2. Add linked abilities. I'm not 100% sure if it really should be default functionality, + but the idea is that after first ability is executed, it will automatically set next, ability + for execution in chain, and so on, until last ability. Last ability will, simply back to first. + This can be implement as very simple linked list (though I'm not sure about nice BP workflow), + at ability level, OR it can be implemented at component level as queue. + But, from game design perspective implementation on ability level makes more sense. + + Moar TODO: (idk, if the above is still relevelant). + 1. Add simple tracing directly inside ability. Aside from targeting tasks. + + 2. Add caching for effects, so we don;'t create new ones every time, just reference handle. +*/ +/* + Base class for abilities. It will only implement few generic virtual functions, needed by all + abilities. + + Ability is what actor can do, not nessesarly, how actor will go about doing it. + For example we can have jump ability, which is nothing else, than object encapsulating, + access jump function inside Movement Component. + + This way you can give actors, certain abilities, which they can then used based on + some critera (for example defined in Blackboard and Behaviour tree), and if it is + possible for actor to perform ability, he will do it (though, one must be careful to + give abilities, which can be performed by actors, an ordinary actor, can't jump). + + More complicated abilities, can be actions in their own right. Like spells. + + Abilities are using state machine, combined with effects, to perform actions, like + casting, channeling etc. + It needs to be better explained on how each state makes use of effect parameters (Duration, Period). +*/ +DECLARE_MULTICAST_DELEGATE(FGASSimpleAbilityDynamicDelegate); + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASGenericAbilityDelegate); + +USTRUCT() +struct FGAActiationInfo +{ + GENERATED_USTRUCT_BODY(); + + UPROPERTY() + float TimeStamp; + UPROPERTY() + float Duration; + UPROPERTY() + float Period; + UPROPERTY() + bool bApplyActivationEffect; + + inline void SetActivationInfo(float TimeStampIn, float DurationIn, float PeriodIn, + bool bApplyActivationEffectIn) + { + TimeStamp = TimeStampIn; + Duration = DurationIn; + Period = PeriodIn; + bApplyActivationEffect = bApplyActivationEffectIn; + //always increment to make sure it is replicated. + ForceReplication++; + } + + UPROPERTY() + int8 ForceReplication; +}; + +enum EAFAbilityState +{ + Waiting, + Activating +}; + +UCLASS(BlueprintType, Blueprintable) +class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInterface, public IAFLatentInterface +{ + GENERATED_BODY() +public: + + /* + Since each ability is instanced per owner, and cannot be activated multiple times (ie, to run in background), + we can assume that PredictionHandle will always be unique per activation. + */ + FAFPredictionHandle PredictionHandle; + /* By default all abilities are considered to be replicated. */ + UPROPERTY(EditAnywhere, Category = "Replication") + bool bReplicate; + + bool bIsNameStable; + + //possibly map TMap ? + UPROPERTY() + TSet ActiveTasks; + /* List of tasks, this ability have. */ + UPROPERTY() + TMap AbilityTasks; + + /* + Delegate is used to confirm ability execution. + After confirming ability will proceed to activation state and either casts instatly or start + casting effect. + */ + FGASSimpleAbilityDynamicDelegate OnConfirmDelegate; + /* + Delegate which is called after ability is confirmed and then cast time ended. + */ + FGASSimpleAbilityDynamicDelegate OnConfirmCastingEndedDelegate; + FSimpleDelegate ConfirmDelegate; + + /* Attributes specific to ability. */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "AbilityFramework|Abilities") + UGAAttributesBase* Attributes; + + UPROPERTY() + class UWorld* World; + /* + Replicated to everyone because we will need it, to determine cosmetic stuff on clients. + */ + /* + */ + UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") + APawn* POwner; + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + APlayerController* PCOwner; + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + class AAIController* AICOwner; + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + class UAFAbilityComponent* AbilityComponent; + + /* + Physical reprsentation of ability in game world. It might be sword, gun, or character. + What differs it from pawn or controller is that Avatar is actually used by ability to perform actions. + + It will need some common interfaces for getting data out. + */ + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + class AActor* AvatarActor; + + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UCameraComponent* OwnerCamera; + + FGAEffectContext DefaultContext; + + /* + Tags applied to instigator of this ability, for duration of cooldown. + Duration of this effect equals cooldown of ability. + */ + UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") + FAFPropertytHandle CooldownEffect; + FGAEffectHandle CooldownEffectHandle; + /* + Tags applied to the time of activation ability. + Only applies to abilities, which are not instant (for now). + Though even instant abilities have animation time, + they probabaly never apply activation tags, since + main usecase for those tags is to make other abilities + being able to interrupt them. + All abilities with casting/channeling time use it. + + Add Periodic Effect ? (For abilities with period). + */ + UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") + FAFPropertytHandle ActivationEffect; + FGAEffectHandle ActivationEffectHandle; + + /* + These attributes will be reduced by specified amount when ability is activated. + Attribute cost from Ability Owner attributes + */ + UPROPERTY(EditAnywhere, Category = "Config") + TArray AttributeCost; + TArray AttributeCostHandle; + /* + Attribute cost from ability own attributes + */ + UPROPERTY(EditAnywhere, Category = "Config") + TArray AbilityAttributeCost; + TArray AbilityAttributeCostHandle; + + UPROPERTY(AssetRegistrySearchable) + FName AbilityTagSearch; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTag AbilityTag; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer OwnedTags; + /* + These tags are added to owner while ability is activating (or channeled). + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationAddedTags; + /* + These tags must be present on onwer to activate this ability. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationRequiredTags; + /* + If any of these tags is present ability activation is blocked. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Tags") + FGameplayTagContainer ActivationBlockedTags; + +public: //because I'm to lazy to write all those friend states.. + UFUNCTION() + void OnActivationEffectPeriod(FGAEffectHandle InHandle); + + /* Replication counters for above events. */ + + + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnInputPressedDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnInputReleasedDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnActivateBeginDelegate; + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnActivationFinishedDelegate; + + UPROPERTY(BlueprintAssignable) + FGASGenericAbilityDelegate OnNotifyOnCooldown; + + /* Stub, I think replicating montage directly from ability will be better, as abilities are replicated regardless. */ + UPROPERTY() + UAnimMontage* RepMontage; +protected: + EAFAbilityState AbilityState; + +public: + UGAAbilityBase(const FObjectInitializer& ObjectInitializer); + + virtual void PostInitProperties() override; + + virtual void Serialize(FArchive& Ar) override; + // UObject interface + virtual FPrimaryAssetId GetPrimaryAssetId() const override; + virtual void PostLoad() override; + +#if WITH_EDITORONLY_DATA + /** This scans the class for AssetBundles metadata on asset properties and initializes the AssetBundleData with InitializeAssetBundlesFromMetadata */ + virtual void UpdateAssetBundleData(); + + /** Updates AssetBundleData */ + virtual void PreSave(const class ITargetPlatform* TargetPlatform) override; + +protected: + /** Asset Bundle data computed at save time. In cooked builds this is accessible from AssetRegistry */ + UPROPERTY() + FAssetBundleData AssetBundleData; +#endif +public: +#if WITH_EDITOR + virtual void PostEditChangeProperty(FPropertyChangedEvent& PropertyChangedEvent) override; +#endif // WITH_EDITOR + + void UpdateAssetRegistryInfo(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void PlayMontage(UAnimMontage* MontageIn, FName SectionName, float Speed = 1); + + void InitAbility(); +public: + UFUNCTION() + void OnAttributeSetReplicated(); + //called on both server and client after InitAbility(); + virtual void OnAbilityInited(); + + /* + Called on server and client, after ability has been bound to some input. + */ + virtual void OnAbilityInputReady() {}; + + /* + * @call Order: + * Previous Function: FGASAbilityContainer::HandleInputPressed + * Next Function: UGAAbilityBase::OnInputPressed + * + * Called on both Client and Server. + * + * @param ActionName - Name of action which tirggered this ability + * @param InPredictionHandle - Prediction Handle Generate By Client + */ + void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); + /* + * @call Order: + * Previous Function: UGAAbilityBase::OnNativeInputPressed + * Next Function: Multiple Choices. Next function is usually called from within Ability Blueprint + * Default Choices: + * UGAAbilityBase::StartActivation + * UGAAbilityBase::CanUseAbility + * Custom Function + * + * Called on both Client and Server. + * + * @param ActionName - Name of action which tirggered this ability + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnInputPressed(FGameplayTag ActionName); + + void OnNativeInputReleased(FGameplayTag ActionName); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnInputReleased(FGameplayTag ActionName); + + + + + void NativeOnAbilityConfirmed(); + + + + /* + * @call Order: + * Previous Function: UGAAbilityBase::StartActivation + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility + * + * Called on both Client and Server to indicate that ability is finished. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivationFinished(); + + /* + * @call Order: + * Previous Function: (Blueprint) UGAAbilityBase::OnInputPressed + * Next Function: UGAAbilityBase::NativeOnBeginAbilityActivation + * + * Called on both Client and Server. + * + * @param bApplyActivationEffect - Should apply activation effect to Owner. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void StartActivation(bool bApplyActivationEffect); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::StartActivation + * Next Function: UGAAbilityBase::ApplyActivationEffect + * Next Function: (Blueprint) UGAAbilityBase::OnActivate + * + * Called on both Client and Server. + * + * @param bApplyActivationEffect - Should apply activation effect to Owner. + */ + virtual void NativeOnBeginAbilityActivation(bool bApplyActivationEffect); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called on both Client and Server. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivate(); + + /* Event called when ability activation has been canceled. */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnActivationCancel(); + /* + * @call Order: + * Previous Function: Called if Periodic effect has been applied and is active. Otherwise inactive. + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * + * Called on both Client and Server. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnPeriod(); + + + + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnCooldownStart(); + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnCooldownEnd(FGAEffectHandle InHandle); + + void NativeOnCooldownEnd(FGAEffectHandle InHandle); + + UFUNCTION() + void OnCooldownEffectExpired(); + UFUNCTION() + void NativeOnAbilityActivationFinish(FGAEffectHandle InHandle); + UFUNCTION() + void NativeOnAbilityActivationCancel(); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeOnBeginAbilityActivation - + * called when activation effect finishes (or immedietly, if there was no activation effect applied). + * Next Function: (Blueprint) Custom Functions + * Next Function: (Blueprint) UGAAbilityBase::FinishAbility - must be called at some point + * finish ability. + * + * Called to finish ability and start clean up. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void FinishAbility(); + /* + * @call Order: + * Previous Function: UGAAbilityBase::FinishAbility + * Next Function: (Blueprint) UGAAbilityBase::OnAbilityFinished + * + * Called to finish ability and start clean up. + */ + void NativeFinishAbility(); + + /* + * @call Order: + * Previous Function: UGAAbilityBase::NativeFinishAbility + * Next Function: (Blueprint) Custom Functions + * + * Called when ability is finished. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") + void OnAbilityFinished(); + /* + Stop effect activation and remove activation effect. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void CancelActivation(); + void NativeCancelActivation(); + + bool IsWaitingForConfirm(); + void ConfirmAbility(); + + bool CanUseAbility(); + bool CanReleaseAbility(); + + UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") + bool BP_CanUseAbility(); + + /** IAFAbilityInterface Begin */ + virtual class UGAAttributesBase* GetAttributes() override; + virtual class UAFAbilityComponent* GetAbilityComp() override; + virtual class UAFEffectsComponent* GetEffectsComponent() override; + virtual class UAFEffectsComponent* NativeGetEffectsComponent() const override; + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Attributes") + virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; + virtual float NativeGetAttributeValue(const FGAAttribute AttributeIn) const override; + virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; + virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; + virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty) override + { + if (!Attributes) + { + UE_LOG(AFAbilities, Log, TEXT("ModifyAttribute Ability Attributes INVALID")); + return; + } + Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); + }; + virtual FAFPredictionHandle GetPredictionHandle() override; + /* IAFAbilityInterface End **/ + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Abilities|Attributes") + virtual float GetAttributeVal(FGAAttribute AttributeIn) const; + +public: //protected ? + bool ApplyCooldownEffect(); + UFUNCTION(Client, Reliable) + void ClientSetCooldownHandle(FGAEffectHandle InCooldownHandle); + void ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle); + + bool ApplyActivationEffect(bool bApplyActivationEffect); + bool ApplyAttributeCost(); + bool ApplyAbilityAttributeCost(); + bool CheckAbilityAttributeCost(); + bool CheckAttributeCost(); + bool IsOnCooldown(); + bool IsActivating(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Is On Cooldown"), Category = "AbilityFramework|Abilities") + bool BP_IsOnCooldown(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Cooldown"), Category = "AbilityFramework|Abilities") + void BP_ApplyCooldown(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_ApplyAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_CheckAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Apply Ability Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_ApplyAbilityAttributeCost(); + + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Check Ability Attribute Cost"), Category = "AbilityFramework|Abilities") + bool BP_CheckAbilityAttributeCost(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + float GetCurrentActivationTime(); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + float CalculateAnimationSpeed(UAnimMontage* MontageIn); + + /* Replication */ + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return bReplicate; + } + void SetNetAddressable(); + +public: + int32 GetFunctionCallspace(UFunction* Function, void* Parameters, FFrame* Stack) override; + virtual bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities") + void ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName); + + virtual class UWorld* GetWorld() const override; + + inline void AddAbilityTask(FName InName, class UAFTaskBase* InTask) + { + if (!AbilityTasks.Contains(InName)) + { + AbilityTasks.Add(InName, InTask); + } + } + class UGAAbilityTask* GetAbilityTask(const FName& InName); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") + bool HaveGameplayTag(AActor* Target, const FGameplayTag& Tag); + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tags") + bool HaveAnyGameplayTag(AActor* Target, const FGameplayTagContainer& Tag); + + /* Tracing Helpers Start */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannel(const FVector Start, const FVector End, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit); + /* Traces location from owner camera position if no camera available traces from eyes */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelFromCamera(float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Traces from ability avatar socket. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelFromSocket(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Make first trace from camera location and then second trace from avatar socket in direction of first trace. */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Abilities|Tracing") + bool LineTraceSingleByChannelCorrected(FName SocketName, float Range, ETraceTypeQuery TraceChannel, bool bTraceComplex, FHitResult& OutHit, + EDrawDebugTrace::Type DrawDebugType, bool bIgnoreSelf, FLinearColor TraceColor, FLinearColor TraceHitColor, float DrawTime); + /* Tracing Helpers End */ + + + //Helpers + float GetActivationRemainingTime() const; + float GetActivationRemainingTimeNormalized() const; + float GetActivationCurrentTime() const; + float GetActivationCurrentTimeNormalized() const; + float GetActivationEndTime() const; + + UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationRemainingTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationCurrentTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetActivationEndTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetActivationEndTime(); + + + float GetCooldownRemainingTime() const; + float GetCooldownRemainingTimeNormalized() const; + float GetCooldownCurrentTime() const; + float GetCooldownCurrentTimeNormalized() const; + float GetCooldownEndTime() const; + + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownRemainingTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownRemainingTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownRemainingTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownCurrentTime(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownCurrentTimeNormalized", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownCurrentTimeNormalized(); + UFUNCTION(BlueprintPure, DisplayName = "GetCooldownEndTime", Category = "AbilityFramework|Abilities|Helpers") + float BP_GetCooldownEndTime(); + + UFUNCTION(BlueprintCallable, DisplayName = "Get Avatar", Category = "AbilityFramework|Abilities|Helpers") + AActor* BP_GetAvatar(); + + virtual void OnAvatarReady() {}; + + + /* IAFLatentInterface */ + virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn); + virtual void AddReplicatedTask(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn); + + virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn); + + virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); + /* IAFLatentInterface */ +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBlueprint.h new file mode 100644 index 0000000..e1c6fef --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBlueprint.h @@ -0,0 +1,31 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAAbilityBlueprint.generated.h" + +/** + * Game Ability Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAAbilityBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() + +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAAbilityBlueprint* FindRootGameplayAbilityBlueprint(UGAAbilityBlueprint* DerivedBlueprint); + +#endif +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h new file mode 100644 index 0000000..5d3e7ae --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/AFAbilityTask_SpawnProjectile.h @@ -0,0 +1,58 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Abilities/Tasks/GAAbilityTask.h" +#include "AFAbilityTask_SpawnProjectile.generated.h" + +UENUM() +enum class EAFPRojectileSpawnTraceOption : uint8 +{ + DoNotTrace, + TraceFullPath, + OnlyTraceWhileAscending, +}; + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FAFOnPRojectileSpawned); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFAbilityTask_SpawnProjectile : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY() + FVector StartLocation; + UPROPERTY() + FVector EndLocation; + UPROPERTY() + float LaunchSpeed; + UPROPERTY() + float OverrideGravityZ; + UPROPERTY() + EAFPRojectileSpawnTraceOption TraceOption; + UPROPERTY() + float CollisionRadius; + UPROPERTY() + bool bFavorHighArc; + UPROPERTY() + bool bDrawDebug; + + UPROPERTY(BlueprintAssignable) + FAFOnPRojectileSpawned Played; +public: + static UAFAbilityTask_SpawnProjectile* Ability_SpawnProjectile(UGAAbilityBase* WorldContextObject, + FName InTaskName, + FVector InStartLocation, + FVector InEndLocation, + float InLaunchSpeed, + float InOverrideGravityZ, + EAFPRojectileSpawnTraceOption InTraceOption, + float InCollisionRadius, + bool InbFavorHighArc, + bool InbDrawDebug); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask.h new file mode 100644 index 0000000..b989524 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask.h @@ -0,0 +1,95 @@ +#pragma once +#include "GameplayTask.h" +#include "GAAbilityBase.h" +#include "AFAbilityComponent.h" + +#include "LatentActions/AFTaskBase.h" + +#include "GAAbilityTask.generated.h" +/* + AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and + the should be activated from ability. + Then can perform tasks, like spawn tagetting helpers (splines, circles), spawn actors, + gather targeting data etc. + + Should they be activated automatically after ability is initialized, (it'e ability enterted in + active state, which means it's ready to be fired and display helpers, but did not yet received input, + or should designer in blueprint decide when to launch actions ?). +*/ + +UCLASS(BlueprintType, Blueprintable, Within=GAAbilityBase) +class ABILITYFRAMEWORK_API UGAAbilityTask : public UAFTaskBase +{ + GENERATED_BODY() + friend struct FAFAbilityTaskMessageTick; +public: + uint8 bIsReplicated : 1; + /* Ability owning this task */ + TWeakObjectPtr Ability; + /* Ability owning this task */ + TWeakObjectPtr AbilityComponent; +public: + + template + static T* NewAbilityTask(UGAAbilityBase* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) + { + check(WorldContextObject); + + T* MyObj = nullptr; + UGAAbilityBase* ThisAbility = CastChecked(WorldContextObject); + MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); + + MyObj->Ability = ThisAbility; + MyObj->AbilityComponent = ThisAbility->AbilityComponent; + + return MyObj; + } + UGAAbilityTask(const FObjectInitializer& ObjectInitializer); + bool IsReplicated() + { + return bIsReplicated; + } + +protected: + bool IsClient() + { + APawn* POwner = Ability->POwner; + if (POwner->GetNetMode() == ENetMode::NM_Client) + { + return true; + } + return false; + } + + bool IsServer() + { + APawn* POwner = Ability->POwner; + if (POwner->GetNetMode() == ENetMode::NM_DedicatedServer + || POwner->GetNetMode() == ENetMode::NM_ListenServer) + { + return true; + } + return false; + } + bool IsServerOrStandalone() + { + APawn* POwner = Ability->POwner; + if (POwner->GetNetMode() == ENetMode::NM_DedicatedServer + || POwner->GetNetMode() == ENetMode::NM_ListenServer + || POwner->GetNetMode() == ENetMode::NM_Standalone) + { + return true; + } + return false; + } + + bool IsAuthority() + { + APawn* POwner = Ability->POwner; + if (POwner->Role >= ENetRole::ROLE_Authority) + { + return true; + } + return false; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_CreateObject.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_CreateObject.h new file mode 100644 index 0000000..3fbdd2c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_CreateObject.h @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_CreateObject.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASSpawnObjectDelegate, class UObject*, SpawnedObject); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_CreateObject : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASSpawnObjectDelegate Success; + UPROPERTY(BlueprintAssignable) + FGASSpawnObjectDelegate Failure; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_CreateObject* CreateObject(UGAAbilityBase* WorldContextObject, + FName InTaskName, TSubclassOf Class, UObject* Outer); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + bool BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, class UObject*& SpawnedActor); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + void FinishSpawningActor(UGAAbilityBase* WorldContextObject, class UObject* SpawnedActor); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_PlayMontage.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_PlayMontage.h new file mode 100644 index 0000000..1c33398 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_PlayMontage.h @@ -0,0 +1,45 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "AFAbilityTypes.h" +#include "GAAbilityTask_PlayMontage.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_TwoParams(FGASGenericMontageDelegate, FGameplayTag, Tag, FName, NotifyName); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_PlayMontage : public UGAAbilityTask +{ + GENERATED_BODY() + +public: + UPROPERTY(BlueprintReadOnly, meta = (ExposeOnSpawn = true)) + UAnimMontage* Montage; + FName SectionName; + float PlayRate; + bool bUseActivationTime; + + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate Played; + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate NotifyBegin; + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate NotifyTick; + UPROPERTY(BlueprintAssignable) + FGASGenericMontageDelegate NotifyEnd; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_PlayMontage* AbilityPlayMontage(UGAAbilityBase* WorldContextObject, + FName InTaskName, UAnimMontage* MontageIn, FName SectionNameIn, float PlayRateIn, + bool bInUseActivationTime); + + virtual void Activate() override; + + void BroadcastStartNotifyState(const FGameplayTag& InTag, const FName& InName); + void BroadcastEndNotifyState(const FGameplayTag& InTag, const FName& InName); + void BroadcastTickNotifyState(const FGameplayTag& InTag, const FName& InName); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_Repeat.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_Repeat.h new file mode 100644 index 0000000..914bf6a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_Repeat.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_Repeat.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnTaskRepeated); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_Repeat : public UGAAbilityTask +{ + GENERATED_BODY() + + UPROPERTY(BlueprintAssignable) + FGASOnTaskRepeated OnTaskRepeated; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_Repeat* CreateRepeatTask(UGAAbilityBase* WorldContextObject, + FName InTaskName); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_SpawnActor.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_SpawnActor.h new file mode 100644 index 0000000..af30e2f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_SpawnActor.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_SpawnActor.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASSpawnActorDelegate, AActor*, SpawnedActor); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_SpawnActor : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASSpawnActorDelegate Success; + UPROPERTY(BlueprintAssignable) + FGASSpawnActorDelegate Failure; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_SpawnActor* SpawnActor(UGAAbilityBase* WorldContextObject, + FName InTaskName, TSubclassOf Class); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + bool BeginSpawningActor(UGAAbilityBase* WorldContextObject, TSubclassOf Class, AActor*& SpawnedActor); + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + void FinishSpawningActor(UGAAbilityBase* WorldContextObject, AActor* SpawnedActor); + + virtual void Activate() override; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h new file mode 100644 index 0000000..2ce9ab4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h @@ -0,0 +1,64 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_TargetData.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASOnReceiveTargetData, const FHitResult&, HitResult); + +UENUM() +enum class EGASConfirmType : uint8 +{ + Instant, + WaitForConfirm +}; + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_TargetData : public UGAAbilityTask, public FTickableGameObject +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnReceiveTargetData OnConfirmed; + UPROPERTY(BlueprintAssignable) + FGASOnReceiveTargetData OnReceiveTargetData; + + EGASConfirmType ConfirmType; + + float Range; + bool bIsTickable; + bool bDrawDebug; + bool bDrawCorrectedDebug; + bool bUseCorrectedTrace; +public: + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_TargetData* CreateTargetDataTask(UGAAbilityBase* WorldContextObject, + FName InTaskName, + bool bDrawDebug, + bool bDrawCorrectedDebug, + bool bUseCorrectedTrace, + EGASConfirmType ConfirmTypeIn, + float Range); + + virtual void Activate() override; + + UFUNCTION() + void OnConfirm(); + + UFUNCTION() + void OnCastEndedConfirm(); + + /* FTickableGameObject Begin */ + virtual void Tick(float DeltaTime) override; + virtual bool IsTickable() const override { return bIsTickable; } + virtual TStatId GetStatId() const override { RETURN_QUICK_DECLARE_CYCLE_STAT(UGAAbilityTask_TargetData, STATGROUP_Tickables); }; + /* FTickableGameObject End */ + +protected: + FHitResult LineTrace(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h new file mode 100644 index 0000000..ea39110 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h @@ -0,0 +1,40 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_TargetData.h" +#include "GAAbilityTask_TargetDataCircle.generated.h" + +//DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FGASOnReceiveTargetData, const FHitResult&, HitResult); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataCircle : public UGAAbilityTask_TargetData +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnReceiveTargetData OnReceiveTargetDataCircle; + + EGASConfirmType ConfirmType; + +public: + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_TargetDataCircle* TargetCircleDataTask(UGAAbilityBase* WorldContextObject, + FName InTaskName, EGASConfirmType ConfirmTypeIn); + + virtual void Activate() override; + + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // bool BeginSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject*& SpawnedActor); + + //UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + // void FinishSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject* SpawnedActor); + // + + UFUNCTION() + void OnConfirm(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h new file mode 100644 index 0000000..bf137c2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h @@ -0,0 +1,107 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "Components/SkeletalMeshComponent.h" +#include "GAAbilityTask_TargetDataLineTrace.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnTargetReceived, const FHitResult&, HitResult); + +UENUM() +enum class EAFConfirmType : uint8 +{ + Instant, + WaitForConfirm +}; + +USTRUCT() +struct FAFLineTraceData +{ + GENERATED_BODY() + UPROPERTY() + float ExactPing; + UPROPERTY() + AActor* HitActor; + UPROPERTY() + FVector HitLocation; +}; +USTRUCT() +struct FAFLineTraceConfirmData +{ + GENERATED_BODY() + + UPROPERTY() + uint8 bConfirmed : 1; + UPROPERTY() + AActor* HitActor; + UPROPERTY() + FVector HitLocation; +}; +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataLineTrace : public UGAAbilityTask, public FTickableGameObject +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnConfirmed; + + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnClientReceiveTargetData; + + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnServerReceiveTargetData; + + ETraceTypeQuery TraceChannel; + USkeletalMeshComponent* SocketComponent; + FName SocketName; + EAFConfirmType ConfirmType; + + float Range; + bool bIsTickable; + bool bDrawDebug; + + //Result of trace from either server or client simulation + FHitResult LocalHitResult; +public: + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_TargetDataLineTrace* CreateTargetDataLineTrace(UGAAbilityBase* WorldContextObject + , FName InTaskName + , ETraceTypeQuery InTraceChannel + , USkeletalMeshComponent* InSocketComponent + , FName InSocketName + , bool bDrawDebug + , EAFConfirmType ConfirmTypeIn + , float Range); + + UGAAbilityTask_TargetDataLineTrace(const FObjectInitializer& ObjectInitializer); + + virtual void Activate() override; + + UFUNCTION(Server, Reliable, WithValidation) + void ServerConfirmHitInfo(FAFLineTraceData TraceData); + void ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData); + bool ServerConfirmHitInfo_Validate(FAFLineTraceData TraceData); + + UFUNCTION(Client, Reliable) + void ClientConfirmHitInfo(FAFLineTraceConfirmData ConfirmData); + void ClientConfirmHitInfo_Implementation(FAFLineTraceConfirmData ConfirmData); + + UFUNCTION() + void OnConfirm(); + + UFUNCTION() + void OnCastEndedConfirm(); + + /* FTickableGameObject Begin */ + virtual void Tick(float DeltaTime) override; + virtual bool IsTickable() const override { return bIsTickable; } + virtual TStatId GetStatId() const override { RETURN_QUICK_DECLARE_CYCLE_STAT(UGAAbilityTask_TargetData, STATGROUP_Tickables); }; + /* FTickableGameObject End */ + +protected: + FHitResult LineTrace(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h new file mode 100644 index 0000000..e81c18a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitForConfirm.h @@ -0,0 +1,30 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_WaitForConfirm.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnConfirmed); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAbilityTask_WaitForConfirm : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnConfirmed OnConfirmed; + + UFUNCTION(BlueprintCallable, meta = (HidePin = "WorldContextObject", DefaultToSelf = "WorldContextObject", BlueprintInternalUseOnly = "true"), Category = "AbilityFramework|Abilities|Tasks") + static UGAAbilityTask_WaitForConfirm* CreateWaitConfirmTask(UGAAbilityBase* WorldContextObject, + FName InTaskName); + + virtual void Activate() override; + virtual void Initialize() override; + + UFUNCTION() + void OnConfirm(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitTargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitTargetData.h new file mode 100644 index 0000000..d50f96e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_WaitTargetData.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GAAbilityTask.h" +#include "GAAbilityTask_WaitTargetData.generated.h" +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGASOnTargetingTaskConfimred); + +/** + * + */ +UCLASS(meta = (ExposedAsyncProxy)) +class ABILITYFRAMEWORK_API UGAAbilityTask_WaitTargetData : public UGAAbilityTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FGASOnTargetingTaskConfimred OnConfirmed; + + UPROPERTY() + float Range; + ETraceTypeQuery TraceChannel; + + virtual void Activate() override; + + virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; + + + UFUNCTION() + void OnConfirm(); + +public: + UGAAbilityTask_WaitTargetData(const FObjectInitializer& ObjectInitializer); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h new file mode 100644 index 0000000..eca4711 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h @@ -0,0 +1,152 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "Engine.h" +#include "IAbilityFramework.h" +#include "InputCoreTypes.h" + +#include "Runtime/UMG/Public/UMG.h" +#include "Runtime/UMG/Public/UMGStyle.h" +#include "Runtime/UMG/Public/Slate/SObjectWidget.h" +#include "Runtime/UMG/Public/IUMGModule.h" +#include "Runtime/UMG/Public/Blueprint/UserWidget.h" +//#include "GameTrace.h" + +enum class EAFEffectTimerStatus : uint8 +{ + Pending, + Active, + Executing, + Paused +}; + +struct FAFEffectTimeHandle +{ + int32 Index; + bool operator==(const FAFEffectTimeHandle& Other) const + { + return Index == Other.Index; + } +}; + +struct FAFEffectTimer +{ + double StartTime; //when started + double ExpireTime; + double NextPeriodTime; + double PeriodTime; + double Duration; //how often timer is executed + + bool bHaveDuration; //does it loop + bool bHavePeriod; + bool bActive; + + EAFEffectTimerStatus Status; + + FSimpleDelegate ExpireDelegate; + FSimpleDelegate PeriodDelegate; + + FAFEffectTimeHandle Handle; + + FAFEffectTimer(); + + bool operator<(const FAFEffectTimer& Other) const + { + return ExpireTime < Other.ExpireTime; + } + bool operator==(const FAFEffectTimer& Other) const + { + return Handle == Other.Handle; + } +}; + +DECLARE_STATS_GROUP(TEXT("EffectTimer"), STATGROUP_EffectTimer, STATCAT_Advanced); +class FAFEffectTimerWorker : public FRunnable +{ + FCriticalSection CS; + TArray Timers; + TArray ActiveTimers; + UWorld* World; + double InternalTime; + bool bActive; +public: + FAFEffectTimerWorker(); + virtual bool Init() override; + + /** + * Runs the runnable object. + * + * This is where all per object thread work is done. This is only called if the initialization was successful. + * + * @return The exit code of the runnable object + * @see Init, Stop, Exit + */ + virtual uint32 Run() override; + + /** + * Stops the runnable object. + * + * This is called if a thread is requested to terminate early. + * @see Init, Run, Exit + */ + virtual void Stop() override; + + /** + * Exits the runnable object. + * + * Called in the context of the aggregating thread to perform any cleanup. + * @see Init, Run, Stop + */ + virtual void Exit() override; + + FAFEffectTimeHandle AddTimer(double InDuration, double InPeriod); +}; + +class FAFEffectTimerManager +{ + FRunnableThread* TimerThread; + FAFEffectTimerWorker* TimerWorker; + + +public: + static FAFEffectTimerManager* Instance; + static FAFEffectTimerManager* Get() + { + //static FAFEffectTimerManager Obj;// = nullptr; + //return Obj; + if (!Instance) + Instance = new FAFEffectTimerManager(); + + return Instance; + + } + + FAFEffectTimerManager(); + + ~FAFEffectTimerManager(); + + void TickTimer(float InDeltaTime); + FAFEffectTimeHandle AddTimer(double InDuration, double InPeriod); +}; + +class FAbilityFramework : public IAbilityFramework +{ + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; + + +DECLARE_LOG_CATEGORY_EXTERN(AbilityFramework, Log, All); + +DECLARE_LOG_CATEGORY_EXTERN(GameAttributesGeneral, Log, All); + +DECLARE_LOG_CATEGORY_EXTERN(GameAttributes, Log, All); + +DECLARE_LOG_CATEGORY_EXTERN(GameAttributesEffects, Log, All); + + + +DECLARE_LOG_CATEGORY_EXTERN(AFAttributes, Log, All); +DECLARE_LOG_CATEGORY_EXTERN(AFEffects, Log, All); +DECLARE_LOG_CATEGORY_EXTERN(AFAbilities, Log, All); \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAbilityNotifyState.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAbilityNotifyState.h new file mode 100644 index 0000000..d2a949a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAbilityNotifyState.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Animation/AnimNotifies/AnimNotifyState.h" +#include "GameplayTags.h" +#include "AFAbilityNotifyState.generated.h" + +/** + * + */ +UCLASS(meta = (DisplayName = "Ability Notify State")) +class ABILITYFRAMEWORK_API UAFAbilityNotifyState : public UAnimNotifyState +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere) + FGameplayTag Tag; + UPROPERTY(EditAnywhere) + FName Name; + UPROPERTY() + class UAFAbilityComponent* CachedAbilitiesComp; +public: + virtual void NotifyBegin(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float TotalDuration) override; + virtual void NotifyTick(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation, float FrameDeltaTime) override; + virtual void NotifyEnd(class USkeletalMeshComponent * MeshComp, class UAnimSequenceBase * Animation) override; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAnimNotify.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAnimNotify.h new file mode 100644 index 0000000..b6e0390 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AnimNotify/AFAnimNotify.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Animation/AnimNotifies/AnimNotify.h" +#include "GameplayTags.h" +#include "AFAnimNotify.generated.h" + +/** + * + */ +UCLASS(meta=(DisplayName = "Ability Notify")) +class ABILITYFRAMEWORK_API UAFAnimNotify : public UAnimNotify +{ + GENERATED_BODY() + + virtual void Notify(USkeletalMeshComponent* MeshComp, UAnimSequenceBase* Animation) override; + + UPROPERTY(EditAnywhere) + FGameplayTag Tag; + UPROPERTY(EditAnywhere) + FName Name; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h new file mode 100644 index 0000000..650b95c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -0,0 +1,148 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "./Effects/GAGameEffect.h" +#include "../Effects/GAEffectGlobalTypes.h" + +// Messaging +//#include "Messaging.h" + +#include "GAAttributeBase.generated.h" + +DECLARE_MULTICAST_DELEGATE(FGAGenericAttributeDelegate); + +DECLARE_STATS_GROUP(TEXT("Attribute"), STATGROUP_Attribute, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("CalculateBonus"), STAT_CalculateBonus, STATGROUP_Attribute, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("CurrentBonusByTag"), STAT_CurrentBonusByTag, STATGROUP_Attribute, ); +DECLARE_CYCLE_STAT_EXTERN(TEXT("FinalBonusByTag"), STAT_FinalBonusByTag, STATGROUP_Attribute, ); + + +struct QueuedAttributeMods +{ +public: + FGAEffectHandle Handle; + FGAEffectMod Mod; + + void operator=(const QueuedAttributeMods& Other) + { + Handle = Other.Handle; + Mod = Other.Mod; + } +}; + +//wrapper for multi-precision attribute. +//works like any numeric type, but depending on preprocessor flag it can int16,in32, float or double. + +typedef int16 AttributeReal; + +struct FNumericAttribute +{ + AttributeReal Value; +}; + +class UAFAbilityComponent; +/* + I probabaly should chaange attribute to use int's instead of floats. Stable, accurate and + I can still have decimal values with them. +*/ +/* + Base data structure describing Attribute: + 1. Base Value - the base value attribute has been initialized with. + 2. Current value - current value of attribute. + 3. Bonuses value. + 4. One bonus value (if need be attribute can take care of calculating it's own bonus value). + + As for now it's made to in mind to use it as meta attribute. Meta attributes, have always + 0 value and are used to change other attributes. Like Damage is used to subtract health. + LifeSteal is used to transfer health from target to instigator etc. + + We could extend attributes, to also support tags, so their bonus can be recalculated, + based on on tags requiremnts from effect asking for this particular attribute. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAttributeBase +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + float BaseValue; + UPROPERTY(EditAnywhere) + float MinValue; + UPROPERTY(EditAnywhere) + float MaxValue; + UPROPERTY() + float CurrentValue; + UPROPERTY() + float BonusValue; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") + TSubclassOf ExtensionClass; + + TArray> Modifiers; + FAFAttributeBase(); + FAFAttributeBase(float BaseValueIn); + void InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName); + /* You should never use those tree function to set attributes. + Only use them for testing/debugging and setting initial values for attributes. */ + inline void SetBaseValue(float ValueIn) { BaseValue = ValueIn; } + inline void SetMinValue(float ValueIn) { MinValue = ValueIn; } + inline void SetMaxValue(float ValueIn) { MaxValue = ValueIn; } + //used internally. NEver call it directly. + inline void SetCurrentValue(float ValueIn) { CurrentValue = ValueIn; } + + inline float GetFinalValue() + { + return FMath::Clamp(BaseValue + BonusValue, MinValue, MaxValue); + }; + inline float GetCurrentValue() { return CurrentValue; }; + void CalculateBonus(); + bool CheckIfStronger(const FGAEffectMod& InMod); + float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); + void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); + void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); + void SetExtensionClass(TSubclassOf InExtensionClass) { ExtensionClass = InExtensionClass; }; +}; +template<> +struct TStructOpsTypeTraits : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = false + }; +}; +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAModifiedAttribute +{ + GENERATED_USTRUCT_BODY() +public: + /** + * Always increment it, to make sure it will replicate. + */ + UPROPERTY() + int8 ReplicationCounter; + + /** + * Attribute we have modified. + */ + UPROPERTY() + FGAAttribute Attribute; + + /** + * Final value by which we modified attribute. + */ + UPROPERTY(BlueprintReadOnly, Category = "UI") + float ModifiedByValue; + + /** + * Final tags appiled by this change. + */ + UPROPERTY() + FGameplayTagContainer Tags; + + UPROPERTY(BlueprintReadOnly, Category = "UI") + FVector TargetLocation; //change to vector, we need only position. + UPROPERTY(BlueprintReadOnly, Category = "UI") + FVector InstigatorLocation; + + UPROPERTY() + TWeakObjectPtr Causer; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h new file mode 100644 index 0000000..34b4b7c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "GAAttributeExtension.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAAttributeExtension : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY() + class UAFAbilityComponent* AbilityComponent; + UPROPERTY() + FGAAttribute Attribute; + void Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName); + + void OnPreAttributeModify(float InValue); + void OnPostAttributeModify(float InValue); + + virtual void PreAttributeModify() {}; + virtual void PostAttributeModify() {}; + virtual float CalculateBonusValueByTags(const FGAIndividualMods& Mods) { return 0; } + virtual float CalculateCurentValue() { return 0; } + virtual bool CanModifyAttribute() { return true; } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeGlobals.h new file mode 100644 index 0000000..e82dfdf --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeGlobals.h @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "GAAttributeGlobals.generated.h" +/** + * + */ + +USTRUCT() +struct FDumbStruct +{ + GENERATED_BODY() +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h new file mode 100644 index 0000000..b5786b6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h @@ -0,0 +1,136 @@ +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "UObject/Object.h" +#include "UObject/Class.h" +#include "Templates/SubclassOf.h" +#include "UObject/UnrealType.h" +#include "UObject/CoreNet.h" +#include "../Effects/GAGameEffect.h" +#include "../GAGlobalTypes.h" +#include "GAAttributeBase.h" +#include "GAAttributesBase.generated.h" + +/* + What I need. + Easy way to create Targeted modifications. + For Example, we have ability Fireball, which have cast time 3s, and recharge time 5 seconds. + Targeted modification, will only affect this one ability! + + So we want attribute which will decrease recharge time of this ability by 2 seconds (or decrease recharge time by 25% + or increase recharge speed). How to do it ? + + Path of least resistance is to create special object, which will be instanced, which will listen for abilities + which are activated, and you can cast to your particular ability (or check for tags), and just modify it's + properties directly. + + Second way, (??) would be to create small objects, contained within array (structs), which would do the same thing. + Except they would only be able to catch something like ability activation by tag. They wouldn't know, what kind of + properties are on ability. + + The ability in this case would be needed to be treated as source of incoming attribute, and that object would check + for this attribute and modify it. + Well kind of. + + The same problems exist for any kind of abilities more broad (like Hex), more narrow (only Necromancer Hex), + or for weapons (we want to increase fire rate, if you have equiped machine gun). + + Though on the very base level attribute system have no idea, what kind of properties you might have on + your machine gun. + + + This bring us to the core issue. How to create system like Traits/Feats/Talents, which can contain + myriads of possible combinations of those tree systems. We would need to mix some instanced/non-instanced UObjects + along with plain structs. Which is probabaly going to be total mess. +*/ +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInlineNew) +class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject +{ + GENERATED_BODY() +public: + + UPROPERTY(EditAnywhere, BlueprintReadOnly, meta=(ExposeOnSpawn)) + UDataTable* AttributeValues; + UGAAttributesBase(const FObjectInitializer& ObjectInitializer); + ~UGAAttributesBase(); + //virtual void PostNetReceive() override; + virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp); + void InitializeAttributesFromTable(); + UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) + bool BP_InitializeAttributes(); + /* + Updates attributes. + @param AttributeIn - attribute which changed value. + + You can use this function to update other attributes (for example derived ones), + based on the primary attribute, if the primary attribute (AttributeIn), changed. + + I have yet to fully figure out how do I want it to work. But one thing for certain is + that it must be fully functional from within blueprint. + */ + UPROPERTY(Replicated) + class UAFAbilityComponent* OwningAttributeComp; +protected: + UProperty* FindProperty(const FGAAttribute& AttributeIn); + +public: + /* + Ticked called from owning component. + */ + virtual void Tick(float DeltaTime);// {}; + /* + Helper C++ functions. Shouldn't ever be exposed or called from blueprint. Also never + try to override them. + + probabaly could also add support for int32 values. + */ + UStructProperty* GetStructAttribute(const FGAAttribute& Name); + /* + Gets pointer to compelx attribute. + */ + FAFAttributeBase* GetAttribute(const FGAAttribute& Name); + /* + Deprecated. I'm going to remove it, since it does not work as intended! + */ + void SetAttribute(const FGAAttribute& NameIn, UObject* NewVal); + + void SetAttributeAdditiveBonus(const FGAAttribute& NameIn, float NewValue); + + /* + Gets value from complex attribute (FAFAttributeBase). + */ + float GetFinalAttributeValue(const FGAAttribute& Name); + float GetCurrentAttributeValue(const FGAAttribute& Name); + + float GetFloatValue(const FGAAttribute& AttributeIn); + float SetFloatValue(const FGAAttribute& AttributeIn, float ValueIn); + float AttributeOperation(const FGAAttribute& AttributeIn, float ValueIn, EGAAttributeMod Operation); + + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return true; + } + void SetNetAddressable(); + + void ModifyAttribute(const FGAEffect& EffectIn); + float ModifyAttribute(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); + void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod); +protected: + bool bNetAddressable; + +private: + TArray TickableAttributes; + UProperty* LastAttributeProp; + FName LastAttributeName; + // cached numeric property. WEll we probabaly don't need UProperty cache then.. + UNumericProperty* CachedFloatPropety; + + float AddAttributeFloat(float ValueA, float ValueB); + float SubtractAttributeFloat(float ValueA, float ValueB); + float MultiplyAttributeFloat(float ValueA, float ValueB); + float DivideAttributeFloat(float ValueA, float ValueB); + + void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBlueprintFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBlueprintFunctionLibrary.h new file mode 100644 index 0000000..6a9cf15 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBlueprintFunctionLibrary.h @@ -0,0 +1,58 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" +#include "GAAttributesBlueprintFunctionLibrary.generated.h" +/* + Some static helper functions, to interact with Attribute system. +*/ +UCLASS() +class ABILITYFRAMEWORK_API UGAAttributesBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_UCLASS_BODY() +public: + UFUNCTION(BlueprintPure, meta=(DisplayName="Equal"), Category = "AbilityFramework|Attributes") + static bool EqualAttribute(const FGAAttribute& Compare, FGAAttribute Against); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + static FName GetAttribute(FGAAttribute AttributeIn); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") + static float GetFinalAttributeValue(AActor* Target, FGAAttribute Name); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") + static float GetCurrentAttributeValue(AActor* Target, FGAAttribute Name); + + /** + * Takes actor, and return value of specified attribute. + * + * @param Target - Actrom from which take attribute + * @param AttributeIn - Attribute from which we want to get value + * + * @return value of attribute from actor. + */ + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Attributes") + static float GetAttributeFloat(AActor* Target, FGAAttribute AttributeIn); + /** + * Subtracts value specified by From effect + * and adds it by effect specified by To. + * + * @param Instigator - Who Insigated effects. + * @param Causer - Who Caused Effects + * @param From - effect which will subtract Value + * @param FromTarget - from whose attributes value will be subtracted + * @param To - Effect specifing where attribute should be added. + * @param ToTarget - Target to which attributes will be added. + * + * @return value of attribute from actor. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") + static void ExchangeAttributesValues( + APawn* Instigator + , UObject* Causer + , FAFPropertytHandle From + , FGAEffectHandle FromHandle + , UObject* FromTarget + , FAFPropertytHandle To + , FGAEffectHandle ToHandle + , UObject* ToTarget); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesStats.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesStats.h new file mode 100644 index 0000000..3f59c93 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesStats.h @@ -0,0 +1,2 @@ +#pragma once + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectApplicationRequirement.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectApplicationRequirement.h new file mode 100644 index 0000000..3225e76 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectApplicationRequirement.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" +#include "AFEffectApplicationRequirement.generated.h" + +/** + * Default requirment always passes. + */ +UCLASS(meta=(DisplayName = "No Requirement")) +class ABILITYFRAMEWORK_API UAFEffectApplicationRequirement : public UObject +{ + GENERATED_BODY() + +public: + virtual bool CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomApplication.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomApplication.h new file mode 100644 index 0000000..24fd308 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomApplication.h @@ -0,0 +1,44 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" +#include "AFEffectCustomApplication.generated.h" + +/** + * Default application used for instant effects. + */ +UCLASS(meta = (DisplayName = "Default Application")) +class ABILITYFRAMEWORK_API UAFEffectCustomApplication : public UObject +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ApplyExecute( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) + { + return true; + } + + virtual bool ShowPeriod() + { + return false; + } + virtual bool ShowDuration() + { + return false; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomStackingRule.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomStackingRule.h new file mode 100644 index 0000000..ba364d2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectCustomStackingRule.h @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "../GAGlobalTypes.h" +#include "AFEffectCustomStackingRule.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectCustomStackingRule : public UObject +{ + GENERATED_BODY() + +public: + virtual bool CanStack(class UAFAbilityComponent* InComp, struct FGAEffectContainer* InContainer, + const FGAEffectHandle& InHandle); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectSpecFunctionLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectSpecFunctionLibrary.h new file mode 100644 index 0000000..7a9aa21 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFEffectSpecFunctionLibrary.h @@ -0,0 +1,57 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Kismet/BlueprintFunctionLibrary.h" +#include "Effects/GAGameEffect.h" +#include "AFEffectSpecFunctionLibrary.generated.h" +UENUM(BlueprintType) +enum class EAFTagCompareResult : uint8 +{ + Match, + NoMatch, +}; +UENUM() +enum class EAFTagContainerCompare : uint8 +{ + HasAny, + HasAnyExact, + HasAll, + HasAllExact, +}; + +UENUM() +enum class EAFTagCompare : uint8 +{ + HasTag, + HasTagExact +}; + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectSpecFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Spec") + static void AppendOwnedTags(FAFEffectSpecHandle Spec, const FGameplayTagContainer& InTags); + + + UFUNCTION(BlueprintCallable, meta = (ExpandEnumAsExecs = "Result"), Category = "AbilityFramework|Effects|Spec") + static void CompareOwnedTags(FAFEffectSpecHandle Spec + , EAFTagContainerCompare Mode + , const FGameplayTagContainer& InTags + , EAFTagCompareResult& Result); + + + UFUNCTION(BlueprintCallable, meta = (ExpandEnumAsExecs = "Result"), Category = "AbilityFramework|Effects|Spec") + static void CompareOwnedTag(FAFEffectSpecHandle Spec + , EAFTagCompare Mode + , FGameplayTag InTag + , EAFTagCompareResult& Result); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFAttributeStongerOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFAttributeStongerOverride.h new file mode 100644 index 0000000..f2e18f5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFAttributeStongerOverride.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectApplicationRequirement.h" +#include "AFAttributeStongerOverride.generated.h" + +/** + * USe only with Duration Based application. + * Effect will be applied if the attribute modifier is stronger than the current one on Attribute. + */ +UCLASS(BlueprintType, meta = (DisplayName = "Attribute Stronger")) +class ABILITYFRAMEWORK_API UAFAttributeStongerOverride : public UAFEffectApplicationRequirement +{ + GENERATED_BODY() +public: + virtual bool CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) override; + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h new file mode 100644 index 0000000..13b21b5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/ApplicationRequirement/AFEffectAlreadyApplied.h @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectApplicationRequirement.h" +#include "AFEffectAlreadyApplied.generated.h" + +/** + * If effect of the same type is already applied, it will be skipped. + */ +UCLASS(meta = (DisplayName = "Only One Of Type")) +class ABILITYFRAMEWORK_API UAFEffectAlreadyApplied : public UAFEffectApplicationRequirement +{ + GENERATED_BODY() +public: + virtual bool CanApply( + const FGAEffect& EffectIn + , const FAFEffectParams& Params + , const FGAEffectHandle& InHandle + , struct FGAEffectContainer* InContainer) override; + + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationAdd.h new file mode 100644 index 0000000..04eca4b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationAdd.h @@ -0,0 +1,32 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAtributeDurationAdd.generated.h" + +/** + * Adds New duration Effect. + */ +UCLASS(meta = (DisplayName = "Duration Add")) +class ABILITYFRAMEWORK_API UAFAtributeDurationAdd : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return true; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationUnique.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationUnique.h new file mode 100644 index 0000000..be69075 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAtributeDurationUnique.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAtributeDurationUnique.generated.h" + +/** + * Adds New Unique duration Effect. If effect of the same class is already applied to target, new effect will be ignored. + */ +UCLASS(meta = (DisplayName = "Duration Add Unique")) +class ABILITYFRAMEWORK_API UAFAtributeDurationUnique : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool CanApply(class IAFAbilityInterface* Target, TSubclassOf EffectClass) override; + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return true; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationInfinite.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationInfinite.h new file mode 100644 index 0000000..7707eda --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationInfinite.h @@ -0,0 +1,33 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAttributeDurationInfinite.generated.h" + +/** + * Adds infinite duration effect. + */ +UCLASS(meta = (DisplayName = "Duration Infinite Add")) +class ABILITYFRAMEWORK_API UAFAttributeDurationInfinite : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return false; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationOverride.h new file mode 100644 index 0000000..158d374 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFAttributeDurationOverride.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFAttributeDurationOverride.generated.h" + +/** + * If effect of the same class is already applied it will be removed, and new one will be applied. + */ +UCLASS(meta = (DisplayName = "Duration Override")) +class ABILITYFRAMEWORK_API UAFAttributeDurationOverride : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + + virtual bool ShowPeriod() override + { + return false; + } + virtual bool ShowDuration() override + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationAdd.h new file mode 100644 index 0000000..00a1e2a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationAdd.h @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationAdd.generated.h" + +/** + * Adds new periodic effect. + */ +UCLASS(meta = (DisplayName = "Periodic Add")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationAdd : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) override; + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationExtend.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationExtend.h new file mode 100644 index 0000000..e5efa4e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationExtend.h @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationExtend.generated.h" + +/** + * If periodic effect of the same class already exists it duration will be extended. If not new effect + * will be applied. + */ +UCLASS(meta = (DisplayName = "Periodic Extend")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationExtend : public UAFEffectCustomApplication +{ + GENERATED_BODY() + +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return true; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h new file mode 100644 index 0000000..745850a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationInfiniteAdd.h @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationInfiniteAdd.generated.h" + +/** + * Periodic effect will be applied for infinite amount of time. + */ +UCLASS(meta = (DisplayName = "Periodic Infinite Add")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationInfiniteAdd : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return false; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationOverride.h new file mode 100644 index 0000000..6f7e271 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodApplicationOverride.h @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodApplicationOverride.generated.h" + +/** + * If effect of the same class already exist it will be removed and new effect will be appllied. + */ +UCLASS(meta = (DisplayName = "Periodic Override")) +class ABILITYFRAMEWORK_API UAFPeriodApplicationOverride : public UAFEffectCustomApplication +{ + GENERATED_BODY() +public: + virtual bool ApplyEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + virtual bool ShowPeriod() override + { + return true; + } + virtual bool ShowDuration() override + { + return true; + } + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h new file mode 100644 index 0000000..8d613d5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/CustomApplications/AFPeriodicApplInfiniteOverride.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFPeriodicApplInfiniteOverride.generated.h" + +/** + * Adds infinite periodic effect. If effect of the same class already exists, it will be removed first. + */ +UCLASS(meta=(DisplayName = "Periodic Infinite Override")) +class ABILITYFRAMEWORK_API UAFPeriodicApplInfiniteOverride : public UAFEffectCustomApplication +{ + GENERATED_BODY() + + + virtual void ExecuteEffect( + const FGAEffectHandle& InHandle + , const FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()) + {}; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask.h new file mode 100644 index 0000000..67a5429 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask.h @@ -0,0 +1,37 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "LatentActions/AFTaskBase.h" +#include "GAEffectExtension.h" +#include "GAGlobalTypes.h" +#include "AFAbilityComponent.h" +#include "AFEffectTask.generated.h" + +/** + * + */ +UCLASS(BlueprintType, meta = (ExposedAsyncProxy = "true") ) +class ABILITYFRAMEWORK_API UAFEffectTask : public UAFTaskBase +{ + GENERATED_BODY() +public: + UPROPERTY() + class UGAEffectExtension* Effect; + UPROPERTY() + class UAFEffectsComponent* EffectsComponent; + +public: + template + static T* NewEffectTask(UGAEffectExtension* WorldContextObject, FName InTaskName = FName(), FName InstanceName = FName()) + { + T* MyObj = nullptr; + UGAEffectExtension* EffectExtension = WorldContextObject; + MyObj = NewTask(WorldContextObject, WorldContextObject, InTaskName); + + MyObj->Effect = EffectExtension; + MyObj->EffectsComponent = EffectExtension->OwningComponent; + + return MyObj; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h new file mode 100644 index 0000000..3393112 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AppliedEffectEvent.h @@ -0,0 +1,49 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "../../GAGlobalTypes.h" +#include "AFEffectTask_AppliedEffectEvent.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_AppliedEffectEvent : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_AppliedEffectEvent* ListenAppliedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_AppliedEffectEvent(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFEventData Payload); + + virtual void OnTaskEnded() override; + + FGameplayTag Tag; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AttributeChange.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AttributeChange.h new file mode 100644 index 0000000..1952d19 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_AttributeChange.h @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "AFEffectTask_AttributeChange.generated.h" +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFTaskAttributeChangedDelegate, FAFAttributeChangedData, Payload); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_AttributeChange : public UAFEffectTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FAFTaskAttributeChangedDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_AttributeChange* ListenAttributeChanged(UGAEffectExtension* OwningExtension, + FGAAttribute InAttribute, + AActor* OptionalExternalTarget = nullptr, + bool OnlyTriggerOnce = false); + + UAFEffectTask_AttributeChange(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + void AttributeChangedCallback(FAFAttributeChangedData Payload); + + FGAAttribute Attribute; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h new file mode 100644 index 0000000..81ac081 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "AFEffectTask_EffectAppliedToSelf.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_EffectAppliedToSelf* ListenEffectAppliedToSelf(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_EffectAppliedToSelf(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec); + + virtual void OnTaskEnded() override; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h new file mode 100644 index 0000000..665f5a4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "AFEffectTask_EffectAppliedToTarget.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_EffectAppliedToTarget* ListenEffectAppliedToTarget(UGAEffectExtension* OwningExtension, FName TaskName, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_EffectAppliedToTarget(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFContextHandle Context + , FAFPropertytHandle Property + , FAFEffectSpecHandle Spec); + + virtual void OnTaskEnded() override; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectEvent.h new file mode 100644 index 0000000..52f79d4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectEvent.h @@ -0,0 +1,48 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "../../GAGlobalTypes.h" +#include "AFEffectTask_EffectEvent.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_EffectEvent : public UAFEffectTask +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_EffectEvent* ListenEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_EffectEvent(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFEventData Payload); + + virtual void OnTaskEnded() override; + + FGameplayTag Tag; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h new file mode 100644 index 0000000..c4253e3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_ExecutedEffectEvent.h @@ -0,0 +1,49 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "../../GAGlobalTypes.h" +#include "AFEffectTask_ExecutedEffectEvent.generated.h" + + + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFEffectTask_ExecutedEffectEvent : public UAFEffectTask +{ + GENERATED_BODY() +public: + DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFEffectEventDelegate, FAFEventData, Payload); + UPROPERTY(BlueprintAssignable) + FAFEffectEventDelegate OnEvent; + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects|Tasks", meta = (HidePin = "OwningExtension", DefaultToSelf = "OwningExtension", BlueprintInternalUseOnly = "TRUE")) + static UAFEffectTask_ExecutedEffectEvent* ListenExecutedEffectEvent(UGAEffectExtension* OwningExtension, FName TaskName, FGameplayTag EventTag, AActor* OptionalExternalTarget = nullptr, bool OnlyTriggerOnce = false); + + UAFEffectTask_ExecutedEffectEvent(const FObjectInitializer& ObjectInitializer); + + void SetExternalTarget(AActor* Actor); + + class UAFEffectsComponent* GetTargetASC(); + + virtual void Activate() override; + + virtual void GameplayEventCallback(FAFEventData Payload); + + virtual void OnTaskEnded() override; + + FGameplayTag Tag; + + UPROPERTY() + UAFEffectsComponent* OptionalExternalTarget; + + bool UseExternalTarget; + bool OnlyTriggerOnce; + + FDelegateHandle MyHandle; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h new file mode 100644 index 0000000..62faec3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h @@ -0,0 +1,111 @@ +#pragma once +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Attributes/GAAttributeBase.h" +#include "GAEffectGlobalTypes.h" +#include "GABlueprintLibrary.generated.h" + +UCLASS(BlueprintType, Blueprintable) +class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_UCLASS_BODY() +public: + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static FGAEffectHandle ApplyGameEffectToObject( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + /* + Makes outgoing effect spec and assign handle to it. + If valid handle is provided it will instead reuse existing effect spec from handle, + and just change context of effect. + */ + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static FGAEffectHandle ApplyGameEffectToActor( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + /* + Makes outgoing effect spec and assign handle to it. + If valid handle is provided it will instead reuse existing effect spec from handle, + and just change context of effect. + */ + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static FGAEffectHandle ApplyGameEffectToLocation( + UPARAM(Ref) FAFPropertytHandle& InEffect + , FGAEffectHandle Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + static FGAEffectHandle ApplyEffect( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + static FGAEffectHandle ApplyEffect( + FGAEffectProperty* InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FHitResult& HitIn + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + static FGAEffectHandle ApplyEffectFromHit( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , const FHitResult& Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + static FGAEffectHandle ApplyEffectToActor( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class AActor* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + static FGAEffectHandle ApplyEffectToObject( + FAFPropertytHandle& InEffect + , const FGAEffectHandle& Handle + , class UObject* Target + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + /* + Create Effect but does not apply it. + */ + + static FAFContextHandle MakeContext(class UObject* Target, class APawn* Instigator, AActor* InAvatar, + UObject* Causer, const FHitResult& HitIn); + static void AddTagsToEffect(FAFEffectSpec* EffectIn); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") + static FGAEffectContext& GetContext(const FAFContextHandle& InHandle); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") + static UAFAbilityComponent* GetTargetComponent(const FGAEffectHandle& InHandle); + + UFUNCTION(BlueprintPure, Category = "AbilityFramework|Effects") + static UAFAbilityComponent* GetInstigatorComponent(const FGAEffectHandle& InHandle); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static void BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GACustomCalculation.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GACustomCalculation.h new file mode 100644 index 0000000..265264d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GACustomCalculation.h @@ -0,0 +1,30 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "../GAHelperTemplates.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAGameEffect.h" +#include "GACustomCalculation.generated.h" + +/* + Simple base class for custom magnitude calculation. + You can implement here any kind of formula, taking arbitrary information, for calculations. + + Object is instanced inside effect spec, so you can add custom properties set up, as per + effect spec base. + + Please refrain from making super complicated things, which calculate everything, it's + generally not purpose of this class, but if you really want.. (;. +*/ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class ABILITYFRAMEWORK_API UGACustomCalculation : public UObject +{ + GENERATED_BODY() +public: + UGACustomCalculation(const FObjectInitializer& ObjectInitializer); + + //UFUNCTION(BlueprintNativeEvent, Category = "Attributes") + // float CalculateMagnitude(const FGAEffectContext& ContextIn); + + + virtual float NativeCalculateMagnitude(const FGAEffectContext& ContextIn) { return 0; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectBlueprint.h new file mode 100644 index 0000000..953751b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectBlueprint.h @@ -0,0 +1,31 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAEffectBlueprint.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAEffectBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() + +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAEffectBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectBlueprint* DerivedBlueprint); + +#endif +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h new file mode 100644 index 0000000..0301b04 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h @@ -0,0 +1,85 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Actor.h" +#include "MovieSceneSequencePlayer.h" +#include "GAGlobalTypes.h" +#include "GameplayTags.h" +#include "AssetBundleData.h" +#include "Engine/AssetManager.h" +#include "GAEffectCue.generated.h" +class UActorSequencePlayer; +UCLASS() +class ABILITYFRAMEWORK_API AGAEffectCue : public AActor +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Cue") + FGameplayTag CueTag; + UPROPERTY(AssetRegistrySearchable) + FName EffectCueTagSearch; + UPROPERTY() + FAssetBundleData AssetBundleData; +public: + // Sets default values for this actor's properties + AGAEffectCue(const FObjectInitializer& ObjectInitializer); + void PostInitProperties() override; + + void Serialize(FArchive& Ar) override; + +#if WITH_EDITORONLY_DATA + void UpdateAssetBundleData(); + void PreSave(const class ITargetPlatform* TargetPlatform) override; +#endif //WITH_EDITORONLY_DATA + void PostLoad() override; + FPrimaryAssetId GetPrimaryAssetId() const override; + // Called when the game starts or when spawned + virtual void BeginPlay() override; + + // Called every frame + virtual void Tick( float DeltaSeconds ) override; + + + UFUNCTION(BlueprintImplementableEvent) + void BeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, + const FHitResult& HitInfo); + + UFUNCTION(BlueprintImplementableEvent) + void OnExecuted(); + + UFUNCTION(BlueprintImplementableEvent) + void OnExpired(); + + UFUNCTION(BlueprintImplementableEvent) + void OnRemoved(); + + void NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, + const FHitResult& HitInfo, const FGAEffectCueParams& CueParams); + + void NativeOnExecuted(); + void NativeOnRemoved(); + UPROPERTY() + float Duration; + UPROPERTY() + float Period; + + void SetAnimation(class UGAEffectCueSequence* InSequence); + UPROPERTY() + double StartTime; + UPROPERTY() + double EndTime; + /** Animation being played */ + UPROPERTY(EditAnywhere, Instanced, Export, Category = Animation) + UGAEffectCueSequence* Sequence; + UPROPERTY(transient, BlueprintReadOnly, Category = Animation) + UActorSequencePlayer* SequencePlayer; + + UPROPERTY(EditAnywhere, Category = "Playback", meta = (ShowOnlyInnerProperties)) + FMovieSceneSequencePlaybackSettings PlaybackSettings; + + FTimerHandle PeriodTimer; + +protected: + void UpdateAssetRegistryInfo(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h new file mode 100644 index 0000000..d6af270 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h @@ -0,0 +1,17 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "GAEffectCueBlueprintGeneratedClass.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAEffectCueBlueprintGeneratedClass : public UBlueprintGeneratedClass +{ + GENERATED_UCLASS_BODY() +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueGlobals.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueGlobals.h new file mode 100644 index 0000000..bed97a4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueGlobals.h @@ -0,0 +1,26 @@ +#pragma once +#include "GameplayTagContainer.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" +#include "GAEffectCueGlobals.generated.h" + +USTRUCT() +struct FGACueContainer +{ + GENERATED_USTRUCT_BODY() +public: + TWeakObjectPtr OwningComponent; + + void AddCue(const FGAEffectHandle& HandleIn, const FGAEffectCueParams& CueParamsIn); + + void AddCue(const FGAEffectHandle& HandleIn); + + /* Return cue. Might return null so always check it first! */ + class UGAEffectCue* GetCue(const FGAEffectHandle& HandleIn); + + void ExecuteCue(const FGAEffectHandle& HandleIn); + + void RemoveCue(const FGAEffectHandle& HandleIn); + + void CueExpired(const FGAEffectHandle& HandleIn); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueSequence.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueSequence.h new file mode 100644 index 0000000..c61235f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueSequence.h @@ -0,0 +1,69 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "GameFramework/Actor.h" +#include "MovieSceneSequence.h" +#include "MovieScene.h" +#include "LazyObjectPtr.h" +#include "ActorSequence.h" +#include "FrameNumber.h" +#include "GAEffectCueSequence.generated.h" + +UCLASS(BlueprintType, DefaultToInstanced) +class ABILITYFRAMEWORK_API UGAEffectCueSequence : public UMovieSceneSequence +{ + GENERATED_BODY() + +public: + UPROPERTY(Instanced) + UMovieScene* MovieScene; +private: + /** Collection of object references. */ + //UPROPERTY() + // FActorSequenceObjectReferenceMap ObjectReferences; + +#if WITH_EDITORONLY_DATA +private: + bool bHasBeenInitialized; +#endif +public: + // Sets default values for this actor's properties + UGAEffectCueSequence(const FObjectInitializer& ObjectInitializer); + virtual void PostInitProperties() override; +#if WITH_EDITOR + /** + * Get a placeholder animation. + * + * @return Placeholder animation. + */ + static UGAEffectCueSequence* GetNullAnimation(); + + /** Event that is fired to initialize default state for a sequence */ + DECLARE_EVENT_OneParam(UGAEffectCueSequence, FOnInitialize, UGAEffectCueSequence*) + static FOnInitialize OnInitializeSequenceEvent; +public: + static FOnInitialize& OnInitializeSequence() { return OnInitializeSequenceEvent; } + + +#endif +public: + inline UMovieScene* GetMovieScene() { return MovieScene; } + UFUNCTION(BlueprintCallable, Category = "Animation") + FFrameNumber GetStartTime() const; + + /** + * Get the end time of this animation. + * + * @return End time in seconds. + * @see GetStartTime + */ + UFUNCTION(BlueprintCallable, Category = "Animation") + FFrameNumber GetEndTime() const; + virtual void BindPossessableObject(const FGuid& ObjectId, UObject& PossessedObject, UObject* Context) override; + virtual bool CanPossessObject(UObject& Object, UObject* InPlaybackContext) const override; + virtual UMovieScene* GetMovieScene() const override; + virtual UObject* GetParentObject(UObject* Object) const override; + virtual void UnbindPossessableObjects(const FGuid& ObjectId) override; + virtual void LocateBoundObjects(const FGuid& ObjectId, UObject* Context, TArray>& OutObjects) const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h new file mode 100644 index 0000000..2236b08 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h @@ -0,0 +1,22 @@ +#pragma once +#include "../GAGlobalTypes.h" +#include "../Attributes/GAAttributeBase.h" +#include "GAGameEffect.h" +#include "GAEffectGlobalTypes.h" +#include "GAEffectExecution.generated.h" + +/* + +*/ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class ABILITYFRAMEWORK_API UGAEffectExecution : public UObject +{ + GENERATED_BODY() +public: + UGAEffectExecution(const FObjectInitializer& ObjectInitializer); + + virtual void PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context); + virtual void ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, + const FAFEffectParams& Params, + const FAFFunctionModifier& Modifier = FAFFunctionModifier()); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h new file mode 100644 index 0000000..342e234 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h @@ -0,0 +1,79 @@ +#pragma once +#include "GameplayTagContainer.h" +#include "../GAGlobalTypes.h" +#include "GAGameEffect.h" + +#include "GameplayTaskOwnerInterface.h" +#include "GAEffectExtension.generated.h" +/* + Instanced effect with active event graph, where you can bind events + on application. + + One instance per ability is applied per actor. (ie, one ability can apply only one instanced + effect to each actor). + So this is not suitable for effects which should have ability to be applied multiple times the same + actor to stack in intensity and still have different durations. + + When the same type of instanced effect from the same instigator will be applied to the same actor + old effect will be terminated and new one will be applied. + Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). +*/ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatentInterface //this interface is not needed, but NewTask is expting those functions. +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "Context") + FGAEffectContext Context; + UPROPERTY() + class UAFEffectsComponent* OwningComponent; + UPROPERTY() + class AActor* Avatar; + + UPROPERTY() + TSet ActiveTasks; + + UPROPERTY() + TMap Tasks; + +public: + UGAEffectExtension(const FObjectInitializer& ObjectInitializer); + void SetParameters(const FGAEffectContext& ContextIn); + void BeginEffect(); + + /* + This event is always executed once upon application. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectApplied(); + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectExecuted(); + /* + Event executed when effet naturally expires. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectExpired(); + /* + Event executed when this effect is removed by force. + */ + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectRemoved(); + + void NativeOnEffectApplied(); + void NativeOnEffectExecuted(); + void NativeOnEffectExpired(); + void NativeOnEffectRemoved(); + + virtual UWorld* GetWorld() const override; + + /* IAFLatentInterface */ + virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn); + virtual void AddReplicatedTask(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn); + + virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn); + virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn); + + virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); + /* IAFLatentInterface */ +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectField.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectField.h new file mode 100644 index 0000000..6c02bb4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectField.h @@ -0,0 +1,60 @@ +#pragma once +#include "GAEffectField.generated.h" + +/* + Base class for effect field. + These fields might exist in two states: + 1. As long as ability is channeled. + 2. They are persistent on their own, which means that ability only create them once + and from create tim they might exist set amount of time (including indefinetly), or + until they are manually removed or destroyed. + + Main use cases: + 1. Createing persistent level effects (fire wall, oil puddle, wall of ice etc). + 2. Spawning other actors (rain of meteors, other pawns). + + Possible functionaltity: + 1. Interacting with other fields (Wind field can extinguish fire field). + 2. Interacting with other direct damage/attribute changes (fire damage, can + ignite oil field, creating fire field). + Not sure about this. I would probabaly need to implement this functionality down the line in + GameSystem Module, or add GameAttributes dependency here. + + Fields are only created on server, and then replicated back to clients. + + Need custom K2 Node to properly spawn this actor!. Default SpawnActorFromClass is + not sufficient. +*/ + +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced) +class ABILITYFRAMEWORK_API AGAEffectField : public AActor +{ + GENERATED_UCLASS_BODY() +public: + /** + * If false, field will exist only as long as ability is channeled. + * Otherwise specific life time. + */ + UPROPERTY(BlueprintReadOnly, meta=(ExposeOnSpawn), Category = "Config") + bool bIsFieldPersistent; + + /** + * How long this field will live in world ? + * Only applicable if bIsFieldPersistent = true; + */ + UPROPERTY(BlueprintReadOnly, meta = (ExposeOnSpawn), Category = "Config") + float Lifetime; + + //UPROPERTY(BlueprintReadOnly, Category = "Owner") + //class AGASAbility* AbilityInstigator; + + void InitializeField(); + + void DestroyField(); + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Field") + void OnAbilityExecuted(); + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Field") + void OnOtherFieldOverlap(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectGlobalTypes.h new file mode 100644 index 0000000..0b2fc2c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectGlobalTypes.h @@ -0,0 +1,155 @@ +#pragma once +#include "../AbilityFramework.h" +#include "../Attributes/GAAttributeGlobals.h" +#include "GameplayTagContainer.h" +#include "../GAGlobalTypes.h" +#include "GAEffectGlobalTypes.generated.h" + + +USTRUCT(BlueprintType) +struct FAFFunctionModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + float Additive; + UPROPERTY() + float Subtract; + UPROPERTY() + float Multiply; + UPROPERTY() + float Divide; + + FAFFunctionModifier() + {}; +}; + +/* +Base concept behind those attributes calculations (not sure if these are any good solutions +/performance firendly but: +1. Prefer getting values directly of attributes (GetBaseValue(), GetFinalValue(), GetBonus() etc), +as attributes can track their own state, we don't need any sophisticated way to access them and calculate bonuses). +2. Prefer simple and direct formulas (either evaluate from CurveTable, just plain add, Multiply various numbers, +or get value directly). +3. This system is not inteded, to calculate absolute final value on effect, before that effect is applied. +It will calculate absolute maximum value from the informations it have access to. +Further modifications like increasing specific damage type value, or reducing damage by value, are done +on AttributeComponent, by implementing approperiate functions, or by existing effects, which happen to intercept +incoming effect. +This might change in future though. But even if, I still prefer the magnitude calculations to be simple, +and we will add needed buffs/debuffs as we progress trough execution chain. +4. All calculations are linear. +*/ +//EGAMagnitudeCalculation::Direct +USTRUCT(BlueprintType) +struct FGADirectModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere) + float Value; + + float GetValue(); + float GetValue() const; +}; +//EGAMagnitudeCalculation::AttributeBased +USTRUCT(BlueprintType) +struct FGAAttributeBasedModifier +{ + /* + We also need to add concept of backing attributes, + though I'm not sure how I want to handle them at this point. + */ + GENERATED_USTRUCT_BODY() +public: + /* + Source of Attribute for this calculation. + */ + UPROPERTY(EditAnywhere) + EGAAttributeSource Source; + /* + Name of attribute Used for calculation. + */ + UPROPERTY(EditAnywhere) + FGAAttribute Attribute; + + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float Coefficient; + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float PreMultiply; + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float PostMultiply; + UPROPERTY(EditAnywhere, meta = (FixedIncrement = "0.01")) + float PostCoefficient; + /* + Should we use secondary attribute for this ecalculation ? + */ + UPROPERTY(EditAnywhere) + bool bUseSecondaryAttribute; + /* + Source for secondary attribute + */ + UPROPERTY(EditAnywhere) + EGAAttributeSource SecondarySource; + /* + Name of secondary attribute used in calculation. + */ + UPROPERTY(EditAnywhere) + FGAAttribute SecondaryAttribute; + + FGAAttributeBasedModifier() + : Source(EGAAttributeSource::Instigator), + Coefficient(1), + PreMultiply(0), + PostMultiply(0), + PostCoefficient(1), + bUseSecondaryAttribute(false) + {} + + float GetValue(const FGAEffectContext& Context); + float GetValue(const FGAEffectContext& Context) const; +}; +//EGAMagnitudeCalculation::CurveBased +USTRUCT(BlueprintType) +struct FGACurveBasedModifier +{ + GENERATED_USTRUCT_BODY() +public: + /* + Source of Attribute for this calculation. + */ + UPROPERTY(EditAnywhere) + EGAAttributeSource Source; + /* + Name of attribute from which we will take XValue for Curve + */ + UPROPERTY(EditAnywhere) + FGAAttribute Attribute; + /* + Curve and row from which we will take YValue. + */ + UPROPERTY(EditAnywhere) + FCurveTableRowHandle CurveTable; + + float GetValue(const FGAEffectContext& ContextIn); + float GetValue(const FGAEffectContext& ContextIn) const; +}; +//EGAMagnitudeCalculation::CustomCalculation +USTRUCT(BlueprintType) +struct FGACustomCalculationModifier +{ + GENERATED_USTRUCT_BODY() +public: + /* + Instanced, so we can setup custom properties this class might provide, per effect spec. + */ + UPROPERTY(EditAnywhere, Instanced) + class UGACustomCalculation* CustomCalculation; + + FGACustomCalculationModifier() + : CustomCalculation(nullptr) + {}; + + float GetValue(const FGAEffectContext& ContextIn); + float GetValue(const FGAEffectContext& ContextIn) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h new file mode 100644 index 0000000..3f15281 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h @@ -0,0 +1,1346 @@ +#pragma once +//#include "GAGlobalTypes.h" +#include "GAEffectGlobalTypes.h" +#include "GameplayTagContainer.h" +#include "UObject/ObjectMacros.h" +#include "UObject/GCObject.h" +#include "GAGameEffect.generated.h" + +DECLARE_STATS_GROUP(TEXT("GameEffect"), STATGROUP_GameEffect, STATCAT_Advanced); +DECLARE_CYCLE_STAT_EXTERN(TEXT("GatherModifiers"), STAT_GatherModifiers, STATGROUP_GameEffect, ); + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAMagnitude +{ + GENERATED_USTRUCT_BODY() +public: + /* + Type of calculation we want to perform for this Magnitude. + */ + UPROPERTY(EditAnywhere) + EGAMagnitudeCalculation CalculationType; + + UPROPERTY(EditAnywhere) + FGADirectModifier DirectModifier; + /* + Simple calculation based on attribute: + (Coefficient * (PreMultiply + AttributeValue) + PostMultiply) * PostCoefficient + + There is no any magic manipulation, it straight off pull attribute from selected source, + and make this operation on it. + */ + UPROPERTY(EditAnywhere) + FGAAttributeBasedModifier AttributeBased; + /* + Get value from selected CurveTable, based on selected attribute value. + */ + UPROPERTY(EditAnywhere) + FGACurveBasedModifier CurveBased; + /* + Provide custom calculation class. + */ + UPROPERTY(EditAnywhere) + FGACustomCalculationModifier Custom; + + float GetFloatValue(const FGAEffectContext& Context); +}; +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAAttributeModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Instant Spec") + FGAAttribute Attribute; + + UPROPERTY(EditAnywhere, Category = "Instant Spec") + EGAAttributeMod AttributeMod; + + /* + Who will be target of this attribute change. + Instigator - pawn which applied effect (regardless of to whom). + Target - targeted pawn (regardless of who applied). + */ + UPROPERTY(EditAnywhere) + EGAModifierTarget ModifierTarget; + /* + How modifier will be executed on target. + */ + //UPROPERTY(EditAnywhere, Category = "Execution Type") + // TSubclassOf ExecutionType; + + /* + Modifier value applied to attribute + */ + UPROPERTY(EditAnywhere) + FGAMagnitude Magnitude; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAttributeModifierContainer +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Modifiers; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFCueContainer +{ + GENERATED_BODY() +public: + /* Cues to apply */ + UPROPERTY(EditAnywhere) + FGameplayTagContainer CueTags; +}; + +USTRUCT(BlueprintType) +struct FAFConditionalEffect +{ + GENERATED_BODY() + /* If target have this tag apply specified effects */ + UPROPERTY(EditAnywhere) + FGameplayTag RequiredTag; + UPROPERTY(EditAnywhere) + TSubclassOf Effect; +}; +USTRUCT(BlueprintType) +struct FAFConditionalEffectContainer +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Effects; +}; + + +/* + Base effect class. You can derive your own specialized classes from it + with preset customizations and values. You should never directly inherit blueprints from it. +*/ +UCLASS(Blueprintable, BlueprintType, Abstract, DefaultToInstanced, EditInlineNew) +class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject +{ + GENERATED_BODY() +public: + /* + Replicate effect back to clients ? + */ + UPROPERTY(EditAnywhere, Category = "Network") + bool bReplicate; + + /* + Individual Tag descrbing effect type. + ie. Condition.Burning + */ + UPROPERTY(EditAnywhere, Category = "Effect Info") + FGameplayTag EffectTag; + + UPROPERTY(EditAnywhere, meta=(UseDisplayName), Category = "Effect Info") + TSubclassOf ApplicationRequirement; + /* + How effect should stack. Only relevelant for periodic effects + and modifiers applied on period. + */ + UPROPERTY(EditAnywhere, meta = (UseDisplayName), Category = "Effect Info") + TSubclassOf Application; + + UPROPERTY(EditAnywhere, Category = "Stacking") + int32 MaxStacks; + + /* + Who should aggregate this effect. Relevelant for stacking type + and by this only relevelant for periodic effects. + */ + UPROPERTY(EditAnywhere, Category = "Stacking") + EGAEffectAggregation EffectAggregation; + + /* Total duration of effect (if applicable) */ + UPROPERTY(EditAnywhere, Category = "Duration") + FGAMagnitude Duration; + /* Duration of single period. */ + UPROPERTY(EditAnywhere, Category = "Period") + FGAMagnitude Period; + /* Total duration of effect (if applicable) */ + UPROPERTY(EditAnywhere, Category = "Duration") + float MaxStackedDuration; + + /* IF true, effect will tick instantly upon application. */ + UPROPERTY(EditAnywhere, Category = "Duration") + bool bTickOnApplication; + UPROPERTY(EditAnywhere, Category = "Duration") + bool bExecuteOnApplication; + + + /* + Modifier applied to attribute + */ + UPROPERTY(EditAnywhere, Category = "Attribute Modifiers") + FGAAttributeModifier AtributeModifier; + UPROPERTY(EditAnywhere, Category = "Attribute Modifiers") + FAFAttributeModifierContainer Modifiers; + + UPROPERTY(EditAnywhere, Category = "Execution Type") + TSubclassOf ExecutionType; + + UPROPERTY(EditAnywhere, Category = "Modifiers") + TSubclassOf Extension; + + /* Cues to apply by this effect. */ + UPROPERTY(EditAnywhere, Category = "Cues") + FAFCueContainer Cues; + /* + Effects applied when this effect is applied. + These effects will be applied with the same context and the same target as + effect, which stores them. + */ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> OnAppliedEffects; + + /* Effects applied when this effect expire*/ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> OnExpiredEffects; + + /* Effects applied when this effect is removed. */ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + TArray> OnRemovedEffects; + + UPROPERTY(EditAnywhere, Category = "Event Tags") + FGameplayTag OnExpiredEvent; + UPROPERTY(EditAnywhere, Category = "Event Tags") + FGameplayTag OnPeriodEvent; + UPROPERTY(EditAnywhere, Category = "Event Tags") + FGameplayTag OnRemovedEvent; + + + UPROPERTY(EditAnywhere, Category = "Event Application Tags") + FGameplayTag OnEffectApplyToTargetEvent; + UPROPERTY(EditAnywhere, Category = "Event Application Tags") + FGameplayTag OnEffectApplyToSelfEvent; + + /* + Effects applied only when certain criteria are met. + Just dumbed here it needs it's own structure that will actually alow to setup those conditions. + */ + UPROPERTY(EditAnywhere, Category = "Linked Effects") + FAFConditionalEffectContainer IfHaveTagEffect; + + + /* Remove effects with these tags. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer RemoveEffectWithTags; + + /* + Tags descrbing what this effect does. + */ + /* Tags I own and I don't apply. New tags can be added here as the effect is applied. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer OwnedTags; + /* Tags owned by this effect and not applied. Describe the type of this effect. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer EffectTags; + + /* + When effect is appied trigger events with these tags. + */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer AppliedEventTags; + /* + When effect is executed trigger events with these tags. + */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ExecuteEventTags; + + /* + Tags applied to attribute when effect is applying non-instant effect. + Owned tags of another effect are checked against these tags to calculate + modifier. + Also it's checked when tag is applied to determine effect stacking, + when stacking is set to Override or StrongerOverride. + + Use only single tag here, with proper hierarchy. + Using multiple tags should be reserved only for special cases. + */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer AttributeTags; + + /* If Target have these tags I will not be applied to it. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer DenyTags; + + /* Applied immunity tags. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer AppliedImmunityTags; + + /* Tags, which are applied to Target when effect is Duration/Periodic based. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ApplyTags; + + /* Tags, required for this effect to be applied. If these tags are not present, effect will be ignored. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer RequiredTags; + + /* Tags, required for this effect to be executed. If these tags are not present, effect will be ignored. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ExecutionRequiredTags; +public: + UGAGameEffectSpec(); +}; +/* + Base effect class to extend from when creating effect blueprints. +*/ +UCLASS(Blueprintable, BlueprintType, Abstract) +class ABILITYFRAMEWORK_API UAFEffectSpecBase : public UGAGameEffectSpec +{ + GENERATED_BODY() +public: +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectClass +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Effect") + TSubclassOf SpecClass; + + FGAEffectClass() + {} + FGAEffectClass(TSubclassOf InClass) + : SpecClass(InClass) + {} + const bool operator==(const FGAEffectClass& Other) const + { + return SpecClass == Other.SpecClass; + } + const bool operator==(const TSubclassOf& OtherClass) const + { + return SpecClass == OtherClass; + } + void operator=(const FGAEffectClass& Other) + { + SpecClass = Other.SpecClass; + } + void operator=(const TSubclassOf& Other) + { + SpecClass = Other; + } + void operator=(UGAGameEffectSpec* Other) + { + SpecClass = Other->GetClass(); + } +}; + +USTRUCT(BlueprintType) +struct FAFContextHandle +{ + GENERATED_BODY() +private: + TSharedPtr DataPtr; + uint32 ID; +public: + static FAFContextHandle Generate(FGAEffectContext* InContext) + { + static uint32 id = 0; + id++; + + TSharedPtr PropPtr = MakeShareable(InContext); + FAFContextHandle Handle(PropPtr, id); + + return Handle; + } + + FAFContextHandle() + : ID(0) + {}; +protected: + FAFContextHandle(TSharedPtr InProperty, uint32 InID) + : DataPtr(InProperty) + , ID(InID) + {}; + +public: + bool IsValid() + { + return DataPtr.IsValid(); + } + + FGAEffectContext& GetRef() + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectContext& GetRef() const + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectContext* GetPtr() + { + return DataPtr.Get(); + } + FGAEffectContext* GetPtr() const + { + return DataPtr.Get(); + } + + void SetTarget(UObject* NewTarget) + { + DataPtr->SetTarget(NewTarget); + } + + bool operator==(const FAFContextHandle& Other) const + { + return ID == Other.ID; + } + + bool operator==(const FObjectKey& Other) const + { + return *DataPtr.Get() == Other; + } + bool operator==(UObject* Other) const + { + return *DataPtr.Get() == Other; + } + + friend uint32 GetTypeHash(const FAFContextHandle& InHandle) + { + return InHandle.ID; + } +}; + +template<> +struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + }; +}; + +/* + +*/ + +struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject +{ +private: + FAFContextHandle Context; + UGAEffectExtension* Extension; //week ptr ? + + TSubclassOf SpecClass; +public: + + FGameplayTagContainer OwnedTags; + FGameplayTagContainer ApplyTags; + FGameplayTagContainer RequiredTags; + +public: + FAFEffectSpec() + : Extension(nullptr) + {} + + FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass); + + void OnApplied(); + void OnExpired(); + void OnRemoved(); + void OnExecuted(); + + void AddOwnedTags(const FGameplayTagContainer& InTags) + { + OwnedTags.AppendTags(InTags); + } + void AddApplyTags(const FGameplayTagContainer& InTags) + { + ApplyTags.AppendTags(InTags); + } + + UGAGameEffectSpec* GetSpec() + { + return SpecClass.GetDefaultObject(); + } + + float GetFloatFromAttributeMagnitude( + const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext) const; + + float GetDuration(const FGAEffectContext& InContext); + float GetPeriod(const FGAEffectContext& InContext); + + const TSubclassOf& GetEffectClass() + { + return SpecClass; + } + + virtual void AddReferencedObjects(FReferenceCollector& Collector) override + { + Collector.AddReferencedObject(Extension, Context.GetPtr()->Target.Get()); + } + +}; +USTRUCT(BlueprintType) +struct FAFEffectSpecHandle +{ + GENERATED_BODY() +public: + TSharedPtr SpecPtr; + uint32 ID; + +public: + static FAFEffectSpecHandle Generate(FAFEffectSpec* Effect) + { + static uint32 id = 0; + id++; + + TSharedPtr PropPtr = MakeShareable(Effect); + FAFEffectSpecHandle Handle(PropPtr, id); + + return Handle; + } + + FAFEffectSpecHandle() + : ID(0) + {} + FAFEffectSpecHandle(TSharedPtr Ptr, uint32 InID) + : SpecPtr(Ptr) + , ID(InID) + {} + + bool IsValid() + { + return SpecPtr.IsValid(); + } + + TSharedPtr GetPtr() + { + return SpecPtr; + } + FAFEffectSpec& GetRef() + { + return SpecPtr.ToSharedRef().Get(); + } + FAFEffectSpec& GetRef() const + { + return SpecPtr.ToSharedRef().Get(); + } +}; +template<> +struct TStructOpsTypeTraits< FAFEffectSpecHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + }; +}; + + + +/* + Container for: + 1. Effect handles applied from this property, sorted per target. + 2. Their contexts (each effect have it's own context). + 3. Targets affected by effect from this container (and which effect). + + Also contains hard pointers to base classes/assets used by effect (Execution, Application, Specification). +*/ + +struct FAFEffectParams; + +struct ABILITYFRAMEWORK_API FGAEffectProperty +{ +protected: + + TWeakObjectPtr ApplicationRequirement; + TWeakObjectPtr Application; + TWeakObjectPtr Execution; + TWeakObjectPtr Spec; + FAFPredictionHandle PredictionHandle; + + float Duration; + float Period; + bool bInstant; + /* + Handle to effect created from SpecClass + This handle is only created and kept for instant effects, + so we don't create new object every time instant effect is created + as potentially there can be quite a lot of allocations. + */ + /* + Holds handle to duration/infinite effects. Since there can be multiple effects active on multiple targets. + + */ + + FAFContextHandle InstantContext; + FAFEffectSpecHandle InstantEffectSpec; + + TMap EffectSpecs; + //Cached context per created effect. + TMap Contexts; + //possibly multiple handles per target ? + TMap Handles; + TMap HandleToTarget; + TMap EffectCues; +public: + FGAEffectProperty(); + + FGAEffectProperty(TSubclassOf InClass); + void PostScriptConstruct(); + + UGAGameEffectSpec* GetSpec() { return Spec.Get(); } + UGAGameEffectSpec* GetSpec() const { return Spec.Get(); } + + bool CanApply( + const struct FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& InParams + , const FGAEffectHandle& InHandle); + + bool ApplyEffect(const FGAEffectHandle& InHandle + , const struct FGAEffect& EffectIn + , struct FGAEffectContainer* InContainer + , const FAFEffectParams& InParams + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + void ApplyExecute(const FGAEffectHandle& InHandle + , const FAFEffectParams& InParams + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + void ExecuteEffect(const FGAEffectHandle& HandleIn + , FGAEffectMod& ModIn + , const FAFEffectParams& InParams + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + //intentionally non const. + //FGAEffectHandle& GetHandleRef() { return Handle; } + //void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; + void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} + + void Initialize(TSubclassOf EffectClass); + void InitializeIfNotInitialized(const FGAEffectContext& InContext + , TSubclassOf EffectClass); + + bool GetIsInstant() const + { + return bInstant; + } + inline float GetPeriod() const + { + return Period; + } + inline float GetDuration() const + { + return Duration; + } + + void RegisterHandle( + UObject* Target + , const FGAEffectHandle& InHandle + , const FAFContextHandle& Context + , const FAFEffectSpecHandle& Spec) + { + if (bInstant) + { + InstantContext = Context; + InstantEffectSpec = Spec; + return; + } + if (HandleToTarget.Contains(InHandle)) + { + UE_LOG(GameAttributes, Log, TEXT("FGAEffectProperty::RegisterHandle Handle already registered \n")); + return; + } + + AddHandle(Target, InHandle); + AddContext(InHandle, Context); + AddEffectSpec(InHandle, Spec); + } + + void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) + { + FObjectKey key(Target); + Handles.Add(key, InHandle); + HandleToTarget.Add(InHandle, Target); + } + + FGAEffectHandle GetHandle(UObject* From) + { + FObjectKey key(From); + if (FGAEffectHandle* handle = Handles.Find(key)) + return *handle; + + return FGAEffectHandle(); + } + FGAEffectHandle GetHandle(UObject* From) const + { + FObjectKey key(From); + if (const FGAEffectHandle* handle = Handles.Find(key)) + return *handle; + + return FGAEffectHandle(); + } + + FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) + { + if (bInstant) + { + return InstantContext; + } + FAFContextHandle* Ctx = Contexts.Find(InHandle); + if (Ctx) + { + return *Ctx; + } + return InstantContext; + } + const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const + { + if (bInstant) + { + return InstantContext; + } + const FAFContextHandle* Ctx = Contexts.Find(InHandle); + if (Ctx) + { + return *Ctx; + } + return InstantContext; + } + + void AddContext(const FGAEffectHandle& InHandle, const FAFContextHandle& ContextHandle) + { + Contexts.Add(InHandle, ContextHandle); + } + + void RemoveContext(const FGAEffectHandle& InHandle) + { + Contexts.Remove(InHandle); + } + + FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) + { + if (bInstant) + { + return InstantEffectSpec; + } + FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); + if (Spec) + { + return *Spec; + } + return InstantEffectSpec; + } + const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const + { + if (bInstant) + { + return InstantEffectSpec; + } + const FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); + if (Spec) + { + return *Spec; + } + return InstantEffectSpec; + } + + void AddEffectSpec(const FGAEffectHandle& InHandle, const FAFEffectSpecHandle& ContextHandle) + { + EffectSpecs.Add(InHandle, ContextHandle); + } + + void RemoveEffectSpec(const FGAEffectHandle& InHandle) + { + EffectSpecs.Remove(InHandle); + } + + inline FAFPredictionHandle GetPredictionHandle() const + { + return PredictionHandle; + } + + bool IsHandleValid(UObject* For) + { + FObjectKey Key(For); + FGAEffectHandle* Handle = Handles.Find(Key); + if (Handle) + { + return Handle->IsValid(); + } + return false; + } + bool IsHandleValid(UObject* For) const + { + FObjectKey Key(For); + const FGAEffectHandle* Handle = Handles.Find(Key); + if (Handle) + { + return Handle->IsValid(); + } + return false; + } + void RemoveHandle(const FGAEffectHandle& InHandle) + { + UObject* Target = nullptr; + HandleToTarget.RemoveAndCopyValue(InHandle, Target); + if(Target) + { + FObjectKey key(Target); + Handles.Remove(key); + } + } + + void CleanUp(const FGAEffectHandle& InHandle) + { + RemoveContext(InHandle); + EffectCues.Remove(InHandle); + RemoveHandle(InHandle); + RemoveEffectSpec(InHandle); + } + + void SetPredictionHandle(const FAFPredictionHandle& InHandle) + { + PredictionHandle = InHandle; + } + + FGAAttributeModifier& GetAttributeModifier() + { + return Spec->AtributeModifier; + } + + + const bool IsInitialized() const + { + return ApplicationRequirement.IsValid() && Application.IsValid() && Execution.IsValid() && Spec.IsValid(); + } + /*const bool IsValidHandle() const + { + return Handle.IsValid(); + }*/ + +}; +template<> +struct TStructOpsTypeTraits< FGAEffectProperty > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + WithPostScriptConstruct = true, + }; +}; + +USTRUCT(BlueprintType) +struct FAFPropertytHandle +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Effect") + FGAEffectClass SpecClass; + + TSharedPtr DataPtr; + //TSharedRef Test; + + uint32 ID; +public: + FAFPropertytHandle() + : ID(0) + { + if (!DataPtr.IsValid()) + { + DataPtr = MakeShareable(new FGAEffectProperty()); + } + }; + + FAFPropertytHandle(TSubclassOf InSpecClass) + : ID(0) + { + SpecClass = InSpecClass; + if (!DataPtr.IsValid()) + { + DataPtr = MakeShareable(new FGAEffectProperty()); + } + }; + + FAFPropertytHandle(const FAFPropertytHandle& Other) + { + SpecClass = Other.SpecClass; + DataPtr = Other.DataPtr; + }; + + + + void PostScriptConstruct() + { + } + /*FAFPropertytHandle(TSharedRef InPtr, uint32 InID) + : Test(InPtr) + , ID(InID) + {}*/ + + TSubclassOf GetClass() const { return SpecClass.SpecClass; } + const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } +public: + + void InitializeIfNotInitialized(const FGAEffectContext& InContext) + { + DataPtr->InitializeIfNotInitialized(InContext, SpecClass.SpecClass); + } + FGAEffectProperty & GetRef() + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectProperty& GetRef() const + { + return DataPtr.ToSharedRef().Get(); + } + FGAEffectProperty* GetPtr() const + { + return DataPtr.Get(); + } + + FObjectKey GetClassKey() const + { + return FObjectKey(GetClass()); + } + inline float GetPeriod() const + { + return DataPtr->GetPeriod(); + } + inline float GetDuration() const + { + return DataPtr->GetDuration(); + } + + UGAGameEffectSpec* GetSpec() + { + return DataPtr->GetSpec(); + } + UGAGameEffectSpec* GetSpec() const + { + return DataPtr->GetSpec(); + } + FGAEffectHandle GetHandle(UObject* From) + { + return DataPtr->GetHandle(From); + } + FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) + { + return DataPtr->GetContext(InHandle); + } + const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const + { + return DataPtr->GetContext(InHandle); + } + FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) + { + return DataPtr->GetEffectSpec(InHandle); + } + const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const + { + return DataPtr->GetEffectSpec(InHandle); + } + void CleanUp(const FGAEffectHandle& InHandle) + { + DataPtr->CleanUp(InHandle); + } + const bool IsInitialized() const + { + return DataPtr->IsInitialized(); + } + const bool IsValid() const + { + return SpecClass.SpecClass ? true : false; + } + const bool operator==(const FAFPropertytHandle& Other) const + { + return SpecClass == Other.SpecClass; + } + const bool operator==(const TSubclassOf& OtherClass) const + { + return SpecClass == OtherClass; + } + FAFPropertytHandle& operator=(const FAFPropertytHandle& Rhs) + { + if (this == &Rhs) + return *this; + DataPtr = Rhs.DataPtr; + SpecClass = Rhs.SpecClass; + return *this; + } + void operator=(const TSubclassOf& Other) + { + SpecClass = Other; + } + void operator=(UGAGameEffectSpec* Other) + { + SpecClass = Other->GetClass(); + } +}; + +template<> +struct TStructOpsTypeTraits< FAFPropertytHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithCopy = true, + WithPostScriptConstruct = true, + }; +}; + +USTRUCT() +struct FAFEffectParams +{ + GENERATED_BODY() + //make this private and allow assign only trough constructr. + FAFContextHandle Context; + FAFPropertytHandle Property; + FAFEffectSpecHandle EffectSpec; + bool bRecreated; + bool bPeriodicEffect; +public: + FAFEffectParams() + {}; + FAFEffectParams(FAFPropertytHandle InProperty) + : bRecreated(false) + , Property(InProperty) + {}; + + FGAEffectContext & GetContext() + { + return Context.GetRef(); + } + FGAEffectContext& GetContext() const + { + return Context.GetRef(); + } + + FGAEffectProperty& GetProperty() const + { + return Property.GetRef(); + } + + FAFEffectSpec& GetSpec() + { + return EffectSpec.SpecPtr.ToSharedRef().Get(); + } + FAFEffectSpec& GetSpec() const + { + return EffectSpec.SpecPtr.ToSharedRef().Get(); + } + FTimerManager& GetTargetTimerManager(); + + UAFEffectsComponent* GetTargetEffectsComponent(); + UAFEffectsComponent* GetTargetEffectsComponent() const; + +}; + +USTRUCT(BlueprintType) +struct FAFEventData +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly) + FAFContextHandle ContextHandle; + UPROPERTY(BlueprintReadOnly) + FAFEffectSpecHandle SpecHandle; + UPROPERTY(BlueprintReadOnly) + FAFPropertytHandle PropertyHandle; + + FAFEventData() + {}; + + FAFEventData(FAFContextHandle InContextHandle + , FAFEffectSpecHandle InSpecHandle + , FAFPropertytHandle InPropertyHandle + ) + : ContextHandle(InContextHandle) + , SpecHandle(InSpecHandle) + , PropertyHandle(InPropertyHandle) + {}; + + FAFEventData(const FAFEffectParams& EffectParams) + : ContextHandle(EffectParams.Context) + , SpecHandle(EffectParams.EffectSpec) + , PropertyHandle(EffectParams.Property) + {}; + +}; + +struct FAFStatics +{ + static float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn + , const FGAEffectContext& InContext + , const FGAEffectHandle& InHandle); + static FGAEffectMod GetAttributeModifier(FGAAttributeModifier& ModInfoIn + , class UGAGameEffectSpec* InSpec, + const FGAEffectContext& InContext, + const FGAEffectHandle& InHandle); +}; + +/* + Calculcated magnitudes, captured attributes and tags, set duration. + Final effect which then is used to apply custom calculations and attribute changes. +*/ +DECLARE_MULTICAST_DELEGATE_OneParam(FAFEffectMulicastDelegate, const FGAEffectHandle&); +UENUM() +enum class ERepInfoType : uint8 +{ + LocallyPredicted, + RemotePredicted, + Server +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, TSharedFromThis +{ + GENERATED_BODY() + + FGAEffectHandle Handle; + UPROPERTY() + FAFPredictionHandle PredictionHandle; + + mutable FTimerHandle PeriodTimerHandle; + mutable FTimerHandle DurationTimerHandle; + + UWorld* World; + +public: + float AppliedTime; + float LastTickTime; + float Period; + float Duration; +public: + void PreReplicatedRemove(const struct FGAEffectContainer& InArraySerializer); + void PostReplicatedAdd(const struct FGAEffectContainer& InArraySerializer); + void PostReplicatedChange(const struct FGAEffectContainer& InArraySerializer); + + inline void SetHandle(const FGAEffectHandle& InHandle) + { + Handle = InHandle; + } + + float GetDurationTime() const; + float GetPeriodTime() const; + float GetCurrentDuration() const; + //float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn) const; + + FGAEffect() + {} + + ~FGAEffect(); + + + bool operator==(const FGAEffect& Other) const + { + return Handle == Other.Handle; + } +}; + +/* + Minimum replicated info about applied info, so we don't replicate full effect if not needed. + Also provide callbacks for cues assigned to this Effect, so they can be predictevly, + executed on clients. + + Add replication optimization. +*/ + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectAttributeModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere) + FGAAttribute Attribute; + UPROPERTY(EditAnywhere) + float Value; +}; +USTRUCT(BlueprintType) +struct FGAEffectDuration +{ + GENERATED_USTRUCT_BODY() +public: + /* + -1 infinite duration, 0-no duration >0 - set duration + */ + UPROPERTY(EditAnywhere, Category = "Duration") + float Duration; + /* + <=0 - no period >0 - set period + */ + UPROPERTY(EditAnywhere, Category = "Duration") + float Period; + /* + If PeriodNum > 0 and Period > 0, then duration of + effect is PeriodNum * Period + */ + UPROPERTY(EditAnywhere, Category = "Duration") + float PeriodNum; +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAInstigatorInstancedEffectContainer +{ + GENERATED_USTRUCT_BODY() + + UPROPERTY() + TArray Effects; +}; + + +USTRUCT() +struct ABILITYFRAMEWORK_API FGAGameCue +{ + GENERATED_BODY() + + + //Handle to effect, which spawned this cue. + UPROPERTY() + FGAEffectHandle EffectHandle; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGameCueContainer +{ + GENERATED_USTRUCT_BODY() + + TWeakObjectPtr OwningComp; +public: + void AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams); +}; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer +{ + GENERATED_BODY() +public: + UPROPERTY() + TArray ActiveEffectInfos; + + UPROPERTY() + TMap HandleByPrediction; + + UPROPERTY() + TMap PredictionByHandle; + + + TMap PredictedEffectInfos; + + + TMap> EffectByAttribute; + + + TMap> EffectByClass; + + TMap ActiveEffects; + /* + Contains effects with infinite duration. + Infinite effects are considred to be special case, where they can only be self spplied + and must be manually removed. + */ + UPROPERTY() + TSet InfiniteEffects; + + //not really sure if we really need set.\ + // it could be usefull, for effects which stack in add. + /* + UObject* - Instigator + FName = Effect class name + FGAEffectHandle = handle to effect of class. + */ + + TMap>> InstigatorEffectByClass; + + /* + FName = Effect class name + FGAEffectHandle = handle to effect of class. + */ + + TMap> TargetEffectByClass; + + //Conditonally applied effects. Only duration/periodic. + //TMap ConditionalEffects; + + UPROPERTY(NotReplicated) + class UAFEffectsComponent* OwningComponent; +public: + + /* + * @call Order: + * Previous Function: UAFAbilityComponent::ApplyEffectToSelf + * Next Function: InProperty.Application->ApplyEffect(); + * FGAEffectContainer::ApplyReplicationInfo() + * + * Apply target to Me. Try to apply effect to container and launch Events in: + * TMap OnEffectEvent - event is called before application; + * TMap OnEffectApplyToSelf - event is called before application; + * + * @param EffectIn* - Effect to apply + * @param InProperty - cached effect information + * @param InContext - Context about effect application. Target, instigator, causer. + * @param Modifier - optional modifier which can be applied to effect. + * @return Handle to Effect @ UAFAbilityComponent::ApplyEffectToSelf + */ + FGAEffectHandle ApplyEffect( + const FGAEffect& EffectIn + , const FGAEffectHandle& InHandle + , const FAFEffectParams& Params + , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); + + /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ + TArray RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num = 1); + /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ + void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty); + + inline int32 GetEffectsNum() const { return ActiveEffectInfos.Num(); }; + + TSet GetHandlesByClass(const FGAEffectProperty& InProperty, + const FGAEffectContext& InContext); + + void AddEffect( + const FGAEffectHandle& InHandle + , const FAFPredictionHandle& InPredHandle + , FGAEffect* InEffect + , const FGAEffectProperty& InProperty + , bool bInfinite = false); + + //modifiers + void ApplyEffectsFromMods() {}; + void DoesQualify() {}; + bool IsEffectActive(const FGAEffectHandle& HandleIn); + bool IsEffectActive(const FGAEffectHandle& HandleIn) const; + bool ContainsEffectOfClass(const FAFPropertytHandle& InProperty); + + void ApplyFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle, FGAEffect* InEffect); + void RemoveFromReplication(const FGAEffectHandle& InHandle, const FAFPredictionHandle& InPredHandle); + + bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) + { + //return FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); + return FFastArraySerializer::FastArrayDeltaSerialize(ActiveEffectInfos, DeltaParms, *this); + } + + UWorld* GetWorld() const; + + ///Helpers + float GetRemainingTime(const FGAEffectHandle& InHandle) const; + float GetRemainingTimeNormalized(const FGAEffectHandle& InHandle) const; + /* Get Current effect ime clamped to max duration */ + float GetCurrentTime(const FGAEffectHandle& InHandle) const; + float GetCurrentTimeNormalized(const FGAEffectHandle& InHandle) const; + float GetEndTime(const FGAEffectHandle& InHandle) const; + + FGAEffect* GetEffect(const FGAEffectHandle& InHandle) + { + return ActiveEffects[InHandle]; + } + bool IsEffectActive(TSubclassOf EffectClass); +private: + void RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle); +}; +template<> +struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithNetDeltaSerializer = true, + WithCopy = false + }; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h new file mode 100644 index 0000000..015aabd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h @@ -0,0 +1,790 @@ +#pragma once +#include "AbilityFramework.h" +#include "GameplayTagsModule.h" +#include "GameplayTagContainer.h" +//#include "Messaging.h" +#include "GAGlobalTypes.generated.h" + +void AddLogDebugInfo(FString Text, UWorld* World); + +/* + Explanation of tags from Fred K, on forums: + https://forums.unrealengine.com/showthread.php?57988-GameplayAbilities-questions&p=220315#post220315 + Here are some examples to illustrate the possible results. Let's assume that our + tag container contains exactly one tag, "A.B.C". + + HasTag("A.B.C", Explicit, Explicit) returns true. + HasTag("A.B", Explicit, Explicit) returns false. + HasTag("A.B.C.D", Explicit, Explicit) returns false. + HasTag("E.B.C", Explicit, Explicit) returns false. + HasTag("A.B.C", IncludeParentTags, IncludeParentTags) returns true. + HasTag("A.B", IncludeParentTags, IncludeParentTags) returns true. + HasTag("A.B.C.D", IncludeParentTags, IncludeParentTags) returns true. + HasTag("E.B.C", IncludeParentTags, IncludeParentTags) returns false. + HasTag("A.B.C", IncludeParentTags, Explicit) returns true. + HasTag("A.B", IncludeParentTags, Explicit) returns true. + HasTag("A.B.C.D", IncludeParentTags, Explicit) returns false. + HasTag("E.B.C", IncludeParentTags, Explicit) returns false. + HasTag("A.B.C", Explicit, IncludeParentTags) returns true. + HasTag("A.B", Explicit, IncludeParentTags) returns false. + HasTag("A.B.C.D", Explicit, IncludeParentTags) returns true. + HasTag("E.B.C", Explicit, IncludeParentTags) returns false. +*/ + +/* + I seriosuly need to clean this shit up. +*/ +/* + TODO:: I probabaly need to change it to normal enum. + So I can use it as array indexes. +*/ +UENUM() +enum class EGAAttributeMod : int32 +{ + Add = 0, //Value = Value + X + Subtract = 1, //Value = Value - X + Multiply = 2, //Value = Value * X + Divide = 3,//Value = Value * X - ok its's not really divide. + Set = 4, //Value = X + PercentageAdd = 5, + PercentageSubtract = 6, + Invalid = 7 +}; + +UENUM() +enum class EGAAttributeSource : uint8 +{ + Instigator, + Target, + Causer, + Ability +}; + +UENUM() +enum class EGAModifierTarget : uint8 +{ + Instigator, + Target +}; + +UENUM() +enum class EGAAttributeValue : uint8 +{ + Base, + Current, + Final, + Bonus +}; + +UENUM() +enum class EGAEffectType : uint8 +{ + Instant = 0, + Duration = 1, + Infinite = 2, +}; + +/* + + StrongetOverride - Does not check for effect type/tags. It will just check if modified + attribute, is already modified, and if incoming effect is stronger it will override + all modifiers affecting this attribute, and remove all weaker ones. + + Override - does not check if it is stronger/weaker, it will simply override any existing modifiers + and effects with the same name. + + Duration - Will add duration to existing effect of EXACTLY the same type. + + Intensity - Undefined. It will either add new effects to stack, + or it will simply sum modifiers, from all effects of the same types, for the same attributes + and refresh duration to the latest applied effect. + + Add - no checks, simply add new effect to stack. +*/ +UENUM() +enum class EGAEffectStacking : uint8 +{ + Add = 0, + Duration = 1, + Override = 2, //override existing effect of the same type, and all other effects which have override the same attribute and have same AttributeTags + Intensity = 3, + //will add duration to existing effect + //will simply add new effect +}; + +UENUM() +enum class EGAMagnitudeCalculation : uint8 +{ + Direct, //straight float value, no calculations. + AttributeBased, //calculate based on attribute Attribute * RestOfEquationToBeDecided + CurveBased, //Takes value of attribute, and then gets value from curve based on this attribute. + CustomCalculation,//uses custom object to calculate magnitude. + Invalid +}; + + +/* +Rules for where we should aggregate effects. +Concept might look bit muddy at first look, but it is actually very simple. + +Let's say we have additive effect which modify Health by 50 points, and effect which modify health by 100. +We want, to only the highest one, affect target (positive bonus). Regardless of who applied this effect. + +To do it we need to tell this effect, that it should be aggregated by target and set effect stacking rule to +HighestOverride. + +Now say we have effect which reduce Health by 30 points, and second which reduce by 20 points. +We might want negative effects from diffrent source to stack. +To do this we need to aggregate those effects by Instigator. +And then we can decide how those effects will stack within single Instigator. +*/ +UENUM() +enum class EGAEffectAggregation : uint8 +{ + /* + Effect will be stacked/aggregated by Instigator who applied it. + Checking for stacking rules will be done only against other effects from the same Instigator. + */ + AggregateByInstigator, + /* + Effects will be stacked/aggregated by Target. + Checking for stacking rules, will be done only for effects, with the same target. + */ + AggregateByTarget +}; + +USTRUCT() +struct FAFAtributeRowData : public FTableRowBase +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float BaseValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float MinValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float MaxValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + float CurrentValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly) + TSubclassOf Extension; +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectContext +{ + GENERATED_USTRUCT_BODY() +public: + /* + Just copy entire hit result struct. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + FHitResult HitResult; + /** + * Where exactly we hit target. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + FVector TargetHitLocation; + + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr TargetAttributes; + + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr InstigatorAttributes; + + /** + * Direct Reference to TargetActor (I will possibly remove FHitResult Target! + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Target; + /** + * Object which caused this effect. Might be ability, weapon, projectile etc. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Causer; + /** + * Pawn, which originally instigated effect (an owned AttributeComponent). + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Instigator; + + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr Avatar; + /** + * Attribute component of Target. + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr TargetComp; + /** + * Attribute component of Intigator + */ + UPROPERTY(BlueprintReadOnly, Category = "Spec") + TWeakObjectPtr InstigatorComp; + + class IAFAbilityInterface* TargetInterface; + class IAFAbilityInterface* InstigatorInterface; + + void SetTarget(UObject* NewTarget); + template + inline T* GetTarget() + { + return Cast(Target); + } + + inline bool IsValid() const + { + /*if (Target.IsValid() && Causer.IsValid() && Instigator.IsValid() && TargetComp.IsValid() && InstigatorComp.IsValid()) + return true;*/ + if (Causer.IsValid() && Instigator.IsValid() && InstigatorComp.IsValid() && TargetInterface) + return true; + //UE_LOG(GameAttributesEffects, Error, TEXT("Effect Context Is Not Valid")); + return false; + } + + inline FString ToString() + { + if (!IsValid()) + { + //UE_LOG(GameAttributesEffects, Error, TEXT("Effect Context Is Not Valid")); + return FString("Context Is not valid"); + } + FString ret; + ret = "TargetHitLocation: "; + ret += TargetHitLocation.ToString(); + ret += "\n"; + ret += "Target: "; + ret += Target->GetName(); + ret += "\n"; + ret += "Causer: "; + ret += Causer->GetName(); + ret += "\n"; + ret += "Instigator: "; + ret += Instigator->GetName(); + ret += "\n"; + ret += "TargetComp: "; + return ret; + } + + bool operator==(UObject* Other) const + { + return FObjectKey(Target.Get()) == FObjectKey(Other); + } + + bool operator==(const FObjectKey& Other) const + { + return FObjectKey(Target.Get()) == Other; + } + + void Reset(); + + class UGAAttributesBase* GetTargetAttributes(); + class UGAAttributesBase* GetInstigatorAttributes(); + class UGAAttributesBase* GetCauserAttributes(); + + class UGAAttributesBase* GetTargetAttributes() const; + class UGAAttributesBase* GetInstigatorAttributes() const; + class UGAAttributesBase* GetCauserAttributes() const; + + class UAFEffectsComponent* GetTargetEffectsComponent(); + class UAFEffectsComponent* GetTargetEffectsComponent() const; + void operator=(const FGAEffectContext& Other); + FGAEffectContext() + {} + + FGAEffectContext(const FGAEffectContext& Other); + + FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, + const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, + TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, + TWeakObjectPtr TargetCompIn, + TWeakObjectPtr InstigatorCompIn, + TWeakObjectPtr InAvatar); + + ~FGAEffectContext(); +}; + + +struct FGAEffect; +class UGAGameEffectSpec; +struct FGAEffectMod; +struct FGAAttribute; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectHandle +{ + GENERATED_BODY() +protected: + //just to be safe we don't run out of numbers.. + UPROPERTY(VisibleAnywhere, Transient) + int32 Handle; //Fname Guid ? +public: + int32 GetHandle() const + { + return Handle; + } + static FGAEffectHandle GenerateHandle(); + bool operator==(const FGAEffectHandle& Other) const + { + return Handle == Other.Handle; + } + bool operator!=(const FGAEffectHandle& Other) const + { + return Handle != Other.Handle; + } + + //FGAEffectHandle& operator=(const FGAEffectHandle& Other) + //{ + // Handle = Other.Handle; + // EffectPtr = Other.EffectPtr; + // return *this; + //} + + void Reset(); + bool IsValid() const; + friend uint32 GetTypeHash(const FGAEffectHandle& InHandle) + { + return InHandle.Handle; + } + + FGAEffectHandle(); + + FGAEffectHandle(uint32 HandleIn); + void PostScriptConstruct(); +public: + ~FGAEffectHandle(); +}; +// +template<> +struct TStructOpsTypeTraits< FGAEffectHandle > : public TStructOpsTypeTraitsBase2 +{ + enum + { + WithPostScriptConstruct = true, + }; +}; + +USTRUCT() +struct FAFPredictionHandle +{ + GENERATED_BODY() +public: + //ID of current handle. + UPROPERTY() + uint32 Handle; + UPROPERTY() + FGAEffectHandle EffectHandle; + + uint64 Timestamp; + + static FAFPredictionHandle GenerateClientHandle(UAFAbilityComponent* InComponent); + /* + Was prediction successful ? + If true nothing happens on client (might interpolate to result from server). + If false, server will override client predicted results. + */ + UPROPERTY() + bool bPredictionValid; + + + bool IsValid() const + { + return true; + } + + const bool operator==(const FAFPredictionHandle& Other) const + { + return Handle == Other.Handle; + } + friend uint32 GetTypeHash(const FAFPredictionHandle& InHandle) + { + return InHandle.Handle; + } +}; + +DECLARE_MULTICAST_DELEGATE(FGAGenericDelegate); + +struct ABILITYFRAMEWORK_API EnumToString +{ + static FString GetStatckingAsString(EGAEffectStacking Stacking) + { + switch (Stacking) + { + case EGAEffectStacking::Override: + return FString("Override"); + case EGAEffectStacking::Intensity: + return FString("Intensity"); + case EGAEffectStacking::Duration: + return FString("Duration"); + case EGAEffectStacking::Add: + return FString("Add"); + } + return FString(""); + } +}; + +/* + Special struct, which allows to use FGameplayTagContainer as key, for TSet and TMap. + Bear in mind slower inserts/remove, but allow for complex keys. +*/ +struct ABILITYFRAMEWORK_API FGAHashedGameplayTagContainer +{ +public: + FGameplayTagContainer Tags; + +private: + FName Key; + void GenerateFNameKey(); + +public: + FGAHashedGameplayTagContainer() + {}; + FGAHashedGameplayTagContainer(const FGameplayTagContainer& TagsIn); + + friend uint32 GetTypeHash(const FGAHashedGameplayTagContainer& InHandle) + { + return ::GetTypeHash(InHandle.Key); + } +}; + +USTRUCT(BlueprintType) +struct FGAIndividualMods +{ + GENERATED_BODY() +public: + UPROPERTY() + float Additive; + UPROPERTY() + float Subtractive; + UPROPERTY() + float Multiplicative; + UPROPERTY() + float Divide; + UPROPERTY() + float PercentageAdd; + UPROPERTY() + float PercentageSubtract; + + FGAIndividualMods() + : Additive(0.0f), + Subtractive(0.0f), + Multiplicative(0.0f), + Divide(0.0f), + PercentageAdd(0.0f), + PercentageSubtract(0.0f) + {}; + FGAIndividualMods(float AdditiveIn, + float SubtractiveIn, + float MultiplicativeIn, + float DivideIn, + float PercentageAddIn, + float PercentageSubtractIn + ) + : Additive(AdditiveIn), + Subtractive(SubtractiveIn), + Multiplicative(MultiplicativeIn), + Divide(DivideIn), + PercentageAdd(PercentageAddIn), + PercentageSubtract(PercentageSubtractIn) + {} +}; +/** +* Struct representing single attribute. Needed for Pin customization. +* What we really need is to use this struct for making "complex" attributes. +* Which means attributes, which needs to track their own state. +* Bonuses applied to them, types of bonues, and who applied those bonuses +* so we can properly remove them, get them, track them, and controll order +* in which theyare added. +* we will two have attributes types. Staless (transient), auxiallry attttributes +* and staefull attributes, which are going to track their state. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAAttribute +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly) + FName AttributeName; + + inline bool operator== (const FGAAttribute& OtherAttribute) const + { + return (OtherAttribute.AttributeName == AttributeName); + } + + inline bool operator!= (const FGAAttribute& OtherAttribute) const + { + return (OtherAttribute.AttributeName != AttributeName); + } + + inline bool IsValid() const + { + return !AttributeName.IsNone(); + } + + inline FString ToString() + { + return AttributeName.ToString(); + } + + FGAAttribute() + { + AttributeName = NAME_None; + }; + FGAAttribute(const FName& AttributeNameIn) + { + AttributeName = AttributeNameIn; + }; + friend uint32 GetTypeHash(const FGAAttribute& InAttribute) + { + return GetTypeHash(InAttribute.AttributeName); + } + //FGAAttribute(const FString& AttributeNameIn) + //{ + // AttributeName = *AttributeNameIn; + //}; +}; + +/* Final calculcated mod from effect, which can be modified by Calculation object. */ +USTRUCT() +struct FGAEffectMod +{ + GENERATED_BODY() + FGAAttribute Attribute; + float Value; + EGAAttributeMod AttributeMod; + struct FGAEffectHandle Handle; + FGameplayTagContainer AttributeTags; + /* + Spec from which this mod has been derived. + Used to do not copy to much heavy data around. + */ + inline bool CompareMods(const FGAEffectMod& OtherMod) const + { + return AttributeMod == OtherMod.AttributeMod; + } + inline bool HasAllTags(const FGameplayTagContainer& TagsIn) const + { + return AttributeTags.HasAll(TagsIn); + } + inline bool HasAllTagsExact(const FGAEffectMod& OtherMod) const + { + return AttributeTags.HasAllExact(OtherMod.AttributeTags); + } + inline bool HasAllTagsExact(const FGameplayTagContainer& TagsIn) const + { + return AttributeTags.HasAllExact(TagsIn); + } + inline bool HasAllTagsIncludingChildren(const FGameplayTagContainer& TagsIn) const + { + return TagsIn.HasAll(AttributeTags); + } + const bool operator==(const FGAEffectMod& Other) const + { + return Value == Other.Value && AttributeMod == Other.AttributeMod; + } + const bool operator!=(const FGAEffectMod& Other) const + { + return Value != Other.Value && AttributeMod == Other.AttributeMod; + } + + const bool operator>(const FGAEffectMod& Other) const + { + return Value > Other.Value && AttributeMod == Other.AttributeMod; + } + + const bool operator<(const FGAEffectMod& Other) const + { + return Value < Other.Value && AttributeMod == Other.AttributeMod; + } + const bool operator>=(const FGAEffectMod& Other) const + { + return Value >= Other.Value && AttributeMod == Other.AttributeMod; + } + + const bool operator<=(const FGAEffectMod& Other) const + { + return Value <= Other.Value && AttributeMod == Other.AttributeMod; + } + + + FGAEffectMod() + : Attribute(NAME_None), + Value(0), + AttributeMod(EGAAttributeMod::Invalid) + {}; + + FGAEffectMod(const FGAAttribute& AttributeIn, float ValueIn, + EGAAttributeMod AttributeModIn, FGAEffectHandle HandleIn, FGameplayTagContainer AttributeTagsIn) + : Attribute(AttributeIn), + Value(ValueIn), + AttributeMod(AttributeModIn), + Handle(HandleIn), + AttributeTags(AttributeTagsIn) + { + }; +}; + +USTRUCT(BlueprintType) +struct FAFAttributeChangedData +{ + GENERATED_BODY() +public: + FGAEffectMod Mod; + UPROPERTY() + TWeakObjectPtr Target; + //HitLocation of applicable; + FVector Location; + float NewValue; +}; + +/* +Struct representing final modifier applied to attribute. +*/ +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAModifier +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY() + EGAAttributeMod AttributeMod; + UPROPERTY() + float Value; + + FGameplayTagContainer Tags; + /* + Weak pointer to effect, which added this modifier. + Useful because, while effect exist it have lots of useful informations. + */ + struct FGAEffectHandle Handle; + + FGAModifier() + {}; + FGAModifier(EGAAttributeMod ModIn, float ValueIn) + : AttributeMod(ModIn), + Value(ValueIn) + {}; + FGAModifier(EGAAttributeMod ModIn, float ValueIn, FGAEffectHandle HandleIn) + : AttributeMod(ModIn), + Value(ValueIn), + Handle(HandleIn) + {}; + + FGAModifier(const FGAEffectMod& ModIn) + : AttributeMod(ModIn.AttributeMod), + Value(ModIn.Value), + Handle(ModIn.Handle) + {}; +}; + +USTRUCT() +struct ABILITYFRAMEWORK_API FGACountedTagContainer +{ + GENERATED_USTRUCT_BODY() +protected: + /* + Here we will store counted GamaplayTags. + If tag is already in map, we just incremement count. + */ + TMap CountedTags; + + /* + Here we store all currently posesd tags. + It is equivalent of CountedTags, except this does not track count of tags, but we need it + to have something against which we can perform queries. + */ +public: + UPROPERTY() + FGameplayTagContainer AllTags; +public: + + inline FGameplayTagContainer GetTags() { return AllTags; }; + + void AddTag(const FGameplayTag& TagIn); + void AddTagContainer(const FGameplayTagContainer& TagsIn); + void RemoveTag(const FGameplayTag& TagIn); + void RemoveTagContainer(const FGameplayTagContainer& TagsIn); + + bool HasTag(const FGameplayTag& TagIn); + bool HasTagExact(const FGameplayTag TagIn); + bool HasAny(const FGameplayTagContainer& TagsIn); + bool HasAnyExact(const FGameplayTagContainer& TagsIn); + bool HasAll(const FGameplayTagContainer& TagsIn); + bool HasAllExact(const FGameplayTagContainer& TagsIn); + + bool HasTag(const FGameplayTag& TagIn) const; + bool HasTagExact(const FGameplayTag TagIn) const; + bool HasAny(const FGameplayTagContainer& TagsIn) const; + bool HasAnyExact(const FGameplayTagContainer& TagsIn) const; + bool HasAll(const FGameplayTagContainer& TagsIn) const; + bool HasAllExact(const FGameplayTagContainer& TagsIn) const; + + inline FGameplayTagContainer& GetAllTags() + { + return AllTags; + } + + inline int32 GetTagCount(const FGameplayTag& TagIn) const + { + return CountedTags.FindRef(TagIn); + } +}; + + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FGAEffectCueParams +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "Gameplay Cue") + FHitResult HitResult; + + /** Instigator actor, the actor that owns the ability system component */ + UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") + TWeakObjectPtr Instigator; + + /** The physical actor that actually did the damage, can be a weapon or projectile */ + UPROPERTY(BlueprintReadWrite, Category = "Gameplay Cue") + TWeakObjectPtr Causer; + + UPROPERTY(BlueprintReadOnly) + FGameplayTagContainer CueTags; + + FGAEffectCueParams() + {}; + FGAEffectCueParams(const FHitResult& InHitResult, AActor* InstigatorIn, UObject* CauserIn) + : HitResult(InHitResult), + Instigator(InstigatorIn), + Causer(CauserIn) + {}; + FGAEffectCueParams(const FGAEffectContext& InContext, const struct FGAEffectProperty& InProperty); + //bool NetSerialize(FArchive& Ar, class UPackageMap* Map, bool& bOutSuccess); +}; + +USTRUCT() +struct FAFCueHandle +{ + GENERATED_BODY(); +private: + UPROPERTY() + uint32 Handle; + + FAFCueHandle(uint32 InHandle) + : Handle(InHandle) + {} +public: + FAFCueHandle() + : Handle(0) + {} + + static FAFCueHandle GenerateHandle(); + + bool operator==(const FAFCueHandle Other) const + { + return Handle == Other.Handle; + } + + friend uint32 GetTypeHash(const FAFCueHandle& InHandle) + { + return InHandle.Handle; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAHelperTemplates.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAHelperTemplates.h new file mode 100644 index 0000000..34b2f98 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAHelperTemplates.h @@ -0,0 +1,59 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once +#include "Engine/NetSerialization.h" +#include "GameplayTags.h" +#include "AFAbilityComponent.h" +#include "GAHelperTemplates.generated.h" + +USTRUCT(BlueprintType) +struct FGAAttributeSource +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + EGAAttributeSource Source; + /* Class which is source for attribute set. */ + UPROPERTY(EditAnywhere)//, meta = (MustImplement = "IGAAbilities")) + FGameplayTag AttributeSource; +}; + +USTRUCT(BlueprintType) +struct FGAAttributeCapture +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FGAAttributeSource Source; + + UPROPERTY(EditAnywhere) + FGameplayTagContainer RequiredTags; + UPROPERTY(EditAnywhere) + FGameplayTagContainer DenyTags; + + template + T* GetAttributeSet(const FGAEffectContext& ContextIn) + { + UAFAbilityComponent* TargetComp = ContextIn.TargetComp.Get(); + UAFAbilityComponent* InstigatorComp = ContextIn.InstigatorComp.Get(); + T* AttributeSet = nullptr; + switch (Source.Source) + { + case EGAAttributeSource::Causer: + { + break; + } + case EGAAttributeSource::Target: + { + AttributeSet = TargetComp->GetAttributeSet(Source.AttributeSource); + break; + } + case EGAAttributeSource::Instigator: + { + AttributeSet = InstigatorComp->GetAttributeSet(Source.AttributeSource); + break; + } + } + return AttributeSet; + } +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAPhysicalMaterial.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAPhysicalMaterial.h new file mode 100644 index 0000000..429f1bd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAPhysicalMaterial.h @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "PhysicalMaterials/PhysicalMaterial.h" +#include "GAPhysicalMaterial.generated.h" + +/** + * + */ +UCLASS(Blueprintable) +class ABILITYFRAMEWORK_API UGAPhysicalMaterial : public UPhysicalMaterial +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Fx") + UParticleEmitter* SurfaceHitFX; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAUIData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAUIData.h new file mode 100644 index 0000000..bc6d205 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAUIData.h @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "Object.h" +#include "GAUIData.generated.h" + +/** + * Base class for UI data for effect. + * Do not instance it. Just use CDO, to get data from it. + */ +UCLASS() +class ABILITYFRAMEWORK_API UGAUIData : public UObject +{ + GENERATED_BODY() +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h new file mode 100644 index 0000000..3b4bce0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h @@ -0,0 +1,37 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "ModuleManager.h" + + +/** + * The public interface to this module. In most cases, this interface is only public to sibling modules + * within this plugin. + */ +class IAbilityFramework : public IModuleInterface +{ + +public: + /** + * Singleton-like access to this module's interface. This is just for convenience! + * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. + * + * @return Returns singleton instance, loading the module on demand if needed + */ + static inline IAbilityFramework& Get() + { + return FModuleManager::LoadModuleChecked< IAbilityFramework >( "AbilityFramework" ); + } + + /** + * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. + * + * @return True if the module is loaded and ready to use + */ + static inline bool IsAvailable() + { + return FModuleManager::Get().IsModuleLoaded( "AbilityFramework" ); + } +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFLatentInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFLatentInterface.h new file mode 100644 index 0000000..0ce54c8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFLatentInterface.h @@ -0,0 +1,25 @@ +#pragma once +#include "AFLatentInterface.generated.h" + + +struct FAFAttributeBase; +struct FGAEffectHandle; +UINTERFACE(Blueprintable, meta = (CannotImplementInterfaceInBlueprint)) +class ABILITYFRAMEWORK_API UAFLatentInterface : public UInterface +{ + GENERATED_UINTERFACE_BODY() +}; + +class IAFLatentInterface +{ + GENERATED_IINTERFACE_BODY() +public: + virtual void OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) = 0; + virtual void AddReplicatedTask(class UAFTaskBase* TaskIn) = 0; + virtual void OnLatentTaskRemoved(class UAFTaskBase* TaskIn) = 0; + + virtual void OnLatentTaskActivated(class UAFTaskBase* TaskIn) = 0; + virtual void OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) = 0; + + virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName) = 0; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h new file mode 100644 index 0000000..2db8241 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h @@ -0,0 +1,102 @@ +#pragma once +#include "CoreMinimal.h" +#include "Engine/EngineBaseTypes.h" +#include "AFLatentInterface.h" + +#include "AFTaskBase.generated.h" + +struct FGALatentFunctionTick: public FTickFunction +{ + /** AActor that is the target of this tick **/ + class UAFTaskBase* Target; + + /** + * Abstract function actually execute the tick. + * @param DeltaTime - frame time to advance, in seconds + * @param TickType - kind of tick for this frame + * @param CurrentThread - thread we are executing on, useful to pass along as new tasks are created + * @param MyCompletionGraphEvent - completion event for this task. Useful for holding the completetion of this task until certain child tasks are complete. + **/ + virtual void ExecuteTick(float DeltaTime, ELevelTick TickType, ENamedThreads::Type CurrentThread, const FGraphEventRef& MyCompletionGraphEvent) override; + /** Abstract function to describe this tick. Used to print messages about illegal cycles in the dependency graph **/ + virtual FString DiagnosticMessage() override; +}; + +UCLASS(meta = (ExposedAsyncProxy = "true")) +class ABILITYFRAMEWORK_API UAFTaskBase : public UObject +{ + GENERATED_BODY() + //never access internals of these classes directly. Use messages instead. +protected: + enum class EState : uint8 + { + Waiting, + Active, + Finished + }; + + EState TaskState; + bool bReplicated; + + UPROPERTY() + UObject* TaskOwner; + friend struct FGALatentFunctionTick; + FGALatentFunctionTick TickFunction; + + UAFTaskBase(const FObjectInitializer& ObjectInitializer); + virtual UWorld* GetWorld() const override; + + //virtual void Tick(float DeltaSecondsIn); + virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) {}; + virtual void Initialize(); +public: + UFUNCTION(BlueprintCallable, meta = (BlueprintInternalUseOnly = "true"), Category = "Latent Action") + virtual void ReadyForActivation(); +protected: + virtual void Activate() {}; + virtual void EndTask(); + virtual void BeginDestroy() override; + virtual void OnTaskEnded() {}; +public: + /* Replication */ + bool IsNameStableForNetworking() const override; + + bool IsSupportedForNetworking() const override + { + return bReplicated; + } + void SetNetAddressable(); + +protected: + + //use template to avoid using interface + template + static TaskType* NewTask(UObject* WorldContextObject, OwnerType* InTaskOwner, FName InstanceName = FName()) + { + TaskType* MyObj = nullptr; + + if (!InstanceName.IsNone()) + { + MyObj = Cast(InTaskOwner->GetCachedLatentAction(InstanceName)); + if (!MyObj) + { + MyObj = NewObject(WorldContextObject); + + InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); + } + } + else + { + MyObj = NewObject(WorldContextObject); + + InTaskOwner->OnLatentTaskAdded(InstanceName, MyObj); + } + if (MyObj->bReplicated) + { + InTaskOwner->AddReplicatedTask(MyObj); + } + MyObj->TaskOwner = InTaskOwner; + + return MyObj; + } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskManager.h new file mode 100644 index 0000000..8a39299 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskManager.h @@ -0,0 +1,17 @@ +#pragma once +#include "CoreMinimal.h" +#include "Engine/EngineBaseTypes.h" + +#include "AFTaskManager.generated.h" + +UCLASS() +class ABILITYFRAMEWORK_API UAFTaskManager : public UObject +{ + GENERATED_BODY() + + static UAFTaskManager* Instance; + +public: + UAFTaskManager(const FObjectInitializer& ObjectInitializer); + static UAFTaskManager* Get(); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/GAWaitAction.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/GAWaitAction.h new file mode 100644 index 0000000..af68fc7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/GAWaitAction.h @@ -0,0 +1,42 @@ +#pragma once +#include "AFTaskBase.h" +#include "GAWaitAction.generated.h" +/* + AbilityActions are generic (preferably C++) defined actions, which then can be added to ability and + the should be activated from ability. + Then can perform tasks, like spawn tagetting helpers (splines, circles), spawn actors, + gather targeting data etc. + + Should they be activated automatically after ability is initialized, (it'e ability enterted in + active state, which means it's ready to be fired and display helpers, but did not yet received input, + or should designer in blueprint decide when to launch actions ?). +*/ +UCLASS(meta = (ExposedAsyncProxy = "true") ) +class ABILITYFRAMEWORK_API UGAWaitAction : public UAFTaskBase +{ + GENERATED_BODY() + +public: + UGAWaitAction(const FObjectInitializer& ObjectInitializer); + float Time; + float TimeStarted; + + DECLARE_DYNAMIC_MULTICAST_DELEGATE(FGAWaitActionDelegate); + UPROPERTY(BlueprintAssignable) + FGAWaitActionDelegate OnInitialized; + UPROPERTY(BlueprintAssignable) + FGAWaitActionDelegate OnFinish; + + UPROPERTY(BlueprintAssignable) + FGAWaitActionDelegate OnTick; + + //virtual void Tick(float DeltaSecondsIn); + + virtual void Activate() override; + virtual void TickTask(float DeltaSeconds, ELevelTick TickType, FGALatentFunctionTick& ThisTickFunction) override; + UFUNCTION(BlueprintCallable, Category = "Latent Actions", meta = (AdvancedDisplay = "InTaskOwner, Priority", DefaultToSelf = "InTaskOwner", BlueprintInternalUseOnly = "TRUE")) + static UGAWaitAction* NewGAWaitAction(UObject* InTaskOwner, float Time); + + void OnTimeFinish(); + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Mods/GAAttributeMod.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Mods/GAAttributeMod.h new file mode 100644 index 0000000..1363965 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Mods/GAAttributeMod.h @@ -0,0 +1,32 @@ +#pragma once +#include "GAGlobalTypes.h" +#include "GameplayTagContainer.h" +#include "GAAttributeMod.generated.h" +/* + Using this class you can perform actions, when change to attribute is instigated. + Outcoming are modifiers appiled by instigator. + Incoming are modifiers appiled by target. + + Common applications are generic mods like damage reduction by armor or other attribute. + Increasing damage. + + Fireing other actions, when certain critera has been meet. + + This system is actually similiar to Effects from GameEffectSystem module. + + The main difference is that, attribute mods, cannot be appiled by other objects. You can add or remove + them on runtime, by providing set of classes, that can be added to component and the constructed. + + But you can't apply those mods by means like weapons or abilities. + They are always passive (as they are listening for events), they are always infinite + (their duration is for the entire lifetime of pawn/controller/game) + and they can't affect other attribute mods. They can only affect attributes, and trigger actions + based on them. This might include launching effects. + + As per usual using GameplayTags is recommened for defining behaviour. +*/ +UCLASS(BlueprintType, Blueprintable, DefaultToInstanced, EditInlineNew) +class ABILITYFRAMEWORK_API UGAAttributeMod : public UObject +{ + GENERATED_UCLASS_BODY() +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.cpp new file mode 100644 index 0000000..02f483d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.cpp @@ -0,0 +1,75 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityActivationSpec.h" +#include "AFAbilityActionSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityActivationSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityActivationSpecDetails); +} + +void FAFAbilityActivationSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityActivationSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityActivationSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityActivationSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.h new file mode 100644 index 0000000..75a6c49 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityActionSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityActivationSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + FSimpleDelegate UpdateEffectTypeyDelegate; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.cpp new file mode 100644 index 0000000..217ee21 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.cpp @@ -0,0 +1,75 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityCooldownSpec.h" +#include "AFAbilityCooldownSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityCooldownSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityCooldownSpecDetails); +} + +void FAFAbilityCooldownSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityCooldownSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityCooldownSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityCooldownSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.h new file mode 100644 index 0000000..be653a3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityCooldownSpecDetails.h @@ -0,0 +1,30 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityCooldownSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.cpp new file mode 100644 index 0000000..d99ea2b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.cpp @@ -0,0 +1,83 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityInfiniteDurationSpec.h" +#include "AFAbilityInfiniteDurationSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityInfiniteDurationSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityInfiniteDurationSpecDetails); +} + +void FAFAbilityInfiniteDurationSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityInfiniteDurationSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityInfiniteDurationSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + DetailLayout.HideCategory("Duration"); + DetailLayout.HideCategory("Period"); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); + + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityInfiniteDurationSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.h new file mode 100644 index 0000000..c1b4218 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfiniteDurationSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityInfiniteDurationSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + TSharedPtr PeriodCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.cpp new file mode 100644 index 0000000..38f91d2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.cpp @@ -0,0 +1,83 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityPeriodicInfiniteSpec.h" +#include "AFAbilityInfinitePeriodSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityInfinitePeriodSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityInfinitePeriodSpecDetails); +} + +void FAFAbilityInfinitePeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityInfinitePeriodSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityPeriodicInfiniteSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DetailLayout.HideCategory("Duration"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); + + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityInfinitePeriodSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.h new file mode 100644 index 0000000..bdffbdd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityInfinitePeriodSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityInfinitePeriodSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + TSharedPtr PeriodCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.cpp new file mode 100644 index 0000000..8fe5b22 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.cpp @@ -0,0 +1,81 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Abilities/AFAbilityPeriodSpec.h" +#include "AFAbilityPeriodSpecDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +TSharedRef FAFAbilityPeriodSpecDetails::MakeInstance() +{ + return MakeShareable(new FAFAbilityPeriodSpecDetails); +} + +void FAFAbilityPeriodSpecDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + FSimpleDelegate UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FAFAbilityPeriodSpecDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFAbilityPeriodSpec* Spec = Cast(obj.Get())) + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplicationRequirement"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Application"); + + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStackedDuration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "MaxStacks"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bTickOnApplication"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "bExecuteOnApplication"); + + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Extension"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnAppliedEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ConditonalEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RemoveEffectWithTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AtributeModifier"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "Modifiers"); + + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedEventTags"); + //FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecuteEventTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "DenyTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "RequiredTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ExecutionRequiredTags"); + + DurationProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodProperty = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(DurationProperty); + DetailLayout.HideProperty(PeriodProperty); + DurationCalcTypeProp = DurationProperty->GetChildHandle("CalculationType"); + PeriodCalcTypeProp = PeriodProperty->GetChildHandle("CalculationType"); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationProperty, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodProperty, "Period"); + + DurationCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeProp->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + } + } +} +void FAFAbilityPeriodSpecDetails::OnDurationPolicyChange() +{ + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.h new file mode 100644 index 0000000..b5e4527 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFAbilityPeriodSpecDetails.h @@ -0,0 +1,31 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FAFAbilityPeriodSpecDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationProperty; + TSharedPtr PeriodProperty; + TSharedPtr DurationCalcTypeProp; + TSharedPtr PeriodCalcTypeProp; + IDetailLayoutBuilder* MyDetailLayout; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.cpp new file mode 100644 index 0000000..f0898d5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.cpp @@ -0,0 +1,79 @@ + +#include "AbilityFrameworkEditor.h" +#include "Kismet/KismetMathLibrary.h" +#include "Kismet/KismetArrayLibrary.h" +#include "LatentActions/AFTaskBase.h" +#include "Effects/EffectTasks/AFEffectTask.h" +#include "Effects/GAEffectExtension.h" +#include "KismetCompiler.h" +#include "BlueprintEditorUtils.h" +#include "AFEK2Node_AsyncEffectTaskCall.h" +#include "K2Node_EnumLiteral.h" +#include "BlueprintFunctionNodeSpawner.h" +#include "BlueprintActionDatabaseRegistrar.h" + +#define LOCTEXT_NAMESPACE "K2Node" + +UAFEK2Node_AsyncEffectTaskCall::UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); +} + +bool UAFEK2Node_AsyncEffectTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const +{ + bool bIsCompatible = false; + + EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); + bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); + + if (bAllowLatentFuncs) + { + UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); + if (MyBlueprint && MyBlueprint->GeneratedClass) + { + if (MyBlueprint->GeneratedClass->IsChildOf(UGAEffectExtension::StaticClass())) + { + bIsCompatible = true; + } + } + } + return bIsCompatible; +} + + +void UAFEK2Node_AsyncEffectTaskCall::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const +{ + //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); + struct GetMenuActions_Utils + { + static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) + { + UAFEK2Node_AsyncEffectTaskCall* AsyncTaskNode = CastChecked(NewNode); + if (FunctionPtr.IsValid()) + { + UFunction* Func = FunctionPtr.Get(); + UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); + + AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); + AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); + AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; + } + } + }; + + UClass* NodeClass = GetClass(); + //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + { + UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); + check(NodeSpawner != nullptr); + NodeSpawner->NodeClass = NodeClass; + + TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); + NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); + return NodeSpawner; + })); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.h new file mode 100644 index 0000000..d9c7d0f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEK2Node_AsyncEffectTaskCall.h @@ -0,0 +1,20 @@ + +#pragma once +#include "EdGraph/EdGraphPin.h" +#include "EdGraphSchema_K2.h" +#include "K2Node_BaseAsyncTask.h" +#include "AFEK2Node_AsyncEffectTaskCall.generated.h" + +UCLASS() +class UAFEK2Node_AsyncEffectTaskCall : public UK2Node_BaseAsyncTask +{ + GENERATED_BODY() + +public: + UAFEK2Node_AsyncEffectTaskCall(const FObjectInitializer& ObjectInitializer); + + // UEdGraphNode interface + virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; + virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; + // End of UEdGraphNode interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.cpp new file mode 100644 index 0000000..ea1ff60 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.cpp @@ -0,0 +1,111 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFrameworkEditor.h" +#include "Effects/GAGameEffect.h" +#include "DetailLayoutBuilder.h" +#include "DetailCategoryBuilder.h" +#include "IDetailGroup.h" +#include "AFEffectCustomizationCommon.h" + +FAFEffectCustomizationCommon::FAFEffectCustomizationCommon() +{ +} + +FAFEffectCustomizationCommon::~FAFEffectCustomizationCommon() +{ +} +void FAFEffectCustomizationCommon::CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, + TSharedPtr& InProperty, FName InCategory) +{ + IDetailCategoryBuilder& DurationCategory = DetailLayout.EditCategory(InCategory); + + TSharedPtr DurationCalcTypeProp = InProperty->GetChildHandle("CalculationType"); + + uint8 CalcType = 0; + DurationCalcTypeProp->GetValue(CalcType); + + TSharedPtr DirectModifier = InProperty->GetChildHandle("DirectModifier"); + TSharedPtr AttributeBased = InProperty->GetChildHandle("AttributeBased"); + TSharedPtr CurveBased = InProperty->GetChildHandle("CurveBased"); + TSharedPtr Custom = InProperty->GetChildHandle("Custom"); + + DurationCategory.AddProperty(DurationCalcTypeProp.ToSharedRef()); + switch (CalcType) + { + case 0: //Direct + { + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Value = DirectModifier->GetChildHandle("Value"); + DurationCategory.AddProperty(Value.ToSharedRef()); + //DetailGroup. + break; + } + case 1: //AttributeBased + { + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Source = AttributeBased->GetChildHandle("Source"); + TSharedPtr Attribute = AttributeBased->GetChildHandle("Attribute"); + TSharedPtr Coefficient = AttributeBased->GetChildHandle("Coefficient"); + TSharedPtr PreMultiply = AttributeBased->GetChildHandle("PreMultiply"); + TSharedPtr PostMultiply = AttributeBased->GetChildHandle("PostMultiply"); + TSharedPtr PostCoefficient = AttributeBased->GetChildHandle("PostCoefficient"); + TSharedPtr bUseSecondaryAttribute = AttributeBased->GetChildHandle("bUseSecondaryAttribute"); + TSharedPtr SecondarySource = AttributeBased->GetChildHandle("SecondarySource"); + TSharedPtr SecondaryAttribute = AttributeBased->GetChildHandle("SecondaryAttribute"); + + DurationCategory.AddProperty(Source.ToSharedRef()); + DurationCategory.AddProperty(Attribute.ToSharedRef()); + DurationCategory.AddProperty(Coefficient.ToSharedRef()); + DurationCategory.AddProperty(PreMultiply.ToSharedRef()); + DurationCategory.AddProperty(PostMultiply.ToSharedRef()); + DurationCategory.AddProperty(PostCoefficient.ToSharedRef()); + DurationCategory.AddProperty(bUseSecondaryAttribute.ToSharedRef()); + DurationCategory.AddProperty(SecondarySource.ToSharedRef()); + DurationCategory.AddProperty(SecondaryAttribute.ToSharedRef()); + + break; + } + case 2: //CurveBased + { + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(Custom); + + TSharedPtr Source = CurveBased->GetChildHandle("Source"); + TSharedPtr Attribute = CurveBased->GetChildHandle("Attribute"); + TSharedPtr CurveTable = CurveBased->GetChildHandle("CurveTable"); + + DurationCategory.AddProperty(Source.ToSharedRef()); + DurationCategory.AddProperty(Attribute.ToSharedRef()); + DurationCategory.AddProperty(CurveTable.ToSharedRef()); + break; + } + case 3: //CustomCalculation + { + DetailLayout.HideProperty(AttributeBased); + DetailLayout.HideProperty(CurveBased); + DetailLayout.HideProperty(DirectModifier); + DetailLayout.HideProperty(Custom); + + TSharedPtr CustomCalculation = Custom->GetChildHandle("CustomCalculation"); + DurationCategory.AddProperty(CustomCalculation.ToSharedRef()); + break; + } + } +} +void FAFEffectCustomizationCommon::HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName) +{ + UProperty* prop = UGAGameEffectSpec::StaticClass()->FindPropertyByName(InName); + + TSharedPtr Property = DetailLayout.GetProperty(InName, UGAGameEffectSpec::StaticClass()); + DetailLayout.HideProperty(Property); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.h new file mode 100644 index 0000000..2c495a7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AFEffectCustomizationCommon.h @@ -0,0 +1,19 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IDetailCustomization.h" +#include "PropertyHandle.h" +/** + * + */ +class ABILITYFRAMEWORKEDITOR_API FAFEffectCustomizationCommon +{ +public: + FAFEffectCustomizationCommon(); + ~FAFEffectCustomizationCommon(); + static void CreateMagnitudeLayout(IDetailLayoutBuilder& DetailLayout, + TSharedPtr& InProperty, FName InCategory); + static void HideProperty(IDetailLayoutBuilder& DetailLayout, FName InName); +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp new file mode 100644 index 0000000..0e2b42a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.cpp @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "AssetTypeActions_GAAbilityBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "GAAbilityEditor.h" +#include "Abilities/GAAbilityBlueprint.h" +#include "Abilities/GAAbilityBase.h" +#include "GAAbilityBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_GAAbilityBlueprint::GetName() const +{ + return FText::FromString("Ability"); +} +UClass* FAssetTypeActions_GAAbilityBlueprint::GetSupportedClass() const +{ + return UGAAbilityBlueprint::StaticClass(); +} + +void FAssetTypeActions_GAAbilityBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FGAAbilityEditor > NewEditor(new FGAAbilityEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitAbilitiesEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_GAAbilityBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return false; +} + +UFactory* FAssetTypeActions_GAAbilityBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UGAAbilityBlueprintFactory* AbilityBlueprintFactory = NewObject(); + AbilityBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return AbilityBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h new file mode 100644 index 0000000..78b71c1 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" +//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_GAAbilityBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.cpp new file mode 100644 index 0000000..3493cac --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.cpp @@ -0,0 +1,334 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityBlueprintFactory.h" +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Effects/GAGameEffect.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "Abilities/GAAbilityBlueprint.h" +#include "Abilities/GAAbilityBase.h" +#include "GAAbilityGraph.h" +#include "GAAbilityGraphSchema.h" + +#include "ClassViewerFilter.h" + +#include "SlateOptMacros.h" + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SAbilityBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAbilityBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UGAAbilityBase::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SAbilityBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SAbilityBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied AbilitiesBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InAbilitiesBlueprintFactory) + { + AbilitiesBlueprintFactory = InAbilitiesBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Ability Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + AbilitiesBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FAbilityBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FAbilityBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FAbilityBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(UGAAbilityBase::StaticClass()); + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SAbilityBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (AbilitiesBlueprintFactory.IsValid()) + { + AbilitiesBlueprintFactory->BlueprintType = BPTYPE_Normal; + AbilitiesBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr AbilitiesBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UAbilitiesBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UGAAbilityBlueprintFactory::UGAAbilityBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UGAAbilityBlueprint::StaticClass(); + ParentClass = UGAAbilityBase::StaticClass(); +} + +bool UGAAbilityBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SAbilityBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UGAAbilityBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(UGAAbilityBase::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UGAAbilityBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAAbilityBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { + UGAAbilityBlueprint* AbilityBP = UGAAbilityBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + if (AbilityBP == NULL) + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); +#if WITH_EDITORONLY_DATA + // Only allow a gameplay ability graph if there isn't one in a parent blueprint + UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAAbilityGraph::StaticClass(), UGAAbilityGraphSchema::StaticClass()); + + if (NewBP->UbergraphPages.Num()) + { + FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); + } + + FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); + NewBP->LastEditedDocuments.Add(NewGraph); + NewGraph->bAllowDeletion = false; +#endif + UBlueprintEditorSettings* Settings = GetMutableDefault(); + if(Settings && Settings->bSpawnDefaultBlueprintNodes) + { + int32 NodePositionY = 0; + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + } + } + } + + return NewBP; + } +} + +UObject* UGAAbilityBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.h new file mode 100644 index 0000000..ec61b23 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "GAAbilityBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UGAAbilityBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.cpp new file mode 100644 index 0000000..ef34e13 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.cpp @@ -0,0 +1,142 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityEditor.h" +#include "EditorReimportHandler.h" + +#if WITH_EDITOR +#include "Editor.h" +#endif +#include "ISequencerModule.h" +#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" +#include "Toolkits/ToolkitManager.h" +#include "Toolkits/GlobalEditorCommonCommands.h" + +#include "Abilities/GAAbilityBlueprint.h" +#include "GAAbilityBlueprintFactory.h" +#include "GAAbilityGraphSchema.h" +#include "Kismet2/BlueprintEditorUtils.h" + +#define LOCTEXT_NAMESPACE "FGAAbilityEditor" + + +///////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +FGAAbilityEditor::FGAAbilityEditor() +{ + +} + +FGAAbilityEditor::~FGAAbilityEditor() +{ + FEditorDelegates::OnAssetPostImport.RemoveAll(this); + FReimportManager::Instance()->OnPostReimport().RemoveAll(this); + + // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor +} +void FGAAbilityEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) +{ + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, ObjectsToEdit, bInIsToolbarFocusable); +} +void FGAAbilityEditor::InitAbilitiesEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) +{ + InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); + + for (auto Blueprint : InBlueprints) + { + EnsureAbilityBlueprintIsUpToDate(Blueprint); + } +} + +void FGAAbilityEditor::EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint) +{ +#if WITH_EDITORONLY_DATA + int32 Count = Blueprint->UbergraphPages.Num(); + for (auto Graph : Blueprint->UbergraphPages) + { + // remove the default event graph, if it exists, from existing Gameplay Ability Blueprints + if (Graph->GetName() == "EventGraph" && Graph->Nodes.Num() == 0) + { + check(!Graph->Schema->GetClass()->IsChildOf(UGAAbilityGraphSchema::StaticClass())); + FBlueprintEditorUtils::RemoveGraph(Blueprint, Graph); + break; + } + } +#endif +} +bool FGAAbilityEditor::IsBlueprintEditor() const +{ + return true; +} +// FRED_TODO: don't merge this back +// FName FGameplayAbilitiesEditor::GetToolkitContextFName() const +// { +// return GetToolkitFName(); +// } + +FName FGAAbilityEditor::GetToolkitFName() const +{ + return FName("GameAbilityEditor"); +} + +FText FGAAbilityEditor::GetBaseToolkitName() const +{ + return FText::FromString("Game Ability Editor"); +} + +FText FGAAbilityEditor::GetToolkitName() const +{ + const TArray& EditingObjs = GetEditingObjects(); + + check(EditingObjs.Num() > 0); + + FFormatNamedArguments Args; + + const UObject* EditingObject = EditingObjs[0]; + + const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); + + Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(FText::FromString("{ObjectName}{DirtyState}"), Args); +} + +FText FGAAbilityEditor::GetToolkitToolTipText() const +{ + const UObject* EditingObject = GetEditingObject(); + + check (EditingObject != NULL); + + return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); +} + +FString FGAAbilityEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("AbilityEditor"); +} + +FLinearColor FGAAbilityEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +UBlueprint* FGAAbilityEditor::GetBlueprintObj() const +{ + const TArray& EditingObjs = GetEditingObjects(); + for (int32 i = 0; i < EditingObjs.Num(); ++i) + { + if (EditingObjs[i]->IsA()) + { + return (UBlueprint*)EditingObjs[i]; + } + } + return nullptr; +} + +FString FGAAbilityEditor::GetDocumentationLink() const +{ + return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.h new file mode 100644 index 0000000..cfd9ffa --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityEditor.h @@ -0,0 +1,64 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Framework/Commands/UICommandList.h" +#include "Framework/MultiBox/MultiBoxExtender.h" +#include "GraphEditor.h" +#include "ISequencer.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" + +////////////////////////////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +/** + * Gameplay abilities asset editor (extends Blueprint editor) + */ +class FGAAbilityEditor : public FBlueprintEditor +{ +public: + virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; + /** + * Edits the specified gameplay ability asset(s) + * + * @param Mode Asset editing mode for this editor (standalone or world-centric) + * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within + * @param InBlueprints The blueprints to edit + * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode + */ + + void InitAbilitiesEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); + +private: + /** + * Updates existing gameplay ability blueprints to make sure that they are up to date + * + * @param Blueprint The blueprint to be updated + */ + void EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint); + +public: + FGAAbilityEditor(); + + virtual ~FGAAbilityEditor(); + +public: + // IToolkit interface + // FRED_TODO: don't merge this back +// virtual FName GetToolkitContextFName() const override; + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual bool IsBlueprintEditor() const override; + // End of IToolkit interface + + /** @return the documentation location for this editor */ + virtual FString GetDocumentationLink() const override; + + /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ + virtual UBlueprint* GetBlueprintObj() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.cpp new file mode 100644 index 0000000..da482a3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityGraph.h" + +#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" + +///////////////////////////////////////////////////// +// UGameplayAbilityGraph + +UGAAbilityGraph::UGAAbilityGraph(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.h new file mode 100644 index 0000000..dcc6890 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraph.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraph/EdGraph.h" +#include "GAAbilityGraph.generated.h" + +UCLASS(MinimalAPI) +class UGAAbilityGraph : public UEdGraph +{ + GENERATED_UCLASS_BODY() +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.cpp new file mode 100644 index 0000000..f51d3ff --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.cpp @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAAbilityGraphSchema.h" +#include "EdGraphSchema_K2_Actions.h" +#include "Effects/GAGameEffect.h" +#include "Kismet2/BlueprintEditorUtils.h" + +UGAAbilityGraphSchema::UGAAbilityGraphSchema(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UK2Node_VariableGet* UGAAbilityGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); +} + +UK2Node_VariableSet* UGAAbilityGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.h new file mode 100644 index 0000000..1c099f8 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityEditor/GAAbilityGraphSchema.h @@ -0,0 +1,38 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraphSchema_K2.h" +#include "GAAbilityGraphSchema.generated.h" + +UCLASS(MinimalAPI) +class UGAAbilityGraphSchema : public UEdGraphSchema_K2 +{ + GENERATED_UCLASS_BODY() + + /** + * Creates a new variable getter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + /** + * Creates a new variable setter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp new file mode 100644 index 0000000..342153e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp @@ -0,0 +1,161 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "AbilityFrameworkEditor.h" +#include "GAAttributePin.h" +#include "Attributes/GAAttributeGlobals.h" +#include "Effects/GAEffectCue.h" +#include "GAAttributePanelGraphPinFactory.h" +#include "GAAttributeDetailCustomization.h" + +#include "GAEffectDetails.h" +//#include "GAEffectSpecStructCustomization.h" +#include "GAEffectPropertyStructCustomization.h" +#include "AFAbilityActionSpecDetails.h" +#include "AFAbilityPeriodSpecDetails.h" +#include "AFAbilityCooldownSpecDetails.h" +#include "AFAbilityInfiniteDurationSpecDetails.h" +#include "AFAbilityInfinitePeriodSpecDetails.h" + +#include "EffectEditor/AssetTypeActions_GAEffectBlueprint.h" +#include "AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h" +#include "EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h" +#include "EffectCueEditor/AFEffectCueDetails.h" + + + +#include "AFCueManager.h" + +TSet FAbilityFrameworkEditor::EffectClasses = TSet(); +/** Shared class type that ensures safe binding to RegisterBlueprintEditorTab through an SP binding without interfering with module ownership semantics */ +FEffectCueequenceEditorTabBinding::FEffectCueequenceEditorTabBinding() +{ + FBlueprintEditorModule& BlueprintEditorModule = FModuleManager::LoadModuleChecked("Kismet"); + BlueprintEditorTabSpawnerHandle = BlueprintEditorModule.OnRegisterTabsForEditor().AddRaw(this, &FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorTab); + BlueprintEditorLayoutExtensionHandle = BlueprintEditorModule.OnRegisterLayoutExtensions().AddRaw(this, &FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorLayout); +} + +void FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) +{ + Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); +} + +void FEffectCueequenceEditorTabBinding::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) +{ + TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); +} + +FEffectCueequenceEditorTabBinding::~FEffectCueequenceEditorTabBinding() +{ + FBlueprintEditorModule* BlueprintEditorModule = FModuleManager::GetModulePtr("Kismet"); + if (BlueprintEditorModule) + { + BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); + BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); + } +} + + +void FAbilityFrameworkEditor::RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action) +{ + AssetTools.RegisterAssetTypeActions(Action); + CreatedAssetTypeActions.Add(Action); +} +void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequence) +{ + auto* ProjectSettings = GetDefault(); + AGAEffectCue* Cue = Cast(Sequence->GetOuter()); + + + if (Cue) + { + TRange Frames(static_cast(Cue->StartTime), static_cast(Cue->EndTime)); + Sequence->GetMovieScene()->SetPlaybackRange(Frames, true); + } + else + { + TRange Frames; + Sequence->GetMovieScene()->SetPlaybackRange(Frames, true); + } +} + /** IModuleInterface implementation */ +void FAbilityFrameworkEditor::StartupModule() +{ + if(GEditor) + BlueprintEditorTabBinding = MakeShared(); + + + + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); + PropertyModule.RegisterCustomPropertyTypeLayout("GAAttribute", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAAttributeDetailCustomization::MakeInstance)); + //PropertyModule.RegisterCustomPropertyTypeLayout("GAEffectProperty", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); + PropertyModule.RegisterCustomPropertyTypeLayout("AFPropertytHandle", FOnGetPropertyTypeCustomizationInstance::CreateStatic(&FGAEffectPropertyStructCustomization::MakeInstance)); + + TSharedPtr GAAttributePanelGraphPinFactory = MakeShareable(new FGAAttributePanelGraphPinFactory()); + FEdGraphUtilities::RegisterVisualPinFactory(GAAttributePanelGraphPinFactory); + + PropertyModule.RegisterCustomClassLayout("AFEffectSpecBase", FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityActivationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityCooldownSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityPeriodicInfiniteSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityInfinitePeriodSpecDetails::MakeInstance)); + PropertyModule.RegisterCustomClassLayout("AFAbilityInfiniteDurationSpec", FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityInfiniteDurationSpecDetails::MakeInstance)); + + PropertyModule.RegisterCustomClassLayout("GAEffectCue", FOnGetDetailCustomizationInstance::CreateStatic(&FAFEffectCueDetails::MakeInstance)); + + IAssetTools& AssetTools = FModuleManager::LoadModuleChecked("AssetTools").Get(); + TSharedRef GABAction = MakeShareable(new FAssetTypeActions_GAEffectBlueprint()); + RegisterAssetTypeAction(AssetTools, GABAction); + TSharedRef GAAbilityAction = MakeShareable(new FAssetTypeActions_GAAbilityBlueprint()); + RegisterAssetTypeAction(AssetTools, GAAbilityAction); + TSharedRef GAEffectCueAction = MakeShareable(new FAssetTypeActions_GAEffectCueBlueprint()); + RegisterAssetTypeAction(AssetTools, GAEffectCueAction); + + //BlueprintEditorTabBinding = MakeShared(); + OnInitializeSequenceHandle = UGAEffectCueSequence::OnInitializeSequence().AddStatic(FAbilityFrameworkEditor::OnInitializeSequence); +} +void FAbilityFrameworkEditor::ShutdownModule() +{ + BlueprintEditorTabBinding = nullptr; + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); + PropertyModule.UnregisterCustomClassLayout("AFEffectSpecBase"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityActivationSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityCooldownSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityPeriodicInfiniteSpec"); + PropertyModule.UnregisterCustomClassLayout("AFAbilityInfiniteDurationSpec"); + + PropertyModule.UnregisterCustomPropertyTypeLayout("GAAttribute"); + //PropertyModule.UnregisterCustomPropertyTypeLayout("GAEffectProperty"); + PropertyModule.UnregisterCustomPropertyTypeLayout("AFPropertytHandle"); + + UGAEffectCueSequence::OnInitializeSequence().Remove(OnInitializeSequenceHandle); + BlueprintEditorTabBinding = nullptr; + if (FModuleManager::Get().IsModuleLoaded("AssetTools")) + { + IAssetTools& AssetToolsModule = FModuleManager::GetModuleChecked("AssetTools").Get(); + for (auto& AssetTypeAction : CreatedAssetTypeActions) + { + if (AssetTypeAction.IsValid()) + { + AssetToolsModule.UnregisterAssetTypeActions(AssetTypeAction.ToSharedRef()); + } + } + } +} + +IMPLEMENT_GAME_MODULE(FAbilityFrameworkEditor, AbilityFrameworkEditor); + + +//void FGameAttributesEditor::StartupModule() +//{ +// +//} +// +// +//void FGameAttributesEditor::ShutdownModule() +//{ +// +//} + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.h new file mode 100644 index 0000000..5a235e7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.h @@ -0,0 +1,60 @@ +#pragma once +#include "Engine.h" +#include "AbilityFramework.h" +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "EditorStyle.h" +#include "Effects/GAEffectCueSequence.h" +#include "EffectCueEditor/GAEffectCueEditor.h" + +#include "UnrealEd.h" +#include "AssetToolsModule.h" +#include "IAssetTypeActions.h" + +#include "BlueprintEditorModule.h" +#include "BlueprintEditorTabs.h" +#include "LayoutExtender.h" +#include "LevelEditor.h" +#include "MovieSceneToolsProjectSettings.h" +#include "PropertyEditorModule.h" +#include "Styling/SlateStyle.h" +#include "WorkflowTabManager.h" +#include "Modules/ModuleManager.h" +#include "Widgets/Docking/SDockTab.h" + +#include "ISettingsModule.h" + +#include "IAbilityFrameworkEditor.h" +class FEffectCueequenceEditorTabBinding + : public TSharedFromThis +{ +public: + + FEffectCueequenceEditorTabBinding(); + + void RegisterBlueprintEditorLayout(FLayoutExtender& Extender); + + void RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor); + ~FEffectCueequenceEditorTabBinding(); + +private: + + /** Delegate binding handle for FBlueprintEditorModule::OnRegisterTabsForEditor */ + FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; +}; +//add static list of registered custom derived effcts. Will be used to specify, from which classes +//new effect blueprints can be created, and which classes are allowed to pick (if not specified +//in metaData. +class FAbilityFrameworkEditor : public IAbilityFrameworkEditor +{ + TArray< TSharedPtr > CreatedAssetTypeActions; + TSharedPtr BlueprintEditorTabBinding; + FDelegateHandle OnInitializeSequenceHandle; + static TSet EffectClasses; + + void RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action); + static void OnInitializeSequence(UGAEffectCueSequence* Sequence); + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.cpp new file mode 100644 index 0000000..5840655 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.cpp @@ -0,0 +1,28 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "GACurveTableDetailCustomization.h" + +TSharedRef FGACurveTableDetailCustomization::MakeInstance() +{ + return MakeShareable(new FGACurveTableDetailCustomization); +} + +FGACurveTableDetailCustomization::~FGACurveTableDetailCustomization() +{ + +} + +void FGACurveTableDetailCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} +void FGACurveTableDetailCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.h new file mode 100644 index 0000000..2b09d86 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CurveTable/GACurveTableDetailCustomization.h @@ -0,0 +1,23 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "../GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FGACurveTableDetailCustomization : public IPropertyTypeCustomization +{ +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FGACurveTableDetailCustomization(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + + + +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp new file mode 100644 index 0000000..f301611 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp @@ -0,0 +1,353 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Effects/GAEffectCue.h" +#include "Effects/GAEffectCueSequence.h" +#include "EditorReimportHandler.h" +#include "MovieScene.h" +#include "Tracks/MovieScenePropertyTrack.h" +#if WITH_EDITOR +#include "Editor.h" +#endif +#include "ISequencerModule.h" +#include "LevelEditorSequencerIntegration.h" +#include "SSCSEditor.h" +#include "SlateIconFinder.h" +#include "BlueprintEditorUtils.h" +#include "Framework/MultiBox/MultiBoxBuilder.h" +#include "Framework/Application/SlateApplication.h" + +#include "AFEffectCueDetails.h" + +class SEffectCueSequenceEditorWidget + : public SCompoundWidget +{ +private: + TWeakObjectPtr WeakSequence; + AGAEffectCue* EffectCue; + TWeakPtr WeakBlueprintEditor; + + TSharedPtr Content; + TSharedPtr Sequencer; + FDelegateHandle OnBlueprintPreCompileHandle; + FDelegateHandle OnObjectSavedHandle; + FDelegateHandle OnSequenceChangedHandle; + FDelegateHandle OnBlueprintCompileHandle; + FDelegateHandle OnBlueprintReinstancedHandle; +public: + + SLATE_BEGIN_ARGS(SEffectCueSequenceEditorWidget) {} + SLATE_END_ARGS(); + + void Construct(const FArguments&, TWeakPtr InBlueprintEditor) + { + OnBlueprintPreCompileHandle = GEditor->OnBlueprintPreCompile().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintPreCompile); + OnObjectSavedHandle = FCoreUObjectDelegates::OnObjectSaved.AddSP(this, &SEffectCueSequenceEditorWidget::OnObjectPreSave); + OnBlueprintCompileHandle = GEditor->OnBlueprintCompiled().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintCompiled); + OnBlueprintReinstancedHandle = GEditor->OnBlueprintReinstanced().AddSP(this, &SEffectCueSequenceEditorWidget::OnBlueprintReinstanced); + + WeakBlueprintEditor = InBlueprintEditor; + + ChildSlot + [ + SAssignNew(Content, SBox) + .MinDesiredHeight(200) + ]; + } + void OnBlueprintCompiled() + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + UBlueprint* bp = BlueprintEditor->GetBlueprintObj(); + float dupa = 0; + } + void OnBlueprintReinstanced() + { + float dupa = 0; + } + ~SEffectCueSequenceEditorWidget() + { + if (Sequencer.IsValid()) + { + Sequencer->Close(); + Sequencer = nullptr; + } + + GEditor->OnBlueprintPreCompile().Remove(OnBlueprintPreCompileHandle); + GEditor->OnBlueprintCompiled().Remove(OnBlueprintCompileHandle); + GEditor->OnBlueprintReinstanced().Remove(OnBlueprintReinstancedHandle); + FCoreUObjectDelegates::OnObjectSaved.Remove(OnObjectSavedHandle); + } + void OnObjectPreSave(UObject* InObject) + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (Sequencer.IsValid() && BlueprintEditor.IsValid() && InObject && InObject == BlueprintEditor->GetBlueprintObj()) + { + Sequencer->RestorePreAnimatedState(); + } + } + + void OnBlueprintPreCompile(UBlueprint* InBlueprint) + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (Sequencer.IsValid() && BlueprintEditor.IsValid() && InBlueprint && InBlueprint == BlueprintEditor->GetBlueprintObj()) + { + Sequencer->RestorePreAnimatedState(); + } + } + void OnSequenceChanged() + { + UGAEffectCueSequence* ActorSequence = WeakSequence.Get(); + /*UBlueprint* Blueprint = ActorSequence ? ActorSequence->GetParentBlueprint() : nullptr; + + if (Blueprint) + { + FBlueprintEditorUtils::MarkBlueprintAsModified(Blueprint); + }*/ + } + void OnSequencerReceivedFocus() + { + if (Sequencer.IsValid()) + { + FLevelEditorSequencerIntegration::Get().OnSequencerReceivedFocus(Sequencer.ToSharedRef()); + } + } + UObject* GetPlaybackContext() const + { + UGAEffectCueSequence* LocalActorSequence = WeakSequence.Get(); + if (LocalActorSequence) + { + if (AActor* Actor = LocalActorSequence->GetTypedOuter()) + { + return Actor; + } + else if (UBlueprintGeneratedClass* GeneratedClass = LocalActorSequence->GetTypedOuter()) + { + return GeneratedClass->SimpleConstructionScript->GetComponentEditorActorInstance(); + } + } + + return nullptr; + } + + TArray GetEventContexts() const + { + TArray Contexts; + if (auto* Context = GetPlaybackContext()) + { + Contexts.Add(Context); + } + return Contexts; + } + AActor* GetPreviewActor() const + { + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (BlueprintEditor.IsValid()) + { + return BlueprintEditor->GetPreviewActor(); + } + if (UGAEffectCueSequence* Sequence = WeakSequence.Get()) + { + return Sequence->GetTypedOuter(); + } + return nullptr; + } + void OnSelectionUpdated(TSharedPtr SelectedNode) + { + if (SelectedNode->GetNodeType() != FSCSEditorTreeNode::ComponentNode) + { + return; + } + + UActorComponent* EditingComponent = nullptr; + + TSharedPtr BlueprintEditor = WeakBlueprintEditor.Pin(); + if (BlueprintEditor.IsValid()) + { + UBlueprint* Blueprint = BlueprintEditor->GetBlueprintObj(); + if (Blueprint) + { + EditingComponent = SelectedNode->GetEditableComponentTemplate(Blueprint); + } + } + else if (AActor* Actor = GetPreviewActor()) + { + EditingComponent = SelectedNode->FindComponentInstanceInActor(Actor); + } + + if (EditingComponent) + { + const FScopedTransaction Transaction(FText::FromString("Add component to Sequencer")); + Sequencer->GetHandleToObject(EditingComponent, true); + } + + FSlateApplication::Get().DismissAllMenus(); + } + void AddPossessComponentMenuExtensions(FMenuBuilder& MenuBuilder) + { + AActor* Actor = GetPreviewActor(); + if (!Actor) + { + return; + } + + Sequencer->State.ClearObjectCaches(*Sequencer); + TSet AllBoundObjects; + if (UGAEffectCueSequence* Sequence = WeakSequence.Get()) + { + AllBoundObjects.Add(Sequence->GetTypedOuter()); + //return Sequence->GetTypedOuter(); + } + UMovieScene* MovieScene = Sequencer->GetFocusedMovieSceneSequence()->GetMovieScene(); + for (int32 Index = 0; Index < MovieScene->GetPossessableCount(); ++Index) + { + FMovieScenePossessable& Possessable = MovieScene->GetPossessable(Index); + for (TWeakObjectPtr<> WeakObject : Sequencer->FindBoundObjects(Possessable.GetGuid(), Sequencer->GetFocusedTemplateID())) + { + if (UObject* Object = WeakObject.Get()) + { + AllBoundObjects.Add(Object); + } + } + } + + bool bIdent = false; + /*MenuBuilder.AddWidget( + SNew(SComponentSelectionTree, Actor) + .IsInEditMode(WeakBlueprintEditor.Pin().IsValid()) + .OnComponentSelected(this, &SEffectCueSequenceEditorWidget::OnSelectionUpdated) + .IsComponentValid_Lambda( + [AllBoundObjects](UActorComponent* Component) + { + return !AllBoundObjects.Contains(Component); + } + ) + , FText(), !bIdent + );*/ + } + void SetActorSequence(UGAEffectCueSequence* NewSequence, AGAEffectCue* InEffectCue) + { + if (UGAEffectCueSequence* OldSequence = WeakSequence.Get()) + { + if (OnSequenceChangedHandle.IsValid()) + { + OldSequence->OnSignatureChanged().Remove(OnSequenceChangedHandle); + } + } + EffectCue = InEffectCue; + WeakSequence = NewSequence; + + if (NewSequence) + { + OnSequenceChangedHandle = NewSequence->OnSignatureChanged().AddSP(this, &SEffectCueSequenceEditorWidget::OnSequenceChanged); + } + + // If we already have a sequencer open, just assign the sequence + if (Sequencer.IsValid() && NewSequence) + { + if (Sequencer->GetRootMovieSceneSequence() != NewSequence) + { + Sequencer->ResetToNewRootSequence(*NewSequence); + } + return; + } + + // If we're setting the sequence to none, destroy sequencer + if (!NewSequence) + { + //Content->SetContent(SNew(STextBlock).Text(LOCTEXT("NothingSelected", "Select a sequence"))); + return; + } + + // We need to initialize a new sequencer instance + FSequencerInitParams SequencerInitParams; + { + TWeakObjectPtr LocalWeakSequence = NewSequence; + + SequencerInitParams.RootSequence = NewSequence; + SequencerInitParams.EventContexts = TAttribute>(this, &SEffectCueSequenceEditorWidget::GetEventContexts); + SequencerInitParams.PlaybackContext = TAttribute(this, &SEffectCueSequenceEditorWidget::GetPlaybackContext); + + TSharedRef AddMenuExtender = MakeShareable(new FExtender); + + AddMenuExtender->AddMenuExtension("AddTracks", EExtensionHook::Before, nullptr, + FMenuExtensionDelegate::CreateLambda([=](FMenuBuilder& MenuBuilder) { + + MenuBuilder.AddSubMenu( + FText::FromString("Component"), + FText::FromString("Add a binding to one of this actor's components and allow it to be animated by Sequencer"), + FNewMenuDelegate::CreateRaw(this, &SEffectCueSequenceEditorWidget::AddPossessComponentMenuExtensions), + false /*bInOpenSubMenuOnClick*/, + FSlateIcon()//"LevelSequenceEditorStyle", "LevelSequenceEditor.PossessNewActor") + ); + + }) + ); + + SequencerInitParams.ViewParams.bReadOnly = false;// !WeakBlueprintEditor.IsValid() && !NewSequence->IsEditable(); + SequencerInitParams.bEditWithinLevelEditor = false; + SequencerInitParams.ViewParams.AddMenuExtender = AddMenuExtender; + SequencerInitParams.ViewParams.UniqueName = "EffectCueActorSequenceEditor"; + SequencerInitParams.ViewParams.OnReceivedFocus.BindRaw(this, &SEffectCueSequenceEditorWidget::OnSequencerReceivedFocus); + } + + Sequencer = FModuleManager::LoadModuleChecked("Sequencer").CreateSequencer(SequencerInitParams); + Content->SetContent(Sequencer->GetSequencerWidget()); + } +}; + + + +FEffectCueSequenceEditorSummoner::FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor) + : FWorkflowTabFactory("EmbeddedEffectCueSequenceID", BlueprintEditor) + , WeakBlueprintEditor(BlueprintEditor) +{ + bIsSingleton = true; + + TabLabel = FText::FromString("Cue Sequencer"); +} + +TSharedRef FEffectCueSequenceEditorSummoner::CreateTabBody(const FWorkflowTabSpawnInfo& Info) const +{ + return SNew(SEffectCueSequenceEditorWidget, WeakBlueprintEditor); +} + +TSharedRef FAFEffectCueDetails::MakeInstance() +{ + return MakeShareable(new FAFEffectCueDetails); +} + +void FAFEffectCueDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + const IDetailsView* DetailsView = DetailLayout.GetDetailsView(); + if (DetailsView) + { + TSharedPtr HostTabManager = DetailsView->GetHostTabManager(); + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + AGAEffectCue* EffectCue = Cast(Objects[0].Get()); + + if (HostTabManager.IsValid() && HostTabManager->CanSpawnTab("EmbeddedEffectCueSequenceID")) + { + TSharedPtr ExistingTab = HostTabManager->FindExistingLiveTab(FName("EmbeddedEffectCueSequenceID")); + if (ExistingTab.IsValid()) + { + //EffectCue->StaticClass()->GetDefaultObject()->Sequence + + //auto SequencerWidget = StaticCastSharedRef(ExistingTab->GetContent()); + StaticCastSharedRef(ExistingTab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); + //bIsExternalTabAlreadyOpened = ThisSequence && SequencerWidget->GetSequence() == ThisSequence; + return; + } + //EffectCue->Sequence + if (!Tab.IsValid()) + Tab = HostTabManager->InvokeTab(FName("EmbeddedEffectCueSequenceID")); + //Tab->SetContent(Sequencer->GetSequencerWidget()); + StaticCastSharedRef(Tab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); + } + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.h new file mode 100644 index 0000000..611e2aa --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.h @@ -0,0 +1,36 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +#include "GraphEditor.h" +#include "ISequencer.h" +#include "Effects/GAEffectCueSequence.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" +#include "WorkflowTabFactory.h" + +struct FEffectCueSequenceEditorSummoner + : public FWorkflowTabFactory +{ + FEffectCueSequenceEditorSummoner(TSharedPtr BlueprintEditor); + + virtual TSharedRef CreateTabBody(const FWorkflowTabSpawnInfo& Info) const override; + /*virtual TSharedRef SpawnTab(const FWorkflowTabSpawnInfo& Info) const override;*/ +protected: + TWeakPtr WeakBlueprintEditor; +}; +class FAFEffectCueDetails : public IDetailCustomization +{ +protected: + TSharedPtr Sequencer; + FDelegateHandle OnBlueprintPreCompileHandle; + TSharedPtr Tab; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp new file mode 100644 index 0000000..326f96c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "AssetTypeActions_GAEffectCueBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "GAEffectCueEditor.h" +#include "GAEffectCueBlueprint.h" +#include "Effects/GAEffectCue.h" +#include "GAEffectCueBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_GAEffectCueBlueprint::GetName() const +{ + return FText::FromString("Effect Cue"); +} +UClass* FAssetTypeActions_GAEffectCueBlueprint::GetSupportedClass() const +{ + return UGAEffectCueBlueprint::StaticClass(); +} + +void FAssetTypeActions_GAEffectCueBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FGAEffectCueEditor > NewEditor(new FGAEffectCueEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitEffectCueEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_GAEffectCueBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return false; +} + +UFactory* FAssetTypeActions_GAEffectCueBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UGAEffectCueBlueprintFactory* EffectCueBlueprintFactory = NewObject(); + EffectCueBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return EffectCueBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h new file mode 100644 index 0000000..55a06ad --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" +//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_GAEffectCueBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp new file mode 100644 index 0000000..dcbb00a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAEffectCueBlueprint* UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint) +{ + UGAEffectCueBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAEffectCueBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h new file mode 100644 index 0000000..e3a7eaf --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAEffectCueBlueprint.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORKEDITOR_API UGAEffectCueBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() +UPROPERTY() + class UGAEffectCueSequence* Animation; +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAEffectCueBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint); + +#endif +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp new file mode 100644 index 0000000..f37eefc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp @@ -0,0 +1,334 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueBlueprintFactory.h" +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Effects/GAGameEffect.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "GAEffectCueBlueprint.h" +#include "Effects/GAEffectCue.h" +#include "GAEffectCueGraph.h" +#include "GAEffectCueGraphSchema.h" + +#include "ClassViewerFilter.h" + +#include "SlateOptMacros.h" + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SEffectCueBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectCueBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = AGAEffectCue::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCueBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCueBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied AbilitiesBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InEffectCueBlueprintFactory) + { + EffectCueBlueprintFactory = InEffectCueBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Ability Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + EffectCueBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FEffectCueBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FEffectCueBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FEffectCueBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(AGAEffectCue::StaticClass()); + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCueBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (EffectCueBlueprintFactory.IsValid()) + { + EffectCueBlueprintFactory->BlueprintType = BPTYPE_Normal; + EffectCueBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr EffectCueBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UAbilitiesBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UGAEffectCueBlueprintFactory::UGAEffectCueBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UGAEffectCueBlueprint::StaticClass(); + ParentClass = AGAEffectCue::StaticClass(); +} + +bool UGAEffectCueBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SEffectCueBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UGAEffectCueBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(AGAEffectCue::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UGAEffectCueBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectCueBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { + UGAEffectCueBlueprint* AbilityBP = UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + if (AbilityBP == NULL) + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + + // Only allow a gameplay ability graph if there isn't one in a parent blueprint + UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAEffectCueGraph::StaticClass(), UGAEffectCueGraphSchema::StaticClass()); +#if WITH_EDITORONLY_DATA + if (NewBP->UbergraphPages.Num()) + { + FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); + } +#endif + FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); + NewBP->LastEditedDocuments.Add(NewGraph); + NewGraph->bAllowDeletion = false; + + UBlueprintEditorSettings* Settings = GetMutableDefault(); + if(Settings && Settings->bSpawnDefaultBlueprintNodes) + { + int32 NodePositionY = 0; + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); + } + } + } + + return NewBP; + } +} + +UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h new file mode 100644 index 0000000..1c78872 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "GAEffectCueBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UGAEffectCueBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp new file mode 100644 index 0000000..4c50866 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp @@ -0,0 +1,210 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "Effects/GAEffectCue.h" +#include "GAEffectCueEditor.h" +#include "Effects/GAEffectCueSequence.h" +#include "EditorReimportHandler.h" +#include "MovieScene.h" +#include "Tracks/MovieScenePropertyTrack.h" +#if WITH_EDITOR +#include "Editor.h" +#endif +#include "ISequencerModule.h" +#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" +#include "Toolkits/ToolkitManager.h" +#include "Toolkits/GlobalEditorCommonCommands.h" + +#include "GAEffectCueBlueprint.h" +#include "GAEffectCueBlueprintFactory.h" +#include "GAEffectCueGraphSchema.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "SDockTab.h" +#include "BlueprintEditorTabs.h" +#include "LayoutExtender.h" +#include "BlueprintEditorModes.h" +#include "BlueprintEditorTabs.h" + +#define LOCTEXT_NAMESPACE "FGAEffectCueEditor" + + +//TSharedRef FEffectCueSequenceEditorSummoner::SpawnTab(const FWorkflowTabSpawnInfo& Info) const +//{ +// TSharedRef Tab = FWorkflowTabFactory::SpawnTab(Info); +// +// TSharedPtr BlueprintEditorPtr = StaticCastSharedPtr(HostingApp.Pin()); +// BlueprintEditorPtr->GetInspector()->SetOwnerTab(Tab); +// +// BlueprintEditorPtr->GetInspector()->GetPropertyView()->SetHostTabManager(Info.TabManager); +// +// return Tab; +//} + +///////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +FGAEffectCueEditor::FGAEffectCueEditor() +{ + EditedCue = nullptr; + FBlueprintEditorModule& BlueprintEditorModule = FModuleManager::LoadModuleChecked("Kismet"); + BlueprintEditorTabSpawnerHandle = BlueprintEditorModule.OnRegisterTabsForEditor().AddRaw(this, &FGAEffectCueEditor::RegisterBlueprintEditorTab); + BlueprintEditorLayoutExtensionHandle = BlueprintEditorModule.OnRegisterLayoutExtensions().AddRaw(this, &FGAEffectCueEditor::RegisterBlueprintEditorLayout); +} + +void FGAEffectCueEditor::RegisterBlueprintEditorLayout(FLayoutExtender& Extender) +{ + //Extender.ExtendLayout(FBlueprintEditorTabs::CompilerResultsID, ELayoutExtensionPosition::Before, FTabManager::FTab(FName("EmbeddedEffectCueSequenceID"), ETabState::ClosedTab)); +} + +void FGAEffectCueEditor::RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor) +{ + //TabFactories.RegisterFactory(MakeShared(BlueprintEditor)); +} +TArray FGAEffectCueEditor::GetAnimationEventContexts() const +{ + TArray EventContexts; + return EventContexts; +} + +void FGAEffectCueEditor::OnSequenceChanged() +{ + UBlueprint* Blueprint = GetBlueprintObj(); + + if (Blueprint) + { + FBlueprintEditorUtils::MarkBlueprintAsModified(Blueprint); + } +} +void FGAEffectCueEditor::OnMovieSceneDataChanged() +{ +} +void FGAEffectCueEditor::ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView) +{ +} +FGAEffectCueEditor::~FGAEffectCueEditor() +{ + FEditorDelegates::OnAssetPostImport.RemoveAll(this); + FReimportManager::Instance()->OnPostReimport().RemoveAll(this); + FBlueprintEditorModule* BlueprintEditorModule = &FModuleManager::LoadModuleChecked("Kismet"); + BlueprintEditorModule->OnRegisterTabsForEditor().Remove(BlueprintEditorTabSpawnerHandle); + BlueprintEditorModule->OnRegisterLayoutExtensions().Remove(BlueprintEditorLayoutExtensionHandle); + BlueprintEditorTabSpawnerHandle.Reset(); + BlueprintEditorLayoutExtensionHandle.Reset(); + TabManager.Pin()->UnregisterTabSpawner(FName("EmbeddedEffectCueSequenceID")); + // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor +} + +void FGAEffectCueEditor::RegisterTabSpawners(const TSharedRef& InTabManager) +{ + TabManager = InTabManager; + FBlueprintEditor::RegisterTabSpawners(InTabManager); +} +void FGAEffectCueEditor::UnregisterTabSpawners(const TSharedRef& InTabManager) +{ + FAssetEditorToolkit::RegisterTabSpawners(InTabManager); +} + +void FGAEffectCueEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) +{ + + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, ObjectsToEdit, bInIsToolbarFocusable); +} +void FGAEffectCueEditor::InitEffectCueEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) +{ + InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); + UBlueprint* BP = InBlueprints[0]; + EditedCue = BP->GeneratedClass->GetDefaultObject(); + CueClass = BP->GeneratedClass; + + for (auto Blueprint : InBlueprints) + { + EnsureAbilityBlueprintIsUpToDate(Blueprint); + } +} + +void FGAEffectCueEditor::EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint) +{ +#if WITH_EDITORONLY_DATA + int32 Count = Blueprint->UbergraphPages.Num(); + for (auto Graph : Blueprint->UbergraphPages) + { + // remove the default event graph, if it exists, from existing Gameplay Ability Blueprints + if (Graph->GetName() == "EventGraph" && Graph->Nodes.Num() == 0) + { + check(!Graph->Schema->GetClass()->IsChildOf(UGAEffectCueGraphSchema::StaticClass())); + FBlueprintEditorUtils::RemoveGraph(Blueprint, Graph); + break; + } + } +#endif +} +bool FGAEffectCueEditor::IsBlueprintEditor() const +{ + return true; +} + +FName FGAEffectCueEditor::GetToolkitFName() const +{ + return FName("EffectCueEditor"); +} + +FText FGAEffectCueEditor::GetBaseToolkitName() const +{ + return FText::FromString("Game Effect Cue"); +} + +FText FGAEffectCueEditor::GetToolkitName() const +{ + const TArray& EditingObjs = GetEditingObjects(); + + check(EditingObjs.Num() > 0); + + FFormatNamedArguments Args; + + const UObject* EditingObject = EditingObjs[0]; + + const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); + + Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(FText::FromString("{ObjectName}{DirtyState}"), Args); +} + +FText FGAEffectCueEditor::GetToolkitToolTipText() const +{ + const UObject* EditingObject = GetEditingObject(); + + check (EditingObject != NULL); + + return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); +} + +FString FGAEffectCueEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("EffectCueEditor"); +} + +FLinearColor FGAEffectCueEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +UBlueprint* FGAEffectCueEditor::GetBlueprintObj() const +{ + const TArray& EditingObjs = GetEditingObjects(); + for (int32 i = 0; i < EditingObjs.Num(); ++i) + { + if (EditingObjs[i]->IsA()) + { + return (UBlueprint*)EditingObjs[i]; + } + } + return nullptr; +} + +FString FGAEffectCueEditor::GetDocumentationLink() const +{ + return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h new file mode 100644 index 0000000..9094f6b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h @@ -0,0 +1,79 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Framework/Commands/UICommandList.h" +#include "Framework/MultiBox/MultiBoxExtender.h" +#include "GraphEditor.h" +#include "ISequencer.h" +#include "Effects/GAEffectCueSequence.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" +#include "WorkflowTabFactory.h" +////////////////////////////////////////////////////////////////////////// +// FGameplayAbilitiesEditor +class UGAEffectCueSequence; +/** + * Gameplay abilities asset editor (extends Blueprint editor) + */ + +class FGAEffectCueEditor : public FBlueprintEditor +{ + TWeakPtr TabManager; + FDelegateHandle OnSequenceChangedHandle; + + TArray GetAnimationEventContexts() const; + FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; + class AGAEffectCue* EditedCue; + TSubclassOf CueClass; + TWeakObjectPtr EditedSequence; + void ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView); + void OnMovieSceneDataChanged(); + void OnSequenceChanged(); + void RegisterBlueprintEditorLayout(FLayoutExtender& Extender); + void RegisterBlueprintEditorTab(FWorkflowAllowedTabSet& TabFactories, FName InModeName, TSharedPtr BlueprintEditor); +public: + virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; + /** + * Edits the specified gameplay ability asset(s) + * + * @param Mode Asset editing mode for this editor (standalone or world-centric) + * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within + * @param InBlueprints The blueprints to edit + * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode + */ + + void InitEffectCueEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); +private: + /** + * Updates existing gameplay ability blueprints to make sure that they are up to date + * + * @param Blueprint The blueprint to be updated + */ + void EnsureAbilityBlueprintIsUpToDate(UBlueprint* Blueprint); + +public: + FGAEffectCueEditor(); + + virtual ~FGAEffectCueEditor(); + +public: + // IToolkit interface + // FRED_TODO: don't merge this back + virtual void RegisterTabSpawners(const TSharedRef& InTabManager) override; + virtual void UnregisterTabSpawners(const TSharedRef& InTabManager) override; + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual bool IsBlueprintEditor() const override; + // End of IToolkit interface + + /** @return the documentation location for this editor */ + virtual FString GetDocumentationLink() const override; + + /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ + virtual UBlueprint* GetBlueprintObj() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.cpp new file mode 100644 index 0000000..1487984 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueGraph.h" + +#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" + +///////////////////////////////////////////////////// +// UGameplayAbilityGraph + +UGAEffectCueGraph::UGAEffectCueGraph(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.h new file mode 100644 index 0000000..5a3bfe0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraph.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraph/EdGraph.h" +#include "GAEffectCueGraph.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectCueGraph : public UEdGraph +{ + GENERATED_UCLASS_BODY() +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.cpp new file mode 100644 index 0000000..bae2670 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.cpp @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectCueGraphSchema.h" +#include "EdGraphSchema_K2_Actions.h" +#include "Effects/GAGameEffect.h" +#include "Kismet2/BlueprintEditorUtils.h" + +UGAEffectCueGraphSchema::UGAEffectCueGraphSchema(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UK2Node_VariableGet* UGAEffectCueGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); +} + +UK2Node_VariableSet* UGAEffectCueGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.h new file mode 100644 index 0000000..1f9b8cc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueGraphSchema.h @@ -0,0 +1,38 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraphSchema_K2.h" +#include "GAEffectCueGraphSchema.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectCueGraphSchema : public UEdGraphSchema_K2 +{ + GENERATED_UCLASS_BODY() + + /** + * Creates a new variable getter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + /** + * Creates a new variable setter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp new file mode 100644 index 0000000..44ef642 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.cpp @@ -0,0 +1,57 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "AssetTypeActions_GAEffectBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "GAEffectEditor.h" +#include "Effects/GAEffectBlueprint.h" +#include "Effects/GAGameEffect.h" +#include "GAEffectBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_GAEffectBlueprint::GetName() const +{ + return FText::FromString("Effect Data"); +} +UClass* FAssetTypeActions_GAEffectBlueprint::GetSupportedClass() const +{ + return UGAEffectBlueprint::StaticClass(); +} + +void FAssetTypeActions_GAEffectBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FGAEffectEditor > NewEditor(new FGAEffectEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitEffectEditor(Mode, EditWithinLevelEditor, Blueprints, ShouldUseDataOnlyEditor(Blueprint)); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Gameplay Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_GAEffectBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return true; +} + +UFactory* FAssetTypeActions_GAEffectBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UGAEffectBlueprintFactory* EffectBlueprintFactory = NewObject(); + EffectBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return EffectBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.h new file mode 100644 index 0000000..ad3cabd --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/AssetTypeActions_GAEffectBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" +//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_GAEffectBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.cpp new file mode 100644 index 0000000..c84d883 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.cpp @@ -0,0 +1,347 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAEffectBlueprintFactory.h" +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Effects/GAGameEffect.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "Effects/GAEffectBlueprint.h" +#include "GAEffectGraph.h" +#include "GAEffectGraphSchema.h" +#include "Abilities/AFAbilityActivationSpec.h" +#include "Abilities/AFAbilityCooldownSpec.h" +#include "Abilities/AFAbilityPeriodSpec.h" +#include "Abilities/AFAbilityInfiniteDurationSpec.h" + +#include "ClassViewerFilter.h" + +#include "SlateOptMacros.h" + +#define LOCTEXT_NAMESPACE "UEffectBlueprintFactory" + + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SEffectBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UGAGameEffectSpec::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied EffectBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InEffectlueprintFactory) + { + EffectBlueprintFactory = InEffectlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Game Effect Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + EffectBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FEffectBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FEffectBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FEffectBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(UAFEffectSpecBase::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityActivationSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityCooldownSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityPeriodSpec::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(UAFAbilityInfiniteDurationSpec::StaticClass()); + + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (EffectBlueprintFactory.IsValid()) + { + EffectBlueprintFactory->BlueprintType = BPTYPE_Normal; + EffectBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr EffectBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UEffectBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UGAEffectBlueprintFactory::UGAEffectBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UGAEffectBlueprint::StaticClass(); + ParentClass = UGAGameEffectSpec::StaticClass(); +} + +bool UGAEffectBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SEffectBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UGAEffectBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UGAEffectBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : LOCTEXT("Null", "(null)") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Effect Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UGAEffectBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { + UGAEffectBlueprint* AbilityBP = UGAEffectBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + if (AbilityBP == NULL) + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + + // Only allow a gameplay ability graph if there isn't one in a parent blueprint + //UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Not Used Effect Graph"), UGAEffectGraph::StaticClass(), UGAEffectGraphSchema::StaticClass()); +#if WITH_EDITORONLY_DATA + if (NewBP->UbergraphPages.Num()) + { + FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); + } +#endif + //FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); + //NewBP->LastEditedDocuments.Add(NewGraph); + //NewGraph->bAllowDeletion = false; + + UBlueprintEditorSettings* Settings = GetMutableDefault(); + if(Settings && Settings->bSpawnDefaultBlueprintNodes) + { + int32 NodePositionY = 0; + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAGameEffectSpec::StaticClass(), NodePositionY); + //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAGameEffectSpec::StaticClass(), NodePositionY); + } + } + } + + return NewBP; + } +} + +UObject* UGAEffectBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.h new file mode 100644 index 0000000..8a9b850 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "GAEffectBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UGAEffectBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.cpp new file mode 100644 index 0000000..5559a8d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.cpp @@ -0,0 +1,124 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "../AbilityFrameworkEditor.h" +#include "GAEffectEditor.h" +#include "EditorReimportHandler.h" + +#if WITH_EDITOR +#include "Editor.h" +#endif +//Editor\UnrealEd\Public\Toolkits\ToolkitManager.h +//\Editor\UnrealEd\Private\Toolkits\SStandaloneAssetEditorToolkitHost.h +#include "Editor/UnrealEd/Private/Toolkits/SStandaloneAssetEditorToolkitHost.h" +#include "Toolkits/ToolkitManager.h" +//#include "Toolkits/AssetEditorCommonCommands.h" +#include "Toolkits/GlobalEditorCommonCommands.h" + +#include "Effects/GAEffectBlueprint.h" +#include "GAEffectBlueprintFactory.h" +#include "GAEffectGraphSchema.h" +#include "Kismet2/BlueprintEditorUtils.h" + +#define LOCTEXT_NAMESPACE "FGAEffectEditor" + + +///////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +FGAEffectEditor::FGAEffectEditor() +{ + // todo: Do we need to register a callback for when properties are changed? + //bCreateMenuExtenders = true; + //bCreateDefaultStandaloneMenu = false; + //bCreateDefaultToolbar = false; +} + +FGAEffectEditor::~FGAEffectEditor() +{ + FEditorDelegates::OnAssetPostImport.RemoveAll(this); + FReimportManager::Instance()->OnPostReimport().RemoveAll(this); + + // NOTE: Any tabs that we still have hanging out when destroyed will be cleaned up by FBaseToolkit's destructor +} +void FGAEffectEditor::InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable) +{ + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, AppIdentifier, StandaloneDefaultLayout, true, true, ObjectsToEdit, true); +} +void FGAEffectEditor::InitEffectEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode) +{ + InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); + RemoveAllToolbarWidgets(); +} + + +// FRED_TODO: don't merge this back +// FName FGameplayAbilitiesEditor::GetToolkitContextFName() const +// { +// return GetToolkitFName(); +// } + +FName FGAEffectEditor::GetToolkitFName() const +{ + return FName("GameEffectEditor"); +} + +FText FGAEffectEditor::GetBaseToolkitName() const +{ + return FText::FromString("Game Effect Editor"); +} + +FText FGAEffectEditor::GetToolkitName() const +{ + const TArray& EditingObjs = GetEditingObjects(); + + check(EditingObjs.Num() > 0); + + FFormatNamedArguments Args; + + const UObject* EditingObject = EditingObjs[0]; + + const bool bDirtyState = EditingObject->GetOutermost()->IsDirty(); + + Args.Add(TEXT("ObjectName"), FText::FromString(EditingObject->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(LOCTEXT("GameplayAbilitiesToolkitName", "{ObjectName}{DirtyState}"), Args); +} + +FText FGAEffectEditor::GetToolkitToolTipText() const +{ + const UObject* EditingObject = GetEditingObject(); + + check(EditingObject != NULL); + + return FAssetEditorToolkit::GetToolTipTextForObject(EditingObject); +} + +FString FGAEffectEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("EffectEditor"); +} + +FLinearColor FGAEffectEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +UBlueprint* FGAEffectEditor::GetBlueprintObj() const +{ + const TArray& EditingObjs = GetEditingObjects(); + for (int32 i = 0; i < EditingObjs.Num(); ++i) + { + if (EditingObjs[i]->IsA()) + { + return (UBlueprint*)EditingObjs[i]; + } + } + return nullptr; +} + +FString FGAEffectEditor::GetDocumentationLink() const +{ + return FBlueprintEditor::GetDocumentationLink(); // todo: point this at the correct documentation +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.h new file mode 100644 index 0000000..e0dd625 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectEditor.h @@ -0,0 +1,53 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Editor/Kismet/Public/BlueprintEditor.h" + +////////////////////////////////////////////////////////////////////////// +// FGameplayAbilitiesEditor + +/** + * Gameplay abilities asset editor (extends Blueprint editor) + */ +class FGAEffectEditor : public FBlueprintEditor +{ +public: + virtual void InitAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const FName AppIdentifier, const TSharedRef& StandaloneDefaultLayout, const bool bCreateDefaultStandaloneMenu, const bool bCreateDefaultToolbar, const TArray& ObjectsToEdit, const bool bInIsToolbarFocusable = false) override; + /** + * Edits the specified gameplay ability asset(s) + * + * @param Mode Asset editing mode for this editor (standalone or world-centric) + * @param InitToolkitHost When Mode is WorldCentric, this is the level editor instance to spawn this editor within + * @param InBlueprints The blueprints to edit + * @param bShouldOpenInDefaultsMode If true, the editor will open in defaults editing mode + */ + + void InitEffectEditor(const EToolkitMode::Type Mode, const TSharedPtr& InitToolkitHost, const TArray& InBlueprints, bool bShouldOpenInDefaultsMode); +public: + FGAEffectEditor(); + + virtual ~FGAEffectEditor(); + +public: + // IToolkit interface + // FRED_TODO: don't merge this back +// virtual FName GetToolkitContextFName() const override; + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual bool IsAssetEditor() const override { return true; } + virtual bool IsBlueprintEditor() const override { return false; }; + virtual void PostRegenerateMenusAndToolbars() override { RemoveAllToolbarWidgets(); }; + // End of IToolkit interface + + /** @return the documentation location for this editor */ + virtual FString GetDocumentationLink() const override; + + /** Returns a pointer to the Blueprint object we are currently editing, as long as we are editing exactly one */ + virtual UBlueprint* GetBlueprintObj() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.cpp new file mode 100644 index 0000000..a802167 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectGraph.h" + +#define LOCTEXT_NAMESPACE "GameplayAbilityGraph" + +///////////////////////////////////////////////////// +// UGameplayAbilityGraph + +UGAEffectGraph::UGAEffectGraph(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.h new file mode 100644 index 0000000..3492fc2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraph.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraph/EdGraph.h" +#include "GAEffectGraph.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectGraph : public UEdGraph +{ + GENERATED_UCLASS_BODY() +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.cpp new file mode 100644 index 0000000..1404740 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.cpp @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "../AbilityFrameworkEditor.h" +#include "GAEffectGraphSchema.h" +#include "EdGraphSchema_K2_Actions.h" +#include "Effects/GAGameEffect.h" +#include "Kismet2/BlueprintEditorUtils.h" + +UGAEffectGraphSchema::UGAEffectGraphSchema(const FObjectInitializer& ObjectInitializer) +: Super(ObjectInitializer) +{ +} + +UK2Node_VariableGet* UGAEffectGraphSchema::SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableGetNode(GraphPosition, ParentGraph, VariableName, Source); +} + +UK2Node_VariableSet* UGAEffectGraphSchema::SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const +{ + return Super::SpawnVariableSetNode(GraphPosition, ParentGraph, VariableName, Source); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.h new file mode 100644 index 0000000..d435fae --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectEditor/GAEffectGraphSchema.h @@ -0,0 +1,38 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "EdGraphSchema_K2.h" +#include "GAEffectGraphSchema.generated.h" + +UCLASS(MinimalAPI) +class UGAEffectGraphSchema : public UEdGraphSchema_K2 +{ + GENERATED_UCLASS_BODY() + + /** + * Creates a new variable getter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableGet* SpawnVariableGetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + /** + * Creates a new variable setter node and adds it to ParentGraph + * + * @param GraphPosition The location of the new node inside the graph + * @param ParentGraph The graph to spawn the new node in + * @param VariableName The name of the variable + * @param Source The source of the variable + * @return A pointer to the newly spawned node + */ + virtual class UK2Node_VariableSet* SpawnVariableSetNode(const FVector2D GraphPosition, class UEdGraph* ParentGraph, FName VariableName, UStruct* Source) const override; + + virtual bool ShouldAlwaysPurgeOnModification() const override { return true; } +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.cpp new file mode 100644 index 0000000..81cbfa0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.cpp @@ -0,0 +1,90 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "SGAAttributeWidget.h" + +#include "GAAttributeDetailCustomization.h" + +TSharedRef FGAAttributeDetailCustomization::MakeInstance() +{ + return MakeShareable(new FGAAttributeDetailCustomization); +} + +FGAAttributeDetailCustomization::~FGAAttributeDetailCustomization() +{ + +} + +void FGAAttributeDetailCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + SocketNameHandle = InStructPropertyHandle->GetChildHandle(GET_MEMBER_NAME_CHECKED(FGAAttribute, AttributeName)); + check(SocketNameHandle.IsValid()); + + HeaderRow + .NameContent() + [ + InStructPropertyHandle->CreatePropertyNameWidget() + ] + .ValueContent() + .MaxDesiredWidth(512) + [ + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .AutoWidth() + .VAlign(VAlign_Center) + [ + SNew(SComboButton) + .OnGetMenuContent(this, &FGAAttributeDetailCustomization::GetSocketTree) + .ContentPadding(FMargin(0.4)) + .ButtonContent() + [ + SNew(STextBlock) + .Margin(FMargin(0.6)) + .Text(this, &FGAAttributeDetailCustomization::GetAttributeName) + ] + ] + ]; +} +void FGAAttributeDetailCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} + +FText FGAAttributeDetailCustomization::GetAttributeName() const +{ + FName attributeName; + if (SocketNameHandle.IsValid()) + { + SocketNameHandle->GetValue(attributeName); + return FText::FromName(attributeName); + } + return FText::FromName(attributeName); +} + +TSharedRef FGAAttributeDetailCustomization::GetSocketTree() +{ + return SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(400) + [ + SNew(SGAAttributeWidget) + .OnAttributeSelectedIn(this, &FGAAttributeDetailCustomization::SetSocketName) + ]; +} + +void FGAAttributeDetailCustomization::SetSocketName(FString AttributeNameIn) +{ + FName name; + FName nameToSet = *AttributeNameIn; + SocketNameHandle->GetValue(name); + if (name != nameToSet) + { + SocketNameHandle->SetValue(nameToSet); + } +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.h new file mode 100644 index 0000000..7b28395 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributeDetailCustomization.h @@ -0,0 +1,33 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FGAAttributeDetailCustomization : public IPropertyTypeCustomization +{ +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FGAAttributeDetailCustomization(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + + +protected: + /** Cached Property Handle */ + TSharedPtr SocketNameHandle; + + /** Used with Combobox, show up socket tree widget. */ + TSharedRef GetSocketTree(); + + FText GetAttributeName() const; + + void SetSocketName(FString AttributeNameIn); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.cpp new file mode 100644 index 0000000..347b0d0 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.cpp @@ -0,0 +1,16 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" + + + +//TSharedPtr FGAAttributePanelGraphPinFactory::CreatePin(class UEdGraphPin* InPin) const +//{ +// const UEdGraphSchema_K2* K2Schema = GetDefault(); +// if (InPin->PinType.PinCategory == K2Schema->PC_Struct) +// //&& InPin->PinType.PinSubCategoryObject == FGAAttribute::StaticStruct()) +// { +// +// } +// return nullptr; +//} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.h new file mode 100644 index 0000000..047dc24 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePanelGraphPinFactory.h @@ -0,0 +1,23 @@ +#pragma once +#include "SlateBasics.h" +#include "Attributes/GAAttributeGlobals.h" +#include "EdGraph/EdGraphPin.h" +#include "EdGraph/EdGraphSchema.h" +#include "EdGraphSchema_K2.h" +#include "GAAttributePanelGraphPinFactory.h" +#include "GAAttributePin.h" +#include "EdGraphUtilities.h" + +class FGAAttributePanelGraphPinFactory : public FGraphPanelPinFactory +{ + virtual TSharedPtr CreatePin(class UEdGraphPin* InPin) const override + { + const UEdGraphSchema_K2* K2Schema = GetDefault(); + if (InPin->PinType.PinCategory == K2Schema->PC_Struct + && InPin->PinType.PinSubCategoryObject == FGAAttribute::StaticStruct()) + { + return SNew(SGAAttributePin, InPin); + } + return nullptr; + } +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.cpp new file mode 100644 index 0000000..51b9723 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.cpp @@ -0,0 +1,105 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" + +#include "KismetEditorUtilities.h" + +#include "STextComboBox.h" +#include "EdGraph/EdGraphPin.h" +#include "EdGraph/EdGraphSchema.h" + +#include "Effects/GAGameEffect.h" +#include "GAGlobalTypes.h" +#include "Attributes/GAAttributesBase.h" +#include "SGAAttributeWidget.h" +#include "GAAttributePin.h" + +void SGAAttributePin::Construct(const FArguments& InArgs, UEdGraphPin* InGraphPinObj) +{ + AttributesList.Empty(); + + SelectedAttribute = InGraphPinObj->GetDefaultAsString(); + SelectedAttribute.RemoveFromStart("(AttributeName=\""); + SelectedAttribute.RemoveFromEnd("\")"); + + for (TObjectIterator ClassIt; ClassIt; ++ClassIt) + { + UClass* Class = *ClassIt; + if (Class->IsChildOf(UGAAttributesBase::StaticClass()) + && !FKismetEditorUtilities::IsClassABlueprintSkeleton(Class)) + { + for (TFieldIterator PropertyIt(Class, EFieldIteratorFlags::ExcludeSuper); PropertyIt; ++PropertyIt) + { + UProperty* Prop = *PropertyIt; + //I need array within array, one for list of attributes, and one for class names. + TSharedPtr attribute = MakeShareable(new FString(Prop->GetName())); + AttributesList.Add(attribute); + } + } + } + SGraphPin::Construct(SGraphPin::FArguments(), InGraphPinObj); +} +TSharedRef SGAAttributePin::GetDefaultValueWidget() +{ + //AttributesList.Empty(); + return SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + [ + SAssignNew(AttributeComboButton, SComboButton) + .OnGetMenuContent(this, &SGAAttributePin::GetAttributesMenu) + .ButtonContent() + [ + SNew(STextBlock) + .Text(this, &SGAAttributePin::GetSelectedAttributeText) + ] + ]; + //return SNew(STextComboBox) + // .OptionsSource(&AttributesList) + // .OnSelectionChanged(this, &SGAAttributePin::OnAttributeSelected); + //return AttributeComboButton.ToSharedRef(); + +} + +TSharedRef SGAAttributePin::GetAttributesMenu() +{ + return SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(400) + [ + SNew(SGAAttributeWidget) + .OnAttributeSelectedIn(this, &SGAAttributePin::OnAttributeSelected) + ]; +} + +FText SGAAttributePin::GetSelectedAttributeText() const +{ + return FText::FromString(SelectedAttribute); +} +void SGAAttributePin::OnAttributeSelected(FString ItemSelected) +{ + SelectedAttribute = ItemSelected; + //FString CurrentValue = GraphPinObj->GetDefaultAsString(); + FString CurrentDefaultValue = GraphPinObj->GetDefaultAsString(); + FString attribute = ItemSelected; + if (CurrentDefaultValue.IsEmpty()) + { + CurrentDefaultValue = FString(TEXT("()")); + } + FString AttributeString = TEXT("("); + if (!attribute.IsEmpty()) + { + AttributeString += TEXT("AttributeName=\""); + AttributeString += attribute; + AttributeString += TEXT("\""); + } + AttributeString += TEXT(")"); + + if (!CurrentDefaultValue.Equals(AttributeString)) + { + GraphPinObj->GetSchema()->TrySetDefaultValue(*GraphPinObj, AttributeString); + } + + //if () +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.h new file mode 100644 index 0000000..74aeb68 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAAttributePin.h @@ -0,0 +1,27 @@ +#pragma once +#include "SlateBasics.h" +#include "SGraphPin.h" + +class SGAAttributePin : public SGraphPin +{ +public: + SLATE_BEGIN_ARGS(SGAAttributePin) {} + SLATE_END_ARGS() + +public: + void Construct(const FArguments& InArgs, UEdGraphPin* InGraphPinObj); + + virtual TSharedRef GetDefaultValueWidget() override; + void OnAttributeSelected(FString ItemSelected); +private: + TArray> AttributesList; + + TSharedPtr AttributeComboButton; + + TSharedRef GetAttributesMenu(); + + FText GetSelectedAttributeText() const; + + FString SelectedAttribute; + +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.cpp new file mode 100644 index 0000000..1784ae6 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.cpp @@ -0,0 +1,79 @@ + +#include "AbilityFrameworkEditor.h" +#include "Kismet/KismetMathLibrary.h" +#include "Kismet/KismetArrayLibrary.h" +#include "GameplayTask.h" +#include "Abilities/Tasks/GAAbilityTask.h" +#include "Abilities/GAAbilityBase.h" +#include "KismetCompiler.h" +#include "BlueprintEditorUtils.h" +#include "GAEK2Node_LatentAbilityTaskCall.h" +#include "K2Node_EnumLiteral.h" +#include "BlueprintFunctionNodeSpawner.h" +#include "BlueprintActionDatabaseRegistrar.h" + +#define LOCTEXT_NAMESPACE "K2Node" + +UGAEK2Node_LatentAbilityTaskCall::UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); +} + +bool UGAEK2Node_LatentAbilityTaskCall::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const +{ + bool bIsCompatible = false; + + EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); + bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); + + if (bAllowLatentFuncs) + { + UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); + if (MyBlueprint && MyBlueprint->GeneratedClass) + { + if (MyBlueprint->GeneratedClass->IsChildOf(UGAAbilityBase::StaticClass())) + { + bIsCompatible = true; + } + } + } + return bIsCompatible; +} + + +void UGAEK2Node_LatentAbilityTaskCall::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const +{ + //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); + struct GetMenuActions_Utils + { + static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) + { + UGAEK2Node_LatentAbilityTaskCall* AsyncTaskNode = CastChecked(NewNode); + if (FunctionPtr.IsValid()) + { + UFunction* Func = FunctionPtr.Get(); + UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); + + AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); + AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); + AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; + } + } + }; + + UClass* NodeClass = GetClass(); + //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + { + UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); + check(NodeSpawner != nullptr); + NodeSpawner->NodeClass = NodeClass; + + TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); + NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); + return NodeSpawner; + })); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.h new file mode 100644 index 0000000..e81d718 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAbilityTaskCall.h @@ -0,0 +1,20 @@ + +#pragma once +#include "EdGraph/EdGraphPin.h" +#include "EdGraphSchema_K2.h" +#include "K2Node_BaseAsyncTask.h" +#include "GAEK2Node_LatentAbilityTaskCall.generated.h" + +UCLASS() +class UGAEK2Node_LatentAbilityTaskCall : public UK2Node_BaseAsyncTask//UK2Node_LatentGameplayTaskCall +{ + GENERATED_BODY() + +public: + UGAEK2Node_LatentAbilityTaskCall(const FObjectInitializer& ObjectInitializer); + + // UEdGraphNode interface + virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; + virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; + // End of UEdGraphNode interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.cpp new file mode 100644 index 0000000..a5c474a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.cpp @@ -0,0 +1,76 @@ + +#include "AbilityFrameworkEditor.h" +#include "Kismet/KismetMathLibrary.h" +#include "Kismet/KismetArrayLibrary.h" +#include "KismetCompiler.h" +#include "BlueprintEditorUtils.h" +#include "GAEK2Node_LatentAction.h" +#include "K2Node_EnumLiteral.h" +#include "BlueprintFunctionNodeSpawner.h" +#include "BlueprintActionDatabaseRegistrar.h" +#include "LatentActions/AFTaskBase.h" +#define LOCTEXT_NAMESPACE "K2Node" + +UGAEK2Node_LatentAction::UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + ProxyActivateFunctionName = GET_FUNCTION_NAME_CHECKED(UAFTaskBase, ReadyForActivation); +} + +bool UGAEK2Node_LatentAction::IsCompatibleWithGraph(UEdGraph const* TargetGraph) const +{ + bool bIsCompatible = true; + + //EGraphType GraphType = TargetGraph->GetSchema()->GetGraphType(TargetGraph); + //bool const bAllowLatentFuncs = (GraphType == GT_Ubergraph || GraphType == GT_Macro); + + //if (bAllowLatentFuncs) + //{ + // UBlueprint* MyBlueprint = FBlueprintEditorUtils::FindBlueprintForGraph(TargetGraph); + // if (MyBlueprint && MyBlueprint->GeneratedClass) + // { + // if (MyBlueprint->GeneratedClass->IsChildOf(UGAAbilityBase::StaticClass())) + // { + // bIsCompatible = true; + // } + // } + //} + return bIsCompatible; +} + + +void UGAEK2Node_LatentAction::GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const +{ + //UK2Node_BaseAsyncTask::GetMenuActions(ActionRegistrar); + struct GetMenuActions_Utils + { + static void SetNodeFunc(UEdGraphNode* NewNode, bool /*bIsTemplateNode*/, TWeakObjectPtr FunctionPtr) + { + UGAEK2Node_LatentAction* AsyncTaskNode = CastChecked(NewNode); + if (FunctionPtr.IsValid()) + { + UFunction* Func = FunctionPtr.Get(); + UObjectProperty* ReturnProp = CastChecked(Func->GetReturnProperty()); + + AsyncTaskNode->ProxyFactoryFunctionName = Func->GetFName(); + AsyncTaskNode->ProxyFactoryClass = Func->GetOuterUClass(); + AsyncTaskNode->ProxyClass = ReturnProp->PropertyClass; + } + } + }; + + UClass* NodeClass = GetClass(); + //FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateUObject(this, &UGAEK2Node_LatentAbilityTaskCall::CreateNodeSpawner); + ActionRegistrar.RegisterClassFactoryActions(FBlueprintActionDatabaseRegistrar::FMakeFuncSpawnerDelegate::CreateLambda([NodeClass](const UFunction* FactoryFunc)->UBlueprintNodeSpawner* + { + UBlueprintNodeSpawner* NodeSpawner = UBlueprintFunctionNodeSpawner::Create(FactoryFunc); + check(NodeSpawner != nullptr); + NodeSpawner->NodeClass = NodeClass; + + TWeakObjectPtr FunctionPtr = const_cast(FactoryFunc); + NodeSpawner->CustomizeNodeDelegate = UBlueprintNodeSpawner::FCustomizeNodeDelegate::CreateStatic(GetMenuActions_Utils::SetNodeFunc, FunctionPtr); + return NodeSpawner; + })); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.h new file mode 100644 index 0000000..5e88133 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEK2Node_LatentAction.h @@ -0,0 +1,19 @@ + +#pragma once +#include "EdGraph/EdGraphPin.h" +#include "EdGraphSchema_K2.h" +#include "K2Node_BaseAsyncTask.h" +#include "GAEK2Node_LatentAction.generated.h" + +UCLASS() +class UGAEK2Node_LatentAction : public UK2Node_BaseAsyncTask +{ + GENERATED_BODY() + +public: + UGAEK2Node_LatentAction(const FObjectInitializer& ObjectInitializer); + + // UEdGraphNode interface + virtual void GetMenuActions(FBlueprintActionDatabaseRegistrar& ActionRegistrar) const override; + virtual bool IsCompatibleWithGraph(UEdGraph const* TargetGraph) const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.cpp new file mode 100644 index 0000000..2eedb36 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.cpp @@ -0,0 +1,856 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "IDetailsView.h" +#include "PropertyEditorModule.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" +#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" +#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" +#include "Editor/PropertyEditor/Private/SDetailsView.h" + +#include "STextCombobox.h" +#include "STreeView.h" +#include "SButton.h" +#include "STextBlock.h" + +#include "ClassViewerModule.h" +#include "ClassViewerFilter.h" + +#include "EditorClassUtils.h" +#include "IAssetTools.h" +#include "AssetRegistryModule.h" +#include "Dialogs/DlgPickAssetPath.h" +#include "AssetToolsModule.h" +#include "KismetCompilerModule.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "Kismet2/CompilerResultsLog.h" +#include "EffectEditor/GAEffectEditor.h" +#include "SMyBlueprint.h" +#include "SKismetInspector.h" + +#include "SGAAttributeWidget.h" +#include "Effects/GAGameEffect.h" +#include "Effects/GAEffectBlueprint.h" +#include "EffectEditor/GAEffectBlueprintFactory.h" +#include "GAEffectClassStructWidget.h" +#include "GAEffectDetails.h" +#include "AFAbilityActionSpecDetails.h" +#include "AFAbilityPeriodSpecDetails.h" +#include "AFAbilityCooldownSpecDetails.h" +#include "Abilities/AFAbilityActivationSpec.h" +#include "Abilities/AFAbilityPeriodSpec.h" +#include "Abilities/AFAbilityCooldownSpec.h" + +class SEffectCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectCreateDialog) {} + SLATE_ARGUMENT(TSet, MetaClass); + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UGAGameEffectSpec::StaticClass(); + MetaClass = InArgs._MetaClass; + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied GameplayAbilitiesBlueprintFactory */ + bool ConfigureProperties(FGAEffectClassStructWidget* InGameplayAbilitiesBlueprintFactory) + { + GameplayAbilitiesBlueprintFactory = InGameplayAbilitiesBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Game Effect Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + GameplayAbilitiesBlueprintFactory = nullptr; + + return bOkClicked; + } + +private: + class FGameplayAbilityBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FGameplayAbilityBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + Options.bShowDisplayNames = true; + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FGameplayAbilityBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses = MetaClass; + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (GameplayAbilitiesBlueprintFactory) + { + GameplayAbilitiesBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + FGAEffectClassStructWidget* GameplayAbilitiesBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + TSet MetaClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; +class FPropertyEditorClassFilter : public IClassViewerFilter +{ +public: + /** The meta class for the property that classes must be a child-of. */ + const UClass* ClassPropertyMetaClass; + + /** The interface that must be implemented. */ + const UClass* InterfaceThatMustBeImplemented; + + /** Whether or not abstract classes are allowed. */ + bool bAllowAbstract; + + bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + bool bMatchesFlags = !InClass->HasAnyClassFlags(CLASS_Hidden | CLASS_HideDropDown | CLASS_Deprecated) && + (bAllowAbstract || !InClass->HasAnyClassFlags(CLASS_Abstract)); + + if (bMatchesFlags && InClass->IsChildOf(ClassPropertyMetaClass) + && (!InterfaceThatMustBeImplemented || InClass->ImplementsInterface(InterfaceThatMustBeImplemented))) + { + return true; + } + + return false; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + bool bMatchesFlags = !InClass->HasAnyClassFlags(CLASS_Hidden | CLASS_HideDropDown | CLASS_Deprecated) && + (bAllowAbstract || !InClass->HasAnyClassFlags(CLASS_Abstract)); + + if (bMatchesFlags && InClass->IsChildOf(ClassPropertyMetaClass) + && (!InterfaceThatMustBeImplemented || InClass->ImplementsInterface(InterfaceThatMustBeImplemented))) + { + return true; + } + + return false; + } +}; + +FGAEffectClassStructWidget::~FGAEffectClassStructWidget() +{ + +} + +TSharedRef FGAEffectClassStructWidget::CreateEffectClassWidget(UObject* OwnerObject) +{ + OuterObject = OwnerObject; + //TAttribute EffectName;// (); + //EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectClassStructWidget::GetClassName)); + return SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .AutoWidth() + [ + SAssignNew(ComboButton, SComboButton) + .OnGetMenuContent(this, &FGAEffectClassStructWidget::GenerateClassPicker) + .ContentPadding(FMargin(2.0f, 2.0f)) + .ToolTipText(this, &FGAEffectClassStructWidget::GetDisplayValueAsString) + .ButtonContent() + [ + SNew(STextBlock) + .Text(this, &FGAEffectClassStructWidget::GetDisplayValueAsString) + //.Font(InArgs._Font) + ] + ] + +SHorizontalBox::Slot() + .AutoWidth() + [ + MakeNewBlueprintButton() + ] + +SHorizontalBox::Slot() + .AutoWidth() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnEditButtonClicked) + [ + SNew(STextBlock) + .Text(FText::FromString("Edit")) + ] + ]; +} + +FText FGAEffectClassStructWidget::GetClassName() const +{ + if (StructPropertyHandle.IsValid()) + { + return StructPropertyHandle->GetPropertyDisplayName(); + } + return FText::FromString("No Effect Selected"); +} +static FString GetClassDisplayName(const UObject* Object) +{ + const UClass* Class = Cast(Object); + if (Class != NULL) + { + UBlueprint* BP = UBlueprint::GetBlueprintFromClass(Class); + if (BP != NULL) + { + return BP->GetName(); + } + } + return (Object) ? Object->GetName() : "None"; +} +FText FGAEffectClassStructWidget::GetDisplayValueAsString() const +{ + static bool bIsReentrant = false; + + // Guard against re-entrancy which can happen if the delegate executed below (SelectedClass.Get()) forces a slow task dialog to open, thus causing this to lose context and regain focus later starting the loop over again + if (!bIsReentrant) + { + TGuardValue(bIsReentrant, true); + if (EffectPropertyHandle.IsValid()) + { + UObject* ObjectValue = NULL; + FPropertyAccess::Result Result = EffectPropertyHandle->GetValue(ObjectValue); + + if (Result == FPropertyAccess::Success && ObjectValue != NULL) + { + return FText::FromString(GetClassDisplayName(ObjectValue)); + } + + return FText::FromString("None"); + } + + return FText::FromString("None"); + } + else + { + return FText::FromString("None"); + } + +} +UClass* FGAEffectClassStructWidget::GetClassFromString(const FString& ClassName) +{ + if (ClassName.IsEmpty() || ClassName == "None") + { + return nullptr; + } + + UClass* Class = FindObject(ANY_PACKAGE, *ClassName); + if (!Class) + { + Class = LoadObject(nullptr, *ClassName); + } + return Class; +} +TSharedRef FGAEffectClassStructWidget::GenerateClassPicker() +{ + FClassViewerInitializationOptions Options; + Options.bShowUnloadedBlueprints = true; + Options.bShowNoneOption = true; + + if (EffectPropertyHandle.IsValid()) + { + Options.PropertyHandle = EffectPropertyHandle; + } + + + class FGameplayAbilityBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + bool bAllowAbstract; + FGameplayAbilityBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + if (!bAllowAbstract) + { + return !InClass->HasAnyClassFlags(CLASS_Abstract) && InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + TSharedPtr ClassFilter = MakeShareable(new FGameplayAbilityBlueprintParentFilter); + + TSet MetaClass; + TSharedPtr EffectPropertyHandleLocal = StructPropertyHandle->GetParentHandle(); + if (EffectPropertyHandleLocal.IsValid()) + { + FString ClassName = EffectPropertyHandleLocal->GetMetaData("AllowedClass"); + TArray ClassNames; + //ClassName.Pars + ClassName.ParseIntoArray(ClassNames, TEXT(",")); + if (ClassNames.Num() > 0) + { + for (const FString& name : ClassNames) + { + UClass* temp = GetClassFromString(name); + if (temp) + { + MetaClass.Add(temp); + } + } + } + else + { + MetaClass.Add(UGAGameEffectSpec::StaticClass()); + } + } + ClassFilter->AllowedChildrenOfClasses = MetaClass; + Options.ClassFilter = ClassFilter; + //ClassFilter->ClassPropertyMetaClass = MetaClass; + //ClassFilter->InterfaceThatMustBeImplemented = nullptr;// UInterface::StaticClass(); + ClassFilter->bAllowAbstract = false; + Options.bIsBlueprintBaseOnly = true; + Options.bIsPlaceableOnly = false; + Options.DisplayMode = EClassViewerDisplayMode::TreeView;// : EClassViewerDisplayMode::ListView; + Options.bAllowViewOptions = true; + Options.bShowDisplayNames = true; + + FOnClassPicked OnPicked(FOnClassPicked::CreateRaw(this, &FGAEffectClassStructWidget::OnClassPicked)); + + return SNew(SBox) + .WidthOverride(280) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(500) + [ + FModuleManager::LoadModuleChecked("ClassViewer").CreateClassViewer(Options, OnPicked) + ] + ]; +} + +void FGAEffectClassStructWidget::OnClassPicked(UClass* InClass) +{ + if (!InClass) + { + SendToObjects(TEXT("None")); + } + else + { + SendToObjects(InClass->GetPathName()); + } + + ComboButton->SetIsOpen(false); +} + +void FGAEffectClassStructWidget::SendToObjects(const FString& NewValue) +{ + if (EffectPropertyHandle.IsValid()) + { + EffectPropertyHandle->SetValueFromFormattedString(NewValue); + } + else + { + UClass* NewClass = FindObject(ANY_PACKAGE, *NewValue); + if (!NewClass) + { + NewClass = LoadObject(nullptr, *NewValue); + } + //OnSetClass.Execute(NewClass); + } +} + +TSharedRef FGAEffectClassStructWidget::MakeNewBlueprintButton() +{ + return + SNew(SButton) + .Text(FText::FromString("New Blueprint")) + //.ToolTipText(OptionalToolTipText.Get().IsEmpty() ? LOCTEXT("NewBlueprintButtonToolTipText", "Create New Blueprint") : OptionalToolTipText) + .OnClicked(this, &FGAEffectClassStructWidget::MakeNewBlueprint) + .IsEnabled(true) + .IsFocusable(false) + .ButtonColorAndOpacity(FSlateColor::UseForeground()) + [ + SNew(SImage) + .Image(FEditorStyle::GetBrush("PropertyWindow.Button_CreateNewBlueprint")) + ]; +} + +FReply FGAEffectClassStructWidget::MakeNewBlueprint() +{ + TSet MetaClass; + TSharedPtr EffectPropertyHandleLocal = StructPropertyHandle->GetParentHandle(); + FString ClassName = EffectPropertyHandleLocal->GetMetaData("AllowedClass"); + TArray ClassNames; + //ClassName.Pars + ClassName.ParseIntoArray(ClassNames, TEXT(",")); + if (ClassNames.Num() > 0) + { + for (const FString& name : ClassNames) + { + UClass* temp = GetClassFromString(name); + if (temp) + { + MetaClass.Add(temp); + } + } + } + else + { + MetaClass.Add(UAFEffectSpecBase::StaticClass()); + } + TSharedRef Dialog = SNew(SEffectCreateDialog).MetaClass(MetaClass); + Dialog->ConfigureProperties(this); + if (ParentClass) + { + check(FKismetEditorUtilities::CanCreateBlueprintOfClass(UGAGameEffectSpec::StaticClass())); + + // Pre-generate a unique asset name to fill out the path picker dialog with. + FString OuterName; + FString OuterName2; + + if (StructPropertyHandle.IsValid()) + { + UProperty* prop = StructPropertyHandle->GetProperty(); + OuterName = prop->GetOuter()->GetName(); + OuterName = prop->GetPathName(); + OuterName = StructPropertyHandle->GeneratePathToProperty(); + } + + + UPackage* OuterMost = OuterObject->GetOutermost(); + FString AssetName = OuterObject->GetName(); + FString Path = OuterMost->GetFullName(); + FJsonSerializableArray OutArray; + Path = Path.RightChop(7); + Path.ParseIntoArrayWS(OutArray, TEXT("/")); + FString OutAsset = OutArray[OutArray.Num() - 1]; + OutArray.RemoveAt(OutArray.Num() - 1); + // OutArray.RemoveAt(0); + FString OutPath = "/"; + for (const FString& str : OutArray) + { + OutPath += str; + OutPath += "/"; + } + OutPath += FString::Printf(TEXT("E_%s_"), *OutAsset); + + FString NewNameSuggestion = "";// FString::Printf(TEXT("E_%s_"), *OutAsset); + UClass* BlueprintClass = UGAGameEffectSpec::StaticClass(); + UClass* BlueprintGeneratedClass = UGAEffectBlueprint::StaticClass(); + + IKismetCompilerInterface& KismetCompilerModule = FModuleManager::LoadModuleChecked("KismetCompiler"); + KismetCompilerModule.GetBlueprintTypesForClass(UGAGameEffectSpec::StaticClass(), BlueprintClass, BlueprintGeneratedClass); + + FString PackageName = OutPath + NewNameSuggestion; + FString OutPackageName; + FString Name; + FAssetToolsModule& AssetToolsModule = FModuleManager::LoadModuleChecked("AssetTools"); + AssetToolsModule.Get().CreateUniqueAssetName(PackageName, NewNameSuggestion, OutPackageName, Name); + + + + TSharedPtr PickAssetPathWidget = + SNew(SDlgPickAssetPath) + .Title(FText::FromString("Create New Effect")) + .DefaultAssetPath(FText::FromString(OutPath)); + UBlueprint* Blueprint = nullptr; + if (EAppReturnType::Ok == PickAssetPathWidget->ShowModal()) + { + // Get the full name of where we want to create the physics asset. + FString UserPackageName = PickAssetPathWidget->GetFullAssetPath().ToString(); + FName BPName(*FPackageName::GetLongPackageAssetName(UserPackageName)); + + // Check if the user inputed a valid asset name, if they did not, give it the generated default name + if (BPName == NAME_None) + { + // Use the defaults that were already generated. + UserPackageName = PackageName; + BPName = *Name; + } + + // Then find/create it. + UPackage* Package = CreatePackage(NULL, *UserPackageName); + check(Package); + + // Create and init a new Blueprint + Blueprint = FKismetEditorUtilities::CreateBlueprint(ParentClass, Package, BPName, BPTYPE_Normal, UGAEffectBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), FName("LevelEditorActions")); + if (Blueprint) + { + // Notify the asset registry + FAssetRegistryModule::AssetCreated(Blueprint); + + // Mark the package dirty... + Package->MarkPackageDirty(); + } + } + if (Blueprint != NULL && Blueprint->GeneratedClass ) + { + UGAEffectBlueprint* eff = Cast(Blueprint); + if (eff) + { + EffectPropertyHandle->SetValueFromFormattedString(eff->GeneratedClass->GetPathName()); + + FAssetEditorManager::Get().OpenEditorForAsset(eff); + return FReply::Handled(); + } + } + } + return FReply::Unhandled(); +} + +FReply FGAEffectClassStructWidget::OnEditButtonClicked() +{ + if (EffectEditorWindow.IsValid()) + { + //EffectEditorWindow->RequestDestroyWindow(); + EffectEditorWindow->DestroyWindowImmediately(); + EffectEditorWindow.Reset(); + // already open, just show it + //EffectEditorWindow->BringToFront(true); + } + + { + UObject* OutVal = nullptr; + UGAEffectBlueprint* Blueprint = nullptr; + UProperty* Prop; + UBlueprintGeneratedClass* Class = nullptr; + if (EffectPropertyHandle.IsValid()) + { + EffectPropertyHandle->GetValue(OutVal); + EffectPropertyHandle->CreatePropertyValueWidget(); + Prop = EffectPropertyHandle->GetProperty(); + + if (OutVal) + { + Class = Cast(OutVal); + if (Class && Class->ClassGeneratedBy && Class->ClassGeneratedBy->IsA(UGAEffectBlueprint::StaticClass())) + { + Blueprint = Cast(Class->ClassGeneratedBy); + } + } + } + + FDetailsViewArgs Args; + Args.bHideSelectionTip = true; + Args.bLockable = false; + FPropertyEditorModule& PropertyEditorModule = FModuleManager::GetModuleChecked("PropertyEditor"); + TSharedRef DetailView = PropertyEditorModule.CreateDetailView(Args); + TArray InObjects; + if (Blueprint) + { + EditedBlueprint = Blueprint; + if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityActivationSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityActivationSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityActivationSpecDetails::MakeInstance)); + } + else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityPeriodSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityPeriodSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityPeriodSpecDetails::MakeInstance)); + } + else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UAFAbilityCooldownSpec::StaticClass())) + { + DetailView->RegisterInstancedCustomPropertyLayout(UAFAbilityCooldownSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FAFAbilityCooldownSpecDetails::MakeInstance)); + } + else if (Blueprint->ParentClass && Blueprint->ParentClass->IsChildOf(UGAGameEffectSpec::StaticClass())) + { + // DetailView->UnregisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass()); + // DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + } + } + if(!Class) + { + return FReply::Unhandled(); + } + if (!Class->ClassDefaultObject) + { + return FReply::Unhandled(); + } + //DetailView->RegisterInstancedCustomPropertyLayout(UGAGameEffectSpec::StaticClass(), FOnGetDetailCustomizationInstance::CreateStatic(&FGAEffectDetails::MakeInstance)); + InObjects.Add(Class->ClassDefaultObject); + DetailView->SetObjects(InObjects); + FString WindowTitle = "Effect Editor: "; + WindowTitle += Blueprint->GetName(); + EffectEditorWindow = SNew(SWindow) + .Title(FText::FromString(WindowTitle)) + .HasCloseButton(true) + .ClientSize(FVector2D(600, 400)); + EffectEditorWindow->SetContent( + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush(TEXT("PropertyWindow.WindowBorder"))) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(24.0f) + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnSaveButtonClicked) + [ + SNew(STextBlock) + .Text(FText::FromString("Save")) + ] + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnSaveCloseButtonClicked) + [ + SNew(STextBlock) + .Text(FText::FromString("Save/Close")) + ] + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(this, &FGAEffectClassStructWidget::OnCloseButtonClicked) + .IsEnabled(true) + .IsFocusable(false) + [ + SNew(STextBlock) + .Text(FText::FromString("Close")) + ] + ] + ] + +SVerticalBox::Slot() + .FillHeight(1) + [ + DetailView + ] + ] + ); + + if (FGlobalTabmanager::Get()->GetRootWindow().IsValid()) + { + FSlateApplication::Get().AddWindowAsNativeChild(EffectEditorWindow.ToSharedRef(), FGlobalTabmanager::Get()->GetRootWindow().ToSharedRef()); + } + else + { + FSlateApplication::Get().AddWindow(EffectEditorWindow.ToSharedRef()); + } + } + + return FReply::Handled(); +} +FReply FGAEffectClassStructWidget::OnSaveButtonClicked() +{ + if (EditedBlueprint) + { + FCompilerResultsLog LogResults; + LogResults.BeginEvent(TEXT("Compile")); + LogResults.bLogDetailedResults = false; + LogResults.EventDisplayThresholdMs = 0.1; + EBlueprintCompileOptions CompileOptions = EBlueprintCompileOptions::None; + CompileOptions |= EBlueprintCompileOptions::SaveIntermediateProducts; + + FKismetEditorUtilities::CompileBlueprint(EditedBlueprint, CompileOptions, &LogResults); + TArray PackagesToSave; + check((EditedBlueprint != nullptr) && EditedBlueprint->IsAsset()); + PackagesToSave.Add(EditedBlueprint->GetOutermost()); + + FEditorFileUtils::PromptForCheckoutAndSave(PackagesToSave, true, /*bPromptToSave=*/ false); + //EditedBlueprint = nullptr; + } + return FReply::Unhandled(); +} +FReply FGAEffectClassStructWidget::OnSaveCloseButtonClicked() +{ + if (EditedBlueprint) + { + FCompilerResultsLog LogResults; + LogResults.BeginEvent(TEXT("Compile")); + LogResults.bLogDetailedResults = false; + LogResults.EventDisplayThresholdMs = 0.1; + EBlueprintCompileOptions CompileOptions = EBlueprintCompileOptions::None; + CompileOptions |= EBlueprintCompileOptions::SaveIntermediateProducts; + + FKismetEditorUtilities::CompileBlueprint(EditedBlueprint, CompileOptions, &LogResults); + TArray PackagesToSave; + check((EditedBlueprint != nullptr) && EditedBlueprint->IsAsset()); + PackagesToSave.Add(EditedBlueprint->GetOutermost()); + + FEditorFileUtils::PromptForCheckoutAndSave(PackagesToSave, true, /*bPromptToSave=*/ false); + + EditedBlueprint = nullptr; + + if (EffectEditorWindow.IsValid()) + { + EffectEditorWindow->RequestDestroyWindow(); + EffectEditorWindow = nullptr; + + return FReply::Handled(); + } + } + + return FReply::Unhandled(); +} +FReply FGAEffectClassStructWidget::OnCloseButtonClicked() +{ + if (EffectEditorWindow.IsValid()) + { + EffectEditorWindow->RequestDestroyWindow(); + EffectEditorWindow = nullptr; + return FReply::Handled(); + } + return FReply::Unhandled(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.h new file mode 100644 index 0000000..f7e557f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectClassStructWidget.h @@ -0,0 +1,58 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FGAEffectClassStructWidget : public TSharedFromThis +{ +protected: + /* Handle to FGAEffectClass*/ + TSharedPtr StructPropertyHandle; + + /* Handle to TSubclassOf SpecClass */ + TSharedPtr EffectPropertyHandle; + + TSharedPtr ComboButton; + + TSharedPtr EffectEditorWindow; + UBlueprint* EditedBlueprint; + UObject* OuterObject; +public: + FGAEffectClassStructWidget() {}; + FGAEffectClassStructWidget(TSharedPtr InStructPropertyHandle, + TSharedPtr InEffectPropertyHandle) + : StructPropertyHandle(InStructPropertyHandle), + EffectPropertyHandle(InEffectPropertyHandle) + {}; + + TSubclassOf ParentClass; + TSharedRef CreateEffectClassWidget(UObject* OwnerObject); + void SetHandles(TSharedPtr InStructPropertyHandle, + TSharedPtr InEffectPropertyHandle) + { + StructPropertyHandle = InStructPropertyHandle; + EffectPropertyHandle = InEffectPropertyHandle; + } + + /** + * Destructor + */ + virtual ~FGAEffectClassStructWidget(); + + FText GetClassName() const; + FText GetDisplayValueAsString() const; + UClass* GetClassFromString(const FString& ClassName); + TSharedRef GenerateClassPicker(); + void OnClassPicked(UClass* InClass); + void SendToObjects(const FString& NewValue); + //FReply OnDrop(const FGeometry& MyGeometry, const FDragDropEvent& DragDropEvent); + TSharedRef MakeNewBlueprintButton(); + FReply MakeNewBlueprint(); + FReply OnEditButtonClicked(); + FReply OnSaveButtonClicked(); + FReply OnSaveCloseButtonClicked(); + FReply OnCloseButtonClicked(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.cpp new file mode 100644 index 0000000..b96e65c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.cpp @@ -0,0 +1,112 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" + +#include "STextCombobox.h" +#include "STreeView.h" + +#include "Effects/GAGameEffect.h" +#include "GAEffectDetails.h" +#include "Effects/AFEffectCustomApplication.h" +#include "AFEffectCustomizationCommon.h" +#include "Abilities/AFAbilityActivationSpec.h" +#include "Abilities/AFAbilityPeriodSpec.h" +#include "Abilities/AFAbilityCooldownSpec.h" +TSharedRef FGAEffectDetails::MakeInstance() +{ + return MakeShareable(new FGAEffectDetails); +} + +void FGAEffectDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + MyDetailLayout = &DetailLayout; + + TArray> Objects; + DetailLayout.GetObjectsBeingCustomized(Objects); + + ApplicationTypeHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Application), UGAGameEffectSpec::StaticClass()); + UpdateEffectTypeyDelegate = FSimpleDelegate::CreateSP(this, &FGAEffectDetails::OnDurationPolicyChange); + ApplicationTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + DurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Duration), UGAGameEffectSpec::StaticClass()); + PeriodHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, Period), UGAGameEffectSpec::StaticClass()); + DurationHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + DurationCalcTypeHandle = DurationHandle->GetChildHandle("CalculationType"); + PeriodCalcTypeHandle = PeriodHandle->GetChildHandle("CalculationType"); + + DurationCalcTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + PeriodCalcTypeHandle->SetOnPropertyValueChanged(UpdateEffectTypeyDelegate); + + for (TWeakObjectPtr obj : Objects) + { + if (UAFEffectSpecBase* Spec = Cast(obj.Get())) + { + /*if (!Spec->IsA(UAFAbilityActivationSpec::StaticClass()) + && !Spec->IsA(UAFAbilityPeriodSpec::StaticClass()) + && !Spec->IsA(UAFAbilityCooldownSpec::StaticClass()) + )*/ + { + bIsDuration = Spec->Application.GetDefaultObject()->ShowDuration(); + bIsPeriodic = Spec->Application.GetDefaultObject()->ShowPeriod(); + + if (bIsPeriodic && bIsDuration) + { + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(DurationHandle); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationHandle, "Duration"); + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodHandle, "Period"); + } + else if (!bIsPeriodic && bIsDuration) + { + TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); + TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(MaxStacksProp); + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(DurationHandle); + DetailLayout.HideProperty(MaxStackedDurationHandle); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, DurationHandle, "Duration"); + } + else if (bIsPeriodic && !bIsDuration) + { + TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); + TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(MaxStacksProp); + DetailLayout.HideProperty(DurationHandle); + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(MaxStackedDurationHandle); + + FAFEffectCustomizationCommon::CreateMagnitudeLayout(DetailLayout, PeriodHandle, "Period"); + } + else if (!bIsPeriodic && !bIsDuration) + { + TSharedPtr MaxStacksProp = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStacks), UGAGameEffectSpec::StaticClass()); + TSharedPtr MaxStackedDurationHandle = DetailLayout.GetProperty(GET_MEMBER_NAME_CHECKED(UGAGameEffectSpec, MaxStackedDuration), UGAGameEffectSpec::StaticClass()); + + DetailLayout.HideProperty(MaxStacksProp); + DetailLayout.HideProperty(DurationHandle); + DetailLayout.HideProperty(PeriodHandle); + DetailLayout.HideProperty(MaxStackedDurationHandle); + DetailLayout.HideCategory("Duration"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "EffectAggregation"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnExpiredEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "OnRemovedEffects"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AttributeTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "AppliedImmunityTags"); + FAFEffectCustomizationCommon::HideProperty(DetailLayout, "ApplyTags"); + + } + } + } + } +} +void FGAEffectDetails::OnDurationPolicyChange() +{ + if(MyDetailLayout) + MyDetailLayout->ForceRefreshDetails(); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.h new file mode 100644 index 0000000..8280469 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectDetails.h @@ -0,0 +1,32 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FGAEffectDetails : public IDetailCustomization +{ + +protected: + bool bIsDuration; + bool bIsPeriodic; + TSharedPtr ApplicationTypeHandle; +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + +private: + TSharedPtr MyProperty; + TSharedPtr DurationHandle; + TSharedPtr PeriodHandle; + TSharedPtr DurationCalcTypeHandle; + TSharedPtr PeriodCalcTypeHandle; + IDetailLayoutBuilder* MyDetailLayout; + FSimpleDelegate UpdateEffectTypeyDelegate; + /** IDetailCustomization interface */ + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; + + void OnDurationPolicyChange(); +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.cpp new file mode 100644 index 0000000..a10c616 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.cpp @@ -0,0 +1,96 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkEditor.h" +#include "IDetailsView.h" +#include "PropertyEditorModule.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" +#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" +#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" +#include "Editor/PropertyEditor/Private/SDetailsView.h" +//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h +#include "STextCombobox.h" +#include "STreeView.h" +#include "SButton.h" +#include "STextBlock.h" + +#include "ClassViewerModule.h" +#include "ClassViewerFilter.h" + +#include "EditorClassUtils.h" +#include "IAssetTools.h" +#include "AssetRegistryModule.h" +#include "Dialogs/DlgPickAssetPath.h" +#include "AssetToolsModule.h" +#include "KismetCompilerModule.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "EffectEditor/GAEffectEditor.h" +#include "SMyBlueprint.h" +#include "SKismetInspector.h" + +#include "SGAAttributeWidget.h" +#include "Effects/GAGameEffect.h" +#include "Effects/GAEffectBlueprint.h" +#include "EffectEditor/GAEffectBlueprintFactory.h" +#include "GAEffectPropertyStructCustomization.h" +#include "GAEffectDetails.h" + +TSharedRef FGAEffectPropertyStructCustomization::MakeInstance() +{ + return MakeShareable(new FGAEffectPropertyStructCustomization); +} + +FGAEffectPropertyStructCustomization::~FGAEffectPropertyStructCustomization() +{ + +} + +void FGAEffectPropertyStructCustomization::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + const TArray>& objs = StructCustomizationUtils.GetPropertyUtilities()->GetSelectedObjects(); + UObject* Owner = nullptr; + if (objs.Num() > 0) + { + Owner = objs[0].Get(); + } + StructPropertyHandle = InStructPropertyHandle; + TAttribute EffectName;// (); + EffectName.Create(TAttribute::FGetter::CreateRaw(this, &FGAEffectPropertyStructCustomization::GetClassName)); + /*SNew(SVerticalBox) + + SVerticalBox::Slot() + [ + SNew(STextBlock) + .Text(EffectName) + ]*/ + EffectPropertyHandle = InStructPropertyHandle->GetChildHandle(TEXT("SpecClass")); //struct + TSharedPtr ClassInStruct = EffectPropertyHandle->GetChildHandle(TEXT("SpecClass")); + EffectClassWidget = MakeShareable(new FGAEffectClassStructWidget()); + EffectClassWidget->SetHandles(EffectPropertyHandle, ClassInStruct); + + HeaderRow + .NameContent() + [ + InStructPropertyHandle->CreatePropertyNameWidget() + ] + .ValueContent() + .HAlign(HAlign_Fill) + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + .AutoWidth() + [ + EffectClassWidget->CreateEffectClassWidget(Owner) + ] + ]; +} +void FGAEffectPropertyStructCustomization::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} +FText FGAEffectPropertyStructCustomization::GetClassName() const +{ + if (StructPropertyHandle.IsValid()) + { + return StructPropertyHandle->GetPropertyDisplayName(); + } + return FText::FromString("No Effect Selected"); +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.h new file mode 100644 index 0000000..4ed717c --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAEffectPropertyStructCustomization.h @@ -0,0 +1,28 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "Attributes/GAAttributeGlobals.h" +#include "GAGlobalTypesEditor.h" + +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +#include "GAEffectClassStructWidget.h" +class FGAEffectPropertyStructCustomization : public IPropertyTypeCustomization +{ +protected: + TSharedPtr StructPropertyHandle; + TSharedPtr EffectPropertyHandle; + TSharedPtr EffectClassWidget; +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FGAEffectPropertyStructCustomization(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + + FText GetClassName() const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAGlobalTypesEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAGlobalTypesEditor.h new file mode 100644 index 0000000..3f87d07 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/GAGlobalTypesEditor.h @@ -0,0 +1,35 @@ + +#pragma once + +#include "GAGlobalTypesEditor.generated.h" + +USTRUCT() +struct FGAAttributeNode +{ + GENERATED_USTRUCT_BODY() +public: + //Name of current node, like class, category, attribute etc. + FString NodeName; + + FString ParentClassName; + + //current attribute for this node); + FString Attribute; + + TWeakPtr ParentNode; + + TArray > ChildNodes; + + /* + List of attributes containe within selected class (ParentClassName) + */ + TArray AttributeNames; + TArray CategoryNames; + FGAAttributeNode() {}; + ~FGAAttributeNode() + { + ParentClassName.Empty(); + Attribute.Empty(); + AttributeNames.Empty(); + }; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/IAbilityFrameworkEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/IAbilityFrameworkEditor.h new file mode 100644 index 0000000..6b825c2 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/IAbilityFrameworkEditor.h @@ -0,0 +1,36 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "ModuleManager.h" + + +/** + * The public interface to this module. In most cases, this interface is only public to sibling modules + * within this plugin. + */ +class IAbilityFrameworkEditor : public IModuleInterface +{ +public: + + /** + * Singleton-like access to this module's interface. This is just for convenience! + * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. + * + * @return Returns singleton instance, loading the module on demand if needed + */ + static inline IAbilityFrameworkEditor& Get() + { + return FModuleManager::LoadModuleChecked< IAbilityFrameworkEditor >("AbilityFrameworkEditor"); + } + + /** + * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. + * + * @return True if the module is loaded and ready to use + */ + static inline bool IsAvailable() + { + return FModuleManager::Get().IsModuleLoaded( "AbilityFrameworkEditor" ); + } +}; + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.cpp new file mode 100644 index 0000000..95453df --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.cpp @@ -0,0 +1,151 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "AbilityFrameworkEditor.h" + +#include "KismetEditorUtilities.h" + +#include "STextComboBox.h" +#include "STreeView.h" +#include "GAGlobalTypesEditor.h" + +#include "Attributes/GAAttributesBase.h" +#include "SGAAttributeWidget.h" + +void SGAAttributeWidget::Construct(const FArguments& InArgs) +{ + AttributesList.Empty(); + AttributesNodes.Empty(); + OnAttributeSelected = InArgs._OnAttributeSelectedIn; + + /* + Intended look: + ClassName + --CategoryName + ----AttributeName + + Or: + ClassName + --CategoryName + ----AttributeType + ------AttributeName + + + search. We really need search! + */ + for (TObjectIterator ClassIt; ClassIt; ++ClassIt) + { + UClass* Class = *ClassIt; + if (Class->IsChildOf(UGAAttributesBase::StaticClass()) + && !FKismetEditorUtilities::IsClassABlueprintSkeleton(Class)) + { + FString className = Class->GetName(); + if (!className.Contains(TEXT("REINST_"))) + { + TSharedPtr classRootNode = MakeShareable(new FGAAttributeNode()); + classRootNode->Attribute = className; + //first let's find root of tree, which is class name + classRootNode->NodeName = className; + FString Category; + //now let's categories as childs + for (TFieldIterator PropertyIt(Class, EFieldIteratorFlags::ExcludeSuper); PropertyIt; ++PropertyIt) + { + UProperty* Prop = *PropertyIt; + Category = Prop->GetMetaData("Category"); + + //check if we already have this category added.. + bool bFoundExistingCategory = false; + if (!Category.IsEmpty()) + { + for (TSharedPtr childNode : classRootNode->ChildNodes) + { + if (childNode->NodeName == Category) + { + bFoundExistingCategory = true; + TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); + attrNode->NodeName = Prop->GetName(); + attrNode->ParentNode = childNode; + childNode->ChildNodes.Add(attrNode); + } + } + if (!bFoundExistingCategory) + { + TSharedPtr categoryNode = MakeShareable(new FGAAttributeNode()); + categoryNode->NodeName = Category; + categoryNode->ParentNode = classRootNode; + classRootNode->ChildNodes.Add(categoryNode); + + TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); + attrNode->NodeName = Prop->GetName(); + attrNode->ParentNode = categoryNode; + categoryNode->ChildNodes.Add(attrNode); + } + } + } + AttributesNodes.Add(classRootNode); + } + } + } + + ChildSlot + [ + SAssignNew(AttributeTreeWidget, STreeView>) + .OnSelectionChanged(this, &SGAAttributeWidget::OnItemSelected) + .TreeItemsSource(&AttributesNodes) + .OnGenerateRow(this, &SGAAttributeWidget::OnGenerateRow) + .OnGetChildren(this, &SGAAttributeWidget::OnGetChildren) + .OnExpansionChanged(this, &SGAAttributeWidget::OnExpansionChanged) + .SelectionMode(ESelectionMode::Single) + ]; +} +SGAAttributeWidget::~SGAAttributeWidget() +{ + AttributesNodes.Empty(); +} + +void SGAAttributeWidget::OnItemSelected(TSharedPtr SelectedItem, ESelectInfo::Type SelectInfo) +{ + if (SelectedItem.IsValid()) + { + if (OnAttributeSelected.IsBound()) + { + OnAttributeSelected.Execute(SelectedItem->NodeName); + } + } +} + +TSharedRef SGAAttributeWidget::OnGenerateRow(TSharedPtr InItem, const TSharedRef& OwnerTable) +{ + return SNew(STableRow< TSharedPtr >, OwnerTable) + [ + SNew(STextBlock) + .Text(FText::FromString(InItem->NodeName)) + ]; +} + +void SGAAttributeWidget::OnGetChildren(TSharedPtr InItem, TArray< TSharedPtr >& OutChildren) +{ + TArray> Children; + + TArray> Children2; + + for (const FString& attribute : InItem->AttributeNames) + { + TSharedPtr attrNode = MakeShareable(new FGAAttributeNode()); + attrNode->Attribute = attribute; + Children.Add(attrNode); + } + + for (TSharedPtr childs : InItem->ChildNodes) + { + Children2.Add(childs); + } + + OutChildren += Children2; +} + + +void SGAAttributeWidget::OnExpansionChanged(TSharedPtr InItem, bool bIsExpanded) +{ + +} + + diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.h new file mode 100644 index 0000000..9ff94f5 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/SGAAttributeWidget.h @@ -0,0 +1,64 @@ + +#pragma once + +#include "SlateBasics.h" +#include "GAGlobalTypesEditor.h" + +DECLARE_DELEGATE_OneParam(FGAOnAttributeSelected, FString); + +class FAFAttributeNode +{ + FString NodeName; + + FString Attribute; + + TWeakPtr ParentNode; + + TArray > ChildNodes; +}; + +class FAFAttributeTree +{ + +}; + +class SGAAttributeWidget : public SCompoundWidget +{ + SLATE_BEGIN_ARGS(SGAAttributeWidget) + {} + SLATE_EVENT(FGAOnAttributeSelected, OnAttributeSelectedIn) + SLATE_END_ARGS(); + + void Construct(const FArguments& InArgs); + ~SGAAttributeWidget(); +private: + TArray> AttributesList; + + TArray > AttributesNodes; + + TSharedPtr > > AttributeTreeWidget; + + FGAOnAttributeSelected OnAttributeSelected; + + void OnItemSelected(TSharedPtr SelectedItem, ESelectInfo::Type SelectInfo); + /** + * Generate a row widget for the specified item node and table + * + * @param InItem Tag node to generate a row widget for + * @param OwnerTable Table that owns the row + * + * @return Generated row widget for the item node + */ + TSharedRef OnGenerateRow(TSharedPtr InItem, const TSharedRef& OwnerTable); + + /** + * Get children nodes of the specified node + * + * @param InItem Node to get children of + * @param OutChildren [OUT] Array of children nodes, if any + */ + void OnGetChildren(TSharedPtr InItem, TArray< TSharedPtr >& OutChildren); + + + void OnExpansionChanged(TSharedPtr InItem, bool bIsExpanded); +}; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp new file mode 100644 index 0000000..705f984 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp @@ -0,0 +1,107 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDAbilityGiveTrigger.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "Abilities/GAAbilityBase.h" + +// Sets default values +AAFDAbilityGiveTrigger::AAFDAbilityGiveTrigger() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + RootComp = CreateDefaultSubobject(RootCompName); + RootComponent = RootComp; + + Icon = CreateDefaultSubobject(IconName); + Icon->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); + Trigger = CreateDefaultSubobject(TriggerName); + Trigger->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); + + //Trigger2 = CreateDefaultSubobject(TriggerName); + //Trigger2->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); +} + +// Called when the game starts or when spawned +void AAFDAbilityGiveTrigger::BeginPlay() +{ + Super::BeginPlay(); + Trigger->OnComponentBeginOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::BeginOverlap); + Trigger->OnComponentEndOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::EndOverlap); +} + +// Called every frame +void AAFDAbilityGiveTrigger::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + +void AAFDAbilityGiveTrigger::BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, + int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) +{ + if (!AbilityConfig.AbilityTag.IsValid()) + return; + + IAFAbilityInterface* AbilityInterface = Cast(OtherActor); + if (!AbilityInterface) + return; + + if(!CurrentComponent) + CurrentComponent = AbilityInterface->GetAbilityComp(); + + //FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityReady, AbilityConfig.AbilityTag, + // AbilityConfig.InputTag); + + APawn* pawn = Cast(OtherActor); + if(pawn) + { + AController* AC = pawn->GetController(); + if(AC) + { + TArray Comps = AC->GetComponentsByTag(UAMAbilityManagerComponent::StaticClass(), TEXT("AbilityManager")); + if(Comps.Num() == 1 && !AbilityManager) + { + AbilityManager = Cast(Comps[0]); + } + + if(AbilityManager) + AbilityManager->NativeEquipAbility(AbilityConfig.AbilityTag, AbilityConfig.Group, AbilityConfig.Slot); + } + } + + //if(AbilityManager) + //{ + // + //} + //CurrentComponent->AddOnAbilityReadyDelegate(AbilityConfig.AbilityTag, del); + //CurrentComponent->NativeAddAbilityFromTag(AbilityConfig.AbilityTag, nullptr);// , /*Input*/ ShootInput); +} + +void AAFDAbilityGiveTrigger::EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex) +{ + if (!AbilityConfig.AbilityTag.IsValid()) + return; +} + +void AAFDAbilityGiveTrigger::OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) +{ + UGAAbilityBase* Ability = Cast(CurrentComponent->BP_GetAbilityByTag(InAbilityTag)); + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityInputReady, + InAbilityTag, InAbilityInput); + + CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); + } + else + { + CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + } +} + + +void AAFDAbilityGiveTrigger::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) +{ + +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h new file mode 100644 index 0000000..2df3625 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h @@ -0,0 +1,83 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "Components/BoxComponent.h" +#include "Components/ShapeComponent.h" +#include "GameplayTags.h" +#include "AMTypes.h" +#include "AMAbilityManagerComponent.h" +#include "AFDAbilityGiveTrigger.generated.h" + +USTRUCT(BlueprintType) +struct FAFDAbilityConfig +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") + EAMGroup Group; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") + EAMSlot Slot; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") + TSoftClassPtr AbilityTag; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") + TArray InputTag; +}; + +static const FName RootCompName = TEXT("RootComp"); +static const FName TriggerName = TEXT("Trigger"); +static const FName IconName = TEXT("Icon"); +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor +{ + GENERATED_BODY() +protected: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + USceneComponent* RootComp; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + UBillboardComponent* Icon; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + UBoxComponent* Trigger; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + UShapeComponent* Trigger2; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") + FAFDAbilityConfig AbilityConfig; + + UPROPERTY() + class UAFAbilityComponent* CurrentComponent; + UPROPERTY() + class UAMAbilityManagerComponent* AbilityManager; + +public: + // Sets default values for this actor's properties + AAFDAbilityGiveTrigger(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; +protected: + UFUNCTION() + void BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, + int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult); + /** Delegate for notification of end of overlap with a specific component */ + UFUNCTION() + void EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex); + + UFUNCTION() + void OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); + + UFUNCTION() + void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); + + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp new file mode 100644 index 0000000..d33bda5 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp @@ -0,0 +1,11 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDBlueprintFunctionLibrary.h" +#include "AFDManager.h" + + + +//void UAFDBlueprintFunctionLibrary::OpenAbilityDebugger() +//{ +// FAFDManager::Get(); +//} diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h new file mode 100644 index 0000000..49d85b9 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Kismet/BlueprintFunctionLibrary.h" +#include "AFDBlueprintFunctionLibrary.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API UAFDBlueprintFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() +public: + //UFUNCTION(Exec) + // static void OpenAbilityDebugger(); + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp new file mode 100644 index 0000000..dc9608a --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp @@ -0,0 +1,41 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDManager.h" +#include "EngineGlobals.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" +#include "Slate.h" +#include "SlateCore.h" +#include "DWManager.h" + +FAFDManager* FAFDManager::Instance = nullptr; + +FAFDManager::FAFDManager() +{ +} + +FAFDManager::~FAFDManager() +{ +} + +void FAFDManager::Init() +{ + Dekstop = SNew(SAFDDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); + GEngine->GameViewport->AddViewportWidgetContent(Dekstop.ToSharedRef()); +} + +FDWWWindowHandle FAFDManager::AddDebugWindow(TSharedPtr InWindowContent) +{ + return FDWManager::Get().CreateWindow(InWindowContent, "Debug"); +} + +#if WITH_EDITORONLY_DATA +void FAFDManager::PIEDestroy() +{ + if (Instance) + { + delete Instance; + Instance = nullptr; + } +} +#endif \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h new file mode 100644 index 0000000..c309907 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SAFDDesktopWidget.h" +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API FAFDManager +{ +private: + static FAFDManager* Instance; + TSharedPtr Dekstop; +protected: + void Init(); +public: + + static FAFDManager& Get() + { + if(!Instance) + { + Instance = new FAFDManager(); + Instance->Init(); + } + return*Instance; + } + +#if WITH_EDITORONLY_DATA + static void PIEDestroy(); +#endif + + + FDWWWindowHandle AddDebugWindow(TSharedPtr InWindowContent); + + FAFDManager(); + ~FAFDManager(); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp new file mode 100644 index 0000000..83672d1 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AFDAbilityBase.h" + + + + diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h new file mode 100644 index 0000000..40341a2 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Abilities/GAAbilityBase.h" +#include "AFDAbilityBase.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORKDEBUGGER_API UAFDAbilityBase : public UGAAbilityBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp new file mode 100644 index 0000000..e0ac611 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp @@ -0,0 +1,45 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFrameworkDebugger.h" +#include "HAL/IConsoleManager.h" +#include "AFDManager.h" +#if WITH_EDITORONLY_DATA +#include "Editor.H" +#endif +#define LOCTEXT_NAMESPACE "FAbilityFrameworkDebuggerModule" + +void FAbilityFrameworkDebuggerModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module + CommandOpenAbilityDebugger = IConsoleManager::Get().RegisterConsoleCommand( + TEXT("OpenAbilityDebugger"), + TEXT("Opens ability debugger"), + FConsoleCommandDelegate::CreateStatic(OpenAbilityDebugger), + ECVF_Default + ); + +#if WITH_EDITORONLY_DATA + FEditorDelegates::EndPIE.AddRaw(this, &FAbilityFrameworkDebuggerModule::HandlePIEEnd); +#endif //WITH_EDITORONLY_DATA +} + +void FAbilityFrameworkDebuggerModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. + IConsoleManager::Get().UnregisterConsoleObject(CommandOpenAbilityDebugger); +} + +void FAbilityFrameworkDebuggerModule::OpenAbilityDebugger() +{ + FAFDManager::Get(); +} +#if WITH_EDITORONLY_DATA +void FAbilityFrameworkDebuggerModule::HandlePIEEnd(bool InVal) +{ + FAFDManager::PIEDestroy(); +} +#endif +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FAbilityFrameworkDebuggerModule, AbilityFrameworkDebugger) \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h new file mode 100644 index 0000000..d50fefe --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h @@ -0,0 +1,22 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FAbilityFrameworkDebuggerModule : public IModuleInterface +{ +private: + IConsoleObject* CommandOpenAbilityDebugger; + static void OpenAbilityDebugger(); +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; + +#if WITH_EDITORONLY_DATA + void HandlePIEEnd(bool InVal); +#endif +}; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp new file mode 100644 index 0000000..48c1171 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp @@ -0,0 +1,74 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDAttributes.h" +#include "SlateOptMacros.h" +#include "SListView.h" +#include "SGridPanel.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDAttributes::Construct(const FArguments& InArgs) +{ + AFInterface = InArgs._AbilityInterface; + ChildSlot + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SOverlay) + +SOverlay::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SListView>) + .ListItemsSource(&Attributes) + .OnGenerateRow(this, &SAFDAttributes::GenerateListRow) + ] + ]; + GatherAttributes(); +} +void SAFDAttributes::GatherAttributes() +{ + if (!AFInterface) + return; + + UGAAttributesBase* AttributesObject = AFInterface->GetAttributes(); + if (!AttributesObject) + return; + + Attributes.Empty(); + for(TFieldIterator It(AttributesObject->GetClass(), EFieldIteratorFlags::IncludeSuper); It; ++It) + { + TSharedPtr AttributeRow = MakeShareable(new FAttributeRow); + UStructProperty* Prop = *It; + FAFAttributeBase* Attr = Prop->ContainerPtrToValuePtr(AttributesObject); + if (Attr) + { + AttributeRow->Attribute = Attr; + AttributeRow->Name = It->GetName(); + AttributeRow->Value = TAttribute::Create(TAttribute::FGetter::CreateSP(AttributeRow.Get(), &FAttributeRow::GetValue)); + } + Attributes.Add(AttributeRow); + } + +} +TSharedRef SAFDAttributes::GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable) +{ + return + SNew(STableRow< TSharedRef >, OwnerTable) + [ + SNew(SGridPanel) + .FillColumn(0, 1) + +SGridPanel::Slot(0,0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(FText::FromString(NotifyName->Name)) + ] + + SGridPanel::Slot(1, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(NotifyName->Value) + ] + ]; +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h new file mode 100644 index 0000000..57f937b --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h @@ -0,0 +1,39 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" +#include "AFAbilityInterface.h" +#include "Attributes/GAAttributesBase.h" + +struct FAttributeRow : public TSharedFromThis +{ + FString Name; + FAFAttributeBase* Attribute; + TAttribute Value; + + FText GetValue() const + { + return FText::AsNumber(Attribute->GetCurrentValue()); + } +}; + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDAttributes : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDAttributes) + {} + SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) + SLATE_END_ARGS() + + IAFAbilityInterface* AFInterface; + TArray> Attributes; + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + void GatherAttributes(); + TSharedRef GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp new file mode 100644 index 0000000..d2091b4 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp @@ -0,0 +1,203 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDDesktopWidget.h" +#include "SlateCore.h" +#include "Slate.h" +#include "SlateOptMacros.h" +#include "SBoxPanel.h" +#include "SButton.h" +#include "STextBlock.h" +#include "AFDManager.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" +#include "GameFramework/PlayerController.h" +#include "SAFDViewportMouseCapture.h" +#include "SAFDEffects.h" +#include "SAFDAttributes.h" + +void SAFDMainWidget::Construct(const FArguments& InArgs) +{ + FWorldContext* WorldContext = GEngine->GetWorldContextFromGameViewport(GEngine->GameViewport); + UWorld* world = WorldContext->World(); + World = world; + FOnClicked OnPickActorClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnPickActorClicked); + + FOnClicked OnAttributesClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnAttributesClicked); + FOnClicked OnEffectsClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnEffectsClicked); + + ChildSlot + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + .FillHeight(1.0f) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SOverlay) + +SOverlay::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Top) + .AutoHeight() + [ + SNew(STextBlock) + .Text(this, &SAFDMainWidget::GetActorName) + ] + + SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Top) + .MaxHeight(24) + .AutoHeight() + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnAttributesClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("Attributes")) + ] + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnEffectsClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("Effects")) + ] + ] + ] + + SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + .FillWidth(1.0f) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SAssignNew(Content, SWidgetSwitcher) + ] + ] + ] + ] + +SVerticalBox::Slot() + .MaxHeight(32.0f) + .AutoHeight() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Bottom) + [ + SNew(SButton) + .OnClicked(OnPickActorClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("Pick Actor")) + ] + ] + ]; +} + +FText SAFDMainWidget::GetActorName() const +{ + if(SelectedActor.IsValid()) + { + return FText::FromString(SelectedActor->GetName()); + } + return FText::FromString("Select Actor from viewport."); +} +FReply SAFDMainWidget::OnPickActorClicked() +{ + CaptureWidget = SNew(SAFDViewportMouseCapture); + FSimpleDelegate del = FSimpleDelegate::CreateSP(this, &SAFDMainWidget::OnActorPicked); + CaptureWidget->OnMouseButtonDownDelegate = del; + GEngine->GameViewport->AddViewportWidgetContent(CaptureWidget.ToSharedRef(), 1001); + + return FReply::Handled(); +} + +FReply SAFDMainWidget::OnAttributesClicked() +{ + Content->SetActiveWidgetIndex(0); + return FReply::Handled(); +} +FReply SAFDMainWidget::OnEffectsClicked() +{ + Content->SetActiveWidgetIndex(1); + return FReply::Handled(); +} + +void SAFDMainWidget::OnActorPicked() +{ + APlayerController* PC = World->GetFirstPlayerController(); + FHitResult OutHit; + PC->GetHitResultUnderCursor(ECollisionChannel::ECC_Visibility, false, OutHit); + + if(OutHit.bBlockingHit) + { + AActor* actor = OutHit.GetActor(); + SelectedActor = OutHit.Actor; + if(IAFAbilityInterface* Interface = Cast(OutHit.GetActor())) + { + Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SAFDAttributes) + .AbilityInterface(Interface) + ]; + Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SAFDEffects) + .AbilityInterface(Interface) + ]; + } + } + + GEngine->GameViewport->RemoveViewportWidgetContent(CaptureWidget.ToSharedRef()); +} +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDDesktopWidget::Construct(const FArguments& InArgs) +{ + FOnClicked OnNewDebugWindowClickedDel = FOnClicked::CreateSP(this, &SAFDDesktopWidget::OnNewDebugWindowClicked); + ChildSlot + [ + SNew(SHorizontalBox) + +SHorizontalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Right) + .VAlign(EVerticalAlignment::VAlign_Top) + [ + SNew(SVerticalBox) + +SVerticalBox::Slot() + [ + SNew(SButton) + .OnClicked(OnNewDebugWindowClickedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("New Debug Window")) + ] + ] + ] + // Populate the widget + ]; + +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +FReply SAFDDesktopWidget::OnNewDebugWindowClicked() +{ + TSharedPtr wid = SNew(SAFDMainWidget); + FDWWWindowHandle Handle = FAFDManager::Get().AddDebugWindow(wid); + wid->SetWindowHandle(Handle); + return FReply::Handled(); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h new file mode 100644 index 0000000..73f612c --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h @@ -0,0 +1,54 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" +#include "SDraggableWindowWidget.h" +#include "SWidgetSwitcher.h" + +class ABILITYFRAMEWORKDEBUGGER_API SAFDMainWidget : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDMainWidget) + {} + SLATE_END_ARGS() +protected: + TWeakObjectPtr World; + TWeakObjectPtr SelectedActor; + TSharedPtr Content; + FDWWWindowHandle WindowHandle; + TSharedPtr CaptureWidget; + /** Constructs this widget with InArgs */ +public: + void Construct(const FArguments& InArgs); +protected: + FReply OnPickActorClicked(); + FReply OnAttributesClicked(); + FReply OnEffectsClicked(); + + void OnActorPicked(); + + FText GetActorName() const; +public: + void SetWindowHandle(const FDWWWindowHandle& InHandle) + { + WindowHandle = InHandle; + } +}; + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDDesktopWidget : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDDesktopWidget) + {} + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + + FReply OnNewDebugWindowClicked(); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp new file mode 100644 index 0000000..babb94a --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDEffectInspector.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDEffectInspector::Construct(const FArguments& InArgs) +{ + /* + ChildSlot + [ + // Populate the widget + ]; + */ +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h new file mode 100644 index 0000000..e9de984 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDEffectInspector : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDEffectInspector) + {} + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp new file mode 100644 index 0000000..53bd36c --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp @@ -0,0 +1,105 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDEffects.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDEffects::Construct(const FArguments& InArgs) +{ + AFInterface = InArgs._AbilityInterface; + AbilityComponent = AFInterface->GetAbilityComp(); + + InitializeEffects(); + ChildSlot + [ + SNew(SOverlay) + + SOverlay::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SAssignNew(ListView, SListView>) + .ListItemsSource(&Effects) + .OnGenerateRow(this, &SAFDEffects::GenerateListRow) + ] + ]; + +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION +SAFDEffects::~SAFDEffects() +{ + +} + +void SAFDEffects::InitializeEffects() +{ + if (!AbilityComponent.IsValid()) + return; + + //ListView->RebuildList(); +} + + +TSharedRef SAFDEffects::GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable) +{ + return + SNew(STableRow< TSharedRef >, OwnerTable) + [ + SNew(SGridPanel) + .FillColumn(0, 1) + /*.FillColumn(1,1) + .FillColumn(2,1)*/ + + SGridPanel::Slot(0, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(FText::FromString(EffectRow->EffectClassName)) + ] + + SGridPanel::Slot(1, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(EffectRow->TimeRemaining) + ] + + SGridPanel::Slot(2, 0) + .HAlign(EHorizontalAlignment::HAlign_Fill) + [ + SNew(STextBlock) + .Text(EffectRow->PeriodTime) + ] + ]; +} + +void SAFDEffects::OnEffectApplied(FGAEffectHandle InHandle) +{ + TSharedPtr Row = MakeShareable(new FAFDEffectRow); + UE_LOG(LogTemp, Warning, TEXT("SAFDEffects::OnEffectAppliede")); + Effects.Add(Row); + + ListView->RebuildList(); +} +void SAFDEffects::OnEffectRemoved(FGAEffectHandle InHandle) +{ + class Predicate + { + FGAEffectHandle HandleC; + public: + Predicate(const FGAEffectHandle& InH) + :HandleC(InH) + {} + bool operator()(const FAFDEffectRow& Other) const + { + return HandleC == Other.Handle; + } + bool operator()(TSharedPtr Other) const + { + return HandleC == Other->Handle; + } + }; + int32 Idx = Effects.IndexOfByPredicate(Predicate(InHandle)); //Effects.IndexOfByKey(InHandle); + if(Idx > -1) + { + Effects.RemoveAt(Idx); + } + + ListView->RebuildList(); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h new file mode 100644 index 0000000..6d17270 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h @@ -0,0 +1,82 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +#include "GAGlobalTypes.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" + +struct FAFDEffectRow : public TSharedFromThis +{ + FString EffectClassName; + FGAEffectHandle Handle; + TAttribute TimeRemaining; + TAttribute PeriodTime; + TWeakObjectPtr AbilityComponent; + + FText GetTimeRemaining() const + { + return FText::AsNumber(0); + //return FText::AsNumber(AbilityComponent->GameEffectContainer.GetRemainingTime(Handle)); + } + + FText GetPeriodTime() const + { + return FText::AsNumber(0); + //return FText::AsNumber(RepInfo->GetPeriodTime(static_cast(FPlatformTime::Seconds()))); + } + + const bool operator==(const FAFDEffectRow& Other) const + { + return Handle == Other.Handle; + } + + const bool operator==(const FGAEffectHandle& InHandle) const + { + return Handle == InHandle; + } + const bool operator==(FGAEffectHandle InHandle) const + { + return Handle == InHandle; + } + const bool operator==(TSharedPtr InHandle) const + { + return Handle == InHandle->Handle; + } +}; + + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDEffects : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDEffects) + {} + SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) + SLATE_END_ARGS() +protected: + IAFAbilityInterface* AFInterface; + TWeakObjectPtr AbilityComponent; + TSharedPtr>> ListView; + FDelegateHandle OnEffectAppliedHandle; + FDelegateHandle OnEffectRemovedHandle; + FDelegateHandle OnEffectExpiredHandle; + + TArray> Effects; + +public: + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + ~SAFDEffects(); +protected: + TSharedRef GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable); + void InitializeEffects(); + void OnEffectApplied(FGAEffectHandle InHandle); + void OnEffectRemoved(FGAEffectHandle InHandle); +}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp new file mode 100644 index 0000000..5560253 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp @@ -0,0 +1,22 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SAFDViewportMouseCapture.h" +#include "SlateOptMacros.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SAFDViewportMouseCapture::Construct(const FArguments& InArgs) +{ + /* + ChildSlot + [ + // Populate the widget + ]; + */ +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +FReply SAFDViewportMouseCapture::OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) +{ + OnMouseButtonDownDelegate.ExecuteIfBound(); + return FReply::Handled(); +} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h new file mode 100644 index 0000000..30e79b2 --- /dev/null +++ b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Widgets/SCompoundWidget.h" + +/** + * + */ +class ABILITYFRAMEWORKDEBUGGER_API SAFDViewportMouseCapture : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SAFDViewportMouseCapture) + {} + SLATE_END_ARGS() + + FSimpleDelegate OnMouseButtonDownDelegate; + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + + virtual FReply OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) override; +}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp new file mode 100644 index 0000000..38779ca --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp @@ -0,0 +1,451 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AMAbilityManagerComponent.h" +#include "AFAbilityComponent.h" +#include "AFAbilityInterface.h" + +// Sets default values for this component's properties +UAMAbilityManagerComponent::UAMAbilityManagerComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + bWantsInitializeComponent = true; + SetIsReplicated(true); + // ... +} + + +// Called when the game starts +void UAMAbilityManagerComponent::BeginPlay() +{ + Super::BeginPlay(); + //OnNextGroupDelegate = FGroupConfirmDelegate::(this, UAMAbilityManagerComponent::OnNextGroupConfirmed); + // ... + +} +void UAMAbilityManagerComponent::InitializeComponent() +{ + uint8 GroupNum = Groups.Num(); + + AbilitySet.SetNum(GroupNum); + AbilityTagsSet.SetNum(GroupNum); + for(int32 Idx = 0; Idx < GroupNum; Idx++) + { + AbilitySet[Idx].SetNum(Groups[Idx].SlotNum); + AbilityTagsSet[Idx].SetNum(Groups[Idx].SlotNum); + } +} + +// Called every frame +void UAMAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} +void UAMAbilityManagerComponent::BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent) +{ + if (!AbilityComponent) + return; + + for (const FGameplayTag& Input : InputsToBind) + { + AbilityComponent->BindAbilityToAction(InputComponent, Input); + } +} + +UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) +{ + return AbilitySet.Num() >= Groups.Num() ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; +} +void UAMAbilityManagerComponent::SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility) +{ + if (AbilitySet.Num() < Groups.Num()) + return; + + AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbility; +} +void UAMAbilityManagerComponent::RemoveAbility(EAMGroup InGroup, EAMSlot InSlot) +{ + if (AbilitySet.Num() < Groups.Num()) + return; + + AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset();; +} + +TArray UAMAbilityManagerComponent::GetInputTag(EAMGroup InGroup, EAMSlot InSlot) +{ + return InputSetup.GetInputs(InGroup, InSlot); +} +void UAMAbilityManagerComponent::SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag) +{ + +} + +TSoftClassPtr UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) +{ + if (AbilityTagsSet.IsValidIndex(AMEnumToInt(InGroup)) + && AbilityTagsSet[AMEnumToInt(InGroup)].IsValidIndex(AMEnumToInt(InSlot))) + { + return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; + } + return TSoftClassPtr(); +} +void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag) +{ + AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; +} +void UAMAbilityManagerComponent::RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot) +{ + AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset(); +} + +void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + TArray IAbilityInput; + + if(ActiveGroup == InGroup) + IAbilityInput = GetInputTag(InGroup, InSlot); + + FAFOnAbilityReady del; + //if (IsClient()) + { + del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, + IAbilityInput, InGroup, InSlot, bBindInput); + AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + } + + AbilityComp->NativeAddAbility(InAbilityTag, IAbilityInput);// , /*Input*/ ShootInput); +} +void UAMAbilityManagerComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + FAFOnAbilityReady del; + //if (IsClient()) + { + //del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, + // IAbilityInput, InGroup, InSlot); + //AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); + } + if (InAbilityTag.IsNull()) + InAbilityTag = GetAbilityTag(InGroup, InSlot); + + RemoveAbility(InGroup, InSlot); + RemoveAbilityTag(InGroup, InSlot); + + AbilityComp->NativeRemoveAbility(InAbilityTag); +} +void UAMAbilityManagerComponent::OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + + + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + if (GetOwner()->GetNetMode() == ENetMode::NM_Client) + { + if (bBindInput) + { + FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityInputReady, + InAbilityTag, InAbilityInput, InGroup, InSlot); + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); + + ExecuteAbilityReadyEvent(InAbilityTag); + } + + } + else + { + SetAbility(InGroup, InSlot, Ability); + SetAbilityTag(InGroup, InSlot, InAbilityTag); + SetInputTag(InGroup, InSlot, InAbilityInput); + if (bBindInput) + { + AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); + ExecuteAbilityReadyEvent(InAbilityTag); + } + } + OnAbilityReady(InAbilityTag, InAbilityInput, InGroup, InSlot); +} + +void UAMAbilityManagerComponent::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) +{ + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return; + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return; + + UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); + if (!AbilityComp) + return; + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + SetAbility(InGroup, InSlot, Ability); + SetAbilityTag(InGroup, InSlot, InAbilityTag); + SetInputTag(InGroup, InSlot, InAbilityInput); + //ExecuteAbilityReadyEvent(InAbilityTag); +} + +void UAMAbilityManagerComponent::NextGroup() +{ + ENetMode NetMode = GetOwner()->GetNetMode(); + if (NetMode == ENetMode::NM_Client + || NetMode == ENetMode::NM_Standalone) + { + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex++; + if(CurrentIndex > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } + + if (ActiveGroup < AMIntToEnum(Groups.Num())) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + } + + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerNextGroup(AMEnumToInt(ActiveGroup)); + } +} + +void UAMAbilityManagerComponent::PreviousGroup() +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex--; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (CurrentIndex < 0) + { + ActiveGroup = AMIntToEnum(Groups.Num() - 1); + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerPreviousGroup(static_cast(ActiveGroup)); + } +} + +void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponIndex) +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex++; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (CurrentIndex > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = AMIntToEnum(CurrentIndex); + } + if (ActiveGroup < AMIntToEnum(Groups.Num())) + { + } + else + { + ActiveGroup = EAMGroup::Group001; + } + //so Server index is different. Client might tried to cheat + //or sometrhing. We will override it. + //situation where client can chage multiple weapons within second + //should not have place, as there is animation and/or internal cooldown on weapon change. + //since it will be done trough ability. + if (ActiveGroup != AMIntToEnum(WeaponIndex)) + { + ClientNextGroup(AMEnumToInt(ActiveGroup), false); + } + else + { + ClientNextGroup(AMEnumToInt(ActiveGroup), true); + } +} +bool UAMAbilityManagerComponent::ServerNextGroup_Validate(int32 WeaponIndex) +{ + return true; +} +void UAMAbilityManagerComponent::ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) +{ + ActiveGroup = AMIntToEnum(WeaponIndex); + OnNextGroupConfirmed(ActiveGroup, bPredictionSuccess); +} + +void UAMAbilityManagerComponent::ServerPreviousGroup_Implementation(int32 WeaponIndex) +{ + int32 CurrentIndex = AMEnumToInt(ActiveGroup); + CurrentIndex--; + ActiveGroup = AMIntToEnum(CurrentIndex); + if (CurrentIndex < 0) + { + ActiveGroup = AMIntToEnum(Groups.Num() -1); + } + if (ActiveGroup != AMIntToEnum(WeaponIndex)) + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); + } + else + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); + } +} +bool UAMAbilityManagerComponent::ServerPreviousGroup_Validate(int32 WeaponIndex) +{ + return true; +} +void UAMAbilityManagerComponent::ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) +{ + ActiveGroup = AMIntToEnum(WeaponIndex); + OnPreviousGroupConfirmed(ActiveGroup, bPredictionSuccess); +} + +void UAMAbilityManagerComponent::SelectGroup(EAMGroup InGroup) +{ + if (AMEnumToInt(InGroup) > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = InGroup; + } + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerSelectGroup(InGroup); + } + else + { + OnGroupSelectionConfirmed(InGroup, true); + } +} +void UAMAbilityManagerComponent::ServerSelectGroup_Implementation(EAMGroup InGroup) +{ + if (AMEnumToInt(InGroup) > Groups.Num()) + { + ActiveGroup = EAMGroup::Group001; + } + else + { + ActiveGroup = InGroup; + } + if (ActiveGroup != InGroup) + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); + } + else + { + ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); + } +} +bool UAMAbilityManagerComponent::ServerSelectGroup_Validate(EAMGroup InGroup) +{ + return true; +} + + +void UAMAbilityManagerComponent::ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess) +{ + if (bPredictionSuccess) + { + OnGroupSelectionConfirmed(InGroup, true); + } + else + { + ActiveGroup = InGroup; + OnGroupSelectionConfirmed(InGroup, false); + } +} + + +class UAFAbilityComponent* UAMAbilityManagerComponent::GetAbilityComponent() +{ + UAFAbilityComponent* AbilityComponent = nullptr; + APlayerController* MyPC = Cast(GetOwner()); + if (!MyPC) + return AbilityComponent; + + IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); + if (!ABInt) + return AbilityComponent; + + AbilityComponent = ABInt->GetAbilityComp(); + + return AbilityComponent; +} + +bool UAMAbilityManagerComponent::IsServerOrStandalone() const +{ + AActor* Owner = GetOwner(); + if (Owner->GetNetMode() == ENetMode::NM_DedicatedServer + || Owner->GetNetMode() == ENetMode::NM_Standalone) + { + return true; + } + return false; +} +bool UAMAbilityManagerComponent::IsClientOrStandalone() const +{ + AActor* Owner = GetOwner(); + if (Owner->GetNetMode() == ENetMode::NM_Client + || Owner->GetNetMode() == ENetMode::NM_Standalone) + { + return true; + } + return false; +} +bool UAMAbilityManagerComponent::IsClient() const +{ + AActor* Owner = GetOwner(); + if (Owner->GetNetMode() == ENetMode::NM_Client + || Owner->Role < ENetRole::ROLE_Authority) + { + return true; + } + return false; +} + +void UAMAbilityManagerComponent::BindOnAbilityReadDelegate(TSoftClassPtr InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) +{ + +} diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h new file mode 100644 index 0000000..08d1adf --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h @@ -0,0 +1,201 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "Net/UnrealNetwork.h" +#include "Engine/ActorChannel.h" + +#include "AMTypes.h" +#include "GameplayTags.h" +#include "Abilities/GAAbilityBase.h" +#include "AMAbilityManagerComponent.generated.h" + + + +/* +- Group +- Set +- Ability +-Inputs (multiple); + +*/ + +//all the inputs assigned to SINGLE ability; + +USTRUCT() +struct FAMAbilityInputSlot +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Inputs; + + TArray operator()() + { + return Inputs; + } +}; + + +USTRUCT() +struct FAMAbilityInputGroup +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Slots; +}; + + +USTRUCT() +struct FAMAbilityInputContainer +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray Groups; + + + TArray GetInputs(EAMGroup InGroup, EAMSlot InSlot) + { + return Groups[AMEnumToInt(InGroup)].Slots[AMEnumToInt(InSlot)](); + } +}; + +USTRUCT() +struct FAMAbilitySlotConfig +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + uint8 SlotNum; +}; + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere) + TArray Groups; + + //Map input bindings to particular slot and group. + UPROPERTY(EditAnywhere) + FAMAbilityInputContainer InputSetup; + + UPROPERTY(EditAnywhere, Category = "Input Config") + TArray InputsToBind; + + EAMGroup ActiveGroup; + + TArray>> AbilityTagsSet; + TArray>> AbilitySet; + TArray> ValidGroups; + TMap, FSimpleDelegate> AbilityReadyEvents; + + DECLARE_DELEGATE_TwoParams(FGroupConfirmDelegate, int32, bool) + + FGroupConfirmDelegate OnNextGroupDelegate; + FGroupConfirmDelegate OnPreviousGroupDelegate; + +public: + // Sets default values for this component's properties + UAMAbilityManagerComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + virtual void InitializeComponent() override; +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + void BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent); + UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); + void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); + void RemoveAbility(EAMGroup InGroup, EAMSlot InSlot); + + TSoftClassPtr GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); + void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag); + void RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot); + + TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); + void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); + + void NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); + void NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); +protected: + virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot) {}; +private: + UFUNCTION() + void OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot, bool bBindInput); + +public: + UFUNCTION() + void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot); + + UFUNCTION(BlueprintCallable) + virtual void NextGroup(); + UFUNCTION(BlueprintCallable) + virtual void PreviousGroup(); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerNextGroup(int32 WeaponIndex); + void ServerNextGroup_Implementation(int32 WeaponIndex); + bool ServerNextGroup_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientNextGroup(int32 WeaponIndex, bool bPredictionSuccess); + void ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); + + UFUNCTION(Server, Reliable, WithValidation) + void ServerPreviousGroup(int32 WeaponIndex); + void ServerPreviousGroup_Implementation(int32 WeaponIndex); + bool ServerPreviousGroup_Validate(int32 WeaponIndex); + UFUNCTION(Client, Reliable) + void ClientPreviousGroup(int32 WeaponIndex, bool bPredictionSuccess); + void ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); + + + virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; + virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; + virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; + + UFUNCTION(BlueprintCallable) + void SelectGroup(EAMGroup InGroup); + UFUNCTION(Server, Reliable, WithValidation) + void ServerSelectGroup(EAMGroup InGroup); + void ServerSelectGroup_Implementation(EAMGroup InGroup); + bool ServerSelectGroup_Validate(EAMGroup InGroup); + UFUNCTION(Client, Reliable) + void ClientSelectGroup(EAMGroup InGroup, bool bPredictionSuccess); + void ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess); + + + void AddOnAbilityReadyEvent(const TSoftClassPtr& Ability, const FSimpleDelegate& Delegate) + { + if (!AbilityReadyEvents.Contains(Ability)) + { + AbilityReadyEvents.Add(Ability, Delegate); + } + } + + void ExecuteAbilityReadyEvent(const TSoftClassPtr& Ability) + { + if (FSimpleDelegate* Event = AbilityReadyEvents.Find(Ability)) + { + Event->ExecuteIfBound(); + AbilityReadyEvents.Remove(Ability); + } + } +protected: + class UAFAbilityComponent* GetAbilityComponent(); + void BindOnAbilityReadDelegate(TSoftClassPtr, TArray InAbilityInput, + EAMGroup InGroup, EAMSlot InSlot); + bool IsServerOrStandalone() const; + bool IsClientOrStandalone() const; + bool IsClient() const; +}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp b/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp new file mode 100644 index 0000000..d34aeaf --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp @@ -0,0 +1,3 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AMTypes.h" \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h b/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h new file mode 100644 index 0000000..90b017d --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h @@ -0,0 +1,95 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AMTypes.generated.h" + +UENUM(BlueprintType) +enum class EAMSlot : uint8 +{ + Slot001 = 0, + Slot002 = 1, + Slot003 = 2, + Slot004 = 3, + Slot005 = 4, + Slot006 = 5, + Slot007 = 6, + Slot008 = 7, + Slot009 = 8, + Slot010 = 9, + Slot011 = 10, + Slot012 = 11, + Slot013 = 12, + Slot014 = 13, + Slot015 = 14, + Slot016 = 15, + Slot017 = 16, + Slot018 = 17, + Slot019 = 18, + Slot020 = 19, + Slot021 = 20, + Slot022 = 21, + Slot023 = 22, + Slot024 = 23, + Slot025 = 24, + Slot026 = 25, + Slot027 = 26, + Slot028 = 27, + Slot029 = 28, + Slot030 = 29, + Slot031 = 30, + Slot032 = 31, + MAX +}; + +UENUM(BlueprintType) +enum class EAMGroup : uint8 +{ + Group001 = 0, + Group002 = 1, + Group003 = 2, + Group004 = 3, + Group005 = 4, + Group006 = 5, + Group007 = 6, + Group008 = 7, + Group009 = 8, + Group010 = 9, + Group011 = 10, + Group012 = 11, + Group013 = 12, + Group014 = 13, + Group015 = 14, + Group016 = 15, + Group017 = 16, + Group018 = 17, + Group019 = 18, + Group020 = 19, + Group021 = 20, + Group022 = 21, + Group023 = 22, + Group024 = 23, + Group025 = 24, + Group026 = 25, + Group027 = 26, + Group028 = 27, + Group029 = 28, + Group030 = 29, + Group031 = 30, + Group032 = 31, + + MAX +}; + +template +int32 AMEnumToInt(T InVal) +{ + return static_cast(InVal); +} + +template +T AMIntToEnum(int32 InVal) +{ + return static_cast(InVal); +} \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp b/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp new file mode 100644 index 0000000..3f142ff --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityManager.h" + +#define LOCTEXT_NAMESPACE "FAbilityManagerModule" + +void FAbilityManagerModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FAbilityManagerModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FAbilityManagerModule, AbilityManager) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h b/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h new file mode 100644 index 0000000..677d67e --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FAbilityManagerModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp new file mode 100644 index 0000000..f87f7b0 --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp @@ -0,0 +1,36 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "AMAbilityInputProperty.h" +#include "AbilityManagerEditor.h" +#include "IDetailsView.h" +#include "PropertyEditorModule.h" +#include "Editor/PropertyEditor/Public/PropertyEditing.h" +#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" +#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" +#include "Editor/PropertyEditor/Private/SDetailsView.h" +//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h +#include "STextCombobox.h" +#include "STreeView.h" +#include "SButton.h" +#include "STextBlock.h" + +#include "EditorClassUtils.h" + + +TSharedRef FAMAbilityInputProperty::MakeInstance() +{ + return MakeShareable(new FAMAbilityInputProperty); +} + +FAMAbilityInputProperty::~FAMAbilityInputProperty() +{ + +} + +void FAMAbilityInputProperty::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} +void FAMAbilityInputProperty::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) +{ + +} diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h new file mode 100644 index 0000000..c31729d --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h @@ -0,0 +1,18 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#pragma once +#include "IPropertyTypeCustomization.h" +#include "PropertyHandle.h" + +class FAMAbilityInputProperty : public IPropertyTypeCustomization +{ +public: + static TSharedRef MakeInstance(); + /** + * Destructor + */ + virtual ~FAMAbilityInputProperty(); + + /** IPropertyTypeCustomization interface */ + virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; + virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; +}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp new file mode 100644 index 0000000..06b8d0e --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityManagerEditor.h" + +#define LOCTEXT_NAMESPACE "FAbilityManagerEditor" + +void FAbilityManagerEditorModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FAbilityManagerEditorModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FAbilityManagerEditorModule, AbilityManagerEditor) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h new file mode 100644 index 0000000..0879ce8 --- /dev/null +++ b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FAbilityManagerEditorModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.cpp new file mode 100644 index 0000000..48e6f7b --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.cpp @@ -0,0 +1,14 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "DWBPFunctionLibrary.h" +#include "DWManager.h" + + +FDWWWindowHandle UDWBPFunctionLibrary::CreateWindow(const FString& WindowName) +{ + return FDWManager::Get().CreateWindow(WindowName); +} +FDWWWindowHandle UDWBPFunctionLibrary::CreateWindowWithContent(UUserWidget* InWindowContent, const FString& WindowName) +{ + return FDWManager::Get().CreateWindow(InWindowContent->TakeWidget(), WindowName); +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.h b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.h new file mode 100644 index 0000000..1914c37 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWBPFunctionLibrary.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Kismet/BlueprintFunctionLibrary.h" +#include "UserWidget.h" +#include "DWTypes.h" + +#include "DWBPFunctionLibrary.generated.h" + +/** + * + */ +UCLASS() +class DRAGGABLEWINDOW_API UDWBPFunctionLibrary : public UBlueprintFunctionLibrary +{ + GENERATED_BODY() + +public: + UFUNCTION(BlueprintCallable, Category = "Draggable Window") + static FDWWWindowHandle CreateWindow(const FString& WindowName); + + UFUNCTION(BlueprintCallable, Category = "Draggable Window") + static FDWWWindowHandle CreateWindowWithContent(UUserWidget* InWindowContent, const FString& WindowName); +}; diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.cpp new file mode 100644 index 0000000..bf1b797 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.cpp @@ -0,0 +1,72 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "DWManager.h" +#include "EngineGlobals.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" + +FDWManager* FDWManager::Instance = nullptr; +void FDWManager::Init() +{ + Desktop = SNew(SDraggableDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); + GEngine->GameViewport->AddViewportWidgetContent(Desktop.ToSharedRef(), 2000); +} +void FDWManager::CleanUp() +{ + Desktop->Clean(); + Desktop.Reset(); + WindowHandles.Empty(); + WindowHandles.Shrink(); +} +void FDWManager::RemoveWindow(const FDWWWindowHandle& InHandle) +{ + Desktop->RemoveWindow(InHandle.Window.Pin()); + WindowHandles.Remove(InHandle); +} +FDWManager& FDWManager::Get() +{ + if (!Instance) + { + Instance = new FDWManager(); + Instance->Init(); + } + return *Instance; +} +#if WITH_EDITORONLY_DATA +void FDWManager::PIEDestroy() +{ + if (Instance) + { + Instance->CleanUp(); + delete Instance; + Instance = nullptr; + } +} +#endif //WITH_EDITORONLY_DATA +FDWManager::FDWManager() +{ +} + +FDWManager::~FDWManager() +{ +} + +FDWWWindowHandle FDWManager::CreateWindow(const FString& WindowName) +{ + TSharedPtr NewWindow = SNew(SDraggableWindowWidget); + return AddWindow(NewWindow, WindowName); +} +FDWWWindowHandle FDWManager::CreateWindow(TSharedPtr InWindowContent, const FString& WindowName) +{ + + TSharedPtr NewWindow = SNew(SDraggableWindowWidget); + NewWindow->AddContent(InWindowContent); + return AddWindow(NewWindow, WindowName); +} +FDWWWindowHandle FDWManager::AddWindow(TSharedPtr InWindowWidget, const FString& WindowName) +{ + FDWWWindowHandle Handle = Desktop->AddWindow(InWindowWidget); + WindowHandles.Add(Handle); + WindowsByName.Add(FName(*WindowName), Handle); + return Handle; +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.h b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.h new file mode 100644 index 0000000..046d245 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWManager.h @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SDraggableWindowWidget.h" + +/** + * + */ +class DRAGGABLEWINDOW_API FDWManager +{ +public: + friend class SDraggableWindowWidget; + friend class SDraggableDesktopWidget; +private: + static FDWManager* Instance; + TSharedPtr Desktop; + TSet WindowHandles; + //name of window, window handle + TMap WindowsByName; + void Init(); + void CleanUp(); + void RemoveWindow(const FDWWWindowHandle& InHandle); + FDWManager(); + +public: + static FDWManager& Get(); +#if WITH_EDITORONLY_DATA + static void PIEDestroy(); +#endif //WITH_EDITORONLY_DATA + ~FDWManager(); + + FDWWWindowHandle CreateWindow(const FString& WindowName); + FDWWWindowHandle CreateWindow(TSharedPtr InWindowContent, const FString& WindowName); + FDWWWindowHandle AddWindow(TSharedPtr InWindowWidget, const FString& WindowName); +}; +typedef FDWManager FDraggableWindowManager; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.cpp new file mode 100644 index 0000000..3fe94f4 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.cpp @@ -0,0 +1,3 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "DWTypes.h" \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.h b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.h new file mode 100644 index 0000000..d5e8c26 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DWTypes.h @@ -0,0 +1,41 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "DWTypes.generated.h" + +USTRUCT(BlueprintType) +struct FDWWWindowHandle +{ + GENERATED_BODY() + TWeakPtr Window; +protected: + uint32 Handle; +public: + FDWWWindowHandle() + {}; + FDWWWindowHandle(uint32 InHandle) + : Handle(InHandle) + { + + } + + ~FDWWWindowHandle() + { + Handle = 0; + Window.Reset(); + } + + static FDWWWindowHandle Make(TSharedPtr InWindow); + + friend uint32 GetTypeHash(const FDWWWindowHandle& InHandle) + { + return InHandle.Handle; + } + + const bool operator==(const FDWWWindowHandle& InHandle) const + { + return Handle == InHandle.Handle; + } +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.cpp new file mode 100644 index 0000000..e401549 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "DraggableWindow.h" +#include "DWManager.h" +#if WITH_EDITORONLY_DATA +#include "Editor.H" +#endif +#define LOCTEXT_NAMESPACE "FDraggableWindowModule" + +void FDraggableWindowModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module + +#if WITH_EDITORONLY_DATA + FEditorDelegates::EndPIE.AddRaw(this, &FDraggableWindowModule::HandlePIEEnd); +#endif //WITH_EDITORONLY_DATA + +} + +void FDraggableWindowModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} +#if WITH_EDITORONLY_DATA +void FDraggableWindowModule::HandlePIEEnd(bool InVal) +{ + FDWManager::PIEDestroy(); +} +#endif +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FDraggableWindowModule, DraggableWindow) \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.h b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.h new file mode 100644 index 0000000..106e834 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/DraggableWindow.h @@ -0,0 +1,21 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "Engine.h" +#include "CoreMinimal.h" +#include "ModuleManager.h" + + + +class FDraggableWindowModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +#if WITH_EDITORONLY_DATA + void HandlePIEEnd(bool InVal); +#endif +}; \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.cpp b/Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.cpp new file mode 100644 index 0000000..a930314 --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.cpp @@ -0,0 +1,706 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SDraggableWindowWidget.h" +#include "SlateOptMacros.h" + +#include "Slate.h" +#include "SlateCore.h" +#include "SBorder.h" +#include "Widgets/Layout/SGridPanel.h" +#include "Widgets/Layout/SBackgroundBlur.h" +#include "DWManager.h" +#include "EngineGlobals.h" +#include "Engine/Engine.h" +#include "Engine/GameViewportClient.h" +#include "SceneViewport.h" + +DECLARE_CYCLE_STAT(TEXT("DraggebleWindow.Tick"), STAT_DraggebleWindowTick, STATGROUP_DraggebleWindow); + +FDWWWindowHandle FDWWWindowHandle::Make(TSharedPtr InWindow) +{ + static uint32 NewHandle = 0; + NewHandle++; + FDWWWindowHandle Handle(NewHandle); + Handle.Window = InWindow; + InWindow->SetHandle(Handle); + return Handle; +} +void SDraggableDesktopWidget::Clean() +{ + for (TSharedPtr& Window : Windows) + { + Window.Reset(); + } + Windows.Empty(); + Windows.Shrink(); +} +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SDraggableDesktopWidget::Construct(const FArguments& InArgs) +{ + SetVisibility(EVisibility::SelfHitTestInvisible); + Container = SNew(SOverlay).Visibility(EVisibility::SelfHitTestInvisible); + ChildSlot + [ + Container.ToSharedRef() + ]; +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +FDWWWindowHandle SDraggableDesktopWidget::AddWindow(TSharedPtr InWindow) +{ + if (!Container.IsValid()) + return FDWWWindowHandle(); + + Container->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Left) + .VAlign(EVerticalAlignment::VAlign_Top) + [ + InWindow.ToSharedRef() + ]; + + FDWWWindowHandle Handle = FDWWWindowHandle::Make(InWindow); + Windows.Add(InWindow); + return Handle; +} + +void SDraggableDesktopWidget::RemoveWindow(TSharedPtr InWindow) +{ + Container->RemoveSlot(InWindow.ToSharedRef()); + Windows.Remove(InWindow); + InWindow.Reset(); +} + +void SWindowBox::Construct(const FArguments& InArgs) +{ + WidthOverride = InArgs._WidthOverride.Get(); + HeightOverride = InArgs._HeightOverride.Get(); + + ChildSlot + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + InArgs._Content.Widget + ]; +} +void SWindowBox::SetWidthOverride(float InWidthOverride) +{ + if (WidthOverride != InWidthOverride) + { + WidthOverride = InWidthOverride; + + Invalidate(EInvalidateWidget::Layout); + } +} + +void SWindowBox::SetHeightOverride(float InHeightOverride) +{ + if (HeightOverride != InHeightOverride) + { + HeightOverride = InHeightOverride; + + Invalidate(EInvalidateWidget::Layout); + } +} +void SWindowBox::OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedChildren& ArrangedChildren) const +{ + const EVisibility& MyCurrentVisibility = this->GetVisibility(); + if (ArrangedChildren.Accepts(MyCurrentVisibility)) + { + const FMargin SlotPadding(ChildSlot.SlotPadding.Get()); + bool bAlignChildren = true; + + AlignmentArrangeResult XAlignmentResult(0, 0); + AlignmentArrangeResult YAlignmentResult(0, 0); + + if (bAlignChildren) + { + XAlignmentResult = AlignChild(AllottedGeometry.GetLocalSize().X, ChildSlot, SlotPadding); + YAlignmentResult = AlignChild(AllottedGeometry.GetLocalSize().Y, ChildSlot, SlotPadding); + } + + const float AlignedSizeX = XAlignmentResult.Size; + const float AlignedSizeY = YAlignmentResult.Size; + + ArrangedChildren.AddWidget( + AllottedGeometry.MakeChild( + ChildSlot.GetWidget(), + FVector2D(XAlignmentResult.Offset, YAlignmentResult.Offset), + FVector2D(AlignedSizeX, AlignedSizeY) + ) + ); + } +} +FChildren* SWindowBox::GetChildren() +{ + return &ChildSlot; +} +FVector2D SWindowBox::ComputeDesiredSize(float) const +{ + EVisibility ChildVisibility = ChildSlot.GetWidget()->GetVisibility(); + + if (ChildVisibility != EVisibility::Collapsed) + { + // If the user specified a fixed width or height, those values override the Box's content. + + const float CurrentWidthOverride = WidthOverride; + const float CurrentHeightOverride = HeightOverride; + + + return FVector2D(CurrentWidthOverride, CurrentHeightOverride); + } + + return FVector2D::ZeroVector; +} +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SDraggableWindowWidget::Construct(const FArguments& InArgs) +{ + CurrentSize = FVector2D(1, 1); + ResizingState = EDDWState::NoResize; + bDestroyOnClose = true; + SetVisibility(EVisibility::SelfHitTestInvisible); + FSimpleDelegate OnPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnPressed); + FSimpleDelegate OnReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnReleased); + TAttribute posAttr = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SDraggableWindowWidget::GetPosition)); + + + FSimpleDelegate OnHorizontalPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizePressed); + FSimpleDelegate OnHorizontalReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeReleased); + FSimpleDelegate OnHorizontalLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeLeftPressed); + FSimpleDelegate OnHorizontalLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnHorizontalResizeLeftReleased); + + FSimpleDelegate OnVerticalTopPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalTopResizePressed); + FSimpleDelegate OnVerticalTopReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalTopResizeReleased); + FSimpleDelegate OnVerticalBottomPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalBottomResizePressed); + FSimpleDelegate OnVerticalBottomReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnVerticalBottomResizeReleased); + + FSimpleDelegate OnBottomRightPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomRightResizePressed); + FSimpleDelegate OnBottomRightReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomRightResizeReleased); + + FSimpleDelegate OnBottomLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizePressed); + FSimpleDelegate OnBottomLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnBottomLeftResizeReleased); + + FSimpleDelegate OnTopRightPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopRightResizePressed); + FSimpleDelegate OnTopRightReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopRightResizeReleased); + + FSimpleDelegate OnTopLeftPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopLeftResizePressed); + FSimpleDelegate OnTopLeftReleasedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnTopLeftResizeReleased); + + + FSimpleDelegate OnCloseButtonPressedDel = FSimpleDelegate::CreateSP(this, &SDraggableWindowWidget::OnCloseButtonPressed); + + CurrentHeight = 200; + CurrentWidth = 200; + + FSlateBrush brush; + brush.DrawAs = ESlateBrushDrawType::Type::NoDrawType; + ButtonStyle.Normal = brush; + ButtonStyle.Hovered = brush; + ButtonStyle.Pressed = brush; + ButtonStyle.Disabled = brush; + BackgroundColor = FSlateColor(FLinearColor(0, 0, 0, 1)); + ChildSlot + [ + SNew(SCanvas) + + SCanvas::Slot() + .HAlign(EHorizontalAlignment::HAlign_Left) + .VAlign(EVerticalAlignment::VAlign_Top) + .Position(posAttr) + //.Size(sizeAttr) + [ + SNew(SGridPanel) + + +SGridPanel::Slot(0, 0) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnTopLeftPressedDel) + .OnReleased(OnTopLeftReleasedDel) + .Cursor(EMouseCursor::ResizeSouthEast) + ] + ] + + SGridPanel::Slot(1 ,0) + [ + SNew(SBox) + .HeightOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnVerticalTopPressedDel) + .OnReleased(OnVerticalTopReleasedDel) + .Cursor(EMouseCursor::ResizeUpDown) + + ] + ] + + SGridPanel::Slot(2, 0) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnTopRightPressedDel) + .OnReleased(OnTopRightReleasedDel) + .Cursor(EMouseCursor::ResizeSouthWest) + ] + ] + + SGridPanel::Slot(0, 1) + [ + SNew(SBox) + .WidthOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnHorizontalLeftPressedDel) + .OnReleased(OnHorizontalLeftReleasedDel) + .Cursor(EMouseCursor::ResizeLeftRight) + ] + ] + + SGridPanel::Slot(1, 1) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SAssignNew(WindowBox, SWindowBox) + .Visibility(EVisibility::SelfHitTestInvisible) + //.HeightOverride(heightAttr) + //.WidthOverride(widthAttr) + [ + SNew(SVerticalBox) + .Visibility(EVisibility::SelfHitTestInvisible) + + SVerticalBox::Slot() + .AutoHeight() + .MaxHeight(24) + [ + SNew(SOverlay) + + SOverlay::Slot() + [ + SNew(SBackgroundBlur) + .BlurRadius(4) + .BlurStrength(16) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + + SOverlay::Slot() + [ + SAssignNew(WindowBar, SButton) + .OnPressed(OnPressedDel) + .OnReleased(OnReleasedDel) + .VAlign(EVerticalAlignment::VAlign_Center) + .HAlign(EHorizontalAlignment::HAlign_Right) + .ContentPadding(FMargin(0)) + .ButtonStyle(&ButtonStyle) + [ + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .FillWidth(0.8f) + .AutoWidth() + [ + SNew(STextBlock) + .Visibility(EVisibility::SelfHitTestInvisible) + .Text(FText::FromString("Window Title")) + ] + + SHorizontalBox::Slot() + [ + SNew(SButton) + .OnPressed(OnCloseButtonPressedDel) + [ + SNew(STextBlock) + .Text(FText::FromString("X")) + ] + ] + ] + ] + + ] + + SVerticalBox::Slot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + .FillHeight(1.0f) + [ + SNew(SBox) + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + SNew(SOverlay) + + SOverlay::Slot() + [ + SNew(SBackgroundBlur) + .BlurRadius(4) + .BlurStrength(8) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + +SOverlay::Slot() + [ + SAssignNew(Content, SOverlay) + .Visibility(EVisibility::SelfHitTestInvisible) + ] + + ] + ] + ] + + ] + + SGridPanel::Slot(2, 1) + [ + SNew(SBox) + .WidthOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnHorizontalPressedDel) + .OnReleased(OnHorizontalReleasedDel) + .Cursor(EMouseCursor::ResizeLeftRight) + ] + ] + + SGridPanel::Slot(0, 2) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnBottomLeftPressedDel) + .OnReleased(OnBottomLeftReleasedDel) + .Cursor(EMouseCursor::ResizeSouthWest) + ] + ] + + SGridPanel::Slot(1, 2) + [ + SNew(SBox) + .HeightOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnVerticalBottomPressedDel) + .OnReleased(OnVerticalBottomReleasedDel) + .Cursor(EMouseCursor::ResizeUpDown) + ] + ] + + SGridPanel::Slot(2, 2) + [ + SNew(SBox) + .HeightOverride(3) + .WidthOverride(3) + [ + SNew(SButton) + .ButtonStyle(&ButtonStyle) + .OnPressed(OnBottomRightPressedDel) + .OnReleased(OnBottomRightReleasedDel) + .Cursor(EMouseCursor::ResizeSouthEast) + ] + ] + ] + ]; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION +SDraggableWindowWidget::~SDraggableWindowWidget() +{ +} +FVector2D SDraggableWindowWidget::ComputeDesiredSize(float) const +{ + return SCompoundWidget::ComputeDesiredSize(1); +} +void SDraggableWindowWidget::Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) +{ + SCOPE_CYCLE_COUNTER(STAT_DraggebleWindowTick); + SCompoundWidget::Tick(AllottedGeometry, InCurrentTime, InDeltaTime); + + FVector2D LastPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetLastCursorPos()); + + FVector2D CurrentPosition = AllottedGeometry.AbsoluteToLocal(FSlateApplicationBase::Get().GetCursorPos()); + + float dist = FVector2D::Distance(CurrentPosition, LastPosition); + + switch (ResizingState) + { + case EDDWState::Dragging: + { + FVector2D AbsPos = FSlateApplicationBase::Get().GetCursorPos(); + + CurrentPosition = CurrentPosition - DragPosition; + AbsPosition = AbsPos - AbsDragPosition; + + FVector2D WindowPosition = GEngine->GameViewport->GetWindow()->GetPositionInScreen(); + FVector2D WindowSize = GEngine->GameViewport->GetWindow()->GetSizeInScreen() - 8; + + const float ApplicationScale = FSlateApplication::Get().GetApplicationScale(); + FVector2D AbsSize = AllottedGeometry.LocalToAbsolute(FVector2D(CurrentWidth, CurrentHeight)); + FVector2D GeomAbs = AllottedGeometry.GetAbsolutePosition(); + FVector2D localSize = WindowSize + WindowPosition; + CurrentCursorPosition = CurrentPosition; + if (CurrentPosition.X <= 0) + { + CurrentCursorPosition.X = 0; + } + if (CurrentPosition.Y <= 0) + { + CurrentCursorPosition.Y = 0; + } + if ((AbsPos.X + ((AbsSize.X - AbsDragPosition.X) * ApplicationScale)) >= localSize.X) + { + FVector2D localSize2 = AllottedGeometry.AbsoluteToLocal(WindowSize + WindowPosition); + CurrentCursorPosition.X = localSize2.X - CurrentWidth; + } + if ((AbsPos.Y + ((AbsSize.Y - AbsDragPosition.Y) * ApplicationScale)) >= localSize.Y) + { + FVector2D localSize2 = AllottedGeometry.AbsoluteToLocal(WindowSize + WindowPosition); + CurrentCursorPosition.Y = localSize2.Y - CurrentHeight; + } + break; + } + case EDDWState::HorizontalRight: + { + float CurrentXX = 0; + if (dist != 0) + { + CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); + } + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::HorizontalLeft: + { + float CurrentXX = 0; + if (dist != 0) + { + CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; + } + + CurrentCursorPosition.X -= CurrentXX; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::VerticalTop: + { + float CurrentXX = 0; + float CurrentY = 0; + if (dist != 0) + { + CurrentXX = CurrentCursorPosition.Y - CurrentPosition.Y; + + } + CurrentCursorPosition.Y -= CurrentXX; + CurrentHeight = CurrentHeight + CurrentXX; + WindowBox->SetHeightOverride(CurrentHeight); + break; + } + case EDDWState::VerticalBottom: + { + float CurrentY = 0; + if (dist != 0) + { + CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + + CurrentHeight = CurrentHeight + CurrentY; + WindowBox->SetHeightOverride(CurrentHeight); + break; + } + case EDDWState::DiagonalBottomRight: + { + float CurrentXX = 0; + float CurrentY = 0; + if (dist != 0) + { + CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); + CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + CurrentWidth = CurrentWidth + CurrentXX; + CurrentHeight = CurrentHeight + CurrentY; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::DiagonalBottomLeft: + { + float CurrentXX = 0; + float CurrentY = 0; + if (dist != 0) + { + CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; + CurrentY = CurrentPosition.Y - (CurrentCursorPosition.Y + CurrentHeight); + } + CurrentCursorPosition.X -= CurrentXX; + CurrentWidth = CurrentWidth + CurrentXX; + CurrentHeight = CurrentHeight + CurrentY; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::DiagonalTopRight: + { + float CurrentXX = 0; + float CurrentY = 0; + if (dist != 0) + { + CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; + CurrentXX = CurrentPosition.X - (CurrentCursorPosition.X + CurrentWidth); + } + CurrentCursorPosition.Y -= CurrentY; + + CurrentHeight = CurrentHeight + CurrentY; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::DiagonalTopLeft: + { + float CurrentXX = 0; + float CurrentY = 0; + if (dist != 0) + { + CurrentY = CurrentCursorPosition.Y - CurrentPosition.Y; + CurrentXX = CurrentCursorPosition.X - CurrentPosition.X; + } + CurrentCursorPosition.Y -= CurrentY; + CurrentCursorPosition.X -= CurrentXX; + CurrentHeight = CurrentHeight + CurrentY; + CurrentWidth = CurrentWidth + CurrentXX; + WindowBox->SetHeightOverride(CurrentHeight); + WindowBox->SetWidthOverride(CurrentWidth); + break; + } + case EDDWState::NoResize: + { break; + } + default: + break; + } +} +void SDraggableWindowWidget::AddContent(TSharedPtr InWidget) +{ + Content->AddSlot() + .HAlign(EHorizontalAlignment::HAlign_Fill) + .VAlign(EVerticalAlignment::VAlign_Fill) + [ + InWidget.ToSharedRef() + ]; +} +void SDraggableWindowWidget::SetHandle(const FDWWWindowHandle& InHandle) +{ + Handle = InHandle; +} +void SDraggableWindowWidget::OnCloseButtonPressed() +{ + if(bDestroyOnClose) + FDWManager::Get().RemoveWindow(Handle); + else + { + SetVisibility(EVisibility::Collapsed); + } +} +void SDraggableWindowWidget::OnPressed() +{ + FGeometry geom = GetCachedGeometry(); + FVector2D CurrentPosAbs = FSlateApplicationBase::Get().GetLastCursorPos(); + FVector2D CurrentPosition = geom.AbsoluteToLocal(CurrentPosAbs); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed Pre DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); + DragPosition = CurrentPosition - CurrentCursorPosition; + AbsDragPosition = CurrentPosAbs - AbsPosition; + + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentPosition X: %f Y: %f"), CurrentPosition.X, CurrentPosition.Y); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed CurrentCursorPosition X: %f Y: %f"), CurrentCursorPosition.X, CurrentCursorPosition.Y); + //UE_LOG(LogTemp, Warning, TEXT("SDraggableWindowWidget::OnPressed DragPosition X: %f Y: %f"), DragPosition.X, DragPosition.Y); + ResizingState = EDDWState::Dragging; +} +void SDraggableWindowWidget::OnReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnHorizontalResizePressed() +{ + ResizingState = EDDWState::HorizontalRight; +} +void SDraggableWindowWidget::OnHorizontalResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} +void SDraggableWindowWidget::OnHorizontalResizeLeftPressed() +{ + ResizingState = EDDWState::HorizontalLeft; +} +void SDraggableWindowWidget::OnHorizontalResizeLeftReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnVerticalTopResizePressed() +{ + ResizingState = EDDWState::VerticalTop; +} +void SDraggableWindowWidget::OnVerticalTopResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} +void SDraggableWindowWidget::OnVerticalBottomResizePressed() +{ + ResizingState = EDDWState::VerticalBottom; +} +void SDraggableWindowWidget::OnVerticalBottomResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnDirectionalResizePressed() +{ +} + +void SDraggableWindowWidget::OnDirectionalResizeReleased() +{ +} + +void SDraggableWindowWidget::OnBottomRightResizePressed() +{ + ResizingState = EDDWState::DiagonalBottomRight; +} +void SDraggableWindowWidget::OnBottomRightResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnBottomLeftResizePressed() +{ + ResizingState = EDDWState::DiagonalBottomLeft; +} +void SDraggableWindowWidget::OnBottomLeftResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnTopRightResizePressed() +{ + ResizingState = EDDWState::DiagonalTopRight; +} +void SDraggableWindowWidget::OnTopRightResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +void SDraggableWindowWidget::OnTopLeftResizePressed() +{ + ResizingState = EDDWState::DiagonalTopLeft; +} +void SDraggableWindowWidget::OnTopLeftResizeReleased() +{ + ResizingState = EDDWState::NoResize; +} + +FVector2D SDraggableWindowWidget::GetPosition() const +{ + return CurrentCursorPosition; +} + +FText SDraggableWindowWidget::GetTitle() const +{ + return WindowTitle; +} \ No newline at end of file diff --git a/Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.h b/Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.h new file mode 100644 index 0000000..13e96bc --- /dev/null +++ b/Plugins/DraggableWindow/Source/DraggableWindow/Public/SDraggableWindowWidget.h @@ -0,0 +1,195 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Input/Events.h" +#include "Widgets/SCompoundWidget.h" +#include "SlateCore.h" +#include "Styling/SlateTypes.h" +#include "SOverlay.h" +#include "SGridPanel.h" +#include "SBox.h" +#include "SBorder.h" +#include "SButton.h" +#include "SConstraintCanvas.h" +#include "DWTypes.h" + +DECLARE_STATS_GROUP(TEXT("DraggebleWindow"), STATGROUP_DraggebleWindow, STATCAT_Advanced); + +enum class EDDWState : uint8 +{ + Dragging = 0, + HorizontalRight = 1, + HorizontalLeft = 2, + VerticalTop = 3, + VerticalBottom = 4, + DiagonalBottomRight = 5, + DiagonalBottomLeft = 6, + DiagonalTopRight = 7, + DiagonalTopLeft = 8, + + NoResize +}; +class DRAGGABLEWINDOW_API SDraggableDesktopWidget : public SCompoundWidget +{ + + SLATE_BEGIN_ARGS(SDraggableDesktopWidget) {} + SLATE_END_ARGS() +public: + friend class FDWManager; + friend class SDraggableWindowWidget; + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); +protected: + TArray> Windows; + TSharedPtr Container; + void Clean(); + FDWWWindowHandle AddWindow(TSharedPtr InWindow); + void RemoveWindow(TSharedPtr InWindow); +}; + +class SWindowBox : public SPanel +{ +public: + class FBoxSlot : public TSupportsOneChildMixin, public TSupportsContentAlignmentMixin, public TSupportsContentPaddingMixin + { + public: + FBoxSlot(SWidget* InOwner) + : TSupportsOneChildMixin(nullptr) + , TSupportsContentAlignmentMixin(HAlign_Fill, VAlign_Fill) + { + } + }; + SLATE_BEGIN_ARGS(SWindowBox) + : _Content() + , _WidthOverride() + , _HeightOverride() + { + _Visibility = EVisibility::SelfHitTestInvisible; + } + SLATE_DEFAULT_SLOT(FArguments, Content) + /** When specified, ignore the content's desired size and report the WidthOverride as the Box's desired width. */ + SLATE_ATTRIBUTE(float, WidthOverride) + + /** When specified, ignore the content's desired size and report the HeightOverride as the Box's desired height. */ + SLATE_ATTRIBUTE(float, HeightOverride) + SLATE_END_ARGS() +private: + /** When specified, ignore the content's desired size and report the.WidthOverride as the Box's desired width. */ + float WidthOverride; + + /** When specified, ignore the content's desired size and report the.HeightOverride as the Box's desired height. */ + float HeightOverride; +protected: + + FBoxSlot ChildSlot; +public: + SWindowBox() + : ChildSlot(this) + {} + void Construct(const FArguments& InArgs); + /** See WidthOverride attribute */ + void SetWidthOverride(float InWidthOverride); + + /** See HeightOverride attribute */ + void SetHeightOverride(float InHeightOverride); +protected: + /** + * Panels arrange their children in a space described by the AllottedGeometry parameter. The results of the arrangement + * should be returned by appending a FArrangedWidget pair for every child widget. See StackPanel for an example + * + * @param AllottedGeometry The geometry allotted for this widget by its parent. + * @param ArrangedChildren The array to which to add the WidgetGeometries that represent the arranged children. + */ + virtual void OnArrangeChildren(const FGeometry& AllottedGeometry, FArrangedChildren& ArrangedChildren) const override; + // Begin SWidget overrides. + virtual FVector2D ComputeDesiredSize(float) const override; + + /** + * All widgets must provide a way to access their children in a layout-agnostic way. + * Panels store their children in Slots, which creates a dilemma. Most panels + * can store their children in a TPanelChildren, where the Slot class + * provides layout information about the child it stores. In that case + * GetChildren should simply return the TPanelChildren. See StackPanel for an example. + */ + virtual FChildren* GetChildren() override; +}; + +/** + * Check IF cursor is moving during resizing. + */ +class DRAGGABLEWINDOW_API SDraggableWindowWidget : public SCompoundWidget +{ + SLATE_BEGIN_ARGS(SDraggableWindowWidget){} + SLATE_ATTRIBUTE(bool, HideOnClose) + SLATE_END_ARGS() +public: + friend struct FDWWWindowHandle; + friend class SDraggableDesktopWidget; + friend class FDWManager; + bool bDestroyOnClose; +protected: + EDDWState ResizingState; + + FVector2D CurrentSize; + FVector2D CurrentCursorPosition; + FVector2D DragPosition; + FVector2D AbsPosition; + FVector2D AbsDragPosition; + + TSharedPtr Content; + TSharedPtr WindowBox; + float CurrentHeight; + float CurrentWidth; + FButtonStyle ButtonStyle; + TAttribute BackgroundColor; + TSharedPtr WindowBar; + FDWWWindowHandle Handle; + + FText WindowTitle; +public: + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + ~SDraggableWindowWidget(); +protected: + virtual FVector2D ComputeDesiredSize(float) const override; + virtual void Tick(const FGeometry& AllottedGeometry, const double InCurrentTime, const float InDeltaTime) override; + + void AddContent(TSharedPtr InWidget); + + void SetHandle(const FDWWWindowHandle& InHandle); + void OnCloseButtonPressed(); + + void OnPressed(); + void OnReleased(); + + void OnHorizontalResizePressed(); + void OnHorizontalResizeReleased(); + void OnHorizontalResizeLeftPressed(); + void OnHorizontalResizeLeftReleased(); + + void OnVerticalTopResizePressed(); + void OnVerticalTopResizeReleased(); + void OnVerticalBottomResizePressed(); + void OnVerticalBottomResizeReleased(); + + void OnDirectionalResizePressed(); + void OnDirectionalResizeReleased(); + + void OnBottomRightResizePressed(); + void OnBottomRightResizeReleased(); + + void OnBottomLeftResizePressed(); + void OnBottomLeftResizeReleased(); + + void OnTopRightResizePressed(); + void OnTopRightResizeReleased(); + + void OnTopLeftResizePressed(); + void OnTopLeftResizeReleased(); + + FVector2D GetPosition() const; + + FText GetTitle() const; +}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp new file mode 100644 index 0000000..7d21067 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp @@ -0,0 +1,86 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFEquipmentComponent.h" +#include "IFInventoryComponent.h" + +// Sets default values for this component's properties +UIFEquipmentComponent::UIFEquipmentComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UIFEquipmentComponent::BeginPlay() +{ + uint8 Counter = 0; + for (uint8 Idx = 0; Idx < MaxSlots; Idx++) + { + FIFItemData NewItem; + NewItem.Item = nullptr; + NewItem.Index = Idx; + Counter++; + EquipmentItems.Add(NewItem); + } + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UIFEquipmentComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + +void UIFEquipmentComponent::AddItemFromInventory(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerAddItemFromInventory(Source, SourceIndex, EquipmentIndex); + } + else + { + UIFItemBase* Item = Source->GetItem(SourceIndex); + if (!Item) + return; + + EquipmentItems[EquipmentIndex].Item = DuplicateObject(Item, this); + OnItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); + OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); + } +} +void UIFEquipmentComponent::ServerAddItemFromInventory_Implementation(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex) +{ + UIFItemBase* Item = Source->GetItem(SourceIndex); + if (!Item) + return; + + EquipmentItems[EquipmentIndex].Item = DuplicateObject(Item, this); + OnServerItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); + ClientAddItemFromInventory(Source, SourceIndex, EquipmentIndex); + OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); +} +bool UIFEquipmentComponent::ServerAddItemFromInventory_Validate(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex) +{ + return true; +} +void UIFEquipmentComponent::ClientAddItemFromInventory_Implementation(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex) +{ + UIFItemBase* Item = Source->GetItem(SourceIndex); + if (!Item) + return; + + EquipmentItems[EquipmentIndex].Item = DuplicateObject(Item, this); + OnItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); + OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); + Source->RemoveItem(SourceIndex); +} \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp new file mode 100644 index 0000000..563d6c3 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp @@ -0,0 +1,11 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "IFTypes.h" + +IFTypes::IFTypes() +{ +} + +IFTypes::~IFTypes() +{ +} diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h new file mode 100644 index 0000000..2fce3b5 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h @@ -0,0 +1,83 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "IFTypes.h" +#include "IFItemBase.h" +#include "IFEquipmentComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class INVENTORYFRAMEWORK_API UIFEquipmentComponent : public UActorComponent +{ + GENERATED_BODY() +protected: + UPROPERTY() + TArray EquipmentItems; + + + UPROPERTY(EditAnywhere, Category = "Inventory") + uint8 MaxSlots; + + /* + Currently available slots (must be smaller or equal to max slots); + */ + UPROPERTY(EditAnywhere, Category = "Inventory") + uint8 AvailableSlots; + + FIFItemEvent OnItemAddedEvent; + FIFItemEvent OnItemUpdatedEvent; + FIFItemEvent OnItemRemovedEvent; + +public: + // Sets default values for this component's properties + UIFEquipmentComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + inline UIFItemBase* GetItem(uint8 InLocalIndex) + { + return EquipmentItems[InLocalIndex].Item; + //return Inventory.Items[InLocalIndex].Item; + } + template + T* GetItem(uint8 InLocalIndex) + { + return Cast(EquipmentItems[InLocalIndex].Item); + //return Cast(Inventory.Items[InLocalIndex].Item); + } + + void AddItemFromInventory(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItemFromInventory(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + void ServerAddItemFromInventory_Implementation(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + bool ServerAddItemFromInventory_Validate(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + /* + Confirm that change can be made and do the same change on client. + We do not predict inventory modifications. Clients MUST wait for server to make changes and send confirmation back. + */ + UFUNCTION(Client, Reliable) + void ClientAddItemFromInventory(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + void ClientAddItemFromInventory_Implementation(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + + virtual void OnItemAdded(UIFItemBase* Item, uint8 Index) {}; + virtual void OnItemChanged(UIFItemBase* Item, uint8 Index) {}; + virtual void OnItemRemoved(uint8 Index) {}; + + //called only on server. + virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; + virtual void OnServerItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; + virtual void OnServerItemRemoved(uint8 LocalIndex) {}; + + inline FIFItemEvent& GetOnItemAdded() { return OnItemAddedEvent; } + inline FIFItemEvent& GetOnItemUpdated() { return OnItemUpdatedEvent; } + inline FIFItemEvent& GetOnItemRemoved() { return OnItemRemovedEvent; } +}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h new file mode 100644 index 0000000..01572d2 --- /dev/null +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h @@ -0,0 +1,42 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFTypes.generated.h" + +DECLARE_MULTICAST_DELEGATE_ThreeParams(FIFItemEvent, uint8, uint8, class UIFItemBase*); +DECLARE_MULTICAST_DELEGATE(FIFOnInventoryChanged); + +USTRUCT(BlueprintType) +struct INVENTORYFRAMEWORK_API FIFItemData +{ + GENERATED_BODY() +public: + UPROPERTY() + class UIFItemBase* Item; + + UPROPERTY(BlueprintReadOnly) + uint8 Index; +}; + + +USTRUCT(BlueprintType) +struct FIFSlotAcceptedClasses +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TArray> AcceptedClasses; + +}; + +/** + * + */ +class INVENTORYFRAMEWORK_API IFTypes +{ +public: + IFTypes(); + ~IFTypes(); +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp new file mode 100644 index 0000000..33f85b1 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp @@ -0,0 +1,548 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "AnimNode_BlendLocomotionFour.h" +#include "AnimationRuntime.h" +#include "GameFramework/CharacterMovementComponent.h" +#include "GameFramework/Character.h" +#include "Animation/AnimClassInterface.h" +#include "Animation/AnimInstanceProxy.h" +#include "Animation/BlendProfile.h" +#include "DrawDebugHelpers.h" + +#include "Engine.h" +///////////////////////////////////////////////////// +// FAnimNode_BlendLocomotionFour +FString FDirToString(EFCardinalDirection Dir) +{ + switch (Dir) + { + case EFCardinalDirection::N: + return "N"; + case EFCardinalDirection::E: + return "E"; + case EFCardinalDirection::S: + return "S"; + case EFCardinalDirection::W: + return "W"; + default: + break; + } + return "Invalid"; +} +void FAnimNode_BlendLocomotionFour::Initialize_AnyThread(const FAnimationInitializeContext& Context) +{ + FAnimNode_Base::Initialize_AnyThread(Context); + + UAnimInstance* AnimInst = Cast(Context.AnimInstanceProxy->GetAnimInstanceObject()); + Character = Cast(AnimInst->TryGetPawnOwner()); + if (!Character) + return; + + CMC = Character->GetCharacterMovement(); + + if (!CMC) + return; + + const int NumPoses = BlendPose.Num(); + checkSlow(BlendTime.Num() == NumPoses); + + BlendWeights.Reset(NumPoses); + PosesToEvaluate.Reset(NumPoses); + if (NumPoses > 0) + { + // If we have at least 1 pose we initialize to full weight on + // the first pose + BlendWeights.AddZeroed(NumPoses); + BlendWeights[0] = 1.0f; + + PosesToEvaluate.Add(0); + + for (int32 ChildIndex = 0; ChildIndex < NumPoses; ++ChildIndex) + { + BlendPose[ChildIndex].Initialize(Context); + } + } + + RemainingBlendTimes.Empty(NumPoses); + RemainingBlendTimes.AddZeroed(NumPoses); + Blends.Empty(NumPoses); + Blends.AddZeroed(NumPoses); + + LastActiveChildIndex = INDEX_NONE; + + for (int32 i = 0; i < Blends.Num(); ++i) + { + FAlphaBlend& Blend = Blends[i]; + + Blend.SetBlendTime(0.0f); + Blend.SetBlendOption(BlendType); + Blend.SetCustomCurve(CustomBlendCurve); + } + Blends[0].SetAlpha(1.0f); + + if (BlendProfile) + { + // Initialise per-bone data + PerBoneSampleData.Empty(NumPoses); + PerBoneSampleData.AddZeroed(NumPoses); + + for (int32 Idx = 0; Idx < NumPoses; ++Idx) + { + FBlendSampleData& SampleData = PerBoneSampleData[Idx]; + SampleData.SampleDataIndex = Idx; + SampleData.PerBoneBlendData.AddZeroed(BlendProfile->GetNumBlendEntries()); + } + } +} + +void FAnimNode_BlendLocomotionFour::CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) +{ + for (int32 ChildIndex = 0; ChildIndexGetActorRightVector(); + FVector Forward = Character->GetActorForwardVector(); + + FTransform Transform = Character->GetTransform(); + FVector CurrentAcceleration = CMC->GetCurrentAcceleration(); + FVector CurrentVelocity = CMC->Velocity; + + FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal2D(); + FVector VelocityDirection = CurrentVelocity.GetSafeNormal2D(); + + FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); + FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); + + float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); + int32 Dir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; + DotBlendTime = FMath::Abs(FVector::DotProduct(LocalVelocity, LocalAcceleration)); + BlendTime[0] = DotBlendTime; + BlendTime[1] = DotBlendTime; + BlendTime[2] = DotBlendTime; + BlendTime[3] = DotBlendTime; + + NDot = FMath::RoundToInt(FVector::DotProduct(Forward, VelocityDirection)); + EDot = FMath::RoundToInt(FVector::DotProduct(Right, VelocityDirection)); + + const int NumPoses = BlendPose.Num(); + checkSlow((BlendTime.Num() == NumPoses) && (BlendWeights.Num() == NumPoses)); + + PosesToEvaluate.Empty(NumPoses); + + if (NumPoses > 0) + { + // Handle a change in the active child index; adjusting the target weights + const int32 ChildIndex = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4;; + + if (ChildIndex != LastActiveChildIndex) + { + bool LastChildIndexIsInvalid = (LastActiveChildIndex == INDEX_NONE); + + const float CurrentWeight = BlendWeights[ChildIndex]; + const float DesiredWeight = 1.0f; + const float WeightDifference = FMath::Clamp(FMath::Abs(DesiredWeight - CurrentWeight), 0.0f, 1.0f); + + // scale by the weight difference since we want always consistency: + // - if you're moving from 0 to full weight 1, it will use the normal blend time + // - if you're moving from 0.5 to full weight 1, it will get there in half the time + const float RemainingBlendTime = LastChildIndexIsInvalid ? 0.0f : (BlendTime[ChildIndex] * WeightDifference); + + for (int32 i = 0; i < RemainingBlendTimes.Num(); ++i) + { + RemainingBlendTimes[i] = RemainingBlendTime; + } + + // If we have a valid previous child and we're instantly blending - update that pose with zero weight + if (RemainingBlendTime == 0.0f && !LastChildIndexIsInvalid) + { + BlendPose[LastActiveChildIndex].Update(Context.FractionalWeight(0.0f)); + } + + for (int32 i = 0; i < Blends.Num(); ++i) + { + FAlphaBlend& Blend = Blends[i]; + + Blend.SetBlendTime(RemainingBlendTime); + + if (i == ChildIndex) + { + Blend.SetValueRange(BlendWeights[i], 1.0f); + } + else + { + Blend.SetValueRange(BlendWeights[i], 0.0f); + } + } + + // when this flag is true, we'll reinitialize the children + if (bResetChildOnActivation) + { + FAnimationInitializeContext ReinitializeContext(Context.AnimInstanceProxy); + + // reinitialize + BlendPose[ChildIndex].Initialize(ReinitializeContext); + } + + LastActiveChildIndex = ChildIndex; + } + + // Advance the weights + //@TODO: This means we advance even in a frame where the target weights/times just got modified; is that desirable? + float SumWeight = 0.0f; + for (int32 i = 0; i < Blends.Num(); ++i) + { + float& BlendWeight = BlendWeights[i]; + + FAlphaBlend& Blend = Blends[i]; + Blend.Update(Context.GetDeltaTime()); + BlendWeight = Blend.GetBlendedValue(); + + SumWeight += BlendWeight; + } + + // Renormalize the weights + if ((SumWeight > ZERO_ANIMWEIGHT_THRESH) && (FMath::Abs(SumWeight - 1.0f) > ZERO_ANIMWEIGHT_THRESH)) + { + float ReciprocalSum = 1.0f / SumWeight; + for (int32 i = 0; i < BlendWeights.Num(); ++i) + { + BlendWeights[i] *= ReciprocalSum; + } + } + + // Update our active children + for (int32 i = 0; i < BlendPose.Num(); ++i) + { + const float BlendWeight = BlendWeights[i]; + if (BlendWeight > ZERO_ANIMWEIGHT_THRESH) + { + BlendPose[i].Update(Context.FractionalWeight(BlendWeight)); + PosesToEvaluate.Add(i); + } + } + + // If we're using a blend profile, extract the scales and build blend sample data + if (BlendProfile) + { + for (int32 i = 0; i < BlendPose.Num(); ++i) + { + // Update Per-Bone Info + const float BlendWeight = BlendWeights[i]; + FBlendSampleData& PoseSampleData = PerBoneSampleData[i]; + PoseSampleData.TotalWeight = BlendWeight; + + for (int32 j = 0; j < PoseSampleData.PerBoneBlendData.Num(); ++j) + { + float& BoneBlend = PoseSampleData.PerBoneBlendData[j]; + float WeightScale = BlendProfile->GetEntryBlendScale(j); + + if (ChildIndex != i) + { + WeightScale = 1.0f / WeightScale; + } + + BoneBlend = BlendWeight * WeightScale; + } + } + + FBlendSampleData::NormalizeDataWeight(PerBoneSampleData); + } + } + + + switch (Dir) + { + case EFCardinalDirection::N: + { + FQuat ForwardQuat = FQuat::FindBetween(Forward, CurrentVelocity); + OrientN = FRotator(ForwardQuat).Yaw; + CurrentOrient = OrientN;// + //if (NDot == EDot) + /*{ + NorthPose.Update(Context.FractionalWeight(DotBlendTime)); + EastPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); + }*/ + /*else + { + NorthPose.Update(Context); + }*/ + + break; + } + case EFCardinalDirection::E: + { + FQuat LeftQuat = FQuat::FindBetween(Right, CurrentVelocity); + OrientE = FRotator(LeftQuat).Yaw; + CurrentOrient = OrientE; + //if (NDot == EDot) + /*{ + NorthPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); + EastPose.Update(Context.FractionalWeight(DotBlendTime)); + }*/ + /*else + { + EastPose.Update(Context); + }*/ + + // FMath::FInterpConstantTo(OldOrient, OrientE, DeltaTime, 300.0f); + break; + } + case EFCardinalDirection::S: + { + FQuat BackQuat = FQuat::FindBetween(Forward*(-1), CurrentVelocity); + OrientS = FRotator(BackQuat).Yaw; + CurrentOrient = OrientS; + break; + } + case EFCardinalDirection::W: + { + FQuat RightQuat = FQuat::FindBetween(Right*(-1), CurrentVelocity); + OrientW = FRotator(RightQuat).Yaw; + CurrentOrient = OrientW;// FMath::FInterpConstantTo(OldOrient, OrientW, DeltaTime, 300.0f); + break; + } + default: + break; + } + +} + +void FAnimNode_BlendLocomotionFour::Evaluate_AnyThread(FPoseContext& Output) +{ + ANIM_MT_SCOPE_CYCLE_COUNTER(BlendPosesInGraph, !IsInGameThread()); + { + //BlendPose[CurrentPose].Evaluate(Output); + } + const int32 NumPoses = PosesToEvaluate.Num(); + if ((NDot == EDot) && (NumPoses > 0) && (BlendPose.Num() == BlendWeights.Num())) + { + // Scratch arrays for evaluation, stack allocated + TArray> FilteredPoses; + TArray> FilteredCurve; + FilteredPoses.SetNum(NumPoses, false); + FilteredCurve.SetNum(NumPoses, false); + + int32 NumActivePoses = 0; + for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) + { + int32 PoseIndex = PosesToEvaluate[i]; + + FPoseContext EvaluateContext(Output); + + FPoseLink& CurrentPose = BlendPose[PoseIndex]; + CurrentPose.Evaluate(EvaluateContext); + + FilteredPoses[i].CopyBonesFrom(EvaluateContext.Pose); + FilteredCurve[i] = EvaluateContext.Curve; + } + + // Use the calculated blend sample data if we're blending per-bone + if (BlendProfile) + { + FAnimationRuntime::BlendPosesTogetherPerBone(FilteredPoses, FilteredCurve, BlendProfile, PerBoneSampleData, PosesToEvaluate, Output.Pose, Output.Curve); + } + else + { + FAnimationRuntime::BlendPosesTogether(FilteredPoses, FilteredCurve, BlendWeights, PosesToEvaluate, Output.Pose, Output.Curve); + } + + } + else + { + for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) + { + int32 PoseIndex = PosesToEvaluate[i]; + + FPoseLink& CurrentPose = BlendPose[PoseIndex]; + CurrentPose.Evaluate(Output); + + } + //Output.ResetToRefPose(); + } + + //FPoseContext EvaluateContext(Output); + //const FBoneContainer& BoneContainer = Output.AnimInstanceProxy->GetRequiredBones(); + //FComponentSpacePoseContext CSOutput(Output.AnimInstanceProxy); + //EFCardinalDirection ghf = Cast(Character)->GetCardianlDirection(); + //switch (Dir) + //{ + //case EFCardinalDirection::N: + //{ + // //if (OldDirection != Dir) + // { + // //if (NDot == EDot) + // { + // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); + + // FPoseContext Pose1(Output); + // FPoseContext Pose2(Output); + + // NorthPose.Evaluate(Pose1); + // EastPose.Evaluate(Pose2); + // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); + // + // } + // /*else + // { + // NorthPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); + // }*/ + // } + // /*else + // { + // NorthPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); + // }*/ + // break; + //} + //case EFCardinalDirection::E: + //{ + // + // //if (OldDirection != Dir) + // { + // //if (NDot == EDot) + // { + // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); + + // FPoseContext Pose1(Output); + // FPoseContext Pose2(Output); + + // NorthPose.Evaluate(Pose2); + // EastPose.Evaluate(Pose1); + // + // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); + // + // + // } + // /*else + // { + // EastPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); + // }*/ + + // } + // /*else + // { + // EastPose.Evaluate(Output); + // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); + // }*/ + // break; + //} + //case EFCardinalDirection::S: + //{ + // break; + //} + //case EFCardinalDirection::W: + //{ + // break; + //} + //{ + //default: + // break; + //} + //} + +} + +void FAnimNode_BlendLocomotionFour::GatherDebugData(FNodeDebugData& DebugData) +{ + //const int32 ChildIndex = GetActiveChildIndex(); + + //FString DebugLine = GetNodeName(DebugData); + //DebugLine += FString::Printf(TEXT("(BlendTime: %f "), DotBlendTime); + + //DebugData.AddDebugItem(DebugLine); + + //NorthPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); + //EastPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); +} + + +void FAnimNode_BlendLocomotionFour::Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient) +{ + if (!FMath::IsNearlyZero(Orient, KINDA_SMALL_NUMBER)) + { + const FRotator DeltaRotation(0.0f, Orient, 0.f); + const FQuat DeltaQuat(DeltaRotation); + const FQuat MeshToComponentQuat(FRotator::ZeroRotator); + + // Convert our rotation from Component Space to Mesh Space. + const FQuat MeshSpaceDeltaQuat = MeshToComponentQuat.Inverse() * DeltaQuat * MeshToComponentQuat; + + // Apply rotation to root bone. + FCompactPoseBoneIndex RootBoneIndex(0); + CompactPose[RootBoneIndex].SetRotation(CompactPose[RootBoneIndex].GetRotation() * DeltaQuat); + CompactPose[RootBoneIndex].NormalizeRotation(); + } + // if (IKFootRootBone.IsValidToEvaluate(BoneContainer)) + // { + // // Prepare convert Quat and BoneContainer. + // const FQuat MeshToComponentQuat(FRotator(0.f, 0.f, 0.f)); + + // CSOutput.Pose.InitPose(CompactPose); + + // //Build our desired rotation for IK root bone. + // FRotator DeltaRotation(0.0f, 0.0f, 0.f); + // switch (Settings.YawRotationAxis) + // { + // case EAxis::X: + // DeltaRotation.Roll = Orient; + // case EAxis::Y: + // DeltaRotation.Pitch = Orient; + // case EAxis::Z: + // DeltaRotation.Yaw = Orient; + // default: + // break; + // } + // const FQuat DeltaQuat(DeltaRotation); + // // Convert our rotation from Component Space to Mesh Space. + // const FQuat MeshSpaceDeltaQuat = DeltaQuat; + // // Apply rotation to IK root bone. + // FCompactPoseBoneIndex RotateBoneIndex = IKFootRootBone.GetCompactPoseIndex(BoneContainer); + // CompactPose[RotateBoneIndex].SetRotation(CompactPose[RotateBoneIndex].GetRotation() * MeshSpaceDeltaQuat); + // CompactPose[RotateBoneIndex].NormalizeRotation(); + + + // // Do the same things like IK foot root bone to pelvis, but in the reversed orientation. + // FCompactPoseBoneIndex PelvisBoneIndex(1); + // FTransform PelvisBoneTM = CSOutput.Pose.GetComponentSpaceTransform(PelvisBoneIndex); + + // const FRotator PelvisDeltaRotation(DeltaRotation.Pitch * Settings.BodyOrientationAlpha, DeltaRotation.Yaw * Settings.BodyOrientationAlpha, DeltaRotation.Roll * Settings.BodyOrientationAlpha); + // FQuat PelvisDeltaQuat(PelvisDeltaRotation); + + // //const FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse() *PelvisDeltaQuat * PelvisBoneTM.GetRotation(); + // FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse()*PelvisDeltaQuat * PelvisBoneTM.GetRotation(); + + // CompactPose[PelvisBoneIndex].ConcatenateRotation(MeshSpacePelvisDeltaQuat); + // CompactPose[PelvisBoneIndex].NormalizeRotation(); + + // // Apply rotation to spine + // if (SpineBones.Num()) + // { + // for (int32 j = 0; j < SpineBones.Num(); j++) + // { + // if (SpineBones[j].Bone.IsValidToEvaluate(BoneContainer)) + // { + // FCompactPoseBoneIndex SpineBoneIndex = SpineBones[j].Bone.GetCompactPoseIndex(BoneContainer); + // FTransform SpineBoneTM = CSOutput.Pose.GetComponentSpaceTransform(SpineBoneIndex); + // const FRotator SpineDeltaRotation((-PelvisDeltaRotation.Pitch / SpineBones.Num()), (-PelvisDeltaRotation.Yaw / SpineBones.Num()), (-PelvisDeltaRotation.Roll / SpineBones.Num())); + // const FQuat SpineDeltaQuat(SpineDeltaRotation); + // const FQuat MeshSpaceSpineDeltaQuat = SpineBoneTM.GetRotation().Inverse() * SpineDeltaQuat * SpineBoneTM.GetRotation(); + // CompactPose[SpineBoneIndex].ConcatenateRotation(MeshSpaceSpineDeltaQuat); + // CompactPose[SpineBoneIndex].NormalizeRotation(); + // //GEngine->AddOnScreenDebugMessage(-1, DeltaTime, FColor::Yellow, (FString::Printf(TEXT(" SpineDeltaQuat: %s, MeshSpaceSpineDeltaQuat: %s PelvisDeltaQuat: %s"), *SpineDeltaQuat.ToString(), *MeshSpaceSpineDeltaQuat.ToString(), *PelvisDeltaQuat.ToString()))); + // } + // } + // } + // } + //} +} diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.h b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.h new file mode 100644 index 0000000..1165134 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.h @@ -0,0 +1,146 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Animation/AnimationAsset.h" +#include "Animation/AnimNodeBase.h" +#include "AlphaBlend.h" +#include "BoneContainer.h" +#include "OrionInterface.h" +#include "Animation/InputScaleBias.h" +#include "AnimNode_BlendLocomotionFour.generated.h" + +class UBlendProfile; +class UCurveFloat; + +enum class EECardinalDirection : uint8 +{ + N = 0, + SW = 1, + E = 2, + NW = 3, + S = 4, + NE = 5, + W = 6, + SE = 7 +}; +USTRUCT(BlueprintType) +struct FOAxisSettings +{ + GENERATED_BODY() + + UPROPERTY(EditAnywhere, Category = "FAxisSettings") + TEnumAsByte YawRotationAxis; + + UPROPERTY(EditAnywhere, Category = "FAxisSettings") + float BodyOrientationAlpha; + + FOAxisSettings() :YawRotationAxis(EAxis::Z) + , BodyOrientationAlpha(0.5f) {} +}; +USTRUCT() +struct FOBoneRef +{ + GENERATED_BODY() + + UPROPERTY(EditAnywhere, Category = "Settings") + FBoneReference Bone; +}; +// Blend list node; has many children +USTRUCT(BlueprintInternalUseOnly) +struct ORIONANIMATION_API FAnimNode_BlendLocomotionFour : public FAnimNode_Base +{ + GENERATED_USTRUCT_BODY() +public: + UPROPERTY(EditAnywhere, EditFixedSize, BlueprintReadWrite, Category = Links) + TArray BlendPose; + + UPROPERTY(EditAnywhere, EditFixedSize, BlueprintReadWrite, Category = Config, meta = (PinShownByDefault)) + TArray BlendTime; + + UPROPERTY(EditAnywhere, Category = BlendType) + EAlphaBlendOption BlendType; + + UPROPERTY(EditAnywhere, Category = BlendType) + UCurveFloat* CustomBlendCurve; + + UPROPERTY(EditAnywhere, Category = BlendType) + UBlendProfile* BlendProfile; + + UPROPERTY() + TArray Blends; + +protected: + UPROPERTY() + TArray BlendWeights; + + UPROPERTY() + TArray RemainingBlendTimes; + + UPROPERTY() + int32 LastActiveChildIndex; + + UPROPERTY() + TArray PerBoneSampleData; + + //Store which poses we need to evaluate + TArray PosesToEvaluate; + + /** This reinitializes child pose when re-activated. For example, when active child changes */ + UPROPERTY(EditAnywhere, Category = Option) + bool bResetChildOnActivation; + +protected: + int32 CurrentDirection; + EFCardinalDirection OldDirection; + EFCardinalDirection Dir; + float OrientN; + float OrientE; + float OrientS; + float OrientW; + float CurrentOrient; + bool bDirectionChanged; + int32 CurrentPose; + + UPROPERTY(Transient) + mutable float InternalBlendAlpha; + + UPROPERTY(Transient) + class ACharacter* Character; + + UPROPERTY(Transient) + class UCharacterMovementComponent* CMC; + + float RemainingBlendTime; + FAlphaBlend AlphaBlend; + + FAlphaBlend NorthBlend; + FAlphaBlend EastBlend; + + float DotBlendTime; + int32 NDot; + int32 EDot; +public: + FAnimNode_BlendLocomotionFour() + : LastActiveChildIndex(0) + , bResetChildOnActivation(false) + { + BlendTime.SetNum(4); + BlendPose.SetNum(4); + } + + // FAnimNode_Base interface + virtual void Initialize_AnyThread(const FAnimationInitializeContext& Context) override; + virtual void CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) override; + virtual void Update_AnyThread(const FAnimationUpdateContext& Context) override; + virtual void Evaluate_AnyThread(FPoseContext& Output) override; + virtual void GatherDebugData(FNodeDebugData& DebugData) override; + // End of FAnimNode_Base interface + +protected: + virtual int32 GetActiveChildIndex() { return 0; } + virtual FString GetNodeName(FNodeDebugData& DebugData) { return DebugData.GetNodeName(this); } + void Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient); +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp new file mode 100644 index 0000000..1cf28be --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "OrionAnimComponent.h" + + +// Sets default values for this component's properties +UOrionAnimComponent::UOrionAnimComponent() +{ + // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features + // off to improve performance if you don't need them. + PrimaryComponentTick.bCanEverTick = true; + + // ... +} + + +// Called when the game starts +void UOrionAnimComponent::BeginPlay() +{ + Super::BeginPlay(); + + // ... + +} + + +// Called every frame +void UOrionAnimComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + + // ... +} + diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h new file mode 100644 index 0000000..93b3c69 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Components/ActorComponent.h" +#include "OrionAnimComponent.generated.h" + + +UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) +class ORIONANIMATION_API UOrionAnimComponent : public UActorComponent +{ + GENERATED_BODY() + +public: + // Sets default values for this component's properties + UOrionAnimComponent(); + +protected: + // Called when the game starts + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + + +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp new file mode 100644 index 0000000..835b245 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "OrionAnimation.h" + +#define LOCTEXT_NAMESPACE "FOrionAnimationModule" + +void FOrionAnimationModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FOrionAnimationModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FOrionAnimationModule, OrionAnimation) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.h b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.h new file mode 100644 index 0000000..da88bbe --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FOrionAnimationModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp new file mode 100644 index 0000000..da8cfef --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp @@ -0,0 +1,6 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "OrionInterface.h" + + +// Add default functionality here for any IOrionInterface functions that are not pure virtual. diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.h b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.h new file mode 100644 index 0000000..66aee9d --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.h @@ -0,0 +1,42 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/Interface.h" +#include "OrionInterface.generated.h" + +enum class EFCardinalDirection : uint8 +{ + N = 0, + E = 1, + S = 2, + W = 3 +}; + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UOrionInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class ORIONANIMATION_API IOrionInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + virtual float GetAnimOrient() { return 0; } + + virtual float GetAnimOrientN() { return 0; } + virtual float GetAnimOrientE() { return 0; } + virtual float GetAnimOrientS() { return 0; } + virtual float GetAnimOrientW() { return 0; } + + virtual EFCardinalDirection GetCardianlDirection() { return EFCardinalDirection::N; } +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/AnimGraphNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/AnimGraphNode_BlendLocomotionFour.cpp new file mode 100644 index 0000000..359a7c0 --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/AnimGraphNode_BlendLocomotionFour.cpp @@ -0,0 +1,130 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#include "AnimGraphNode_BlendLocomotionFour.h" +#include "OrionAnimationEditor.h" + +#define LOCTEXT_NAMESPACE "A3Nodes" + +UAnimGraphNode_BlendLocomotionFour::UAnimGraphNode_BlendLocomotionFour() +{ + +} + +FLinearColor UAnimGraphNode_BlendLocomotionFour::GetNodeTitleColor() const +{ + return FLinearColor(0.7f, 0.7f, 0.7f); +} + +FText UAnimGraphNode_BlendLocomotionFour::GetTooltipText() const +{ + return LOCTEXT("LocomotionFour", "Locomotion Four Direction"); +} + +FText UAnimGraphNode_BlendLocomotionFour::GetNodeTitle(ENodeTitleType::Type TitleType) const +{ + return LOCTEXT("LocomotionFour", "Locomotion Four Direction"); +} + +FString UAnimGraphNode_BlendLocomotionFour::GetNodeCategory() const +{ + return TEXT("Orion Animation"); +} +void GetPinInformation(const FString& InPinName, int32& Out_PinIndex, bool& Out_bIsPosePin, bool& Out_bIsTimePin) +{ + const int32 UnderscoreIndex = InPinName.Find(TEXT("_"), ESearchCase::CaseSensitive); + if (UnderscoreIndex != INDEX_NONE) + { + const FString ArrayName = InPinName.Left(UnderscoreIndex); + Out_PinIndex = FCString::Atoi(*(InPinName.Mid(UnderscoreIndex + 1))); + + Out_bIsPosePin = (ArrayName == TEXT("BlendPose")); + Out_bIsTimePin = (ArrayName == TEXT("BlendTime")); + } + else + { + Out_bIsPosePin = false; + Out_bIsTimePin = false; + Out_PinIndex = INDEX_NONE; + } +} +void UAnimGraphNode_BlendLocomotionFour::CustomizePinData(UEdGraphPin* Pin, FName SourcePropertyName, int32 ArrayIndex) const +{ + // if pin name starts with BlendPose or BlendWeight, change to enum name + bool bIsPosePin; + bool bIsTimePin; + int32 RawArrayIndex; + GetPinInformation(Pin->PinName.ToString(), /*out*/ RawArrayIndex, /*out*/ bIsPosePin, /*out*/ bIsTimePin); + checkSlow(RawArrayIndex == ArrayIndex); + + + if (bIsPosePin) + { + if (RawArrayIndex == 0) + { + //Pin->PinFriendlyName = FText::FromName("North Pose"); + //FFormatNamedArguments Args; + //Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); + Pin->PinFriendlyName = FText::FromString("N Pose"); + } + else if (RawArrayIndex == 1) + { + Pin->PinFriendlyName = FText::FromString("E Pose"); + } + else if (RawArrayIndex == 2) + { + Pin->PinFriendlyName = FText::FromString("S Pose"); + } + else if (RawArrayIndex == 3) + { + Pin->PinFriendlyName = FText::FromString("W Pose"); + } + } + //if (bIsPosePin || bIsTimePin) + //{ + // if (RawArrayIndex > 0) + // { + // const int32 ExposedEnumPinIndex = RawArrayIndex - 1; + + // // find pose index and see if it's mapped already or not + // if (VisibleEnumEntries.IsValidIndex(ExposedEnumPinIndex) && (BoundEnum != NULL)) + // { + // const FName& EnumElementName = VisibleEnumEntries[ExposedEnumPinIndex]; + // const int32 EnumIndex = BoundEnum->GetIndexByName(EnumElementName); + // if (EnumIndex != INDEX_NONE) + // { + // Pin->PinFriendlyName = BoundEnum->GetDisplayNameTextByIndex(EnumIndex); + // } + // else + // { + // Pin->PinFriendlyName = FText::FromName(EnumElementName); + // } + // } + // else + // { + // Pin->PinFriendlyName = LOCTEXT("InvalidIndex", "Invalid index"); + // } + // } + // else if (ensure(RawArrayIndex == 0)) + // { + // Pin->PinFriendlyName = LOCTEXT("Default", "Default"); + // } + + // // Append the pin type + // if (bIsPosePin) + // { + // FFormatNamedArguments Args; + // Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); + // Pin->PinFriendlyName = FText::Format(LOCTEXT("FriendlyNamePose", "{PinFriendlyName} Pose"), Args); + // } + + // if (bIsTimePin) + // { + // FFormatNamedArguments Args; + // Args.Add(TEXT("PinFriendlyName"), Pin->PinFriendlyName); + // Pin->PinFriendlyName = FText::Format(LOCTEXT("FriendlyNameBlendTime", "{PinFriendlyName} Blend Time"), Args); + // } + //} +} + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/OrionAnimationEditor.cpp b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/OrionAnimationEditor.cpp new file mode 100644 index 0000000..05b5d7f --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Private/OrionAnimationEditor.cpp @@ -0,0 +1,20 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#include "OrionAnimationEditor.h" + +#define LOCTEXT_NAMESPACE "OrionAnimationEditorModule" + +void FOrionAnimationEditorModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FOrionAnimationEditorModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FOrionAnimationEditorModule, OrionAnimationEditor) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/AnimGraphNode_BlendLocomotionFour.h b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/AnimGraphNode_BlendLocomotionFour.h new file mode 100644 index 0000000..71f79fb --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/AnimGraphNode_BlendLocomotionFour.h @@ -0,0 +1,35 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "AnimGraphNode_Base.h" +#include "AnimNode_BlendLocomotionFour.h" +#include "AnimGraphNode_BlendLocomotionFour.generated.h" + +struct FAnimMode_OrientationWarping; +/** +* +*/ +UCLASS() +class ORIONANIMATIONEDITOR_API UAnimGraphNode_BlendLocomotionFour : public UAnimGraphNode_Base +{ + GENERATED_BODY() + + UPROPERTY(EditAnywhere, Category = "Settings") + FAnimNode_BlendLocomotionFour Node; + + //~ Begin UEdGraphNode Interface. + virtual FLinearColor GetNodeTitleColor() const override; + virtual FText GetTooltipText() const override; + virtual FText GetNodeTitle(ENodeTitleType::Type TitleType) const override; + //~ End UEdGraphNode Interface. + + //~ Begin UAnimGraphNode_Base Interface + virtual FString GetNodeCategory() const override; + //~ End UAnimGraphNode_Base Interface + virtual void CustomizePinData(UEdGraphPin* Pin, FName SourcePropertyName, int32 ArrayIndex) const override; + UAnimGraphNode_BlendLocomotionFour(); + + +}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/OrionAnimationEditor.h b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/OrionAnimationEditor.h new file mode 100644 index 0000000..e60cb6a --- /dev/null +++ b/Plugins/OrionAnimation/Source/OrionAnimationEditor/Public/OrionAnimationEditor.h @@ -0,0 +1,15 @@ +// Copyright 2018 Sean Chen. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FOrionAnimationEditorModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.cpp new file mode 100644 index 0000000..44a9f01 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "SpectrAI.h" + +#define LOCTEXT_NAMESPACE "FSpectrAIModule" + +void FSpectrAIModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FSpectrAIModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FSpectrAIModule, SpectrAI) \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.h new file mode 100644 index 0000000..a266684 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAI.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FSpectrAIModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.cpp new file mode 100644 index 0000000..c5103bd --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.cpp @@ -0,0 +1,12 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrAIController.h" +#include "SpectrBrainComponent.h" + + +ASpectrAIController::ASpectrAIController(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + SpectrBrain = ObjectInitializer.CreateDefaultSubobject(this, TEXT("SpectrBrain")); + AIPerception = ObjectInitializer.CreateDefaultSubobject(this, TEXT("AIPerception")); +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.h new file mode 100644 index 0000000..19287ea --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAIController.h @@ -0,0 +1,48 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "AIController.h" +#include "Perception/AIPerceptionComponent.h" +#include "SpectrAIController.generated.h" + +//Consideration (calculates score) +//--normalized 0-1 +//--calculated against curve + +//Qualifier +//--Contains Considerations +//--defines how score Considerations should be combined +//--return score. + +//Decision (what should I do?) +//--contain exactly ONE action to execute if decision wins + +//Decision Score Evaluator (Selector) +//--containts multiple considerations +//--all condsiderations are calculated with given context +//--they are summed (or multiplied) +//--contains single decision to execute. + + + +/** + * + */ +UCLASS() +class SPECTRAI_API ASpectrAIController : public AAIController +{ + GENERATED_BODY() +public: + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + class USpectrBrainComponent* SpectrBrain; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly) + class UAIPerceptionComponent* AIPerception; + + + ASpectrAIController(const FObjectInitializer& ObjectInitializer); + + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.cpp new file mode 100644 index 0000000..e57eba5 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.cpp @@ -0,0 +1,60 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrAction.h" +#include "SpectrBrainComponent.h" + + +void USpectrAction::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + MoveTo(Brain); +} +void USpectrAction::NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +{ + OnMoveFinished(InContext, AIController, Brain); +} +void USpectrAction::FinishMove(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +{ + NativeOnMoveFinished(InContext, AIController, Brain); +} +void USpectrAction::MoveTo_Implementation(class USpectrBrainComponent* Brain) +{ + +} + +float USpectrAction::NativeScore(class USpectrContext* InContext, class AAIController* AIController) +{ + return Score(InContext, AIController); +} + +float USpectrAction::Score_Implementation(class USpectrContext* InContext, class AAIController* AIController) +{ + return Cost; +} +bool USpectrAction::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + return EvaluateCondition(InContext, AIController); +} +bool USpectrAction::EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController) +{ + return true; +} + +void USpectrAction::NativeFinished() +{ + OwningBrain->OnActionFinished(this); +} + +void USpectrAction::NativeExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain) +{ + OnExecute(InContext, AIController, Brain); +} + +void USpectrAction::ActionFinished() +{ + NativeFinished(); +} + +void USpectrAction::MoveToTarget(AActor* Target, float MinimumDistance) +{ + OwningBrain->MoveToActor(Target, MinimumDistance); +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.h new file mode 100644 index 0000000..b6ac82b --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrAction.h @@ -0,0 +1,94 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "SpectrAction.generated.h" + +/** + * Default implmenetations of Native* functions call to either blueprint events + * or blueprint Native functions which can be overriden from blueprint. + * Though they do provide default implementation (where possible). + */ + +UCLASS(BlueprintType, Blueprintable) +class SPECTRAI_API USpectrAction : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "State Configuration") + int32 Cost; + /* + Tag Name of requirent condition in agent state, Desiared State Value + */ + UPROPERTY(EditAnywhere, Category = "State Configuration") + TMap PreConditions; + + /* + Tag Name of change applied to agent state is effect is executed, Desiared State Value + */ + UPROPERTY(EditAnywhere, Category = "State Configuration") + TMap Effects; + + UPROPERTY(BlueprintReadOnly, Category = "Spectr AI") + USpectrBrainComponent* OwningBrain; + + /* Override to check if action in rnage of Target/Location to execute */ + virtual bool NativeIsInRange(class AAIController* AIController) + { + return true; + } + + virtual void NativeMoveTo(class USpectrBrainComponent* Brain); + + virtual void NativeOnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + + UFUNCTION(BlueprintNativeEvent) + void MoveTo(class USpectrBrainComponent* Brain); + virtual void MoveTo_Implementation(class USpectrBrainComponent* Brain); + + UFUNCTION(BlueprintImplementableEvent, Category = "Spectr AI") + void OnMoveFinished(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + + UFUNCTION(BlueprintCallable, Category = "Spectr AI") + void FinishMove(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + + /* + Call Super::NativeExecute if you want to execute OnExecuted BP event, or call it manually. + + Remember to call NativeFinished() somewhere, to indicate that Action finished execution. + */ + virtual void NativeExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + + virtual float NativeScore(class USpectrContext* InContext, class AAIController* AIController); + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); + + /* + Remember to call it always after Action has finished execution. Otherwise Action Queue will be stuck. + */ + void NativeFinished(); + + UFUNCTION(BlueprintImplementableEvent, Category = "Spectr AI") + void OnExecute(class USpectrContext* InContext, class AAIController* AIController, class USpectrBrainComponent* Brain); + + UFUNCTION(BlueprintCallable, Category = "Spectr AI") + void ActionFinished(); + + UFUNCTION(BlueprintNativeEvent) + float Score(class USpectrContext* InContext, class AAIController* AIController); + virtual float Score_Implementation(class USpectrContext* InContext, class AAIController* AIController); + + UFUNCTION(BlueprintNativeEvent) + bool EvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); + virtual bool EvaluateCondition_Implementation(class USpectrContext* InContext, class AAIController* AIController); + + + + + UFUNCTION(BlueprintCallable) + void MoveToTarget(AActor* Target, float MinimumDistance); +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.cpp new file mode 100644 index 0000000..9a38a52 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.cpp @@ -0,0 +1,175 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrBrainComponent.h" +#include "SpectrContext.h" +#include "AIController.h" +#include "Engine/World.h" +#include "TimerManager.h" + +bool operator==(const FSpectrNode& Other, const USpectrAction*& Action) +{ + return Other.Action == Action; +} + +USpectrBrainComponent::USpectrBrainComponent(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + FSMState = ESpectrState::Idle; + if(Context) + CurrentContext = Cast(CreateDefaultSubobject(TEXT("CurrentContext"), Context, Context, true, false, false)); +} + +void USpectrBrainComponent::TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) +{ + Super::TickComponent(DeltaTime, TickType, ThisTickFunction); + //check for new goals + //evaluate if new goal is worth pursuing over the current one. +} +void USpectrBrainComponent::BeginPlay() +{ + Super::BeginPlay(); + if (AAIController* AIController = Cast(GetOwner())) + { + AIController->GetPathFollowingComponent()->OnRequestFinished.AddUObject(this, &USpectrBrainComponent::OnMoveFinished); + } + for (const TSubclassOf& ActionClass : ActionList) + { + USpectrAction* Action = NewObject(this, ActionClass); + Action->OwningBrain = this; + Actions.Add(Action); + } +} +void USpectrBrainComponent::StarPlanning() +{ + //no point of running planner on clients. + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + return; + } + + TArray OutActionList; + if (AAIController* AIController = Cast(GetOwner())) + { + SpectrAI.Plan(Goal, CurrentState, OutActionList, Actions, CurrentContext, AIController); + } + for (int32 Idx = OutActionList.Num() - 1; Idx >= 0; Idx--) + { + FString name = OutActionList[Idx]->GetName(); + + PendingPlan.Add(OutActionList[Idx]); + PendingPlan2.Enqueue(OutActionList[Idx]); + + UE_LOG(LogTemp, Log, TEXT("Action Name: %s \n"), *name); + } + if (OutActionList.Num() == 0) + { + FTimerManager& Timer = GetWorld()->GetTimerManager(); + FTimerDelegate del = FTimerDelegate::CreateUObject(this, &USpectrBrainComponent::NextPlan); + Timer.SetTimer(NextPlanTimerHandle, del, 0.2f, false, 0.2f); + } + else + { + ExecutePlan(nullptr); + } + +} +void USpectrBrainComponent::NextPlan() +{ + TArray OutActionList; + if (AAIController* AIController = Cast(GetOwner())) + { + SpectrAI.Plan(Goal, CurrentState, OutActionList, Actions, CurrentContext, AIController); + } + if (OutActionList.Num() == 0) + { + FTimerManager& Timer = GetWorld()->GetTimerManager(); + FTimerDelegate del = FTimerDelegate::CreateUObject(this, &USpectrBrainComponent::NextPlan); + Timer.SetTimer(NextPlanTimerHandle, del, 0.2f, false, 0.2f); + } + else + { + ExecutePlan(nullptr); + } + +} +void USpectrBrainComponent::SelectGoal() +{ + +} + +void USpectrBrainComponent::ExecutePlan(class USpectrAction* PreviousAction) +{ + if (PendingPlan2.IsEmpty()) + { + //plan finished + StarPlanning(); //plan again + //in reality look for new goal. + return; + } + while (!PendingPlan2.IsEmpty()) + { + USpectrAction* OutAction; + PendingPlan2.Dequeue(OutAction); + if (OutAction != PreviousAction) + { + CurrentAction = OutAction; + break; + } + } + /*if (PendingPlan.Num() && PendingPlan[0]) + { + CurrentAction = PendingPlan[0]; + PendingPlan.RemoveAt(0, 1, true); + }*/ + if (AAIController* AIController = Cast(GetOwner())) + { + //Not in range + if (!CurrentAction->NativeIsInRange(AIController)) + { + FSMState = ESpectrState::Move; + CurrentAction->NativeMoveTo(this); + FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(CurrentAction, &USpectrAction::NativeOnMoveFinished, CurrentContext, AIController, this); + PendingMoveEvent = Delegate; + } + else //in range, just execute action. + { + FSMState = ESpectrState::Action; + CurrentAction->NativeExecute(CurrentContext, AIController, this); + } + // + } +} +void USpectrBrainComponent::AbortPlan(const FString& Reason) +{ + +} +void USpectrBrainComponent::OnActionFinished(USpectrAction* InAction) +{ + ExecutePlan(InAction); +} +void USpectrBrainComponent::OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result) +{ + if (AAIController* AIController = Cast(GetOwner())) + { + if (CurrentAction) + { + CurrentAction->NativeOnMoveFinished(CurrentContext, AIController, this); + } + } + //PendingMoveEvent.ExecuteIfBound(); + //PendingMoveEvent.Unbind(); + //ExecutePlan(); +} + +void USpectrBrainComponent::MoveToLocation() +{ + FSMState = ESpectrState::Move; +} +void USpectrBrainComponent::MoveToActor(AActor* Target, float MinDistance) +{ + FSMState = ESpectrState::Move; + if (AAIController* AIController = Cast(GetOwner())) + { + AIController->MoveToActor(Target, MinDistance); + } +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.h new file mode 100644 index 0000000..332e97b --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrBrainComponent.h @@ -0,0 +1,323 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameplayTasksComponent.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "Queue.h" +#include "SpectrAction.h" +#include "Navigation/PathFollowingComponent.h" +#include "AITypes.h" + +#include "SpectrBrainComponent.generated.h" + +enum class ESpectrState : uint8 +{ + Idle = 0, + Action = 1, + Move = 2 +}; + +//Node representing single step in plan. +struct FSpectrNode +{ + int32 Cost; + float Score; + int32 RemainingCost; + TWeakPtr Parent; + TMap State; + USpectrAction* Action; + TArray> Children; + FSpectrNode() {} + FSpectrNode(const TMap& InState, int32 InCost, int32 InRemainingCost) + : Cost(InCost) + , RemainingCost(InRemainingCost) + , State(InState) + {} + + bool Equals(USpectrAction* InAction) + { + return Action == InAction; + } + + bool operator==(const FSpectrNode& Other) const + { + return Action == Other.Action; + } + bool operator==(const USpectrAction*& Other) const + { + return Action == Other; + } + +}; + +bool operator==(const FSpectrNode& Other, const USpectrAction*& Action); + + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrAI +{ + GENERATED_BODY() +public: + //Precondition, List of action for this precondition; + TMap> > ActionMap; + + bool CheckGoal(const TMap& InEffects, const TMap& InGoal) + { + bool bAchieved = false; + for (TPair Test : InGoal) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Check Current Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + + for (TPair Test : InEffects) + { + if (InGoal.Contains(Test.Key)) + { + if (InGoal[Test.Key] == Test.Value) + { + UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Passed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); + bAchieved = true; + } + else + { + UE_LOG(LogTemp, Log, TEXT("----Build Plan - Check Failed Test %s Value %d \n"), *Test.Key.ToString(), Test.Value); + bAchieved = false; + break; //all or nothing. + } + } + } + + + return bAchieved; + } + + TMap UpdateState(const TMap& InEffects, + const TMap& InCurrentState) + { + TMap NewState; + NewState.Append(InCurrentState); + for (TPair Effect : InEffects) + { + if (NewState.Contains(Effect.Key)) + { + bool* dd = NewState.Find(Effect.Key); + *dd = Effect.Value; + } + } + return NewState; + } + + TMap AddGoalChanges(const TMap& InCurrentGoal, + const TMap& InGoalChange) + { + TMap NewSet; + + NewSet.Append(InCurrentGoal); + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE START")); + for (TPair Test : InCurrentGoal) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges PRE END")); + for (TPair Change : InGoalChange) + { + if (NewSet.Contains(Change.Key)) + { + /*bool* dd = NewSet.Find(Change.Key); + *dd = Change.Value;*/ + } + else + { + NewSet.Add(Change.Key, Change.Value); + } + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST START")); + for (TPair Test : NewSet) + { + UE_LOG(LogTemp, Log, TEXT("---Build Plan - Key %s Value %d \n"), *Test.Key.ToString(), Test.Value); + } + UE_LOG(LogTemp, Log, TEXT("---Build Plan - AddGoalChanges POST END")); + return NewSet; + } + void InitializeMap(const TArray>& ActionList) + { + for (const TSubclassOf Action : ActionList) + { + for (const TPair& Effect : Action.GetDefaultObject()->Effects) + { + TArray>& ActionArray = ActionMap.FindOrAdd(Effect.Key); + ActionArray.Add(Action); + } + + } + } + void Plan(const TMap& InTargetGoal, const TMap& InCurrentState + , TArray& InActionQueue + , const TArray& ActionList + , class USpectrContext* InContext + , class AAIController* AIController) + { + TArray> OpenNodes; + TArray> ClosedNodes; + + TSharedPtr Node = MakeShareable(new FSpectrNode(InTargetGoal, 0, 0)); + + //actually made action when constructing node path. + //and then execute it in reverse (from last item in array to first). + //so we don't was time traversing node tree and then reordering actions.. + TArray ActionPlan; + + OpenNodes.Push(Node); + + TArray AvailableActions = ActionList; + + //reverse A*, or something similiar to it at least.. + while (OpenNodes.Num()) + { + TSharedPtr CurrentNode = OpenNodes.Pop(); + ClosedNodes.Push(CurrentNode); + + for (USpectrAction*& Action : AvailableActions) + { + //or instead of pushing to closed actions... we can remove them for Available Actions hmm ? + if (ClosedNodes.ContainsByPredicate([&](const TSharedPtr& Item) + { + return Item->Equals(Action); + })) + { + continue; + } + + if (!(CurrentNode->Action == Action)) + { + if (CheckGoal(Action->Effects, CurrentNode->State)) + { + //action scored Zero, so it probabaly can't be used anyway. + if (!Action->NativeEvaluateCondition(InContext, AIController)) + { + continue; + } + float Score = Action->NativeScore(InContext, AIController); + + TSharedPtr Node2 = MakeShareable(new FSpectrNode(Action->PreConditions, Action->Cost, 0)); + Node2->Action = Action; + Node2->Score = Score; + OpenNodes.Add(Node2); + + if (CurrentNode->Children.Num() == 0) + { + CurrentNode->Children.Add(Node2); + ActionPlan.Add(Action); + } + else + { + //add new action, only if it is cheaper than current one. + //very primitive we need to check if the actuall path will be cheaper. + //so compare current cost of the path with + if (Score > Node2->Score) + { + ActionPlan.Remove(CurrentNode->Children[0]->Action); + CurrentNode->Children.Empty(); + CurrentNode->Children.Add(Node2); + + ActionPlan.Add(Action); + } + else + { + //action has been discarded, remove it from OpenNodes + OpenNodes.Remove(Node2); + //and add to closed nodes. No reason to ever consider it again. + ClosedNodes.Add(Node2); + } + } + } + } + } + } + + InActionQueue = ActionPlan; + } +}; + +USTRUCT(BlueprintType) +struct FGoalSpec +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Instanced) + class USpectrGoal* Goal; + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; +}; + +/** + * + */ +UCLASS() +class SPECTRAI_API USpectrBrainComponent : public UGameplayTasksComponent +{ + GENERATED_BODY() +public: + ESpectrState FSMState; + + UPROPERTY(EditAnywhere) + TMap Goal; + UPROPERTY(EditAnywhere) + TMap CurrentState; + UPROPERTY(EditAnywhere) + TArray> ActionList; + UPROPERTY() + TArray Actions; + UPROPERTY(EditAnywhere) + TArray Goals2; + + UPROPERTY(EditAnywhere, Instanced) + TArray Goals; + UPROPERTY() + class USpectrGoal* CurrentGoal; + + + UPROPERTY() + TArray PendingPlan; + + TQueue PendingPlan2; + + UPROPERTY() + USpectrAction* CurrentAction; + + + + UPROPERTY(EditAnywhere) + TSubclassOf Context; + UPROPERTY() + class USpectrContext* CurrentContext; + + FSpectrAI SpectrAI; + + //Map of pending move events. + FSimpleDelegate PendingMoveEvent; + + FTimerHandle NextPlanTimerHandle; + + USpectrBrainComponent(const FObjectInitializer& ObjectInitializer); + virtual void BeginPlay() override; + virtual void TickComponent(float DeltaTime, enum ELevelTick TickType, FActorComponentTickFunction *ThisTickFunction) override; + UFUNCTION(BlueprintCallable) + void StarPlanning(); + UFUNCTION() + void NextPlan(); + + void SelectGoal(); + void ExecutePlan(class USpectrAction* PreviousAction); + void AbortPlan(const FString& Reason); + void OnActionFinished(USpectrAction* InAction); + void OnMoveFinished(FAIRequestID RequestID, const FPathFollowingResult& Result); + + void MoveToLocation(); + void MoveToActor(AActor* Target, float MinDistance); + + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.cpp new file mode 100644 index 0000000..88cf50e --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrConsideration.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.h new file mode 100644 index 0000000..da8ec6e --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrConsideration.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "SpectrConsideration.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class SPECTRAI_API USpectrConsideration : public UObject +{ + GENERATED_BODY() + +public: + virtual float Score() const { return 0; } + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.cpp new file mode 100644 index 0000000..988813d --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrContext.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.h new file mode 100644 index 0000000..8822a25 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrContext.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "SpectrContext.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAI_API USpectrContext : public UObject +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.cpp new file mode 100644 index 0000000..37d9944 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrEvaluator.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.h new file mode 100644 index 0000000..673ff31 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrEvaluator.h @@ -0,0 +1,72 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "SpectrConsideration.h" +#include "SpectrEvaluator.generated.h" + + +//USTRUCT(BlueprintType) +//struct SPECTRAI_API FSpectrConsideration +//{ +// GENERATED_BODY() +//public: +// virtual float Score() const { return 0; } +// virtual ~FSpectrConsideration() +// {} +//}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrQualifier +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; +public: + virtual ~FSpectrQualifier() + {} + virtual float Qualify() const + { + float TotalScore = 0; + for (USpectrConsideration* Consideration : Considerations) + { + TotalScore += Consideration->Score(); + } + return TotalScore; + } +}; + +USTRUCT(BlueprintType) +struct SPECTRAI_API FSpectrEvaluator +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + FSpectrQualifier Qualifier; + + mutable float Score; + + float Evaluate() const + { + Score = 0; + float score = Qualifier.Qualify(); + Score = score; + return score; + } +}; + +/** + * + */ +//UCLASS() +//class SPECTRAI_API USpectrEvaluator : public UObject +//{ +// GENERATED_BODY() +// +// +// +// +//}; diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.cpp b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.cpp new file mode 100644 index 0000000..3b2ccbf --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "SpectrGoal.h" + + + + diff --git a/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.h b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.h new file mode 100644 index 0000000..f2b5ca8 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAI/Public/SpectrGoal.h @@ -0,0 +1,63 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/NoExportTypes.h" +#include "GameplayTags.h" +#include "GameplayTagContainer.h" +#include "SpectrEvaluator.h" +#include "SpectrGoal.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable, EditInLineNew) +class SPECTRAI_API USpectrGoal : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TMap Goal; + + //What to change in state if goal has been achieved ? + UPROPERTY(EditAnywhere) + TMap FinishedState; + + UPROPERTY(EditAnywhere, Instanced) + TArray Considerations; + + UPROPERTY(EditAnywhere) + FSpectrEvaluator ScoreEvaluator; + + virtual float QualifyGoal(class USpectrContext* InContext) + { + return -1.0f; + } + + //What Should we do if this goal is selected ? + virtual void GoalSelected() + { + + } + + //Called when goal has been selected, just before plan is executed. + virtual void GoalStarted() + { + + } + + //called just after plan finished execution + virtual void GoalFinished() + { + + } + + //called if plan for some reason cannot be finished and is aborted. + virtual void GoalAborted() + { + + } + + +}; diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.cpp b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.cpp new file mode 100644 index 0000000..7e6a50e --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "SpectrAIEditor.h" + +#define LOCTEXT_NAMESPACE "FSpectrAIEditor" + +void FSpectrAIEditorModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FSpectrAIEditorModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FSpectrAIEditorModule, SpectrAIEditor) \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.h b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.h new file mode 100644 index 0000000..7b2e8e7 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrAIEditor.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FSpectrAIEditorModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.cpp b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.cpp new file mode 100644 index 0000000..6269568 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.cpp @@ -0,0 +1,12 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "SpectrGoalCustomization.h" + +TSharedRef FSpectrGoalCustomization::MakeInstance() +{ + return MakeShareable(new FSpectrGoalCustomization()); +} +void FSpectrGoalCustomization::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) +{ + +} \ No newline at end of file diff --git a/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.h b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.h new file mode 100644 index 0000000..767e7f9 --- /dev/null +++ b/Plugins/SpectrAI/Source/SpectrAIEditor/Public/SpectrGoalCustomization.h @@ -0,0 +1,17 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrGoal.h" + +#include "IDetailCustomization.h" +#include "PropertyHandle.h" + +class FSpectrGoalCustomization : public IDetailCustomization +{ +public: + /** Makes a new instance of this detail layout class for a specific detail view requesting it */ + static TSharedRef MakeInstance(); + virtual void CustomizeDetails(IDetailLayoutBuilder& DetailLayout) override; +}; \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.cpp new file mode 100644 index 0000000..7b04f84 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAIControllerBase.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.h new file mode 100644 index 0000000..f79cf73 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAIControllerBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAIController.h" +#include "STestAIControllerBase.generated.h" + +/** + * + */ +UCLASS() +class SPECTRAITEST_API ASTestAIControllerBase : public ASpectrAIController +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.cpp new file mode 100644 index 0000000..793d1af --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.cpp @@ -0,0 +1,54 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_ChopFirewood.h" +#include "AIController.h" +#include "SpectrBrainComponent.h" +#include "STestTree.h" +#include "EngineUtils.h" + +bool USTestAction_ChopFirewood::NativeIsInRange(class AAIController* AIController) +{ + //We can evaluate again here if we have target, and if it worth going. + //we can either find better fit or abort plan at this point. + bool bInRange = false; + if (TargetTree) + { + APawn* Pawn = AIController->GetPawn(); + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetTree->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance < MinDistance) + { + bInRange = true; + } + } + return bInRange; +} +void USTestAction_ChopFirewood::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + Brain->MoveToActor(TargetTree, MinDistance); +} +void USTestAction_ChopFirewood::NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeExecute(InContext, AIController, Brain); +} +//void USTestAction_ChopFirewood::NativeExecute(class USpectrContext* InContext +// , class AAIController* AIController +// , class USpectrBrainComponent* Brain) +//{ +// NativeFinished(); +//} + +bool USTestAction_ChopFirewood::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + bool bFound = false; + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetTree = *ActorIt; + bFound = true; + break; + } + return bFound; +} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.h new file mode 100644 index 0000000..d2378c8 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopFirewood.h @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_ChopFirewood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_ChopFirewood : public USpectrAction +{ + GENERATED_BODY() + + UPROPERTY() + AActor* TargetTree; + UPROPERTY(EditAnywhere) + float MinDistance; + +public: + virtual bool NativeIsInRange(class AAIController* AIController) override; + virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; + virtual void NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + //virtual void NativeExecute(class USpectrContext* InContext + // , class AAIController* AIController + // , class USpectrBrainComponent* Brain) override; + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.cpp new file mode 100644 index 0000000..001a874 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_ChopWood.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.h new file mode 100644 index 0000000..4428927 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_ChopWood.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_ChopWood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_ChopWood : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.cpp new file mode 100644 index 0000000..876aefc --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_CollectBranches.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.h new file mode 100644 index 0000000..bae50a2 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectBranches.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_CollectBranches.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_CollectBranches : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.cpp new file mode 100644 index 0000000..3800d2d --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_CollectOre.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.h new file mode 100644 index 0000000..212463b --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_CollectOre.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_CollectOre.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_CollectOre : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.cpp new file mode 100644 index 0000000..e23a260 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.cpp @@ -0,0 +1,52 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_DropFirewood.h" +#include "AIController.h" +#include "SpectrBrainComponent.h" +#include "STestStorage.h" +#include "EngineUtils.h" + +bool USTestAction_DropFirewood::NativeIsInRange(class AAIController* AIController) +{ + bool bInRange = false; + if (TargetDropPoint) + { + APawn* Pawn = AIController->GetPawn(); + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetDropPoint->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance < MinDistance) + { + bInRange = true; + } + } + return bInRange; +} +void USTestAction_DropFirewood::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + Brain->MoveToActor(TargetDropPoint, MinDistance); +} +void USTestAction_DropFirewood::NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeExecute(InContext, AIController, Brain); +} +void USTestAction_DropFirewood::NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeFinished(); +} + +bool USTestAction_DropFirewood::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + bool bFound = false; + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetDropPoint = *ActorIt; + bFound = true; + break; + } + return bFound; +} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.h new file mode 100644 index 0000000..9a8cb95 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropFirewood.h @@ -0,0 +1,36 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_DropFirewood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_DropFirewood : public USpectrAction +{ + GENERATED_BODY() + + UPROPERTY() + AActor* TargetDropPoint; + UPROPERTY(EditAnywhere) + float MinDistance; + +public: + virtual bool NativeIsInRange(class AAIController* AIController) override; + virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; + virtual void NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual void NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.cpp new file mode 100644 index 0000000..d017aad --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_DropOre.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.h new file mode 100644 index 0000000..2883ff4 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropOre.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_DropOre.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_DropOre : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.cpp new file mode 100644 index 0000000..0cafb3b --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_DropWood.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.h new file mode 100644 index 0000000..04fb1c8 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_DropWood.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_DropWood.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_DropWood : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.cpp new file mode 100644 index 0000000..365c590 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_GoTo.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.h new file mode 100644 index 0000000..393bce0 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_GoTo.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_GoTo.generated.h" + +/** + * + */ +UCLASS() +class SPECTRAITEST_API USTestAction_GoTo : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.cpp new file mode 100644 index 0000000..c9b4702 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_MakeAxe.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.h new file mode 100644 index 0000000..030d66c --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakeAxe.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_MakeAxe.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_MakeAxe : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.cpp new file mode 100644 index 0000000..a50a2b5 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_MakePick.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.h new file mode 100644 index 0000000..b694046 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MakePick.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_MakePick.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_MakePick : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.cpp new file mode 100644 index 0000000..6c91e77 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_MineOre.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.h new file mode 100644 index 0000000..6472f2e --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_MineOre.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_MineOre.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_MineOre : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.cpp new file mode 100644 index 0000000..eeb7171 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.cpp @@ -0,0 +1,52 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_PickItemAxe.h" +#include "AIController.h" +#include "SpectrBrainComponent.h" +#include "STestAxePickup.h" +#include "EngineUtils.h" + +bool USTestAction_PickItemAxe::NativeIsInRange(class AAIController* AIController) +{ + bool bInRange = false; + if (TargetItem) + { + APawn* Pawn = AIController->GetPawn(); + FVector Position = Pawn->GetActorLocation(); + FVector TargetPosition = TargetItem->GetActorLocation(); + float Distance = FVector::Dist(Position, TargetPosition); + if (Distance < MinDistance) + { + bInRange = true; + } + } + return bInRange; +} +void USTestAction_PickItemAxe::NativeMoveTo(class USpectrBrainComponent* Brain) +{ + Brain->MoveToActor(TargetItem, MinDistance); +} +void USTestAction_PickItemAxe::NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeExecute(InContext, AIController, Brain); +} +void USTestAction_PickItemAxe::NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) +{ + NativeFinished(); +} + +bool USTestAction_PickItemAxe::NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController) +{ + bool bFound = false; + for (TActorIterator ActorIt(AIController->GetWorld()); ActorIt; ++ActorIt) + { + TargetItem = *ActorIt; + bFound = true; + break; + } + return bFound; +} \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.h new file mode 100644 index 0000000..e1a25f0 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemAxe.h @@ -0,0 +1,34 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_PickItemAxe.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_PickItemAxe : public USpectrAction +{ + GENERATED_BODY() +protected: + /* Minimum distance from item to pick it. */ + UPROPERTY(EditAnywhere) + float MinDistance; + UPROPERTY() + AActor* TargetItem; +public: + virtual bool NativeIsInRange(class AAIController* AIController) override; + virtual void NativeMoveTo(class USpectrBrainComponent* Brain) override; + virtual void NativeOnMoveFinished(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual void NativeExecute(class USpectrContext* InContext + , class AAIController* AIController + , class USpectrBrainComponent* Brain) override; + + virtual bool NativeEvaluateCondition(class USpectrContext* InContext, class AAIController* AIController); +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.cpp new file mode 100644 index 0000000..4d1578b --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAction_PickItemPick.h" + + + + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.h new file mode 100644 index 0000000..a22eaff --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAction_PickItemPick.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "SpectrAction.h" +#include "STestAction_PickItemPick.generated.h" + +/** + * + */ +UCLASS(BlueprintType, Blueprintable) +class SPECTRAITEST_API USTestAction_PickItemPick : public USpectrAction +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.cpp new file mode 100644 index 0000000..a25fb52 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestAxePickup.h" + + +// Sets default values +ASTestAxePickup::ASTestAxePickup() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestAxePickup::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestAxePickup::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.h new file mode 100644 index 0000000..970ff76 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestAxePickup.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestAxePickup.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestAxePickup : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestAxePickup(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.cpp new file mode 100644 index 0000000..9296a87 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestBranch.h" + + +// Sets default values +ASTestBranch::ASTestBranch() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestBranch::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestBranch::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.h new file mode 100644 index 0000000..2c1755a --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestBranch.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestBranch.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestBranch : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestBranch(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.cpp new file mode 100644 index 0000000..22d4aa4 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestForge.h" + + +// Sets default values +ASTestForge::ASTestForge() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestForge::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestForge::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.h new file mode 100644 index 0000000..21f2f0e --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestForge.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestForge.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestForge : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestForge(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.cpp new file mode 100644 index 0000000..a28db48 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestStorage.h" + + +// Sets default values +ASTestStorage::ASTestStorage() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestStorage::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestStorage::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.h new file mode 100644 index 0000000..fcf1463 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestStorage.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestStorage.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestStorage : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestStorage(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.cpp new file mode 100644 index 0000000..cc09e79 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.cpp @@ -0,0 +1,27 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "STestTree.h" + + +// Sets default values +ASTestTree::ASTestTree() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void ASTestTree::BeginPlay() +{ + Super::BeginPlay(); + +} + +// Called every frame +void ASTestTree::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.h new file mode 100644 index 0000000..1c0cb6c --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/STestTree.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "STestTree.generated.h" + +UCLASS() +class SPECTRAITEST_API ASTestTree : public AActor +{ + GENERATED_BODY() + +public: + // Sets default values for this actor's properties + ASTestTree(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + + +}; diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.cpp b/Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.cpp new file mode 100644 index 0000000..ebd2517 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "SpectrAITest.h" + +#define LOCTEXT_NAMESPACE "FSpectrAITestModule" + +void FSpectrAITestModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FSpectrAITestModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FSpectrAITestModule, SpectrAITest) \ No newline at end of file diff --git a/Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.h b/Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.h new file mode 100644 index 0000000..8f51c72 --- /dev/null +++ b/Plugins/SpectrAITest/Source/SpectrAITest/Public/SpectrAITest.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FSpectrAITestModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Plugins/TimeOfDay/Source/TimeOfDay/Private/TimeOfDay.cpp b/Plugins/TimeOfDay/Source/TimeOfDay/Private/TimeOfDay.cpp new file mode 100644 index 0000000..6db1c67 --- /dev/null +++ b/Plugins/TimeOfDay/Source/TimeOfDay/Private/TimeOfDay.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "TimeOfDay.h" + +#define LOCTEXT_NAMESPACE "FTimeOfDayModule" + +void FTimeOfDayModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FTimeOfDayModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FTimeOfDayModule, TimeOfDay) \ No newline at end of file diff --git a/Plugins/TimeOfDay/Source/TimeOfDay/Public/TimeOfDay.h b/Plugins/TimeOfDay/Source/TimeOfDay/Public/TimeOfDay.h new file mode 100644 index 0000000..1dc167f --- /dev/null +++ b/Plugins/TimeOfDay/Source/TimeOfDay/Public/TimeOfDay.h @@ -0,0 +1,15 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" + +class FTimeOfDayModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/TimeOfDay/Source/TimeOfDay/TimeOfDay.Build.cs b/Plugins/TimeOfDay/Source/TimeOfDay/TimeOfDay.Build.cs new file mode 100644 index 0000000..5e2f864 --- /dev/null +++ b/Plugins/TimeOfDay/Source/TimeOfDay/TimeOfDay.Build.cs @@ -0,0 +1,47 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class TimeOfDay : ModuleRules +{ + public TimeOfDay(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PrivateIncludePaths.AddRange( + new string[] { + "TimeOfDay/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/WeaponFramework/Source/WeaponFramework/Private/WeaponFramework.cpp b/Plugins/WeaponFramework/Source/WeaponFramework/Private/WeaponFramework.cpp new file mode 100644 index 0000000..a6f7d38 --- /dev/null +++ b/Plugins/WeaponFramework/Source/WeaponFramework/Private/WeaponFramework.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "WeaponFramework.h" + +#define LOCTEXT_NAMESPACE "FWeaponFrameworkModule" + +void FWeaponFrameworkModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FWeaponFrameworkModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FWeaponFrameworkModule, WeaponFramework) \ No newline at end of file diff --git a/Plugins/WeaponFramework/Source/WeaponFramework/Public/WeaponFramework.h b/Plugins/WeaponFramework/Source/WeaponFramework/Public/WeaponFramework.h new file mode 100644 index 0000000..50e98a9 --- /dev/null +++ b/Plugins/WeaponFramework/Source/WeaponFramework/Public/WeaponFramework.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FWeaponFrameworkModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Plugins/WeaponFramework/Source/WeaponFramework/WeaponFramework.Build.cs b/Plugins/WeaponFramework/Source/WeaponFramework/WeaponFramework.Build.cs new file mode 100644 index 0000000..27f87a3 --- /dev/null +++ b/Plugins/WeaponFramework/Source/WeaponFramework/WeaponFramework.Build.cs @@ -0,0 +1,48 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class WeaponFramework : ModuleRules +{ + public WeaponFramework(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PrivateIncludePaths.AddRange( + new string[] { + "WeaponFramework/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "AbilityFramework" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.cpp new file mode 100644 index 0000000..9bf851f --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.cpp @@ -0,0 +1,610 @@ +#include "WALandscapeGraphAssetEditor.h" +#include "WALandscapeGraphAssetEditorToolbar.h" +#include "WALandscapeGraphSchema.h" +#include "WALandscapeGraphEditorCommands.h" +#include "WALandscapeGraphEdGraph.h" +#include "AssetToolsModule.h" +#include "WALandscapeGraphAssetEditorToolbar.h" +#include "PropertyEditorModule.h" +#include "BlueprintEditorUtils.h" +#include "EdGraphUtilities.h" +#include "ScopedTransaction.h" +#include "PlatformApplicationMisc.h" +#include "WALandscapeGraph.h" +#include "WALandscapeGraphEdNode_Output.h" + +#define LOCTEXT_NAMESPACE "GenericGraphAssetEditor" + +const FName GenericGraphEditorAppName = FName(TEXT("LandscapeGraphEditor")); + +struct FWALandscapeGraphAssetEditorTabs +{ + // Tab identifiers + static const FName DetailsID; + static const FName ViewportID; +}; + +////////////////////////////////////////////////////////////////////////// + +const FName FWALandscapeGraphAssetEditorTabs::DetailsID(TEXT("Details")); +const FName FWALandscapeGraphAssetEditorTabs::ViewportID(TEXT("Viewport")); + +////////////////////////////////////////////////////////////////////////// + +FWALandscapeGraphAssetEditor::FWALandscapeGraphAssetEditor() +{ + EditingGraph = nullptr; + + OnPackageSavedDelegateHandle = UPackage::PackageSavedEvent.AddRaw(this, &FWALandscapeGraphAssetEditor::OnPackageSaved); +} + +FWALandscapeGraphAssetEditor::~FWALandscapeGraphAssetEditor() +{ + UPackage::PackageSavedEvent.Remove(OnPackageSavedDelegateHandle); +} + +void FWALandscapeGraphAssetEditor::InitGenericGraphAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, UWALandscapeGraph* Graph) +{ + EditingGraph = Graph; + CreateEdGraph(); + + FGenericCommands::Register(); + FGraphEditorCommands::Register(); + FWALandscapeGraphEditorCommands::Register(); + + if (!ToolbarBuilder.IsValid()) + { + ToolbarBuilder = MakeShareable(new FWALandscapeGraphAssetEditorToolbar(SharedThis(this))); + } + + BindCommands(); + + CreateInternalWidgets(); + + TSharedPtr ToolbarExtender = MakeShareable(new FExtender); + + ToolbarBuilder->AddGenericGraphToolbar(ToolbarExtender); + + // Layout + const TSharedRef StandaloneDefaultLayout = FTabManager::NewLayout("Standalone_GenericGraphEditor_Layout_v1") + ->AddArea + ( + FTabManager::NewPrimaryArea()->SetOrientation(Orient_Vertical) + ->Split + ( + FTabManager::NewStack() + ->SetSizeCoefficient(0.1f) + ->AddTab(GetToolbarTabId(), ETabState::OpenedTab)->SetHideTabWell(true) + ) + ->Split + ( + FTabManager::NewSplitter()->SetOrientation(Orient_Horizontal)->SetSizeCoefficient(0.9f) + ->Split + ( + FTabManager::NewStack() + ->SetSizeCoefficient(0.225f) + ->AddTab(FWALandscapeGraphAssetEditorTabs::ViewportID, ETabState::OpenedTab) + ) + ->Split + ( + FTabManager::NewStack() + ->SetSizeCoefficient(0.65f) + ->AddTab(FWALandscapeGraphAssetEditorTabs::DetailsID, ETabState::OpenedTab)->SetHideTabWell(true) + ) + ) + ); + + const bool bCreateDefaultStandaloneMenu = true; + const bool bCreateDefaultToolbar = true; + FAssetEditorToolkit::InitAssetEditor(Mode, InitToolkitHost, GenericGraphEditorAppName, StandaloneDefaultLayout, bCreateDefaultStandaloneMenu, bCreateDefaultToolbar, EditingGraph, false); + + RegenerateMenusAndToolbars(); +} + +void FWALandscapeGraphAssetEditor::RegisterTabSpawners(const TSharedRef& InTabManager) +{ + WorkspaceMenuCategory = InTabManager->AddLocalWorkspaceMenuCategory(LOCTEXT("WorkspaceMenu_SoundCueEditor", "Sound Cue Editor")); + auto WorkspaceMenuCategoryRef = WorkspaceMenuCategory.ToSharedRef(); + + FAssetEditorToolkit::RegisterTabSpawners(InTabManager); + + InTabManager->RegisterTabSpawner(FWALandscapeGraphAssetEditorTabs::ViewportID, FOnSpawnTab::CreateSP(this, &FWALandscapeGraphAssetEditor::SpawnTab_Viewport)) + .SetDisplayName(LOCTEXT("GraphCanvasTab", "Viewport")) + .SetGroup(WorkspaceMenuCategoryRef) + .SetIcon(FSlateIcon(FEditorStyle::GetStyleSetName(), "GraphEditor.EventGraph_16x")); + + InTabManager->RegisterTabSpawner(FWALandscapeGraphAssetEditorTabs::DetailsID, FOnSpawnTab::CreateSP(this, &FWALandscapeGraphAssetEditor::SpawnTab_Details)) + .SetDisplayName(LOCTEXT("DetailsTab", "Details")) + .SetGroup(WorkspaceMenuCategoryRef) + .SetIcon(FSlateIcon(FEditorStyle::GetStyleSetName(), "LevelEditor.Tabs.Details")); +} + +void FWALandscapeGraphAssetEditor::UnregisterTabSpawners(const TSharedRef& InTabManager) +{ + FAssetEditorToolkit::UnregisterTabSpawners(InTabManager); + + InTabManager->UnregisterTabSpawner(FWALandscapeGraphAssetEditorTabs::ViewportID); + InTabManager->UnregisterTabSpawner(FWALandscapeGraphAssetEditorTabs::DetailsID); +} + +FName FWALandscapeGraphAssetEditor::GetToolkitFName() const +{ + return FName("FGenericGraphEditor"); +} + +FText FWALandscapeGraphAssetEditor::GetBaseToolkitName() const +{ + return LOCTEXT("GenericGraphEditorAppLabel", "Generic Graph Editor"); +} + +FText FWALandscapeGraphAssetEditor::GetToolkitName() const +{ + const bool bDirtyState = EditingGraph->GetOutermost()->IsDirty(); + + FFormatNamedArguments Args; + Args.Add(TEXT("GenericGraphName"), FText::FromString(EditingGraph->GetName())); + Args.Add(TEXT("DirtyState"), bDirtyState ? FText::FromString(TEXT("*")) : FText::GetEmpty()); + return FText::Format(LOCTEXT("GenericGraphEditorToolkitName", "{GenericGraphName}{DirtyState}"), Args); +} + +FText FWALandscapeGraphAssetEditor::GetToolkitToolTipText() const +{ + return FAssetEditorToolkit::GetToolTipTextForObject(EditingGraph); +} + +FLinearColor FWALandscapeGraphAssetEditor::GetWorldCentricTabColorScale() const +{ + return FLinearColor::White; +} + +FString FWALandscapeGraphAssetEditor::GetWorldCentricTabPrefix() const +{ + return TEXT("GenericGraphEditor"); +} + +FString FWALandscapeGraphAssetEditor::GetDocumentationLink() const +{ + return TEXT(""); +} + +void FWALandscapeGraphAssetEditor::SaveAsset_Execute() +{ + if (EditingGraph != nullptr) + { + RebuildGenericGraph(); + } + + FAssetEditorToolkit::SaveAsset_Execute(); +} + +void FWALandscapeGraphAssetEditor::AddReferencedObjects(FReferenceCollector& Collector) +{ + Collector.AddReferencedObject(EditingGraph); + Collector.AddReferencedObject(EditingGraph->EdGraph); +} + +TSharedRef FWALandscapeGraphAssetEditor::SpawnTab_Viewport(const FSpawnTabArgs& Args) +{ + check(Args.GetTabId() == FWALandscapeGraphAssetEditorTabs::ViewportID); + + TSharedRef SpawnedTab = SNew(SDockTab) + .Label(FText::FromString("Viewport")); + + if (ViewportWidget.IsValid()) + { + SpawnedTab->SetContent(ViewportWidget.ToSharedRef()); + } + + return SpawnedTab; +} + +TSharedRef FWALandscapeGraphAssetEditor::SpawnTab_Details(const FSpawnTabArgs& Args) +{ + check(Args.GetTabId() == FWALandscapeGraphAssetEditorTabs::DetailsID); + + return SNew(SDockTab) + .Icon(FEditorStyle::GetBrush("LevelEditor.Tabs.Details")) + .Label(FText::FromString("Details")) + [ + PropertyWidget.ToSharedRef() + ]; +} + +void FWALandscapeGraphAssetEditor::CreateInternalWidgets() +{ + ViewportWidget = CreateViewportWidget(); + + FDetailsViewArgs Args; + Args.bHideSelectionTip = true; + Args.NotifyHook = this; + + FPropertyEditorModule& PropertyModule = FModuleManager::LoadModuleChecked("PropertyEditor"); + PropertyWidget = PropertyModule.CreateDetailView(Args); + PropertyWidget->SetObject(EditingGraph); + + //PropertyWidget->SetIsPropertyEditingEnabledDelegate(FIsPropertyEditingEnabled::CreateSP(this, &FWALandscapeGraphAssetEditor::IsPropertyEditable)); + PropertyWidget->OnFinishedChangingProperties().AddSP(this, &FWALandscapeGraphAssetEditor::OnFinishedChangingProperties); +} + +TSharedRef FWALandscapeGraphAssetEditor::CreateViewportWidget() +{ + FGraphAppearanceInfo AppearanceInfo; + AppearanceInfo.CornerText = FText::FromString("Landscape Graph"); + + CreateCommandList(); + + SGraphEditor::FGraphEditorEvents InEvents; + InEvents.OnSelectionChanged = SGraphEditor::FOnSelectionChanged::CreateSP(this, &FWALandscapeGraphAssetEditor::OnSelectedNodesChanged); + InEvents.OnNodeDoubleClicked = FSingleNodeEvent::CreateSP(this, &FWALandscapeGraphAssetEditor::OnNodeDoubleClicked); + + return SNew(SGraphEditor) + .AdditionalCommands(GraphEditorCommands) + .IsEditable(true) + .Appearance(AppearanceInfo) + .GraphToEdit(EditingGraph->EdGraph) + .GraphEvents(InEvents) + .AutoExpandActionMenu(true) + .ShowGraphStateOverlay(false); +} + + +void FWALandscapeGraphAssetEditor::BindCommands() +{ + ToolkitCommands->MapAction(FWALandscapeGraphEditorCommands::Get().GraphSettings, + FExecuteAction::CreateSP(this, &FWALandscapeGraphAssetEditor::GraphSettings), + FCanExecuteAction::CreateSP(this, &FWALandscapeGraphAssetEditor::CanGraphSettings) + ); + ToolkitCommands->MapAction(FWALandscapeGraphEditorCommands::Get().GenerateLandscape, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::GenerateLandscape)); +} + +void FWALandscapeGraphAssetEditor::CreateEdGraph() +{ + if (EditingGraph->EdGraph == nullptr) + { + EditingGraph->EdGraph = CastChecked(FBlueprintEditorUtils::CreateNewGraph(EditingGraph, NAME_None, UWALandscapeGraphEdGraph::StaticClass(), UWALandscapeGraphSchema::StaticClass())); + EditingGraph->EdGraph->bAllowDeletion = false; + + // Give the schema a chance to fill out any required nodes (like the results node) + const UEdGraphSchema* Schema = EditingGraph->EdGraph->GetSchema(); + Schema->CreateDefaultNodesForGraph(*EditingGraph->EdGraph); + + EditingGraph->Schema = Cast(const_cast(Schema)); + } +} + +void FWALandscapeGraphAssetEditor::CreateCommandList() +{ + if (GraphEditorCommands.IsValid()) + { + return; + } + + GraphEditorCommands = MakeShareable(new FUICommandList); + + // Can't use CreateSP here because derived editor are already implementing TSharedFromThis + // however it should be safe, since commands are being used only within this editor + // if it ever crashes, this function will have to go away and be reimplemented in each derived class + + GraphEditorCommands->MapAction(FWALandscapeGraphEditorCommands::Get().GraphSettings, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::GraphSettings), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanGraphSettings)); + + GraphEditorCommands->MapAction(FWALandscapeGraphEditorCommands::Get().GenerateLandscape, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::GenerateLandscape)); + + GraphEditorCommands->MapAction(FGenericCommands::Get().SelectAll, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::SelectAllNodes), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanSelectAllNodes) + ); + + GraphEditorCommands->MapAction(FGenericCommands::Get().Delete, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::DeleteSelectedNodes), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanDeleteNodes) + ); + + GraphEditorCommands->MapAction(FGenericCommands::Get().Copy, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CopySelectedNodes), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanCopyNodes) + ); + + GraphEditorCommands->MapAction(FGenericCommands::Get().Cut, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CutSelectedNodes), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanCutNodes) + ); + + GraphEditorCommands->MapAction(FGenericCommands::Get().Paste, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::PasteNodes), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanPasteNodes) + ); + + GraphEditorCommands->MapAction(FGenericCommands::Get().Duplicate, + FExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::DuplicateNodes), + FCanExecuteAction::CreateRaw(this, &FWALandscapeGraphAssetEditor::CanDuplicateNodes) + ); +} + +TSharedPtr FWALandscapeGraphAssetEditor::GetCurrGraphEditor() +{ + return ViewportWidget; +} + +FGraphPanelSelectionSet FWALandscapeGraphAssetEditor::GetSelectedNodes() +{ + FGraphPanelSelectionSet CurrentSelection; + TSharedPtr FocusedGraphEd = GetCurrGraphEditor(); + if (FocusedGraphEd.IsValid()) + { + CurrentSelection = FocusedGraphEd->GetSelectedNodes(); + } + + return CurrentSelection; +} + +void FWALandscapeGraphAssetEditor::RebuildGenericGraph() +{ + if (EditingGraph == nullptr) + { + //LOG_WARNING(TEXT("FWALandscapeGraphAssetEditor::RebuildGenericGraph EditingGraph is nullptr")); + return; + } + + UWALandscapeGraphEdGraph* EdGraph = Cast(EditingGraph->EdGraph); + check(EdGraph != nullptr); + + EdGraph->RebuildGenericGraph(); +} + +void FWALandscapeGraphAssetEditor::SelectAllNodes() +{ + TSharedPtr CurrentGraphEditor = GetCurrGraphEditor(); + if (CurrentGraphEditor.IsValid()) + { + CurrentGraphEditor->SelectAllNodes(); + } +} + +bool FWALandscapeGraphAssetEditor::CanSelectAllNodes() +{ + return true; +} + +void FWALandscapeGraphAssetEditor::DeleteSelectedNodes() +{ + TSharedPtr CurrentGraphEditor = GetCurrGraphEditor(); + if (!CurrentGraphEditor.IsValid()) + { + return; + } + + const FScopedTransaction Transaction(FGenericCommands::Get().Delete->GetDescription()); + CurrentGraphEditor->GetCurrentGraph()->Modify(); + + const FGraphPanelSelectionSet SelectedNodes = CurrentGraphEditor->GetSelectedNodes(); + CurrentGraphEditor->ClearSelectionSet(); + + for (FGraphPanelSelectionSet::TConstIterator NodeIt(SelectedNodes); NodeIt; ++NodeIt) + { + if (UEdGraphNode* Node = Cast(*NodeIt)) + { + if (Node->CanUserDeleteNode()) + { + Node->Modify(); + Node->DestroyNode(); + } + } + } + + //LOG_WARNING(TEXT("FWALandscapeGraphAssetEditor::DeleteSelectedNodes Exec")); +} + +bool FWALandscapeGraphAssetEditor::CanDeleteNodes() +{ + // If any of the nodes can be deleted then we should allow deleting + const FGraphPanelSelectionSet SelectedNodes = GetSelectedNodes(); + for (FGraphPanelSelectionSet::TConstIterator SelectedIter(SelectedNodes); SelectedIter; ++SelectedIter) + { + UEdGraphNode* Node = Cast(*SelectedIter); + if (Node != nullptr && Node->CanUserDeleteNode()) + { + return true; + } + } + + //LOG_WARNING(TEXT("FWALandscapeGraphAssetEditor::CanDeleteNodes Can't delete")); + + return false; +} + +void FWALandscapeGraphAssetEditor::DeleteSelectedDuplicatableNodes() +{ + TSharedPtr CurrentGraphEditor = GetCurrGraphEditor(); + if (!CurrentGraphEditor.IsValid()) + { + return; + } + + const FGraphPanelSelectionSet OldSelectedNodes = CurrentGraphEditor->GetSelectedNodes(); + CurrentGraphEditor->ClearSelectionSet(); + + for (FGraphPanelSelectionSet::TConstIterator SelectedIter(OldSelectedNodes); SelectedIter; ++SelectedIter) + { + UEdGraphNode* Node = Cast(*SelectedIter); + if (Node && Node->CanDuplicateNode()) + { + CurrentGraphEditor->SetNodeSelection(Node, true); + } + } + + // Delete the duplicatable nodes + DeleteSelectedNodes(); + + CurrentGraphEditor->ClearSelectionSet(); + + for (FGraphPanelSelectionSet::TConstIterator SelectedIter(OldSelectedNodes); SelectedIter; ++SelectedIter) + { + if (UEdGraphNode* Node = Cast(*SelectedIter)) + { + CurrentGraphEditor->SetNodeSelection(Node, true); + } + } +} + +void FWALandscapeGraphAssetEditor::CutSelectedNodes() +{ + CopySelectedNodes(); + DeleteSelectedDuplicatableNodes(); +} + +bool FWALandscapeGraphAssetEditor::CanCutNodes() +{ + return CanCopyNodes() && CanDeleteNodes(); +} + +void FWALandscapeGraphAssetEditor::CopySelectedNodes() +{ + // Export the selected nodes and place the text on the clipboard + FGraphPanelSelectionSet SelectedNodes = GetSelectedNodes(); + + FString ExportedText; + + for (FGraphPanelSelectionSet::TIterator SelectedIter(SelectedNodes); SelectedIter; ++SelectedIter) + { + UEdGraphNode* Node = Cast(*SelectedIter); + if (Node == nullptr) + { + SelectedIter.RemoveCurrent(); + continue; + } + + Node->PrepareForCopying(); + } + + FEdGraphUtilities::ExportNodesToText(SelectedNodes, ExportedText); + FPlatformApplicationMisc::ClipboardCopy(*ExportedText); +} + +bool FWALandscapeGraphAssetEditor::CanCopyNodes() +{ + // If any of the nodes can be duplicated then we should allow copying + const FGraphPanelSelectionSet SelectedNodes = GetSelectedNodes(); + for (FGraphPanelSelectionSet::TConstIterator SelectedIter(SelectedNodes); SelectedIter; ++SelectedIter) + { + UEdGraphNode* Node = Cast(*SelectedIter); + if (Node && Node->CanDuplicateNode()) + { + return true; + } + } + + return false; +} + +void FWALandscapeGraphAssetEditor::PasteNodes() +{ + TSharedPtr CurrentGraphEditor = GetCurrGraphEditor(); + if (CurrentGraphEditor.IsValid()) + { + PasteNodesHere(CurrentGraphEditor->GetPasteLocation()); + } +} + +void FWALandscapeGraphAssetEditor::PasteNodesHere(const FVector2D& Location) +{ +} + +bool FWALandscapeGraphAssetEditor::CanPasteNodes() +{ + return false; +} + +void FWALandscapeGraphAssetEditor::DuplicateNodes() +{ + CopySelectedNodes(); + PasteNodes(); +} + +bool FWALandscapeGraphAssetEditor::CanDuplicateNodes() +{ + //return CanCopyNodes(); + return false; +} + +void FWALandscapeGraphAssetEditor::GraphSettings() +{ + PropertyWidget->SetObject(EditingGraph); + if (EditingGraph->LandscapeOutput) + { + EditingGraph->LandscapeOutput->GenerateHeightmap(); + } + //LOG_WARNING(TEXT("FWALandscapeGraphAssetEditor::GraphSettings")); +} + +void FWALandscapeGraphAssetEditor::GenerateLandscape() +{ + + if (const UWALandscapeGraphSchema* Schema = Cast(EditingGraph->EdGraph->GetSchema())) + { + TArray out; + Schema->Output->GenerateHeightMap(out); + } + //LOG_WARNING(TEXT("FWALandscapeGraphAssetEditor::GraphSettings")); +} + +bool FWALandscapeGraphAssetEditor::CanGraphSettings() const +{ + return true; +} + +void FWALandscapeGraphAssetEditor::OnSelectedNodesChanged(const TSet& NewSelection) +{ + TArray Selection; + + for (UObject* SelectionEntry : NewSelection) + { + Selection.Add(SelectionEntry); + } + + if (Selection.Num() == 0) + { + PropertyWidget->SetObject(EditingGraph); + + } + else if (Selection.Num() == 1) + { + PropertyWidget->SetObject(Selection[0]); + } + else + { + PropertyWidget->SetObject(nullptr); + } +} + +void FWALandscapeGraphAssetEditor::OnNodeDoubleClicked(UEdGraphNode* Node) +{ + +} + +void FWALandscapeGraphAssetEditor::OnFinishedChangingProperties(const FPropertyChangedEvent& PropertyChangedEvent) +{ + if (EditingGraph == nullptr) + return; + + RebuildGenericGraph(); + + EditingGraph->EdGraph->GetSchema()->ForceVisualizationCacheClear(); +} + +void FWALandscapeGraphAssetEditor::OnPackageSaved(const FString& PackageFileName, UObject* Outer) +{ + RebuildGenericGraph(); +} + +void FWALandscapeGraphAssetEditor::RegisterToolbarTab(const TSharedRef& InTabManager) +{ + FAssetEditorToolkit::RegisterTabSpawners(InTabManager); +} + + +#undef LOCTEXT_NAMESPACE + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.h new file mode 100644 index 0000000..9f43eb3 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditor.h @@ -0,0 +1,116 @@ +#pragma once +#include "WALandscapeGraphEditorCommands.h" + +#include "GenericCommands.h" +#include "SDockTab.h" +#include "GraphEditor.h" +#include "GraphEditorActions.h" +#include "AssetEditorToolkit.h" +#include "WALandscapeGraph.h" +#include "WALandscapeNode.h" +#include "Misc/NotifyHook.h" +#include "IDetailsView.h" +class FWALandscapeGraphAssetEditorToolbar; + +class FWALandscapeGraphAssetEditor : public FAssetEditorToolkit, public FNotifyHook, public FGCObject +{ +public: + FWALandscapeGraphAssetEditor(); + virtual ~FWALandscapeGraphAssetEditor(); + + void InitGenericGraphAssetEditor(const EToolkitMode::Type Mode, const TSharedPtr< IToolkitHost >& InitToolkitHost, UWALandscapeGraph* Graph); + + // IToolkit interface + virtual void RegisterTabSpawners(const TSharedRef& TabManager) override; + virtual void UnregisterTabSpawners(const TSharedRef& TabManager) override; + // End of IToolkit interface + + // FAssetEditorToolkit + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual FText GetToolkitName() const override; + virtual FText GetToolkitToolTipText() const override; + virtual FLinearColor GetWorldCentricTabColorScale() const override; + virtual FString GetWorldCentricTabPrefix() const override; + virtual FString GetDocumentationLink() const override; + virtual void SaveAsset_Execute() override; + // End of FAssetEditorToolkit + + //Toolbar + void UpdateToolbar(); + TSharedPtr GetToolbarBuilder() { return ToolbarBuilder; } + void RegisterToolbarTab(const TSharedRef& TabManager); + + + // FSerializableObject interface + virtual void AddReferencedObjects(FReferenceCollector& Collector) override; + // End of FSerializableObject interface + +private: + TSharedRef SpawnTab_Viewport(const FSpawnTabArgs& Args); + TSharedRef SpawnTab_Details(const FSpawnTabArgs& Args); + + void CreateInternalWidgets(); + TSharedRef CreateViewportWidget(); + + + void BindCommands(); + + void CreateEdGraph(); + + void CreateCommandList(); + + TSharedPtr GetCurrGraphEditor(); + + FGraphPanelSelectionSet GetSelectedNodes(); + + void RebuildGenericGraph(); + + // Delegates for graph editor commands + void SelectAllNodes(); + bool CanSelectAllNodes(); + void DeleteSelectedNodes(); + bool CanDeleteNodes(); + void DeleteSelectedDuplicatableNodes(); + void CutSelectedNodes(); + bool CanCutNodes(); + void CopySelectedNodes(); + bool CanCopyNodes(); + void PasteNodes(); + void PasteNodesHere(const FVector2D& Location); + bool CanPasteNodes(); + void DuplicateNodes(); + bool CanDuplicateNodes(); + + void GraphSettings(); + void GenerateLandscape(); + bool CanGraphSettings() const; + + ////////////////////////////////////////////////////////////////////////// + // graph editor event + void OnSelectedNodesChanged(const TSet& NewSelection); + + void OnNodeDoubleClicked(UEdGraphNode* Node); + + void OnFinishedChangingProperties(const FPropertyChangedEvent& PropertyChangedEvent); + + void OnPackageSaved(const FString& PackageFileName, UObject* Outer); + + +private: + UWALandscapeGraph* EditingGraph; + + //Toolbar + TSharedPtr ToolbarBuilder; + + /** Handle to the registered OnPackageSave delegate */ + FDelegateHandle OnPackageSavedDelegateHandle; + + TSharedPtr ViewportWidget; + TSharedPtr PropertyWidget; + + /** The command list for this editor */ + TSharedPtr GraphEditorCommands; +}; + + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.cpp new file mode 100644 index 0000000..dd919df --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.cpp @@ -0,0 +1,51 @@ +#include "WALandscapeGraphAssetEditorToolbar.h" +#include "WALandscapeGraphAssetEditor.h" +#include "WALandscapeGraphEditorCommands.h" +#include "MultiBoxBuilder.h" + +#define LOCTEXT_NAMESPACE "GenericGraphAssetEditorToolbar" + +void FWALandscapeGraphAssetEditorToolbar::AddGenericGraphToolbar(TSharedPtr Extender) +{ + check(GenericGraphEditor.IsValid()); + TSharedPtr GenericGraphEditorPtr = GenericGraphEditor.Pin(); + + TSharedPtr ToolbarExtender = MakeShareable(new FExtender); + ToolbarExtender->AddToolBarExtension("Asset", EExtensionHook::After, GenericGraphEditorPtr->GetToolkitCommands(), FToolBarExtensionDelegate::CreateSP( this, &FWALandscapeGraphAssetEditorToolbar::FillGenericGraphToolbar )); + GenericGraphEditorPtr->AddToolbarExtender(ToolbarExtender); +} + +void FWALandscapeGraphAssetEditorToolbar::FillGenericGraphToolbar(FToolBarBuilder& ToolbarBuilder) +{ + check(GenericGraphEditor.IsValid()); + TSharedPtr GenericGraphEditorPtr = GenericGraphEditor.Pin(); + + ToolbarBuilder.BeginSection("Landscape Graph"); + { + { + const FText GraphSettingsLabel = LOCTEXT("GraphSettings_Label", "Graph Settings"); + const FText GraphSettingsTip = LOCTEXT("GraphSettings_ToolTip", "Show the Graph Settings"); + const FSlateIcon GraphSettingsIcon = FSlateIcon(FEditorStyle::GetStyleSetName(), "LevelEditor.GameSettings"); + ToolbarBuilder.AddToolBarButton(FWALandscapeGraphEditorCommands::Get().GraphSettings, + NAME_None, + GraphSettingsLabel, + GraphSettingsTip, + GraphSettingsIcon); + } + { + const FText GraphSettingsLabel = LOCTEXT("GraphSettings_Label", "Generate Landscape"); + const FText GraphSettingsTip = LOCTEXT("GraphSettings_ToolTip", "enerate LAndscape from Current graph"); + const FSlateIcon GraphSettingsIcon = FSlateIcon(FEditorStyle::GetStyleSetName(), "LevelEditor.GameSettings"); + ToolbarBuilder.AddToolBarButton(FWALandscapeGraphEditorCommands::Get().GenerateLandscape, + NAME_None, + GraphSettingsLabel, + GraphSettingsTip, + GraphSettingsIcon); + } + } + ToolbarBuilder.EndSection(); + +} + + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.h new file mode 100644 index 0000000..970caf7 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphAssetEditorToolbar.h @@ -0,0 +1,28 @@ + +#pragma once + +#include "CoreMinimal.h" + +class FWALandscapeGraphAssetEditor; +class FExtender; +class FToolBarBuilder; + +class FWALandscapeGraphAssetEditorToolbar : public TSharedFromThis +{ +public: + FWALandscapeGraphAssetEditorToolbar(TSharedPtr InGenericGraphEditor) + : GenericGraphEditor(InGenericGraphEditor) {} + + //void AddModesToolbar(TSharedPtr Extender); + //void AddDebuggerToolbar(TSharedPtr Extender); + void AddGenericGraphToolbar(TSharedPtr Extender); + +private: + //void FillModesToolbar(FToolBarBuilder& ToolbarBuilder); + //void FillDebuggerToolbar(FToolBarBuilder& ToolbarBuilder); + void FillGenericGraphToolbar(FToolBarBuilder& ToolbarBuilder); + +protected: + /** Pointer back to the blueprint editor tool that owns us */ + TWeakPtr GenericGraphEditor; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphColors.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphColors.h new file mode 100644 index 0000000..805f26e --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphColors.h @@ -0,0 +1,43 @@ +#pragma once + +namespace WALandscapeGraphColors +{ + namespace NodeBody + { + const FLinearColor Default(0.1f, 0.1f, 0.1f); + const FLinearColor Root(0.5f, 0.5f, 0.5f, 0.1f); + const FLinearColor Error(1.0f, 0.0f, 0.0f); + } + + namespace NodeBorder + { + const FLinearColor Inactive(0.08f, 0.08f, 0.08f); + const FLinearColor Root(0.2f, 0.2f, 0.2f, 0.2f); + const FLinearColor Selected(1.00f, 0.08f, 0.08f); + const FLinearColor ActiveDebugging(1.0f, 1.0f, 0.0f); + const FLinearColor InactiveDebugging(0.4f, 0.4f, 0.0f); + const FLinearColor HighlightAbortRange0(0.0f, 0.22f, 0.4f); + const FLinearColor HighlightAbortRange1(0.0f, 0.4f, 0.22f); + const FLinearColor Disconnected(0.f, 0.f, 0.f); + const FLinearColor BrokenWithParent(1.f, 0.f, 1.f); + const FLinearColor QuickFind(0.f, 0.8f, 0.f); + } + + namespace Pin + { + const FLinearColor Diff(0.9f, 0.2f, 0.15f); + const FLinearColor Hover(1.0f, 0.7f, 0.0f); + const FLinearColor Default(0.02f, 0.02f, 0.02f); + const FLinearColor SingleNode(0.02f, 0.02f, 0.02f); + } + + namespace Connection + { + const FLinearColor Default(1.0f, 1.0f, 1.0f); + } + + namespace Action + { + const FLinearColor DragMarker(1.0f, 1.0f, 0.2f); + } +} diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.cpp new file mode 100644 index 0000000..bad80ff --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.cpp @@ -0,0 +1,117 @@ +#include "WALandscapeGraphConnectionDrawingPolicy.h" + +FWALandscapeGraphConnectionDrawingPolicy::FWALandscapeGraphConnectionDrawingPolicy(int32 InBackLayerID, int32 InFrontLayerID, float ZoomFactor, const FSlateRect& InClippingRect, FSlateWindowElementList& InDrawElements, UEdGraph* InGraphObj) + : FConnectionDrawingPolicy(InBackLayerID, InFrontLayerID, ZoomFactor, InClippingRect, InDrawElements) + , GraphObj(InGraphObj) +{ +} + +void FWALandscapeGraphConnectionDrawingPolicy::DetermineWiringStyle(UEdGraphPin* OutputPin, UEdGraphPin* InputPin, /*inout*/ FConnectionParams& Params) +{ + Params.AssociatedPin1 = OutputPin; + Params.AssociatedPin2 = InputPin; + Params.WireThickness = 1.5f; + + const bool bDeemphasizeUnhoveredPins = HoveredPins.Num() > 0; + if (bDeemphasizeUnhoveredPins) + { + ApplyHoverDeemphasis(OutputPin, InputPin, /*inout*/ Params.WireThickness, /*inout*/ Params.WireColor); + } +} + +void FWALandscapeGraphConnectionDrawingPolicy::Draw(TMap, FArrangedWidget>& InPinGeometries, FArrangedChildren& ArrangedNodes) +{ + // Build an acceleration structure to quickly find geometry for the nodes + NodeWidgetMap.Empty(); + for (int32 NodeIndex = 0; NodeIndex < ArrangedNodes.Num(); ++NodeIndex) + { + FArrangedWidget& CurWidget = ArrangedNodes[NodeIndex]; + TSharedRef ChildNode = StaticCastSharedRef(CurWidget.Widget); + NodeWidgetMap.Add(ChildNode->GetNodeObj(), NodeIndex); + } + + // Now draw + FConnectionDrawingPolicy::Draw(InPinGeometries, ArrangedNodes); +} + +void FWALandscapeGraphConnectionDrawingPolicy::DrawPreviewConnector(const FGeometry& PinGeometry, const FVector2D& StartPoint, const FVector2D& EndPoint, UEdGraphPin* Pin) +{ + FConnectionParams Params; + DetermineWiringStyle(Pin, nullptr, /*inout*/ Params); + + if (Pin->Direction == EEdGraphPinDirection::EGPD_Output) + { + DrawSplineWithArrow(FGeometryHelper::FindClosestPointOnGeom(PinGeometry, EndPoint), EndPoint, Params); + } + else + { + DrawSplineWithArrow(FGeometryHelper::FindClosestPointOnGeom(PinGeometry, StartPoint), StartPoint, Params); + } +} + +void FWALandscapeGraphConnectionDrawingPolicy::DrawSplineWithArrow(const FVector2D& StartAnchorPoint, const FVector2D& EndAnchorPoint, const FConnectionParams& Params) +{ + // bUserFlag1 indicates that we need to reverse the direction of connection (used by debugger) + const FVector2D& P0 = Params.bUserFlag1 ? EndAnchorPoint : StartAnchorPoint; + const FVector2D& P1 = Params.bUserFlag1 ? StartAnchorPoint : EndAnchorPoint; + + Internal_DrawLineWithArrow(P0, P1, Params); +} + +void FWALandscapeGraphConnectionDrawingPolicy::Internal_DrawLineWithArrow(const FVector2D& StartAnchorPoint, const FVector2D& EndAnchorPoint, const FConnectionParams& Params) +{ + //@TODO: Should this be scaled by zoom factor? + const float LineSeparationAmount = 4.5f; + + const FVector2D DeltaPos = EndAnchorPoint - StartAnchorPoint; + const FVector2D UnitDelta = DeltaPos.GetSafeNormal(); + const FVector2D Normal = FVector2D(DeltaPos.Y, -DeltaPos.X).GetSafeNormal(); + + // Come up with the final start/end points + const FVector2D DirectionBias = Normal * LineSeparationAmount; + const FVector2D LengthBias = ArrowRadius.X * UnitDelta; + const FVector2D StartPoint = StartAnchorPoint + DirectionBias + LengthBias; + const FVector2D EndPoint = EndAnchorPoint + DirectionBias - LengthBias; + + // Draw a line/spline + DrawConnection(WireLayerID, StartPoint, EndPoint, Params); + + // Draw the arrow + const FVector2D ArrowDrawPos = EndPoint - ArrowRadius; + const float AngleInRadians = FMath::Atan2(DeltaPos.Y, DeltaPos.X); + + FSlateDrawElement::MakeRotatedBox( + DrawElementsList, + ArrowLayerID, + FPaintGeometry(ArrowDrawPos, ArrowImage->ImageSize * ZoomFactor, ZoomFactor), + ArrowImage, + ESlateDrawEffect::None, + AngleInRadians, + TOptional(), + FSlateDrawElement::RelativeToElement, + Params.WireColor + ); +} + +void FWALandscapeGraphConnectionDrawingPolicy::DrawSplineWithArrow(const FGeometry& StartGeom, const FGeometry& EndGeom, const FConnectionParams& Params) +{ + // Get a reasonable seed point (halfway between the boxes) + const FVector2D StartCenter = FGeometryHelper::CenterOf(StartGeom); + const FVector2D EndCenter = FGeometryHelper::CenterOf(EndGeom); + const FVector2D SeedPoint = (StartCenter + EndCenter) * 0.5f; + + // Find the (approximate) closest points between the two boxes + const FVector2D StartAnchorPoint = FGeometryHelper::FindClosestPointOnGeom(StartGeom, SeedPoint); + const FVector2D EndAnchorPoint = FGeometryHelper::FindClosestPointOnGeom(EndGeom, SeedPoint); + + DrawSplineWithArrow(StartAnchorPoint, EndAnchorPoint, Params); +} + +FVector2D FWALandscapeGraphConnectionDrawingPolicy::ComputeSplineTangent(const FVector2D& Start, const FVector2D& End) const +{ + const FVector2D Delta = End - Start; + const FVector2D NormDelta = Delta.GetSafeNormal(); + + return NormDelta; +} + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.h new file mode 100644 index 0000000..16a62be --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphConnectionDrawingPolicy.h @@ -0,0 +1,25 @@ +#pragma once + +#include "ConnectionDrawingPolicy.h" + +class FWALandscapeGraphConnectionDrawingPolicy : public FConnectionDrawingPolicy +{ +protected: + UEdGraph* GraphObj; + TMap NodeWidgetMap; + +public: + FWALandscapeGraphConnectionDrawingPolicy(int32 InBackLayerID, int32 InFrontLayerID, float ZoomFactor, const FSlateRect& InClippingRect, FSlateWindowElementList& InDrawElements, UEdGraph* InGraphObj); + + // FConnectionDrawingPolicy interface + virtual void DetermineWiringStyle(UEdGraphPin* OutputPin, UEdGraphPin* InputPin, /*inout*/ FConnectionParams& Params) override; + virtual void Draw(TMap, FArrangedWidget>& PinGeometries, FArrangedChildren& ArrangedNodes) override; + virtual void DrawSplineWithArrow(const FGeometry& StartGeom, const FGeometry& EndGeom, const FConnectionParams& Params) override; + virtual void DrawSplineWithArrow(const FVector2D& StartPoint, const FVector2D& EndPoint, const FConnectionParams& Params) override; + virtual void DrawPreviewConnector(const FGeometry& PinGeometry, const FVector2D& StartPoint, const FVector2D& EndPoint, UEdGraphPin* Pin) override; + virtual FVector2D ComputeSplineTangent(const FVector2D& Start, const FVector2D& End) const override; + // End of FConnectionDrawingPolicy interface + +protected: + void Internal_DrawLineWithArrow(const FVector2D& StartAnchorPoint, const FVector2D& EndAnchorPoint, const FConnectionParams& Params); +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.cpp new file mode 100644 index 0000000..7e24b85 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.cpp @@ -0,0 +1,76 @@ +#include "WALandscapeGraphEdGraph.h" +#include "WALandscapeGraphEdNode.h" +#include "WALandscapeGraph.h" +#include "WALandscapeGraphEdGraph.h" +#include "WALandscapeGraphEditorTypes.h" +#include "EdGraph/EdGraphPin.h" + +UWALandscapeGraphEdGraph::UWALandscapeGraphEdGraph() +{ + +} + +UWALandscapeGraphEdGraph::~UWALandscapeGraphEdGraph() +{ + +} + +void UWALandscapeGraphEdGraph::RebuildGenericGraph() +{ + //UWALandscapeGraph* G = CastChecked(GetOuter()); + + //G->ClearGraph(); + //for (int i = 0; i < Nodes.Num(); ++i) + //{ + // UWALandscapeGraphEdNode* EdNode = Cast(Nodes[i]); + + // if (EdNode == nullptr || EdNode->GenericGraphNode == nullptr) + // continue; + + // UWALandscapeNode* GNode = EdNode->GenericGraphNode; + + // G->AllNodes.Add(GNode); + // GNode->MaskNode = nullptr; + // for (int PinIdx = 0; PinIdx < EdNode->Pins.Num(); ++PinIdx) + // { + // UEdGraphPin* Pin = EdNode->Pins[PinIdx]; + + // if (Pin->Direction == EEdGraphPinDirection::EGPD_Input + // && Pin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_MaskInput) + // { + // UWALandscapeGraphEdNode* InputNode = nullptr; + // InputNode = Cast(Pin->GetOwningNode()); + // for (UEdGraphPin* LinkedPin : Pin->LinkedTo) + // { + // if (LinkedPin->Direction == EEdGraphPinDirection::EGPD_Output + // && LinkedPin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_SingleNode) + // { + // UWALandscapeGraphEdNode* OutputNode = Cast(LinkedPin->GetOwningNode()); + + // if (OutputNode != InputNode) + // { + // UWALandscapeNode* nodeInput = InputNode->GenericGraphNode; + // UWALandscapeNode* nodeOutput = OutputNode->GenericGraphNode; + // if (nodeInput && nodeOutput) + // { + // nodeInput->MaskNode = nodeOutput; + // } + // } + // } + // } + // } + // } + //} +} + +#if WITH_EDITOR +void UWALandscapeGraphEdGraph::PostEditUndo() +{ + Super::PostEditUndo(); + + RebuildGenericGraph(); + + Modify(); +} +#endif + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.h new file mode 100644 index 0000000..e7469cc --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdGraph.h @@ -0,0 +1,19 @@ +#pragma once + +#include "WALandscapeGraphEdGraph.generated.h" + +UCLASS() +class UWALandscapeGraphEdGraph : public UEdGraph +{ + GENERATED_BODY() + +public: + UWALandscapeGraphEdGraph(); + virtual ~UWALandscapeGraphEdGraph(); + + virtual void RebuildGenericGraph(); + +#if WITH_EDITOR + virtual void PostEditUndo() override; +#endif +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.cpp new file mode 100644 index 0000000..2d4d6ee --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.cpp @@ -0,0 +1,65 @@ +#include "WALandscapeGraphEdNode.h" +#include "WALandscapeGraphEdGraph.h" +#include "WALandscapeGraph.h" +#include "WALandscapeNode.h" +#include "WALandscapeGraphEditorTypes.h" +#include "EdGraph/EdGraphPin.h" +#define LOCTEXT_NAMESPACE "GenericGraphEdNode" + +void UWALandscapeGraphEdNode::AllocateDefaultPins() +{ + CreatePin(EGPD_Input, UWALandscapeGraphEditorTypes::PinCategory_SingleNode, TEXT("Height Out")); + CreatePin(EGPD_Output, UWALandscapeGraphEditorTypes::PinCategory_MaskInput, TEXT("Height In")); + //CreatePin(EGPD_Output, UWALandscapeGraphEditorTypes::PinCategory_SingleNode, TEXT(""), NULL, false, false, TEXT("Height Out")); + //CreatePin(EGPD_Input, UWALandscapeGraphEditorTypes::PinCategory_MaskInput, TEXT(""), NULL, false, false, TEXT("Mask In")); +} + +void UWALandscapeGraphEdNode::NodeConnectionListChanged() +{ + Super::NodeConnectionListChanged(); + + GetGenericGraphEdGraph()->RebuildGenericGraph(); +} + +UWALandscapeGraphEdGraph* UWALandscapeGraphEdNode::GetGenericGraphEdGraph() +{ + return Cast(GetGraph()); +} + +FText UWALandscapeGraphEdNode::GetNodeTitle(ENodeTitleType::Type TitleType) const +{ + if (GenericGraphNode == nullptr) + { + return Super::GetNodeTitle(TitleType); + } + else + { + return FText::FromString(GenericGraphNode->GetNodeTitle()); + } +} + +void UWALandscapeGraphEdNode::SetGenericGraphNode(UWALandscapeNode* InNode) +{ + GenericGraphNode = InNode; +} + +FText UWALandscapeGraphEdNode::GetDescription() const +{ + UWALandscapeGraph* Graph = GenericGraphNode->GetGraph(); + + return FText::FromString("Dupa Description"); +} + +FLinearColor UWALandscapeGraphEdNode::GetBackgroundColor() const +{ + return GenericGraphNode->BackgroundColor; +} +void UWALandscapeGraphEdNode::PinConnectionListChanged(UEdGraphPin* Pin) +{ + +} +void UWALandscapeGraphEdNode::GenerateHeightMap(TArray& InOutMap) +{ + +} +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.h new file mode 100644 index 0000000..ed8a3f2 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode.h @@ -0,0 +1,33 @@ +#pragma once +#include "EdGraph/EdGraphNode.h" +#include "WALandscapeGraphEdNode.generated.h" + +UCLASS(MinimalAPI) +class UWALandscapeGraphEdNode : public UEdGraphNode +{ + GENERATED_BODY() + +public: + UPROPERTY() + UWALandscapeGraphEdNode* Output; + + UPROPERTY(VisibleAnywhere, instanced, Category = "GenericGraph") + class UWALandscapeNode* GenericGraphNode; + + virtual void AllocateDefaultPins() override; + virtual void NodeConnectionListChanged() override; + + class UWALandscapeGraphEdGraph* GetGenericGraphEdGraph(); + + virtual FText GetNodeTitle(ENodeTitleType::Type TitleType) const; + + void SetGenericGraphNode(UWALandscapeNode* InNode); + + virtual FText GetDescription() const; + + FLinearColor GetBackgroundColor() const; + virtual void PinConnectionListChanged(UEdGraphPin* Pin) override; + + virtual void GenerateHeightMap(TArray& InOutMap); + +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.cpp new file mode 100644 index 0000000..9e6f9b3 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.cpp @@ -0,0 +1,79 @@ +// Fill out your copyright notice in the Description page of Project Settings. +#include "WALandscapeGraphEdNode_Multiply.h" +#include "WALandscapeGraphEditorTypes.h" +#include "../WALandscapeNode_Multiply.h" + + +void UWALandscapeGraphEdNode_Multiply::AllocateDefaultPins() +{ + CreatePin(EGPD_Input, UWALandscapeGraphEditorTypes::PinCategory_InputA, TEXT("In A")); + CreatePin(EGPD_Input, UWALandscapeGraphEditorTypes::PinCategory_InputB, TEXT("In B")); + CreatePin(EGPD_Output, UWALandscapeGraphEditorTypes::PinCategory_Output, TEXT("Out")); +} + +void UWALandscapeGraphEdNode_Multiply::PinConnectionListChanged(UEdGraphPin* Pin) +{ + //UWALandscapeGraphEdNode_Output* InputNode = nullptr; + //UWALandscapeGraphEdNode_Multiply* ThisEdNode = this; + //UWALandscapeNode_Multiply* ThisNode = Cast(ThisEdNode->GenericGraphNode); + UWALandscapeGraphEdNode* ThisEdNode = Cast(Pin->GetOwningNode()); + UWALandscapeNode_Multiply* ThisNode = Cast(ThisEdNode->GenericGraphNode); + + if (Pin->Direction == EEdGraphPinDirection::EGPD_Input) + { + if (Pin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_InputA) + { + //InputNode = Cast(Pin->GetOwningNode()); + for (UEdGraphPin* LinkedPin : Pin->LinkedTo) + { + if (LinkedPin->Direction == EEdGraphPinDirection::EGPD_Output + && LinkedPin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_Output) + { + UWALandscapeGraphEdNode* InputNode = Cast(LinkedPin->GetOwningNode()); + InputA = InputNode; + if (ThisEdNode != InputNode) + { + UWALandscapeNode* NodeA = InputNode->GenericGraphNode; + ThisNode->InputA = NodeA; + } + } + } + } + else if (Pin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_InputB) + { + for (UEdGraphPin* LinkedPin : Pin->LinkedTo) + { + if (LinkedPin->Direction == EEdGraphPinDirection::EGPD_Output + && LinkedPin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_Output) + { + UWALandscapeGraphEdNode* InputNode = Cast(LinkedPin->GetOwningNode()); + + if (ThisEdNode != InputNode) + { + InputB = InputNode; + UWALandscapeNode* NodeB = InputNode->GenericGraphNode; + ThisNode->InputB = NodeB; + } + } + } + } + } + else if (Pin->Direction == EEdGraphPinDirection::EGPD_Output) + { + //InputNode = Cast(Pin->GetOwningNode()); + } +} +void UWALandscapeGraphEdNode_Multiply::GenerateHeightMap(TArray& InOutMap) +{ + TArray OutputA; + TArray OutputB; + + if (InputA) + { + InputA->GenerateHeightMap(OutputA); + } + if (InputB) + { + InputB->GenerateHeightMap(OutputB); + } +} diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.h new file mode 100644 index 0000000..a5e0bf8 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Multiply.h @@ -0,0 +1,26 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "LandscapeGraphEditor/WALandscapeGraphEdNode.h" +#include "WALandscapeGraphEdNode_Multiply.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALandscapeGraphEdNode_Multiply : public UWALandscapeGraphEdNode +{ + GENERATED_BODY() +public: + UPROPERTY() + UWALandscapeGraphEdNode* InputA; + UPROPERTY() + UWALandscapeGraphEdNode* InputB; +public: + virtual void AllocateDefaultPins() override; + virtual void PinConnectionListChanged(UEdGraphPin* Pin) override; + + virtual void GenerateHeightMap(TArray& InOutMap) override; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.cpp new file mode 100644 index 0000000..12fffe2 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.cpp @@ -0,0 +1,55 @@ +// Fill out your copyright notice in the Description page of Project Settings. +#include "WALandscapeGraphEdNode_Output.h" +#include "WALandscapeGraphEditorTypes.h" +#include "WALandscapeNode_Output.h" + + + +void UWALandscapeGraphEdNode_Output::AllocateDefaultPins() +{ + CreatePin(EGPD_Input, UWALandscapeGraphEditorTypes::PinCategory_FinalInput, TEXT("In")); +} + +void UWALandscapeGraphEdNode_Output::PinConnectionListChanged(UEdGraphPin* Pin) +{ + UWALandscapeGraphEdNode_Output* InputNode = nullptr; + UWALandscapeGraphEdNode_Output* NodeToAdd = this; + if (Pin->Direction == EEdGraphPinDirection::EGPD_Input) + { + if (Pin->PinType.PinCategory == UWALandscapeGraphEditorTypes::PinCategory_FinalInput) + { + InputNode = Cast(Pin->GetOwningNode()); + for (UEdGraphPin* LinkedPin : Pin->LinkedTo) + { + if (LinkedPin->Direction == EEdGraphPinDirection::EGPD_Output) + { + UWALandscapeGraphEdNode* OutputNode = Cast(LinkedPin->GetOwningNode()); + + Input = OutputNode; + if (OutputNode != InputNode) + { + UWALandscapeNode_Output* nodeInput = Cast(InputNode->GenericGraphNode); + UWALandscapeNode* nodeOutput = OutputNode->GenericGraphNode; + if (nodeInput && nodeOutput) + { + + nodeInput->Heightmap = nodeOutput; + } + } + } + } + } + } + else if (Pin->Direction == EEdGraphPinDirection::EGPD_Output) + { + //InputNode = Cast(Pin->GetOwningNode()); + } +} +void UWALandscapeGraphEdNode_Output::GenerateHeightMap(TArray& InOutMap) +{ + if (Input) + { + TArray Out; + Input->GenerateHeightMap(Out); + } +} diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.h new file mode 100644 index 0000000..f92ab31 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEdNode_Output.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "LandscapeGraphEditor/WALandscapeGraphEdNode.h" +#include "WALandscapeGraphEdNode_Output.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALandscapeGraphEdNode_Output : public UWALandscapeGraphEdNode +{ + GENERATED_BODY() +public: + UWALandscapeGraphEdNode* Input; +public: + virtual void AllocateDefaultPins() override; + virtual void PinConnectionListChanged(UEdGraphPin* Pin) override; + + virtual void GenerateHeightMap(TArray& InOutMap) override; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.cpp new file mode 100644 index 0000000..6536709 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.cpp @@ -0,0 +1,12 @@ + +#include "WALandscapeGraphEditorCommands.h" + +#define LOCTEXT_NAMESPACE "GenericGraphEditorCommands" + +void FWALandscapeGraphEditorCommands::RegisterCommands() +{ + UI_COMMAND(GraphSettings, "Graph Settings", "Graph Settings", EUserInterfaceActionType::Button, FInputChord()); + UI_COMMAND(GenerateLandscape, "Generate Landscape", "Generate Landscape", EUserInterfaceActionType::Button, FInputChord()); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.h new file mode 100644 index 0000000..cb79380 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphEditorCommands.h @@ -0,0 +1,17 @@ +#pragma once + +class FWALandscapeGraphEditorCommands : public TCommands +{ +public: + /** Constructor */ + FWALandscapeGraphEditorCommands() + : TCommands("GenericGraphEditor", NSLOCTEXT("Contexts", "GenericGraphEditor", "Generic Graph Editor"), NAME_None, FEditorStyle::GetStyleSetName()) + { + } + + TSharedPtr GraphSettings; + + TSharedPtr GenerateLandscape; + + virtual void RegisterCommands() override; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.cpp new file mode 100644 index 0000000..ef1886b --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.cpp @@ -0,0 +1,344 @@ +#include "WALandscapeGraphSchema.h" +#include "WALandscapeGraphEdNode.h" +#include "WALandscapeGraphConnectionDrawingPolicy.h" +#include "WALandscapeGraph.h" +#include "WALandscapeNode.h" +#include "EdGraph/EdGraph.h" +#include "GraphEditorActions.h" +#include "WALandscapeGraphEdNode_Output.h" +#include "WALandscapeNode_Output.h" +#include "WALandscapeGraphEdNode_Multiply.h" +#include "../WALandscapeNode_Multiply.h" +#include "../WALGEdNode_Start.h" +#include "GenericCommands.h" + +#define LOCTEXT_NAMESPACE "GenericGraphAssetSchema" + +int32 UWALandscapeGraphSchema::CurrentCacheRefreshID = 0; + +class FNodeVisitorCycleChecker +{ +public: + /** Check whether a loop in the graph would be caused by linking the passed-in nodes */ + bool CheckForLoop(UEdGraphNode* StartNode, UEdGraphNode* EndNode) + { + VisitedNodes.Add(StartNode); + + return TraverseInputNodesToRoot(EndNode); + } + +private: + bool TraverseInputNodesToRoot(UEdGraphNode* Node) + { + VisitedNodes.Add(Node); + + for (int32 PinIndex = 0; PinIndex < Node->Pins.Num(); ++PinIndex) + { + UEdGraphPin* MyPin = Node->Pins[PinIndex]; + + if (MyPin->Direction == EGPD_Output) + { + for (int32 LinkedPinIndex = 0; LinkedPinIndex < MyPin->LinkedTo.Num(); ++LinkedPinIndex) + { + UEdGraphPin* OtherPin = MyPin->LinkedTo[LinkedPinIndex]; + if (OtherPin) + { + UEdGraphNode* OtherNode = OtherPin->GetOwningNode(); + if (VisitedNodes.Contains(OtherNode)) + { + return false; + } + else + { + return TraverseInputNodesToRoot(OtherNode); + } + } + } + } + } + + return true; + } + + TSet VisitedNodes; +}; + +UEdGraphNode* FWALandscapeGraphAssetSchemaAction_NewNode::PerformAction(class UEdGraph* ParentGraph, UEdGraphPin* FromPin, const FVector2D Location, bool bSelectNewNode /*= true*/) +{ + UWALandscapeGraph* Graph = CastChecked(ParentGraph->GetOuter()); + + //const FScopedTransaction Transaction(LOCTEXT("GenericGraphEditorNewNode", "Generic Graph Editor: New Node")); + ParentGraph->Modify(); + Graph->Modify(); + + UWALandscapeNode* NewNode = NewObject(Graph, NodeType); + + //Graph->AllNodes.Add(NewNode); + + //FGraphNodeCreator NodeCreator(*Graph->EdGraph); + //UWALandscapeGraphEdNode* GraphNode = NodeCreator.CreateNode(true); + //GraphNode->SetGenericGraphNode(NewNode); + //NodeCreator.Finalize(); + + //GraphNode->NodePosX = Location.X; + //GraphNode->NodePosY = Location.Y; + + //GraphNode->AutowireNewNode(FromPin); + + //Graph->PostEditChange(); + //Graph->MarkPackageDirty(); + + //return GraphNode; + + UEdGraphNode* ResultNode = NULL; + + // If there is a template, we actually use it + if (NodeTemplate != NULL) + { + const FScopedTransaction Transaction(LOCTEXT("AddNode", "Add Node")); + ParentGraph->Modify(); + if (FromPin) + { + FromPin->Modify(); + } + + NodeTemplate->SetFlags(RF_Transactional); + + // set outer to be the graph so it doesn't go away + NodeTemplate->Rename(NULL, ParentGraph, REN_NonTransactional); + ParentGraph->AddNode(NodeTemplate, true); + + NodeTemplate->CreateNewGuid(); + NodeTemplate->PostPlacedNewNode(); + + // For input pins, new node will generally overlap node being dragged off + // Work out if we want to visually push away from connected node + //int32 XLocation = Location.X; + //if (FromPin && FromPin->Direction == EGPD_Input) + //{ + // UEdGraphNode* PinNode = FromPin->GetOwningNode(); + // const float XDelta = FMath::Abs(PinNode->NodePosX - Location.X); + + // if (XDelta < NodeDistance) + // { + // // Set location to edge of current node minus the max move distance + // // to force node to push off from connect node enough to give selection handle + // XLocation = PinNode->NodePosX - NodeDistance; + // } + //} + + NodeTemplate->NodePosX = Location.X; + NodeTemplate->NodePosY = Location.Y; + + // setup pins after placing node in correct spot, since pin sorting will happen as soon as link connection change occurs + NodeTemplate->AllocateDefaultPins(); + NodeTemplate->AutowireNewNode(FromPin); + NodeTemplate->SetGenericGraphNode(NewNode); + Graph->PostEditChange(); + Graph->MarkPackageDirty(); + + ResultNode = NodeTemplate; + } + + return ResultNode; +} +void UWALandscapeGraphSchema::CreateDefaultNodesForGraph(UEdGraph& Graph) const +{ + { + FGraphNodeCreator NodeCreator(Graph); + UWALandscapeGraph* LandscapeGraph = CastChecked(Graph.GetOuter()); + UWALandscapeGraphEdNode_Output* MyNode = NodeCreator.CreateNode(); + Output = MyNode; + UWALandscapeNode_Output* NewNode = NewObject(LandscapeGraph, UWALandscapeNode_Output::StaticClass()); + LandscapeGraph->LandscapeOutput = NewNode; + MyNode->SetGenericGraphNode(NewNode); + NodeCreator.Finalize(); + SetNodeMetaData(MyNode, FNodeMetadata::DefaultGraphNode); + } + //{ + // FGraphNodeCreator NodeCreator(Graph); + // UWALandscapeGraph* LandscapeGraph = CastChecked(Graph.GetOuter()); + // UWALGEdNode_Start* MyNode = NodeCreator.CreateNode(); + // //UWALandscapeNode_Output* NewNode = NewObject(LandscapeGraph, UWALandscapeNode_Output::StaticClass()); + // //LandscapeGraph->LandscapeOutput = NewNode; + // //MyNode->SetGenericGraphNode(NewNode); + // NodeCreator.Finalize(); + // SetNodeMetaData(MyNode, FNodeMetadata::DefaultGraphNode); + //} + //WALGEdNode_Start +} +void UWALandscapeGraphSchema::GetBreakLinkToSubMenuActions(class FMenuBuilder& MenuBuilder, class UEdGraphPin* InGraphPin) +{ + // Make sure we have a unique name for every entry in the list + TMap< FString, uint32 > LinkTitleCount; + + // Add all the links we could break from + for (TArray::TConstIterator Links(InGraphPin->LinkedTo); Links; ++Links) + { + UEdGraphPin* Pin = *Links; + FString TitleString = Pin->GetOwningNode()->GetNodeTitle(ENodeTitleType::ListView).ToString(); + FText Title = FText::FromString(TitleString); + if (Pin->PinName != TEXT("")) + { + //TitleString = FString::Printf(TEXT("%s (%s)"), *TitleString, *Pin->PinName); + + // Add name of connection if possible + FFormatNamedArguments Args; + Args.Add(TEXT("NodeTitle"), Title); + Args.Add(TEXT("PinName"), Pin->GetDisplayName()); + Title = FText::Format(LOCTEXT("BreakDescPin", "{NodeTitle} ({PinName})"), Args); + } + + uint32 &Count = LinkTitleCount.FindOrAdd(TitleString); + + FText Description; + FFormatNamedArguments Args; + Args.Add(TEXT("NodeTitle"), Title); + Args.Add(TEXT("NumberOfNodes"), Count); + + if (Count == 0) + { + Description = FText::Format(LOCTEXT("BreakDesc", "Break link to {NodeTitle}"), Args); + } + else + { + Description = FText::Format(LOCTEXT("BreakDescMulti", "Break link to {NodeTitle} ({NumberOfNodes})"), Args); + } + ++Count; + + //MenuBuilder.AddMenuEntry(Description, Description, FSlateIcon(), FUIAction( + // FExecuteAction::CreateUObject(this, &UWALandscapeGraphSchema::BreakSinglePinLink, const_cast(InGraphPin), *Links))); + } +} + +void UWALandscapeGraphSchema::GetGraphContextActions(FGraphContextMenuBuilder& ContextMenuBuilder) const +{ + const bool bNoParent = (ContextMenuBuilder.FromPin == NULL); + { + const FText AddToolTip; + const FText Desc = LOCTEXT("NewGenericGraphNodeTooltip", "Multiply"); + TSharedPtr NewNodeAction(new FWALandscapeGraphAssetSchemaAction_NewNode(LOCTEXT("GenericGraphNodeAction", "Common"), Desc, AddToolTip, 1)); + NewNodeAction->NodeTemplate = NewObject(ContextMenuBuilder.OwnerOfTemporaries); + NewNodeAction->NodeType = UWALandscapeNode_Multiply::StaticClass(); + ContextMenuBuilder.AddAction(NewNodeAction); + } +} + +void UWALandscapeGraphSchema::GetContextMenuActions(const UEdGraph* CurrentGraph, const UEdGraphNode* InGraphNode, const UEdGraphPin* InGraphPin, class FMenuBuilder* MenuBuilder, bool bIsDebugging) const +{ + if (InGraphPin != nullptr) + { + MenuBuilder->BeginSection("GenericGraphAssetGraphSchemaNodeActions", LOCTEXT("PinActionsMenuHeader", "Pin Actions")); + { + // Only display the 'Break Link' option if there is a link to break! + if (InGraphPin->LinkedTo.Num() > 0) + { + MenuBuilder->AddMenuEntry(FGraphEditorCommands::Get().BreakPinLinks); + + // add sub menu for break link to + if (InGraphPin->LinkedTo.Num() > 1) + { + MenuBuilder->AddSubMenu( + LOCTEXT("BreakLinkTo", "Break Link To..."), + LOCTEXT("BreakSpecificLinks", "Break a specific link..."), + FNewMenuDelegate::CreateUObject((UWALandscapeGraphSchema*const)this, &UWALandscapeGraphSchema::GetBreakLinkToSubMenuActions, const_cast(InGraphPin))); + } + else + { + ((UWALandscapeGraphSchema*const)this)->GetBreakLinkToSubMenuActions(*MenuBuilder, const_cast(InGraphPin)); + } + } + } + MenuBuilder->EndSection(); + } + else if(InGraphNode != nullptr) + { + MenuBuilder->BeginSection("GenericGraphAssetGraphSchemaNodeActions", LOCTEXT("NodeActionsMenuHeader", "Node Actions")); + { + MenuBuilder->AddMenuEntry(FGenericCommands::Get().Delete); + MenuBuilder->AddMenuEntry(FGenericCommands::Get().Cut); + MenuBuilder->AddMenuEntry(FGenericCommands::Get().Copy); + MenuBuilder->AddMenuEntry(FGenericCommands::Get().Duplicate); + + MenuBuilder->AddMenuEntry(FGraphEditorCommands::Get().BreakNodeLinks); + } + MenuBuilder->EndSection(); + } + + Super::GetContextMenuActions(CurrentGraph, InGraphNode, InGraphPin, MenuBuilder, bIsDebugging); +} + +const FPinConnectionResponse UWALandscapeGraphSchema::CanCreateConnection(const UEdGraphPin* A, const UEdGraphPin* B) const +{ + // Make sure the pins are not on the same node + if (A->GetOwningNode() == B->GetOwningNode()) + { + return FPinConnectionResponse(CONNECT_RESPONSE_DISALLOW, LOCTEXT("PinErrorSameNode", "Both are on the same node")); + } + + // Compare the directions + if ((A->Direction == EGPD_Input) && (B->Direction == EGPD_Input)) + { + return FPinConnectionResponse(CONNECT_RESPONSE_DISALLOW, LOCTEXT("PinErrorInput", "Can't connect input node to input node")); + } + else if ((A->Direction == EGPD_Output) && (B->Direction == EGPD_Output)) + { + return FPinConnectionResponse(CONNECT_RESPONSE_DISALLOW, LOCTEXT("PinErrorOutput", "Can't connect output node to output node")); + } + + // check for cycles + FNodeVisitorCycleChecker CycleChecker; + if (!CycleChecker.CheckForLoop(A->GetOwningNode(), B->GetOwningNode())) + { + return FPinConnectionResponse(CONNECT_RESPONSE_DISALLOW, LOCTEXT("PinErrorCycle", "Can't create a graph cycle")); + } + + return FPinConnectionResponse(CONNECT_RESPONSE_MAKE, LOCTEXT("PinConnect", "Connect nodes")); +} + +class FConnectionDrawingPolicy* UWALandscapeGraphSchema::CreateConnectionDrawingPolicy(int32 InBackLayerID, int32 InFrontLayerID, float InZoomFactor, const FSlateRect& InClippingRect, class FSlateWindowElementList& InDrawElements, class UEdGraph* InGraphObj) const +{ + return new FWALandscapeGraphConnectionDrawingPolicy(InBackLayerID, InFrontLayerID, InZoomFactor, InClippingRect, InDrawElements, InGraphObj); +} + +FLinearColor UWALandscapeGraphSchema::GetPinTypeColor(const FEdGraphPinType& PinType) const +{ + return FColor::White; +} + +void UWALandscapeGraphSchema::BreakNodeLinks(UEdGraphNode& TargetNode) const +{ + const FScopedTransaction Transaction(NSLOCTEXT("UnrealEd", "GraphEd_BreakNodeLinks", "Break Node Links")); + + Super::BreakNodeLinks(TargetNode); +} + +void UWALandscapeGraphSchema::BreakPinLinks(UEdGraphPin& TargetPin, bool bSendsNodeNotifcation) const +{ + const FScopedTransaction Transaction(NSLOCTEXT("UnrealEd", "GraphEd_BreakPinLinks", "Break Pin Links")); + + Super::BreakPinLinks(TargetPin, bSendsNodeNotifcation); +} + +//void UWALandscapeGraphSchema::BreakSinglePinLink(UEdGraphPin* SourcePin, UEdGraphPin* TargetPin) +//{ +// const FScopedTransaction Transaction(NSLOCTEXT("UnrealEd", "GraphEd_BreakSinglePinLink", "Break Pin Link")); +// +// Super::BreakSinglePinLink(SourcePin, TargetPin); +//} + +bool UWALandscapeGraphSchema::IsCacheVisualizationOutOfDate(int32 InVisualizationCacheID) const +{ + return CurrentCacheRefreshID != InVisualizationCacheID; +} + +int32 UWALandscapeGraphSchema::GetCurrentVisualizationCacheID() const +{ + return CurrentCacheRefreshID; +} + +void UWALandscapeGraphSchema::ForceVisualizationCacheClear() const +{ + ++CurrentCacheRefreshID; +} +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.h new file mode 100644 index 0000000..be8e541 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/LandscapeGraphEditor/WALandscapeGraphSchema.h @@ -0,0 +1,63 @@ +#pragma once +#include "EdGraph/EdGraphSchema.h" +#include "WALandscapeNode.h" + +#include "WALandscapeGraphSchema.generated.h" + +/** Action to add a node to the graph */ +USTRUCT() +struct FWALandscapeGraphAssetSchemaAction_NewNode : public FEdGraphSchemaAction +{ + GENERATED_USTRUCT_BODY(); + + UPROPERTY() + class UWALandscapeGraphEdNode* NodeTemplate; + + TSubclassOf NodeType; + + FWALandscapeGraphAssetSchemaAction_NewNode() + : FEdGraphSchemaAction() + {} + + FWALandscapeGraphAssetSchemaAction_NewNode(const FText& InNodeCategory, const FText& InMenuDesc, const FText& InToolTip, const int32 InGrouping) + : FEdGraphSchemaAction(InNodeCategory, InMenuDesc, InToolTip, InGrouping) + {} + + virtual UEdGraphNode* PerformAction(class UEdGraph* ParentGraph, UEdGraphPin* FromPin, const FVector2D Location, bool bSelectNewNode = true) override; + + +}; + +UCLASS(MinimalAPI) +class UWALandscapeGraphSchema : public UEdGraphSchema +{ + GENERATED_BODY() +public: + UPROPERTY() + mutable class UWALandscapeGraphEdNode_Output* Output; + + void GetBreakLinkToSubMenuActions(class FMenuBuilder& MenuBuilder, class UEdGraphPin* InGraphPin); + + //~ Begin EdGraphSchema Interface + virtual void CreateDefaultNodesForGraph(UEdGraph& Graph) const override; + virtual void GetGraphContextActions(FGraphContextMenuBuilder& ContextMenuBuilder) const override; + virtual void GetContextMenuActions(const UEdGraph* CurrentGraph, const UEdGraphNode* InGraphNode, const UEdGraphPin* InGraphPin, class FMenuBuilder* MenuBuilder, bool bIsDebugging) const override; + virtual const FPinConnectionResponse CanCreateConnection(const UEdGraphPin* A, const UEdGraphPin* B) const override; + virtual class FConnectionDrawingPolicy* CreateConnectionDrawingPolicy(int32 InBackLayerID, int32 InFrontLayerID, float InZoomFactor, const FSlateRect& InClippingRect, class FSlateWindowElementList& InDrawElements, class UEdGraph* InGraphObj) const override; + virtual FLinearColor GetPinTypeColor(const FEdGraphPinType& PinType) const override; + virtual void BreakNodeLinks(UEdGraphNode& TargetNode) const override; + virtual void BreakPinLinks(UEdGraphPin& TargetPin, bool bSendsNodeNotifcation) const override; +// virtual void BreakSinglePinLink(UEdGraphPin* SourcePin, UEdGraphPin* TargetPin) override; +// virtual void DroppedAssetsOnGraph(const TArray& Assets, const FVector2D& GraphPosition, UEdGraph* Graph) const override; +// virtual void DroppedAssetsOnNode(const TArray& Assets, const FVector2D& GraphPosition, UEdGraphNode* Node) const override; +// virtual int32 GetNodeSelectionCount(const UEdGraph* Graph) const override; +// virtual TSharedPtr GetCreateCommentAction() const override; + virtual bool IsCacheVisualizationOutOfDate(int32 InVisualizationCacheID) const override; + virtual int32 GetCurrentVisualizationCacheID() const override; + virtual void ForceVisualizationCacheClear() const override; + //~ End EdGraphSchema Interface + +private: + static int32 CurrentCacheRefreshID; +}; + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.cpp new file mode 100644 index 0000000..74544cd --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.cpp @@ -0,0 +1,26 @@ +#include "WALandscapeGraph.h" + +#define LOCTEXT_NAMESPACE "GenericGraph" + +UWALandscapeGraph::UWALandscapeGraph() +{ + NodeType = UWALandscapeNode::StaticClass(); + +#if WITH_EDITORONLY_DATA + EdGraph = nullptr; +#endif +} + +UWALandscapeGraph::~UWALandscapeGraph() +{ + +} + +void UWALandscapeGraph::ClearGraph() +{ +} +void UWALandscapeGraph::GenerateLandscape() +{ + +} +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.h new file mode 100644 index 0000000..8a52663 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeGraph.h @@ -0,0 +1,41 @@ +#pragma once + +#include "WALandscapeNode.h" +#include "WALandscapeGraph.generated.h" + +UCLASS(Blueprintable) +class WORLDARCHITECTEDITOR_API UWALandscapeGraph : public UObject +{ + GENERATED_BODY() + +public: + UWALandscapeGraph(); + virtual ~UWALandscapeGraph(); + + ////////////////////////////////////////////////////////////////////////// + // uproperties + UPROPERTY(EditAnywhere, Category = "GenericGraph") + FString Name; + + UPROPERTY(EditAnywhere, Category = "GenericGraph") + TSubclassOf NodeType; + + UPROPERTY(BlueprintReadOnly, Category = "GenericGraph") + UWALandscapeNode* LandscapeOutput; + + UPROPERTY(BlueprintReadOnly, Category = "GenericGraph") + TArray RootNodes; + + UPROPERTY(BlueprintReadOnly, Category = "GenericGraph") + TArray AllNodes; + +//#if WITH_EDITORONLY_DATA + UPROPERTY() + class UEdGraph* EdGraph; + + UPROPERTY() + class UWALandscapeGraphSchema* Schema; +//#endif + void GenerateLandscape(); + void ClearGraph(); +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.cpp new file mode 100644 index 0000000..b559779 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.cpp @@ -0,0 +1,31 @@ +#include "WALandscapeNode.h" +#include "WALandscapeGraph.h" +#define LOCTEXT_NAMESPACE "GenericGraphNode" + +UWALandscapeNode::UWALandscapeNode() +{ + BackgroundColor = FLinearColor(0.0f, 0.0f, 0.0f, 1.0f); +} + +UWALandscapeNode::~UWALandscapeNode() +{ + +} + +FString UWALandscapeNode::GetNodeTitle() +{ + return CustomNodeTitle; +} + +UWALandscapeGraph* UWALandscapeNode::GetGraph() +{ + return Cast(GetOuter()); +} + +TArray UWALandscapeNode::GenerateHeightmap() +{ + TArray RetVal; + return RetVal; +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.h new file mode 100644 index 0000000..5d0243e --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/Runtime/WALandscapeNode.h @@ -0,0 +1,45 @@ +#pragma once + +#include "WALandscapeNode.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FWAOnHeightmapReady, const TArray&, OutHeighmap); + +UCLASS(Blueprintable) +class WORLDARCHITECTEDITOR_API UWALandscapeNode : public UObject +{ + GENERATED_BODY() + +public: + UWALandscapeNode(); + virtual ~UWALandscapeNode(); + UPROPERTY() + bool bDirty; + + ////////////////////////////////////////////////////////////////////////// + // uproperties + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "GenericGraphNode") + FString CustomNodeTitle; + + UPROPERTY(BlueprintReadOnly, Category = "GenericGraphNode") + UWALandscapeNode* MaskNode; + +#if WITH_EDITOR + UPROPERTY(EditDefaultsOnly, Category = "GenericGraphNode") + FLinearColor BackgroundColor; +#endif + UPROPERTY() + FWAOnHeightmapReady OnHeightmapReady; + ////////////////////////////////////////////////////////////////////////// + // ufunctions + UFUNCTION(BlueprintCallable, Category = "GenericGraphNode") + FString GetNodeTitle(); + + virtual void ExecuteNode(const TArray& InHeightData) {}; + + ////////////////////////////////////////////////////////////////////////// + class UWALandscapeGraph* GetGraph(); + + + virtual TArray GenerateHeightmap(); +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.cpp new file mode 100644 index 0000000..4735d63 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "WALGEdNode_Combine.h" + + + + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.h new file mode 100644 index 0000000..ba6e2e3 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Combine.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "LandscapeGraphEditor/WALandscapeGraphEdNode.h" +#include "WALGEdNode_Combine.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALGEdNode_Combine : public UWALandscapeGraphEdNode +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.cpp new file mode 100644 index 0000000..87ab2eb --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.cpp @@ -0,0 +1,64 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "WALGEdNode_PerlinNoise.h" +#include "LandscapeEditorUtils.h" +#include "LandscapeInfoMap.h" +#include "LandscapeStreamingProxy.h" + +void UWALGEdNode_PerlinNoise::GenerateHeightMap(TArray& InOutMap) +{ + //GEditor->GetWorld(); + //TArray Landscapes; + //for (TActorIterator LIter(GetEditorMode()->GetWorld()); LIter; ++LIter) + //{ + // Landscapes.Add(*LIter); + //} + //auto& LandscapeInfoMap = ULandscapeInfoMap::GetLandscapeInfoMap(GetEditorMode()->GetWorld()); + + + //if (Landscapes.Num() > 0) + //{ + // FIntRect bounds = Landscapes[0]->GetBoundingRect(); + + // int32 numHeights = (bounds.Width() + 1)*(bounds.Height() + 1); + // TArray Data; + // Data.Init(0, numHeights); + // TArray DataFloat; + // DataFloat.Init(0, numHeights); + // TArray DataFloat2; + // DataFloat2.Init(0, numHeights); + // TArray DataFloat3; + // DataFloat3.Init(0, numHeights); + + // int32 cols = bounds.Width() + 1, rows = bounds.Height() + 1; + // int32 octaves = 16, px = 4, py = 4; + // float amplitude = 20000.f; + // //for (int i = 0; i < Data.Num(); i++) + // //{ + // // float nx = (i % cols) / (float)cols; //normalized col + // // float ny = (i / cols) / (float)rows; //normalized row + // // Data[i] = FMath::Clamp(PerlinNoise2D(nx, ny, amplitude, octaves, px, py), 0, 32768); + // //} + // for (int i = 0; i < DataFloat.Num(); i++) + // { + // float nx = (i % cols) / (float)cols; //normalized col + // float ny = (i / cols) / (float)rows; //normalized row + // DataFloat[i] = PerlinNoise2DFloat(nx, ny, amplitude, octaves, px, py); + // DataFloat2[i] = PerlinNoise2DFloat(nx, ny, amplitude, 4, 12, 12); + // DataFloat3[i] = DataFloat[i] * DataFloat2[i]; + // } + // for (int i = 0; i < Data.Num(); i++) + // { + // Data[i] = (USHRT_MAX / 2.f) + (DataFloat3[i] * amplitude); + // } + // InOutMap = Data; + //} +} +void UWALGEdNode_PerlinNoise::AllocateDefaultPins() +{ + +} +void UWALGEdNode_PerlinNoise::PinConnectionListChanged(UEdGraphPin* Pin) +{ + +} \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.h new file mode 100644 index 0000000..ffa4369 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_PerlinNoise.h @@ -0,0 +1,40 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "WANoise.h" +#include "LandscapeGraphEditor/WALandscapeGraphEdNode.h" +#include "WALGEdNode_PerlinNoise.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALGEdNode_PerlinNoise : public UWALandscapeGraphEdNode +{ + GENERATED_BODY() + + virtual void GenerateHeightMap(TArray& InOutMap) override; + virtual void AllocateDefaultPins() override; + virtual void PinConnectionListChanged(UEdGraphPin* Pin) override; + + uint16 PerlinNoise2D(float x, float y, float amp, int32 octaves, int32 px, int32 py) + { + float noise = 0.f; + for (int octave = 1; octave < octaves; octave *= 2) + noise += FNoise::pnoise(x*px*octave, y*py*octave, px, py) / octave; + + return USHRT_MAX / 2.f + amp*noise; + } + float PerlinNoise2DFloat(float x, float y, float amp, int32 octaves, int32 px, int32 py) + { + float noise = 0.f; + for (int octave = 1; octave < octaves; octave *= 2) + noise += FNoise::pnoise(x*px*octave, y*py*octave, px, py) / octave; + + return noise; + } + + +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.cpp new file mode 100644 index 0000000..415623a --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.cpp @@ -0,0 +1,12 @@ +// Fill out your copyright notice in the Description page of Project Settings. +#include "WALGEdNode_Start.h" +#include "WALandscapeGraphEditorTypes.h" + + + + + +void UWALGEdNode_Start::AllocateDefaultPins() +{ + CreatePin(EGPD_Output, UWALandscapeGraphEditorTypes::PinCategory_Start, TEXT("Start")); +} \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.h new file mode 100644 index 0000000..076ac01 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALGEdNode_Start.h @@ -0,0 +1,21 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "LandscapeGraphEditor/WALandscapeGraphEdNode.h" +#include "WALGEdNode_Start.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALGEdNode_Start : public UWALandscapeGraphEdNode +{ + GENERATED_BODY() + +public: + virtual void AllocateDefaultPins() override; + + +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.cpp new file mode 100644 index 0000000..4c7c875 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.cpp @@ -0,0 +1,47 @@ +#include "WALandscapeGraphAssetTypeActions.h" +#include "WALandscapeGraphAssetEditor.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FWALandscapeGraphAssetTypeActions::FWALandscapeGraphAssetTypeActions(EAssetTypeCategories::Type InAssetCategory) + : MyAssetCategory(InAssetCategory) +{ +} + +FText FWALandscapeGraphAssetTypeActions::GetName() const +{ + return FText::FromString("Landscape Graph"); +} + +FColor FWALandscapeGraphAssetTypeActions::GetTypeColor() const +{ + return FColor(129, 196, 115); +} + +UClass* FWALandscapeGraphAssetTypeActions::GetSupportedClass() const +{ + return UWALandscapeGraph::StaticClass(); +} + +void FWALandscapeGraphAssetTypeActions::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + const EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + if (UWALandscapeGraph* Graph = Cast(*ObjIt)) + { + TSharedRef NewGraphEditor(new FWALandscapeGraphAssetEditor()); + NewGraphEditor->InitGenericGraphAssetEditor(Mode, EditWithinLevelEditor, Graph); + } + } +} + +uint32 FWALandscapeGraphAssetTypeActions::GetCategories() +{ + return EAssetTypeCategories::Basic | MyAssetCategory; +} + +////////////////////////////////////////////////////////////////////////// + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.h new file mode 100644 index 0000000..74e40e1 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphAssetTypeActions.h @@ -0,0 +1,18 @@ +#pragma once + +#include "AssetTypeActions_Base.h" + +class FWALandscapeGraphAssetTypeActions : public FAssetTypeActions_Base +{ +public: + FWALandscapeGraphAssetTypeActions(EAssetTypeCategories::Type InAssetCategory); + + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override; + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override; + +private: + EAssetTypeCategories::Type MyAssetCategory; +}; \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.cpp new file mode 100644 index 0000000..4b4155c --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.cpp @@ -0,0 +1,19 @@ +#include "WALandscapeGraphEditorTypes.h" + + +const FName UWALandscapeGraphEditorTypes::PinCategory_MultipleNodes("MultipleNodes"); +const FName UWALandscapeGraphEditorTypes::PinCategory_SingleNode("HeightOutput"); +const FName UWALandscapeGraphEditorTypes::PinCategory_MaskInput("MaskInput"); +const FName UWALandscapeGraphEditorTypes::PinCategory_FinalInput("FinalInput"); + +const FName UWALandscapeGraphEditorTypes::PinCategory_InputA("InputA"); +const FName UWALandscapeGraphEditorTypes::PinCategory_InputB("InputA"); +const FName UWALandscapeGraphEditorTypes::PinCategory_LerpMask("LerpMask"); + +const FName UWALandscapeGraphEditorTypes::PinCategory_Output("Output"); +const FName UWALandscapeGraphEditorTypes::PinCategory_Start("Start"); + +UWALandscapeGraphEditorTypes::UWALandscapeGraphEditorTypes(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) +{ +} + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.h new file mode 100644 index 0000000..0d79a95 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphEditorTypes.h @@ -0,0 +1,21 @@ +#pragma once + +#include "WALandscapeGraphEditorTypes.generated.h" + +UCLASS() +class UWALandscapeGraphEditorTypes : public UObject +{ + GENERATED_UCLASS_BODY() + + static const FName PinCategory_MultipleNodes; + static const FName PinCategory_SingleNode; + static const FName PinCategory_MaskInput; + static const FName PinCategory_FinalInput; + + static const FName PinCategory_InputA; + static const FName PinCategory_InputB; + static const FName PinCategory_LerpMask; + + static const FName PinCategory_Output; + static const FName PinCategory_Start; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.cpp new file mode 100644 index 0000000..e7c544f --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.cpp @@ -0,0 +1,22 @@ +#include "WALandscapeGraphFactory.h" +#include "WALandscapeGraph.h" +#define LOCTEXT_NAMESPACE "GenericGraph" + +UWALandscapeGraphFactory::UWALandscapeGraphFactory() +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UWALandscapeGraph::StaticClass(); +} + +UWALandscapeGraphFactory::~UWALandscapeGraphFactory() +{ + +} + +UObject* UWALandscapeGraphFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return NewObject(InParent, Class, Name, Flags | RF_Transactional); +} + +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.h new file mode 100644 index 0000000..b4dd463 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeGraphFactory.h @@ -0,0 +1,15 @@ +#pragma once + +#include "WALandscapeGraphFactory.generated.h" + +UCLASS() +class WORLDARCHITECTEDITOR_API UWALandscapeGraphFactory : public UFactory +{ + GENERATED_BODY() + +public: + UWALandscapeGraphFactory(); + virtual ~UWALandscapeGraphFactory(); + + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.cpp new file mode 100644 index 0000000..9347038 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.cpp @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "WALandscapeNode_Multiply.h" + + + +TArray UWALandscapeNode_Multiply::GenerateHeightmap() +{ + TArray OutputA; + TArray OutputB; + TArray RetVal; + + if (InputA && InputB) + { + OutputA = InputA->GenerateHeightmap(); + + OutputB = InputB->GenerateHeightmap(); + + + RetVal.Init(0, OutputA.Num()); + for (int32 Idx = 0; Idx < OutputA.Num(); Idx++) + { + RetVal[Idx] = OutputA[Idx] * OutputB[Idx]; + } + + } + return RetVal; +} diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.h new file mode 100644 index 0000000..5a1c9e0 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Multiply.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Runtime/WALandscapeNode.h" +#include "WALandscapeNode_Multiply.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALandscapeNode_Multiply : public UWALandscapeNode +{ + GENERATED_BODY() +protected: + TArray InputACache; + TArray InputBCache; +public: + UPROPERTY(BlueprintReadOnly, Category = "GenericGraphNode") + UWALandscapeNode* InputA; + UPROPERTY(BlueprintReadOnly, Category = "GenericGraphNode") + UWALandscapeNode* InputB; + UPROPERTY(BlueprintReadOnly, Category = "GenericGraphNode") + UWALandscapeNode* Output; + + virtual TArray GenerateHeightmap() override; + +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.cpp new file mode 100644 index 0000000..fd9434f --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.cpp @@ -0,0 +1,16 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "WALandscapeNode_Output.h" + + + + +TArray UWALandscapeNode_Output::GenerateHeightmap() +{ + TArray RetVal; + if (Heightmap) + { + RetVal = Heightmap->GenerateHeightmap(); + } + return RetVal; +} \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.h new file mode 100644 index 0000000..96b1f1c --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_Output.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Runtime/WALandscapeNode.h" +#include "WALandscapeNode_Output.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALandscapeNode_Output : public UWALandscapeNode +{ + GENERATED_BODY() +public: + TArray CachedHeightmap; + + UPROPERTY(BlueprintReadOnly, Category = "GenericGraphNode") + UWALandscapeNode* Heightmap; + +public: + virtual TArray GenerateHeightmap() override; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.cpp new file mode 100644 index 0000000..ab4740a --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.cpp @@ -0,0 +1,18 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "WALandscapeNode_PerlinNoise.h" + + + +TArray UWALandscapeNode_PerlinNoise::GenerateHeightmap() +{ + TArray RetVal; + if (bDirty) + { + return RetVal; + } + else + { + return CachedHeightmap; + } +} diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.h new file mode 100644 index 0000000..b007b0f --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WALandscapeNode_PerlinNoise.h @@ -0,0 +1,38 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Runtime/WALandscapeNode.h" +#include "WANoise.h" +#include "WALandscapeNode_PerlinNoise.generated.h" + +/** + * + */ +UCLASS() +class WORLDARCHITECTEDITOR_API UWALandscapeNode_PerlinNoise : public UWALandscapeNode +{ + GENERATED_BODY() +public: + TArray CachedHeightmap; +public: + virtual TArray GenerateHeightmap() override; + + uint16 PerlinNoise2D(float x, float y, float amp, int32 octaves, int32 px, int32 py) + { + float noise = 0.f; + for (int octave = 1; octave < octaves; octave *= 2) + noise += FNoise::pnoise(x*px*octave, y*py*octave, px, py) / octave; + + return USHRT_MAX / 2.f + amp*noise; + } + float PerlinNoise2DFloat(float x, float y, float amp, int32 octaves, int32 px, int32 py) + { + float noise = 0.f; + for (int octave = 1; octave < octaves; octave *= 2) + noise += FNoise::pnoise(x*px*octave, y*py*octave, px, py) / octave; + + return noise; + } +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.cpp new file mode 100644 index 0000000..06bfbb8 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.cpp @@ -0,0 +1,29 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "WANoise.h" +unsigned char FNoise::perm[] = { 151,160,137,91,90,15, +131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,23, +190, 6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33, +88,237,149,56,87,174,20,125,136,171,168, 68,175,74,165,71,134,139,48,27,166, +77,146,158,231,83,111,229,122,60,211,133,230,220,105,92,41,55,46,245,40,244, +102,143,54, 65,25,63,161, 1,216,80,73,209,76,132,187,208, 89,18,169,200,196, +135,130,116,188,159,86,164,100,109,198,173,186, 3,64,52,217,226,250,124,123, +5,202,38,147,118,126,255,82,85,212,207,206,59,227,47,16,58,17,182,189,28,42, +223,183,170,213,119,248,152, 2,44,154,163, 70,221,153,101,155,167, 43,172,9, +129,22,39,253, 19,98,108,110,79,113,224,232,178,185, 112,104,218,246,97,228, +251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107, +49,192,214, 31,181,199,106,157,184, 84,204,176,115,121,50,45,127, 4,150,254, +138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180, +151,160,137,91,90,15, +131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,23, +190, 6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33, +88,237,149,56,87,174,20,125,136,171,168, 68,175,74,165,71,134,139,48,27,166, +77,146,158,231,83,111,229,122,60,211,133,230,220,105,92,41,55,46,245,40,244, +102,143,54, 65,25,63,161, 1,216,80,73,209,76,132,187,208, 89,18,169,200,196, +135,130,116,188,159,86,164,100,109,198,173,186, 3,64,52,217,226,250,124,123, +5,202,38,147,118,126,255,82,85,212,207,206,59,227,47,16,58,17,182,189,28,42, +223,183,170,213,119,248,152, 2,44,154,163, 70,221,153,101,155,167, 43,172,9, +129,22,39,253, 19,98,108,110,79,113,224,232,178,185, 112,104,218,246,97,228, +251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107, +49,192,214, 31,181,199,106,157,184, 84,204,176,115,121,50,45,127, 4,150,254, +138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180 +}; \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.h new file mode 100644 index 0000000..2f2aba5 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WANoise.h @@ -0,0 +1,459 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + + + +class FNoise +{ +#define FADE(t) ( t * t * t * ( t * ( t * 6 - 15 ) + 10 ) ) + +#define FASTFLOOR(x) ( ((x)>0) ? ((int)x) : ((int)x-1 ) ) +#define LERP(t, a, b) ((a) + (t)*((b)-(a))) + + + //--------------------------------------------------------------------- + // Static data + /* + * Permutation table. This is just a random jumble of all numbers 0-255, + * repeated twice to avoid wrapping the index at 255 for each lookup. + * This needs to be exactly the same for all instances on all platforms, + * so it's easiest to just keep it as static explicit data. + * This also removes the need for any initialisation of this class. + * + * Note that making this an int[] instead of a char[] might make the + * code run faster on platforms with a high penalty for unaligned single + * byte addressing. Intel x86 is generally single-byte-friendly, but + * some other CPUs are faster with 4-aligned reads. + * However, a char[] is smaller, which avoids cache trashing, and that + * is probably the most important aspect on most architectures. + * This array is accessed a *lot* by the noise functions. + * A vector-valued noise over 3D accesses it 96 times, and a + * float-valued 4D noise 64 times. We want this to fit in the cache! + */ +public: + static unsigned char perm[]; + FNoise() + { + + } + static float grad(int hash, float x) { + int h = hash & 15; + float grad = 1.0 + (h & 7); // Gradient value 1.0, 2.0, ..., 8.0 + if (h & 8) grad = -grad; // and a random sign for the gradient + return (grad * x); // Multiply the gradient with the distance + } + + static float grad(int hash, float x, float y) { + int h = hash & 7; // Convert low 3 bits of hash code + float u = h<4 ? x : y; // into 8 simple gradient directions, + float v = h<4 ? y : x; // and compute the dot product with (x,y). + return ((h & 1) ? -u : u) + ((h & 2) ? -2.0*v : 2.0*v); + } + + static float grad(int hash, float x, float y, float z) { + int h = hash & 15; // Convert low 4 bits of hash code into 12 simple + float u = h<8 ? x : y; // gradient directions, and compute dot product. + float v = h<4 ? y : h == 12 || h == 14 ? x : z; // Fix repeats at h = 12 to 15 + return ((h & 1) ? -u : u) + ((h & 2) ? -v : v); + } + + static float grad(int hash, float x, float y, float z, float t) { + int h = hash & 31; // Convert low 5 bits of hash code into 32 simple + float u = h<24 ? x : y; // gradient directions, and compute dot product. + float v = h<16 ? y : z; + float w = h<8 ? z : t; + return ((h & 1) ? -u : u) + ((h & 2) ? -v : v) + ((h & 4) ? -w : w); + } + + //--------------------------------------------------------------------- + /** 1D float Perlin noise, SL "noise()" + */ + static float noise(float x) + { + int ix0, ix1; + float fx0, fx1; + float s, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + fx0 = x - ix0; // Fractional part of x + fx1 = fx0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; + ix0 = ix0 & 0xff; // Wrap to 0..255 + + s = FADE(fx0); + + n0 = grad(perm[ix0], fx0); + n1 = grad(perm[ix1], fx1); + return 0.188f * (LERP(s, n0, n1)); + } + + //--------------------------------------------------------------------- + /** 1D float Perlin periodic noise, SL "pnoise()" + */ + static float pnoise(float x, int px) + { + int ix0, ix1; + float fx0, fx1; + float s, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + fx0 = x - ix0; // Fractional part of x + fx1 = fx0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 *and* wrap to 0..255 + ix0 = (ix0 % px) & 0xff; // (because px might be greater than 256) + + s = FADE(fx0); + + n0 = grad(perm[ix0], fx0); + n1 = grad(perm[ix1], fx1); + return 0.188f * (LERP(s, n0, n1)); + } + + + //--------------------------------------------------------------------- + /** 2D float Perlin noise. + */ + static float noise(float x, float y) + { + int ix0, iy0, ix1, iy1; + float fx0, fy0, fx1, fy1; + float s, t, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; // Wrap to 0..255 + iy1 = (iy0 + 1) & 0xff; + ix0 = ix0 & 0xff; + iy0 = iy0 & 0xff; + + t = FADE(fy0); + s = FADE(fx0); + + nx0 = grad(perm[ix0 + perm[iy0]], fx0, fy0); + nx1 = grad(perm[ix0 + perm[iy1]], fx0, fy1); + n0 = LERP(t, nx0, nx1); + + nx0 = grad(perm[ix1 + perm[iy0]], fx1, fy0); + nx1 = grad(perm[ix1 + perm[iy1]], fx1, fy1); + n1 = LERP(t, nx0, nx1); + + return 0.507f * (LERP(s, n0, n1)); + } + + //--------------------------------------------------------------------- + /** 2D float Perlin periodic noise. + */ + static float pnoise(float x, float y, int px, int py) + { + int ix0, iy0, ix1, iy1; + float fx0, fy0, fx1, fy1; + float s, t, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 and wrap to 0..255 + iy1 = ((iy0 + 1) % py) & 0xff; // Wrap to 0..py-1 and wrap to 0..255 + ix0 = (ix0 % px) & 0xff; + iy0 = (iy0 % py) & 0xff; + + t = FADE(fy0); + s = FADE(fx0); + + nx0 = grad(perm[ix0 + perm[iy0]], fx0, fy0); + nx1 = grad(perm[ix0 + perm[iy1]], fx0, fy1); + n0 = LERP(t, nx0, nx1); + + nx0 = grad(perm[ix1 + perm[iy0]], fx1, fy0); + nx1 = grad(perm[ix1 + perm[iy1]], fx1, fy1); + n1 = LERP(t, nx0, nx1); + + return 0.507f * (LERP(s, n0, n1)); + } + + + //--------------------------------------------------------------------- + /** 3D float Perlin noise. + */ + static float noise(float x, float y, float z) + { + int ix0, iy0, ix1, iy1, iz0, iz1; + float fx0, fy0, fz0, fx1, fy1, fz1; + float s, t, r; + float nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of z + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; // Wrap to 0..255 + iy1 = (iy0 + 1) & 0xff; + iz1 = (iz0 + 1) & 0xff; + ix0 = ix0 & 0xff; + iy0 = iy0 & 0xff; + iz0 = iz0 & 0xff; + + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxy0 = grad(perm[ix0 + perm[iy0 + perm[iz0]]], fx0, fy0, fz0); + nxy1 = grad(perm[ix0 + perm[iy0 + perm[iz1]]], fx0, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix0 + perm[iy1 + perm[iz0]]], fx0, fy1, fz0); + nxy1 = grad(perm[ix0 + perm[iy1 + perm[iz1]]], fx0, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxy0 = grad(perm[ix1 + perm[iy0 + perm[iz0]]], fx1, fy0, fz0); + nxy1 = grad(perm[ix1 + perm[iy0 + perm[iz1]]], fx1, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix1 + perm[iy1 + perm[iz0]]], fx1, fy1, fz0); + nxy1 = grad(perm[ix1 + perm[iy1 + perm[iz1]]], fx1, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.936f * (LERP(s, n0, n1)); + } + + //--------------------------------------------------------------------- + /** 3D float Perlin periodic noise. + */ + static float pnoise(float x, float y, float z, int px, int py, int pz) + { + int ix0, iy0, ix1, iy1, iz0, iz1; + float fx0, fy0, fz0, fx1, fy1, fz1; + float s, t, r; + float nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of z + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 and wrap to 0..255 + iy1 = ((iy0 + 1) % py) & 0xff; // Wrap to 0..py-1 and wrap to 0..255 + iz1 = ((iz0 + 1) % pz) & 0xff; // Wrap to 0..pz-1 and wrap to 0..255 + ix0 = (ix0 % px) & 0xff; + iy0 = (iy0 % py) & 0xff; + iz0 = (iz0 % pz) & 0xff; + + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxy0 = grad(perm[ix0 + perm[iy0 + perm[iz0]]], fx0, fy0, fz0); + nxy1 = grad(perm[ix0 + perm[iy0 + perm[iz1]]], fx0, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix0 + perm[iy1 + perm[iz0]]], fx0, fy1, fz0); + nxy1 = grad(perm[ix0 + perm[iy1 + perm[iz1]]], fx0, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxy0 = grad(perm[ix1 + perm[iy0 + perm[iz0]]], fx1, fy0, fz0); + nxy1 = grad(perm[ix1 + perm[iy0 + perm[iz1]]], fx1, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix1 + perm[iy1 + perm[iz0]]], fx1, fy1, fz0); + nxy1 = grad(perm[ix1 + perm[iy1 + perm[iz1]]], fx1, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.936f * (LERP(s, n0, n1)); + } + + + //--------------------------------------------------------------------- + /** 4D float Perlin noise. + */ + + static float noise(float x, float y, float z, float w) + { + int ix0, iy0, iz0, iw0, ix1, iy1, iz1, iw1; + float fx0, fy0, fz0, fw0, fx1, fy1, fz1, fw1; + float s, t, r, q; + float nxyz0, nxyz1, nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of y + iw0 = FASTFLOOR(w); // Integer part of w + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fw0 = w - iw0; // Fractional part of w + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + fw1 = fw0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; // Wrap to 0..255 + iy1 = (iy0 + 1) & 0xff; + iz1 = (iz0 + 1) & 0xff; + iw1 = (iw0 + 1) & 0xff; + ix0 = ix0 & 0xff; + iy0 = iy0 & 0xff; + iz0 = iz0 & 0xff; + iw0 = iw0 & 0xff; + + q = FADE(fw0); + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx0, fy0, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx0, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx0, fy0, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx0, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx0, fy1, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx0, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx0, fy1, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx0, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx1, fy0, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx1, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx1, fy0, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx1, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx1, fy1, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx1, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx1, fy1, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx1, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.87f * (LERP(s, n0, n1)); + } + + //--------------------------------------------------------------------- + /** 4D float Perlin periodic noise. + */ + + static float pnoise(float x, float y, float z, float w, + int px, int py, int pz, int pw) + { + int ix0, iy0, iz0, iw0, ix1, iy1, iz1, iw1; + float fx0, fy0, fz0, fw0, fx1, fy1, fz1, fw1; + float s, t, r, q; + float nxyz0, nxyz1, nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of y + iw0 = FASTFLOOR(w); // Integer part of w + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fw0 = w - iw0; // Fractional part of w + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + fw1 = fw0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 and wrap to 0..255 + iy1 = ((iy0 + 1) % py) & 0xff; // Wrap to 0..py-1 and wrap to 0..255 + iz1 = ((iz0 + 1) % pz) & 0xff; // Wrap to 0..pz-1 and wrap to 0..255 + iw1 = ((iw0 + 1) % pw) & 0xff; // Wrap to 0..pw-1 and wrap to 0..255 + ix0 = (ix0 % px) & 0xff; + iy0 = (iy0 % py) & 0xff; + iz0 = (iz0 % pz) & 0xff; + iw0 = (iw0 % pw) & 0xff; + + q = FADE(fw0); + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx0, fy0, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx0, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx0, fy0, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx0, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx0, fy1, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx0, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx0, fy1, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx0, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx1, fy0, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx1, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx1, fy0, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx1, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx1, fy1, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx1, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx1, fy1, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx1, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.87f * (LERP(s, n0, n1)); + } + +}; \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.cpp new file mode 100644 index 0000000..555b953 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.cpp @@ -0,0 +1,50 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "WorldArchitectEdMode.h" +#include "WorldArchitectEdModeToolkit.h" +#include "Toolkits/ToolkitManager.h" +#include "EditorModeManager.h" + +const FEditorModeID FWorldArchitectEdMode::EM_WorldArchitectEdModeId = TEXT("EM_WorldArchitectEdMode"); + +FWorldArchitectEdMode::FWorldArchitectEdMode() +{ + +} + +FWorldArchitectEdMode::~FWorldArchitectEdMode() +{ + +} + +void FWorldArchitectEdMode::Enter() +{ + FEdMode::Enter(); + + if (!Toolkit.IsValid() && UsesToolkits()) + { + Toolkit = MakeShareable(new FWorldArchitectEdModeToolkit); + Toolkit->Init(Owner->GetToolkitHost()); + } +} + +void FWorldArchitectEdMode::Exit() +{ + if (Toolkit.IsValid()) + { + FToolkitManager::Get().CloseToolkit(Toolkit.ToSharedRef()); + Toolkit.Reset(); + } + + // Call base Exit method to ensure proper cleanup + FEdMode::Exit(); +} + +bool FWorldArchitectEdMode::UsesToolkits() const +{ + return true; +} + + + + diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.h new file mode 100644 index 0000000..6a04795 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdMode.h @@ -0,0 +1,24 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "EdMode.h" + +class FWorldArchitectEdMode : public FEdMode +{ +public: + const static FEditorModeID EM_WorldArchitectEdModeId; +public: + FWorldArchitectEdMode(); + virtual ~FWorldArchitectEdMode(); + + // FEdMode interface + virtual void Enter() override; + virtual void Exit() override; + //virtual void Tick(FEditorViewportClient* ViewportClient, float DeltaTime) override; + //virtual void Render(const FSceneView* View, FViewport* Viewport, FPrimitiveDrawInterface* PDI) override; + //virtual void ActorSelectionChangeNotify() override; + bool UsesToolkits() const override; + // End of FEdMode interface +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.cpp new file mode 100644 index 0000000..8a0a028 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.cpp @@ -0,0 +1,857 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "WorldArchitectEdModeToolkit.h" +#include "WorldArchitectEdMode.h" +#include "Engine/Selection.h" +#include "Widgets/Input/SButton.h" +#include "Widgets/Text/STextBlock.h" +#include "EditorModeManager.h" +#include "Landscape.h" +#include "LandscapeInfo.h" +#include "EngineUtils.h" +#include "LandscapeEditorUtils.h" +#include "LandscapeInfoMap.h" +#include "LandscapeStreamingProxy.h" +#include "PropertyCustomizationHelpers.h" +#include "Runtime/WALandscapeGraph.h" +#include "WALandscapeGraphFactory.h" +#include "LandscapeGraphEditor/WALandscapeGraphSchema.h" +#include "LandscapeGraphEditor/WALandscapeGraphEdNode_Output.h" + +// Noise1234 +// Author: Stefan Gustavson (stegu@itn.liu.se) +// +// This library is public domain software, released by the author +// into the public domain in February 2011. You may do anything +// you like with it. You may even remove all attributions, +// but of course I'd appreciate it if you kept my name somewhere. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. + +/** \file +\brief Implements the Noise1234 class for producing Perlin noise. +\author Stefan Gustavson (stegu@itn.liu.se) +*/ + +/* +* This implementation is "Improved Noise" as presented by +* Ken Perlin at Siggraph 2002. The 3D function is a direct port +* of his Java reference code available on www.noisemachine.com +* (although I cleaned it up and made the code more readable), +* but the 1D, 2D and 4D cases were implemented from scratch +* by me. +* +* This is a highly reusable class. It has no dependencies +* on any other file, apart from its own header file. +*/ + + +// This is the new and improved, C(2) continuous interpolant +#define FADE(t) ( t * t * t * ( t * ( t * 6 - 15 ) + 10 ) ) + +#define FASTFLOOR(x) ( ((x)>0) ? ((int)x) : ((int)x-1 ) ) +#define LERP(t, a, b) ((a) + (t)*((b)-(a))) + + +//--------------------------------------------------------------------- +// Static data + +/* +* Permutation table. This is just a random jumble of all numbers 0-255, +* repeated twice to avoid wrapping the index at 255 for each lookup. +* This needs to be exactly the same for all instances on all platforms, +* so it's easiest to just keep it as static explicit data. +* This also removes the need for any initialisation of this class. +* +* Note that making this an int[] instead of a char[] might make the +* code run faster on platforms with a high penalty for unaligned single +* byte addressing. Intel x86 is generally single-byte-friendly, but +* some other CPUs are faster with 4-aligned reads. +* However, a char[] is smaller, which avoids cache trashing, and that +* is probably the most important aspect on most architectures. +* This array is accessed a *lot* by the noise functions. +* A vector-valued noise over 3D accesses it 96 times, and a +* float-valued 4D noise 64 times. We want this to fit in the cache! +*/ +unsigned char Noise1234::perm[] = { 151,160,137,91,90,15, +131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,23, +190, 6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33, +88,237,149,56,87,174,20,125,136,171,168, 68,175,74,165,71,134,139,48,27,166, +77,146,158,231,83,111,229,122,60,211,133,230,220,105,92,41,55,46,245,40,244, +102,143,54, 65,25,63,161, 1,216,80,73,209,76,132,187,208, 89,18,169,200,196, +135,130,116,188,159,86,164,100,109,198,173,186, 3,64,52,217,226,250,124,123, +5,202,38,147,118,126,255,82,85,212,207,206,59,227,47,16,58,17,182,189,28,42, +223,183,170,213,119,248,152, 2,44,154,163, 70,221,153,101,155,167, 43,172,9, +129,22,39,253, 19,98,108,110,79,113,224,232,178,185, 112,104,218,246,97,228, +251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107, +49,192,214, 31,181,199,106,157,184, 84,204,176,115,121,50,45,127, 4,150,254, +138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180, +151,160,137,91,90,15, +131,13,201,95,96,53,194,233,7,225,140,36,103,30,69,142,8,99,37,240,21,10,23, +190, 6,148,247,120,234,75,0,26,197,62,94,252,219,203,117,35,11,32,57,177,33, +88,237,149,56,87,174,20,125,136,171,168, 68,175,74,165,71,134,139,48,27,166, +77,146,158,231,83,111,229,122,60,211,133,230,220,105,92,41,55,46,245,40,244, +102,143,54, 65,25,63,161, 1,216,80,73,209,76,132,187,208, 89,18,169,200,196, +135,130,116,188,159,86,164,100,109,198,173,186, 3,64,52,217,226,250,124,123, +5,202,38,147,118,126,255,82,85,212,207,206,59,227,47,16,58,17,182,189,28,42, +223,183,170,213,119,248,152, 2,44,154,163, 70,221,153,101,155,167, 43,172,9, +129,22,39,253, 19,98,108,110,79,113,224,232,178,185, 112,104,218,246,97,228, +251,34,242,193,238,210,144,12,191,179,162,241, 81,51,145,235,249,14,239,107, +49,192,214, 31,181,199,106,157,184, 84,204,176,115,121,50,45,127, 4,150,254, +138,236,205,93,222,114,67,29,24,72,243,141,128,195,78,66,215,61,156,180 +}; + +//--------------------------------------------------------------------- + +/* +* Helper functions to compute gradients-dot-residualvectors (1D to 4D) +* Note that these generate gradients of more than unit length. To make +* a close match with the value range of classic Perlin noise, the final +* noise values need to be rescaled. To match the RenderMan noise in a +* statistical sense, the approximate scaling values (empirically +* determined from test renderings) are: +* 1D noise needs rescaling with 0.188 +* 2D noise needs rescaling with 0.507 +* 3D noise needs rescaling with 0.936 +* 4D noise needs rescaling with 0.87 +* Note that these noise functions are the most practical and useful +* signed version of Perlin noise. To return values according to the +* RenderMan specification from the SL noise() and pnoise() functions, +* the noise values need to be scaled and offset to [0,1], like this: +* float SLnoise = (Noise1234::noise(x,y,z) + 1.0) * 0.5; +*/ + +float Noise1234::grad(int hash, float x) { + int h = hash & 15; + float grad = 1.0 + (h & 7); // Gradient value 1.0, 2.0, ..., 8.0 + if (h & 8) grad = -grad; // and a random sign for the gradient + return (grad * x); // Multiply the gradient with the distance +} + +float Noise1234::grad(int hash, float x, float y) { + int h = hash & 7; // Convert low 3 bits of hash code + float u = h<4 ? x : y; // into 8 simple gradient directions, + float v = h<4 ? y : x; // and compute the dot product with (x,y). + return ((h & 1) ? -u : u) + ((h & 2) ? -2.0*v : 2.0*v); +} + +float Noise1234::grad(int hash, float x, float y, float z) { + int h = hash & 15; // Convert low 4 bits of hash code into 12 simple + float u = h<8 ? x : y; // gradient directions, and compute dot product. + float v = h<4 ? y : h == 12 || h == 14 ? x : z; // Fix repeats at h = 12 to 15 + return ((h & 1) ? -u : u) + ((h & 2) ? -v : v); +} + +float Noise1234::grad(int hash, float x, float y, float z, float t) { + int h = hash & 31; // Convert low 5 bits of hash code into 32 simple + float u = h<24 ? x : y; // gradient directions, and compute dot product. + float v = h<16 ? y : z; + float w = h<8 ? z : t; + return ((h & 1) ? -u : u) + ((h & 2) ? -v : v) + ((h & 4) ? -w : w); +} + +//--------------------------------------------------------------------- +/** 1D float Perlin noise, SL "noise()" +*/ +float Noise1234::noise(float x) +{ + int ix0, ix1; + float fx0, fx1; + float s, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + fx0 = x - ix0; // Fractional part of x + fx1 = fx0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; + ix0 = ix0 & 0xff; // Wrap to 0..255 + + s = FADE(fx0); + + n0 = grad(perm[ix0], fx0); + n1 = grad(perm[ix1], fx1); + return 0.188f * (LERP(s, n0, n1)); +} + +//--------------------------------------------------------------------- +/** 1D float Perlin periodic noise, SL "pnoise()" +*/ +float Noise1234::pnoise(float x, int px) +{ + int ix0, ix1; + float fx0, fx1; + float s, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + fx0 = x - ix0; // Fractional part of x + fx1 = fx0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 *and* wrap to 0..255 + ix0 = (ix0 % px) & 0xff; // (because px might be greater than 256) + + s = FADE(fx0); + + n0 = grad(perm[ix0], fx0); + n1 = grad(perm[ix1], fx1); + return 0.188f * (LERP(s, n0, n1)); +} + + +//--------------------------------------------------------------------- +/** 2D float Perlin noise. +*/ +float Noise1234::noise(float x, float y) +{ + int ix0, iy0, ix1, iy1; + float fx0, fy0, fx1, fy1; + float s, t, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; // Wrap to 0..255 + iy1 = (iy0 + 1) & 0xff; + ix0 = ix0 & 0xff; + iy0 = iy0 & 0xff; + + t = FADE(fy0); + s = FADE(fx0); + + nx0 = grad(perm[ix0 + perm[iy0]], fx0, fy0); + nx1 = grad(perm[ix0 + perm[iy1]], fx0, fy1); + n0 = LERP(t, nx0, nx1); + + nx0 = grad(perm[ix1 + perm[iy0]], fx1, fy0); + nx1 = grad(perm[ix1 + perm[iy1]], fx1, fy1); + n1 = LERP(t, nx0, nx1); + + return 0.507f * (LERP(s, n0, n1)); +} + +//--------------------------------------------------------------------- +/** 2D float Perlin periodic noise. +*/ +float Noise1234::pnoise(float x, float y, int px, int py) +{ + int ix0, iy0, ix1, iy1; + float fx0, fy0, fx1, fy1; + float s, t, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 and wrap to 0..255 + iy1 = ((iy0 + 1) % py) & 0xff; // Wrap to 0..py-1 and wrap to 0..255 + ix0 = (ix0 % px) & 0xff; + iy0 = (iy0 % py) & 0xff; + + t = FADE(fy0); + s = FADE(fx0); + + nx0 = grad(perm[ix0 + perm[iy0]], fx0, fy0); + nx1 = grad(perm[ix0 + perm[iy1]], fx0, fy1); + n0 = LERP(t, nx0, nx1); + + nx0 = grad(perm[ix1 + perm[iy0]], fx1, fy0); + nx1 = grad(perm[ix1 + perm[iy1]], fx1, fy1); + n1 = LERP(t, nx0, nx1); + + return 0.507f * (LERP(s, n0, n1)); +} + + +//--------------------------------------------------------------------- +/** 3D float Perlin noise. +*/ +float Noise1234::noise(float x, float y, float z) +{ + int ix0, iy0, ix1, iy1, iz0, iz1; + float fx0, fy0, fz0, fx1, fy1, fz1; + float s, t, r; + float nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of z + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; // Wrap to 0..255 + iy1 = (iy0 + 1) & 0xff; + iz1 = (iz0 + 1) & 0xff; + ix0 = ix0 & 0xff; + iy0 = iy0 & 0xff; + iz0 = iz0 & 0xff; + + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxy0 = grad(perm[ix0 + perm[iy0 + perm[iz0]]], fx0, fy0, fz0); + nxy1 = grad(perm[ix0 + perm[iy0 + perm[iz1]]], fx0, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix0 + perm[iy1 + perm[iz0]]], fx0, fy1, fz0); + nxy1 = grad(perm[ix0 + perm[iy1 + perm[iz1]]], fx0, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxy0 = grad(perm[ix1 + perm[iy0 + perm[iz0]]], fx1, fy0, fz0); + nxy1 = grad(perm[ix1 + perm[iy0 + perm[iz1]]], fx1, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix1 + perm[iy1 + perm[iz0]]], fx1, fy1, fz0); + nxy1 = grad(perm[ix1 + perm[iy1 + perm[iz1]]], fx1, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.936f * (LERP(s, n0, n1)); +} + +//--------------------------------------------------------------------- +/** 3D float Perlin periodic noise. +*/ +float Noise1234::pnoise(float x, float y, float z, int px, int py, int pz) +{ + int ix0, iy0, ix1, iy1, iz0, iz1; + float fx0, fy0, fz0, fx1, fy1, fz1; + float s, t, r; + float nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of z + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 and wrap to 0..255 + iy1 = ((iy0 + 1) % py) & 0xff; // Wrap to 0..py-1 and wrap to 0..255 + iz1 = ((iz0 + 1) % pz) & 0xff; // Wrap to 0..pz-1 and wrap to 0..255 + ix0 = (ix0 % px) & 0xff; + iy0 = (iy0 % py) & 0xff; + iz0 = (iz0 % pz) & 0xff; + + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxy0 = grad(perm[ix0 + perm[iy0 + perm[iz0]]], fx0, fy0, fz0); + nxy1 = grad(perm[ix0 + perm[iy0 + perm[iz1]]], fx0, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix0 + perm[iy1 + perm[iz0]]], fx0, fy1, fz0); + nxy1 = grad(perm[ix0 + perm[iy1 + perm[iz1]]], fx0, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxy0 = grad(perm[ix1 + perm[iy0 + perm[iz0]]], fx1, fy0, fz0); + nxy1 = grad(perm[ix1 + perm[iy0 + perm[iz1]]], fx1, fy0, fz1); + nx0 = LERP(r, nxy0, nxy1); + + nxy0 = grad(perm[ix1 + perm[iy1 + perm[iz0]]], fx1, fy1, fz0); + nxy1 = grad(perm[ix1 + perm[iy1 + perm[iz1]]], fx1, fy1, fz1); + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.936f * (LERP(s, n0, n1)); +} + + +//--------------------------------------------------------------------- +/** 4D float Perlin noise. +*/ + +float Noise1234::noise(float x, float y, float z, float w) +{ + int ix0, iy0, iz0, iw0, ix1, iy1, iz1, iw1; + float fx0, fy0, fz0, fw0, fx1, fy1, fz1, fw1; + float s, t, r, q; + float nxyz0, nxyz1, nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of y + iw0 = FASTFLOOR(w); // Integer part of w + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fw0 = w - iw0; // Fractional part of w + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + fw1 = fw0 - 1.0f; + ix1 = (ix0 + 1) & 0xff; // Wrap to 0..255 + iy1 = (iy0 + 1) & 0xff; + iz1 = (iz0 + 1) & 0xff; + iw1 = (iw0 + 1) & 0xff; + ix0 = ix0 & 0xff; + iy0 = iy0 & 0xff; + iz0 = iz0 & 0xff; + iw0 = iw0 & 0xff; + + q = FADE(fw0); + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx0, fy0, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx0, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx0, fy0, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx0, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx0, fy1, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx0, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx0, fy1, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx0, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx1, fy0, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx1, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx1, fy0, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx1, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx1, fy1, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx1, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx1, fy1, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx1, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.87f * (LERP(s, n0, n1)); +} + +//--------------------------------------------------------------------- +/** 4D float Perlin periodic noise. +*/ + +float Noise1234::pnoise(float x, float y, float z, float w, + int px, int py, int pz, int pw) +{ + int ix0, iy0, iz0, iw0, ix1, iy1, iz1, iw1; + float fx0, fy0, fz0, fw0, fx1, fy1, fz1, fw1; + float s, t, r, q; + float nxyz0, nxyz1, nxy0, nxy1, nx0, nx1, n0, n1; + + ix0 = FASTFLOOR(x); // Integer part of x + iy0 = FASTFLOOR(y); // Integer part of y + iz0 = FASTFLOOR(z); // Integer part of y + iw0 = FASTFLOOR(w); // Integer part of w + fx0 = x - ix0; // Fractional part of x + fy0 = y - iy0; // Fractional part of y + fz0 = z - iz0; // Fractional part of z + fw0 = w - iw0; // Fractional part of w + fx1 = fx0 - 1.0f; + fy1 = fy0 - 1.0f; + fz1 = fz0 - 1.0f; + fw1 = fw0 - 1.0f; + ix1 = ((ix0 + 1) % px) & 0xff; // Wrap to 0..px-1 and wrap to 0..255 + iy1 = ((iy0 + 1) % py) & 0xff; // Wrap to 0..py-1 and wrap to 0..255 + iz1 = ((iz0 + 1) % pz) & 0xff; // Wrap to 0..pz-1 and wrap to 0..255 + iw1 = ((iw0 + 1) % pw) & 0xff; // Wrap to 0..pw-1 and wrap to 0..255 + ix0 = (ix0 % px) & 0xff; + iy0 = (iy0 % py) & 0xff; + iz0 = (iz0 % pz) & 0xff; + iw0 = (iw0 % pw) & 0xff; + + q = FADE(fw0); + r = FADE(fz0); + t = FADE(fy0); + s = FADE(fx0); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx0, fy0, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx0, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx0, fy0, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx0, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx0, fy1, fz0, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx0, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx0, fy1, fz1, fw0); + nxyz1 = grad(perm[ix0 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx0, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n0 = LERP(t, nx0, nx1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw0]]]], fx1, fy0, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz0 + perm[iw1]]]], fx1, fy0, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw0]]]], fx1, fy0, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy0 + perm[iz1 + perm[iw1]]]], fx1, fy0, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx0 = LERP(r, nxy0, nxy1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw0]]]], fx1, fy1, fz0, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz0 + perm[iw1]]]], fx1, fy1, fz0, fw1); + nxy0 = LERP(q, nxyz0, nxyz1); + + nxyz0 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw0]]]], fx1, fy1, fz1, fw0); + nxyz1 = grad(perm[ix1 + perm[iy1 + perm[iz1 + perm[iw1]]]], fx1, fy1, fz1, fw1); + nxy1 = LERP(q, nxyz0, nxyz1); + + nx1 = LERP(r, nxy0, nxy1); + + n1 = LERP(t, nx0, nx1); + + return 0.87f * (LERP(s, n0, n1)); +} + +//--------------------------------------------------------------------- + +#define LOCTEXT_NAMESPACE "FWorldArchitectEdModeToolkit" + +FWorldArchitectEdModeToolkit::FWorldArchitectEdModeToolkit() +{ +} + +void FWorldArchitectEdModeToolkit::Init(const TSharedPtr& InitToolkitHost) +{ + struct Locals + { + static bool IsWidgetEnabled() + { + return GEditor->GetSelectedActors()->Num() != 0; + } + + static FReply OnButtonClick(FVector InOffset) + { + USelection* SelectedActors = GEditor->GetSelectedActors(); + + // Let editor know that we're about to do something that we want to undo/redo + GEditor->BeginTransaction(LOCTEXT("MoveActorsTransactionName", "MoveActors")); + + // For each selected actor + for (FSelectionIterator Iter(*SelectedActors); Iter; ++Iter) + { + if (AActor* LevelActor = Cast(*Iter)) + { + // Register actor in opened transaction (undo/redo) + LevelActor->Modify(); + // Move actor to given location + LevelActor->TeleportTo(LevelActor->GetActorLocation() + InOffset, FRotator(0, 0, 0)); + } + } + + // We're done moving actors so close transaction + GEditor->EndTransaction(); + + return FReply::Handled(); + } + + static TSharedRef MakeButton(FText InLabel, const FVector InOffset) + { + return SNew(SButton) + .Text(InLabel) + .OnClicked_Static(&Locals::OnButtonClick, InOffset); + } + }; + + const float Factor = 256.0f; + FAssetData DefaultAsset; + FOnGetAllowedClasses OnGetAllowedClassesDel = FOnGetAllowedClasses::CreateSP(this, &FWorldArchitectEdModeToolkit::OnGetAllowedClasses); + FOnAssetSelected OnAssetSelectedFromPickerDel = FOnAssetSelected::CreateSP(this, &FWorldArchitectEdModeToolkit::OnAssetSelected); + FOnShouldFilterAsset OnShouldFilterAssetDel = FOnShouldFilterAsset::CreateSP(this, &FWorldArchitectEdModeToolkit::OnShouldFilterAsset); + FSimpleDelegate OnCloseDel; + TArray AllowedClasses; + AllowedClasses.Add(UWALandscapeGraph::StaticClass()); + TArray NewAssetFactory; + NewAssetFactory.Add(UWALandscapeGraphFactory::StaticClass()->GetDefaultObject()); + + SAssignNew(ToolkitWidget, SBorder) + .HAlign(HAlign_Center) + .Padding(25) + //.IsEnabled_Static(&Locals::IsWidgetEnabled) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Center) + .Padding(50) + [ + SNew(STextBlock) + .AutoWrapText(true) + .Text(LOCTEXT("HelperLabel", "Select some actors and move them around using buttons below")) + ] + + SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + Locals::MakeButton(LOCTEXT("UpButtonLabel", "Up"), FVector(0, 0, Factor)) + ] + + SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + SNew(SHorizontalBox) + + SHorizontalBox::Slot() + .AutoWidth() + [ + Locals::MakeButton(LOCTEXT("LeftButtonLabel", "Left"), FVector(0, -Factor, 0)) + ] + + SHorizontalBox::Slot() + .AutoWidth() + [ + Locals::MakeButton(LOCTEXT("RightButtonLabel", "Right"), FVector(0, Factor, 0)) + ] + ] + + SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + Locals::MakeButton(LOCTEXT("DownButtonLabel", "Down"), FVector(0, 0, -Factor)) + ] + + SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + SNew(SButton) + .Text(FText::FromString("Make Noise")) + .OnClicked(this, &FWorldArchitectEdModeToolkit::OnGenerateNoise) + ] + + SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + SNew(SButton) + .Text(FText::FromString("Generate Landscape")) + .OnClicked(this, &FWorldArchitectEdModeToolkit::OnGenerateLandscape) + ] + + SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + SNew(STextBlock) + .Text(this, &FWorldArchitectEdModeToolkit::OnGetGraphName) + + ] + +SVerticalBox::Slot() + .HAlign(HAlign_Center) + .AutoHeight() + [ + //PropertyCustomizationHelpers::MakeAssetPickerAnchorButton(OnGetAllowedClassesDel, OnAssetSelectedFromPickerDel) + PropertyCustomizationHelpers::MakeAssetPickerWithMenu(DefaultAsset, true, AllowedClasses, NewAssetFactory, OnShouldFilterAssetDel, OnAssetSelectedFromPickerDel, OnCloseDel) + ] + + ]; + + FModeToolkit::Init(InitToolkitHost); +} + +FName FWorldArchitectEdModeToolkit::GetToolkitFName() const +{ + return FName("WorldArchitectEdMode"); +} + +FText FWorldArchitectEdModeToolkit::GetBaseToolkitName() const +{ + return NSLOCTEXT("WorldArchitectEdModeToolkit", "DisplayName", "WorldArchitectEdMode Tool"); +} + +class FEdMode* FWorldArchitectEdModeToolkit::GetEditorMode() const +{ + return GLevelEditorModeTools().GetActiveMode(FWorldArchitectEdMode::EM_WorldArchitectEdModeId); +} +uint16 FWorldArchitectEdModeToolkit::PerlinNoise2D(float x, float y, float amp, int32 octaves, int32 px, int32 py) +{ + float noise = 0.f; + for (int octave = 1; octave < octaves; octave *= 2) + noise += Noise1234::pnoise( x*px*octave, y*py*octave, px, py ) / octave; + + return USHRT_MAX/2.f + amp*noise; +} +float FWorldArchitectEdModeToolkit::PerlinNoise2DFloat(float x, float y, float amp, int32 octaves, int32 px, int32 py) +{ + float noise = 0.f; + for (int octave = 1; octave < octaves; octave *= 2) + noise += Noise1234::pnoise(x*px*octave, y*py*octave, px, py) / octave; + + return noise; +} +FReply FWorldArchitectEdModeToolkit::OnGenerateNoise() +{ + GEditor->GetWorld(); + TArray Landscapes; + for (TActorIterator LIter(GetEditorMode()->GetWorld()); LIter; ++LIter) + { + Landscapes.Add(*LIter); + } + auto& LandscapeInfoMap = ULandscapeInfoMap::GetLandscapeInfoMap(GetEditorMode()->GetWorld()); + + + if (Landscapes.Num() > 0) + { + FIntRect bounds = Landscapes[0]->GetBoundingRect(); + + int32 numHeights = (bounds.Width() + 1)*(bounds.Height() + 1); + TArray Data; + Data.Init(0, numHeights); + TArray DataFloat; + DataFloat.Init(0, numHeights); + TArray DataFloat2; + DataFloat2.Init(0, numHeights); + TArray DataFloat3; + DataFloat3.Init(0, numHeights); + + int32 cols = bounds.Width() + 1, rows = bounds.Height() + 1; + int32 octaves = 16, px = 4, py = 4; + float amplitude = 20000.f; + //for (int i = 0; i < Data.Num(); i++) + //{ + // float nx = (i % cols) / (float)cols; //normalized col + // float ny = (i / cols) / (float)rows; //normalized row + // Data[i] = FMath::Clamp(PerlinNoise2D(nx, ny, amplitude, octaves, px, py), 0, 32768); + //} + for (int i = 0; i < DataFloat.Num(); i++) + { + float nx = (i % cols) / (float)cols; //normalized col + float ny = (i / cols) / (float)rows; //normalized row + DataFloat[i] = PerlinNoise2DFloat(nx, ny, amplitude, octaves, px, py); + DataFloat2[i] = PerlinNoise2DFloat(nx, ny, amplitude, 4, 12, 12); + DataFloat3[i] = DataFloat[i] * DataFloat2[i]; + } + for (int i = 0; i < Data.Num(); i++) + { + Data[i] = (USHRT_MAX / 2.f) + (DataFloat3[i] * amplitude); + } + ULandscapeInfo::RecreateLandscapeInfo(GetEditorMode()->GetWorld(), 1); + LandscapeEditorUtils::SetHeightmapData(Landscapes[0], Data); + ULandscapeInfo::RecreateLandscapeInfo(GetEditorMode()->GetWorld(), 1); + for (auto It = LandscapeInfoMap.Map.CreateIterator(); It; ++It) + { + ULandscapeInfo* LandscapeInfo = It.Value(); + if (LandscapeInfo && !LandscapeInfo->IsPendingKill()) + { + ALandscapeProxy* LandscapeProxy = LandscapeInfo->GetLandscapeProxy(); + if (LandscapeProxy) + { + for (ALandscapeStreamingProxy* Proxy : LandscapeInfo->Proxies) + { + ULandscapeInfo::RecreateLandscapeInfo(GetEditorMode()->GetWorld(), 1); + LandscapeEditorUtils::SetHeightmapData(Proxy, Data); + ULandscapeInfo::RecreateLandscapeInfo(GetEditorMode()->GetWorld(), 1); + } + + //if (CurrentToolTarget.LandscapeInfo == LandscapeInfo) + { + //CurrentIndex = Index; + + // Update GizmoActor Landscape Target (is this necessary?) + //if (CurrentGizmoActor.IsValid()) + { + // CurrentGizmoActor->SetTargetLandscape(LandscapeInfo); + } + } + + int32 MinX, MinY, MaxX, MaxY; + int32 Width = 0, Height = 0; + if (LandscapeInfo->GetLandscapeExtent(MinX, MinY, MaxX, MaxY)) + { + Width = MaxX - MinX + 1; + Height = MaxY - MinY + 1; + } + + /*LandscapeList.Add(FLandscapeListInfo(*LandscapeProxy->GetName(), LandscapeInfo, + LandscapeInfo->ComponentSizeQuads, LandscapeInfo->ComponentNumSubsections, Width, Height)); + Index++;*/ + } + } + } + } + + + //LandscapeEditorUtils::SetHeightmapData(Landscapes[0], Data); + + return FReply::Unhandled(); +} +FReply FWorldArchitectEdModeToolkit::OnGenerateLandscape() +{ + if(!LandscapeGraph.IsValid()) + return FReply::Unhandled(); + + //LandscapeGraph->GenerateLandscape(); + if (!LandscapeGraph->Schema) + return FReply::Unhandled(); + + if (!LandscapeGraph->Schema->Output) + return FReply::Unhandled(); + + TArray Out; + LandscapeGraph->Schema->Output->GenerateHeightMap(Out); + return FReply::Handled(); +} +void FWorldArchitectEdModeToolkit::OnAssetSelected(const FAssetData& InAssetData) +{ + UObject* Object = InAssetData.GetAsset(); + if (UWALandscapeGraph* Graph = Cast(Object)) + { + LandscapeGraph = Graph; + return; + } + + LandscapeGraph.Reset(); +} +void FWorldArchitectEdModeToolkit::OnGetAllowedClasses(TArray& OutAllowedClasses) +{ + OutAllowedClasses.Add(UWALandscapeGraph::StaticClass()); +} +bool FWorldArchitectEdModeToolkit::OnShouldFilterAsset(const FAssetData& InAssetData) +{ + return false; +} +FText FWorldArchitectEdModeToolkit::OnGetGraphName() const +{ + if (LandscapeGraph.IsValid()) + { + return FText::FromString(LandscapeGraph->GetName()); + } + + return FText::FromString("No Graph Selected"); +} +#undef LOCTEXT_NAMESPACE diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.h new file mode 100644 index 0000000..4791b20 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEdModeToolkit.h @@ -0,0 +1,91 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Toolkits/BaseToolkit.h" +// Noise1234 +// Author: Stefan Gustavson (stegu@itn.liu.se) +// +// This library is public domain software, released by the author +// into the public domain in February 2011. You may do anything +// you like with it. You may even remove all attributions, +// but of course I'd appreciate it if you kept my name somewhere. +// +// This library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +// General Public License for more details. + +/** \file +\brief Declares the Noise1234 class for producing Perlin noise. +\author Stefan Gustavson (stegu@itn.liu.se) +*/ + +/* +* This is a clean, fast, modern and free Perlin noise class in C++. +* Being a stand-alone class with no external dependencies, it is +* highly reusable without source code modifications. +* +* Note: +* Replacing the "float" type with "double" can actually make this run faster +* on some platforms. A templatized version of Noise1234 could be useful. +*/ + +class Noise1234 { + +public: + Noise1234() {} + ~Noise1234() {} + + /** 1D, 2D, 3D and 4D float Perlin noise, SL "noise()" + */ + static float noise(float x); + static float noise(float x, float y); + static float noise(float x, float y, float z); + static float noise(float x, float y, float z, float w); + + /** 1D, 2D, 3D and 4D float Perlin periodic noise, SL "pnoise()" + */ + static float pnoise(float x, int px); + static float pnoise(float x, float y, int px, int py); + static float pnoise(float x, float y, float z, int px, int py, int pz); + static float pnoise(float x, float y, float z, float w, + int px, int py, int pz, int pw); + +private: + static unsigned char perm[]; + static float grad(int hash, float x); + static float grad(int hash, float x, float y); + static float grad(int hash, float x, float y, float z); + static float grad(int hash, float x, float y, float z, float t); + +}; +class FWorldArchitectEdModeToolkit : public FModeToolkit +{ + + TWeakObjectPtr LandscapeGraph; +public: + + FWorldArchitectEdModeToolkit(); + + /** FModeToolkit interface */ + virtual void Init(const TSharedPtr& InitToolkitHost) override; + + /** IToolkit interface */ + virtual FName GetToolkitFName() const override; + virtual FText GetBaseToolkitName() const override; + virtual class FEdMode* GetEditorMode() const override; + virtual TSharedPtr GetInlineContent() const override { return ToolkitWidget; } + uint16 PerlinNoise2D(float x, float y, float amp, int32 octaves, int32 px, int32 py); + float PerlinNoise2DFloat(float x, float y, float amp, int32 octaves, int32 px, int32 py); + FReply OnGenerateNoise(); + FReply OnGenerateLandscape(); + void OnAssetSelected(const FAssetData& InAssetData); + void OnGetAllowedClasses(TArray& OutAllowedClasses); + bool OnShouldFilterAsset(const FAssetData& InAssetData); + FText OnGetGraphName() const; +private: + + TSharedPtr ToolkitWidget; +}; diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.cpp b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.cpp new file mode 100644 index 0000000..c7ae9d5 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.cpp @@ -0,0 +1,41 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "WorldArchitectEditor.h" +#include "WorldArchitectEdMode.h" +#include "WALandscapeGraphAssetTypeActions.h" +#define LOCTEXT_NAMESPACE "FWorldArchitectModule" +void FWorldArchitectEditorModule::RegisterAssetTypeAction(IAssetTools& AssetTools, + TSharedRef Action) +{ + AssetTools.RegisterAssetTypeActions(Action); + CreatedAssetTypeActions.Add(Action); +} +void FWorldArchitectEditorModule::StartupModule() +{ + IAssetTools& AssetTools = FModuleManager::LoadModuleChecked("AssetTools").Get(); + + GenericGraphAssetCategoryBit = AssetTools.RegisterAdvancedAssetCategory(FName(TEXT("Landscape")), FText::FromString("Landscape")); + RegisterAssetTypeAction(AssetTools, MakeShareable(new FWALandscapeGraphAssetTypeActions(GenericGraphAssetCategoryBit))); + + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module + FEditorModeRegistry::Get().RegisterMode(FWorldArchitectEdMode::EM_WorldArchitectEdModeId, LOCTEXT("WorldArchitectEdModeName", "WorldArchitectEdMode"), FSlateIcon(), true); +} + +void FWorldArchitectEditorModule::ShutdownModule() +{ + if (FModuleManager::Get().IsModuleLoaded("AssetTools")) + { + IAssetTools& AssetTools = FModuleManager::GetModuleChecked("AssetTools").Get(); + for (int32 Index = 0; Index < CreatedAssetTypeActions.Num(); ++Index) + { + AssetTools.UnregisterAssetTypeActions(CreatedAssetTypeActions[Index].ToSharedRef()); + } + } + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. + FEditorModeRegistry::Get().UnregisterMode(FWorldArchitectEdMode::EM_WorldArchitectEdModeId); +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FWorldArchitectEditorModule, WorldArchitect) \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.h b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.h new file mode 100644 index 0000000..01747e7 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/Public/WorldArchitectEditor.h @@ -0,0 +1,18 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "ModuleManager.h" +#include "IAssetTools.h" + +class FWorldArchitectEditorModule : public IModuleInterface +{ + TArray< TSharedPtr > CreatedAssetTypeActions; + EAssetTypeCategories::Type GenericGraphAssetCategoryBit; +public: + void RegisterAssetTypeAction(IAssetTools& AssetTools, TSharedRef Action); + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; \ No newline at end of file diff --git a/Plugins/WorldArchitect/Source/WorldArchitectEditor/WorldArchitectEditor.Build.cs b/Plugins/WorldArchitect/Source/WorldArchitectEditor/WorldArchitectEditor.Build.cs new file mode 100644 index 0000000..6009f34 --- /dev/null +++ b/Plugins/WorldArchitect/Source/WorldArchitectEditor/WorldArchitectEditor.Build.cs @@ -0,0 +1,59 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class WorldArchitectEditor : ModuleRules +{ + public WorldArchitectEditor(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PrivateIncludePaths.AddRange( + new string[] { + "WorldArchitectEditor/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "Core", + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "InputCore", + "UnrealEd", + "LevelEditor", + "Landscape", + "LandscapeEditor", + "GraphEditor", + "PropertyEditor", + "EditorStyle", + "Kismet", + "KismetWidgets", + "ApplicationCore" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp index 2431bd2..01c94f6 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp @@ -221,6 +221,7 @@ void UARUIInventoryComponent::RemoveMagazineUpgrade() return; UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; + //UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); //TSoftClassPtr Item = Weapon->RemoveMagazineUpgrade(); From c67f1ff227916be8491f30c29a4c9283594155be Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 16:23:22 +0200 Subject: [PATCH 155/187] adding back weapon upgrades --- .../Private/IFInventoryComponent.cpp | 18 +++++++++++++++++- .../Public/UI/Inventory/ARItemView.h | 3 +++ .../Public/Weapons/ARItemWeapon.cpp | 4 +++- .../Weapons/ARWeaponInventoryComponent.cpp | 7 +++++-- 4 files changed, 28 insertions(+), 4 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 0b19d93..f32f608 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -272,6 +272,12 @@ void UIFInventoryComponent::RemoveItem(uint8 InIndex) return; } //remove from backend + if (InventoryItems[InIndex].Item) + InventoryItems[InIndex].Item->MarkPendingKill(); + + InventoryItems[InIndex].Item = nullptr; + OnServerItemRemoved(InIndex); + ClientRemoveItem(InIndex); } void UIFInventoryComponent::ServerRemoveItem_Implementation(uint8 InIndex) { @@ -299,7 +305,17 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr ItemClass = InItem.Get(); FIFItemData Item; - Item.Index = 0; + uint8 FreeIndex = 0; + + for (uint8 Idx = 0; Idx < InventoryItems.Num(); Idx++) + { + if (!InventoryItems[Idx].Item) + { + FreeIndex = Idx; + break; + } + } + Item.Index = FreeIndex; Item.Item = NewObject(this, ItemClass); //Inventory.AddItemToFreeSlot(Item); diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.h b/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.h index f72e929..b8efd2c 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.h @@ -16,6 +16,9 @@ class ACTIONRPGGAME_API UARItemView : public UIFItemWidget public: TWeakObjectPtr InventoryComponent; + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + UImage* Icon; + public: virtual void NativeConstruct() override; diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp index f033716..b61023e 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp @@ -22,7 +22,7 @@ void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineU } void UARItemWeapon::OnMagazineUpdateAdded() { - //should be called only fropm server. + //should be called only from server. FARWeaponModInfo Info; Info.Icon = MagazineModificationObj->Icon->GetPathName(); Info.UpgradeType = EARWeaponUpgradeType::Magazine; @@ -46,6 +46,8 @@ void UARItemWeapon::ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& { if (AARHUD* HUD = Cast(PC->GetHUD())) { + UTexture2D* Icon = ModInfo.Icon.LoadSynchronous(); + HUD->GetUIInventory()->GetInventoryView()->MagazineUpgrade->Icon->SetBrushFromTexture(Icon); } } } diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index 2ce5245..126d3a9 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -648,9 +648,9 @@ void UARWeaponInventoryComponent::AddMagazineMod(int8 WeaponIdx, int8 MagazineMo if (GetOwnerRole() < ENetRole::ROLE_Authority) { ServerAddMagazineMod(WeaponIdx, MagazineModIndex); - return; } + //Predictively apply mod on client, and show it on UI. if (AARCharacter* Character = Cast(GetOwner())) { if (AARPlayerController* PC = Cast(Character->Controller)) @@ -664,7 +664,10 @@ void UARWeaponInventoryComponent::AddMagazineMod(int8 WeaponIdx, int8 MagazineMo if (Weapon) { Weapon->AddMagazineUpgrade(Magazine); - MainInventory->RemoveItem(MagazineModIndex); + FARWeaponModInfo Info; + Info.Icon = Magazine->Icon->GetPathName(); + Info.UpgradeType = EARWeaponUpgradeType::Magazine; + Weapon->ClientOnMagazineAdded(Info); } } } From 7c38fd350ec2db13a6441e21cce9d69f68a045b5 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 22:12:41 +0200 Subject: [PATCH 156/187] added ability to remove equiped weapon --- .../Private/IFEquipmentComponent.cpp | 35 ++++++++++++++ .../Private/IFInventoryComponent.cpp | 46 ++++++++++++++++++- .../Public/IFEquipmentComponent.h | 10 ++++ .../Public/IFInventoryComponent.h | 14 ++++++ .../UI/Inventory/ARUIInventoryComponent.cpp | 19 ++++++++ .../UI/Inventory/ARUIInventoryComponent.h | 2 +- .../Inventory/Weapons/ARItemWeaponWidget.cpp | 14 ++++-- 7 files changed, 135 insertions(+), 5 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp index 7d21067..4fcb4dc 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp @@ -83,4 +83,39 @@ void UIFEquipmentComponent::ClientAddItemFromInventory_Implementation(class UIFI OnItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); Source->RemoveItem(SourceIndex); +} + + +void UIFEquipmentComponent::RemoveFromEquipment(uint8 EquipmentIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerRemoveFromEquipment(EquipmentIndex); + return; + } +} + +void UIFEquipmentComponent::ServerRemoveFromEquipment_Implementation(uint8 EquipmentIndex) +{ + if (EquipmentItems[EquipmentIndex].Item) + { + EquipmentItems[EquipmentIndex].Item->MarkPendingKill(); + } + EquipmentItems[EquipmentIndex].Item = nullptr; + ClientRemoveFromEquipment(EquipmentIndex); + OnServerItemRemoved(EquipmentIndex); +} +bool UIFEquipmentComponent::ServerRemoveFromEquipment_Validate(uint8 EquipmentIndex) +{ + return true; +} + +void UIFEquipmentComponent::ClientRemoveFromEquipment_Implementation(uint8 EquipmentIndex) +{ + if (EquipmentItems[EquipmentIndex].Item) + { + EquipmentItems[EquipmentIndex].Item->MarkPendingKill(); + } + EquipmentItems[EquipmentIndex].Item = nullptr; + OnItemRemoved(EquipmentIndex); } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index f32f608..9865855 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -8,6 +8,7 @@ #include "IFItemBase.h" #include "IFItemActorBase.h" #include "IFInventoryInterface.h" +#include "IFEquipmentComponent.h" #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" @@ -264,6 +265,49 @@ void UIFInventoryComponent::ClientAddItemFromEquipment_Implementation(class UIFE } +void UIFInventoryComponent::AddItemFromEquipmentAnySlot(class UIFEquipmentComponent* Source, uint8 SourceIndex) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + UIFItemBase* Item = Source->GetItem(SourceIndex); + if (!Item) + return; + ServerAddItemFromEquipmentAnySlot(Source, SourceIndex); + return; + } +} +void UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex) +{ + UIFItemBase* Item = Source->GetItem(SourceIndex); + if (!Item) + return; + + uint8 FreeSlot = 0; + for (uint8 Idx = 0; Idx < InventoryItems.Num(); Idx++) + { + if (InventoryItems[Idx].Item == nullptr) + { + FreeSlot = Idx; + break; + } + } + + InventoryItems[FreeSlot].Item = DuplicateObject(Item, this); + ClientAddItemFromEquipmentAnySlot(Source, SourceIndex, FreeSlot); +} +bool UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Validate(class UIFEquipmentComponent* Source, uint8 SourceIndex) +{ + return true; +} +void UIFInventoryComponent::ClientAddItemFromEquipmentAnySlot_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex) +{ + UIFItemBase* Item = Source->GetItem(SourceIndex); + + InventoryItems[InventoryIndex].Item = DuplicateObject(Item, this); + Source->RemoveFromEquipment(SourceIndex); +} + + void UIFInventoryComponent::RemoveItem(uint8 InIndex) { if(GetOwnerRole() < ENetRole::ROLE_Authority) @@ -321,7 +365,7 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr Obj = MakeShareable(new FJsonObject()); - FJsonObjectConverter::UStructToJsonObject(Item.StaticStruct(), &Item, Obj.ToSharedRef(), 0, 0); + FJsonObjectConverter::UStructToJsonObject(FIFItemData::StaticStruct(), &Item, Obj.ToSharedRef(), 0, 0); FakeBackend.Add(Obj); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h index 2fce3b5..9e81cda 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h @@ -68,6 +68,16 @@ class INVENTORYFRAMEWORK_API UIFEquipmentComponent : public UActorComponent void ClientAddItemFromInventory(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); void ClientAddItemFromInventory_Implementation(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex); + void RemoveFromEquipment(uint8 EquipmentIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerRemoveFromEquipment(uint8 EquipmentIndex); + void ServerRemoveFromEquipment_Implementation(uint8 EquipmentIndex); + bool ServerRemoveFromEquipment_Validate(uint8 EquipmentIndex); + UFUNCTION(Client, Reliable) + void ClientRemoveFromEquipment(uint8 EquipmentIndex); + void ClientRemoveFromEquipment_Implementation(uint8 EquipmentIndex); + + virtual void OnItemAdded(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemRemoved(uint8 Index) {}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index aa9130c..f2e0824 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -176,6 +176,20 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent void ClientAddItemFromEquipment(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); void ClientAddItemFromEquipment_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + void AddItemFromEquipmentAnySlot(class UIFEquipmentComponent* Source, uint8 SourceIndex); + UFUNCTION(Server, Reliable, WithValidation) + void ServerAddItemFromEquipmentAnySlot(class UIFEquipmentComponent* Source, uint8 SourceIndex); + void ServerAddItemFromEquipmentAnySlot_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex); + bool ServerAddItemFromEquipmentAnySlot_Validate(class UIFEquipmentComponent* Source, uint8 SourceIndex); + /* + Confirm that change can be made and do the same change on client. + We do not predict inventory modifications. Clients MUST wait for server to make changes and send confirmation back. + */ + UFUNCTION(Client, Reliable) + void ClientAddItemFromEquipmentAnySlot(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + void ClientAddItemFromEquipmentAnySlot_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + + virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemRemoved(uint8 LocalIndex) {}; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp index 01c94f6..bab572c 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp @@ -112,6 +112,25 @@ void UARUIInventoryComponent::ShowWeaponsForSlot(class UARItemView* ForSlot) InventoryView->UpdateItemList(Items, ListItemWeaponClass, PC, ForSlot); } +void UARUIInventoryComponent::RemoveWeaponFromSlot(int8 Index) +{ + AARPlayerController* PC = nullptr; + AARCharacter* Character = nullptr; + if (AARHUD* HUD = Cast(GetOwner())) + { + PC = Cast(HUD->PlayerOwner); + + if (!PC) + return; + Character = Cast(PC->GetPawn()); + if (!Character) + return; + + PC->MainInventory->AddItemFromEquipmentAnySlot(Character->WeaponInventory, Index); + + } +} + void UARUIInventoryComponent::AddWeaponToSlot(uint8 TargetNetIndex , uint8 TargetLocalIndex , uint8 SourceNetIndex diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h index ebf345f..cc5a916 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h @@ -52,7 +52,7 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent public: void ShowWeaponsForSlot(class UARItemView* ForSlot); - + void RemoveWeaponFromSlot(int8 Index); void AddWeaponToSlot(uint8 TargetNetIndex , uint8 TargetLocalIndex , uint8 SourceNetIndex diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index 7056fa6..b625792 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -39,9 +39,17 @@ void UARItemWeaponWidget::NativeConstruct() FReply UARItemWeaponWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { - UObject* Out = GetOuter(); - UARInventoryScreenWidget* MainView = Cast(Out); - InventoryComponent->ShowWeaponsForSlot(this); + if (InMouseEvent.GetEffectingButton() == EKeys::LeftMouseButton) + { + UObject* Out = GetOuter(); + UARInventoryScreenWidget* MainView = Cast(Out); + InventoryComponent->ShowWeaponsForSlot(this); + } + else if (InMouseEvent.GetEffectingButton() == EKeys::RightMouseButton) + { + InventoryComponent->RemoveWeaponFromSlot(LocalIndex); + } + return FReply::Handled(); } From c8d787f3b2ca6002f40d80aeee5e7c94ecf3090a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 22:24:16 +0200 Subject: [PATCH 157/187] changed applying magazine upgrade to be inline with other inventory functions, no predction, confirmation from server on client --- .../Weapons/ARWeaponInventoryComponent.cpp | 26 +++++++++++-------- .../Weapons/ARWeaponInventoryComponent.h | 4 +++ 2 files changed, 19 insertions(+), 11 deletions(-) diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index 126d3a9..afe8202 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -648,9 +648,11 @@ void UARWeaponInventoryComponent::AddMagazineMod(int8 WeaponIdx, int8 MagazineMo if (GetOwnerRole() < ENetRole::ROLE_Authority) { ServerAddMagazineMod(WeaponIdx, MagazineModIndex); + return; } - - //Predictively apply mod on client, and show it on UI. +} +void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex) +{ if (AARCharacter* Character = Cast(GetOwner())) { if (AARPlayerController* PC = Cast(Character->Controller)) @@ -664,16 +666,18 @@ void UARWeaponInventoryComponent::AddMagazineMod(int8 WeaponIdx, int8 MagazineMo if (Weapon) { Weapon->AddMagazineUpgrade(Magazine); - FARWeaponModInfo Info; - Info.Icon = Magazine->Icon->GetPathName(); - Info.UpgradeType = EARWeaponUpgradeType::Magazine; - Weapon->ClientOnMagazineAdded(Info); + ClientAddMagazineMod(WeaponIdx, MagazineModIndex); } } } } } -void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex) +bool UARWeaponInventoryComponent::ServerAddMagazineMod_Validate(int8 WeaponIdx, int8 MagazineModIndex) +{ + return true; +} + +void UARWeaponInventoryComponent::ClientAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex) { if (AARCharacter* Character = Cast(GetOwner())) { @@ -688,13 +692,13 @@ void UARWeaponInventoryComponent::ServerAddMagazineMod_Implementation(int8 Weapo if (Weapon) { Weapon->AddMagazineUpgrade(Magazine); + FARWeaponModInfo Info; + Info.Icon = Magazine->Icon->GetPathName(); + Info.UpgradeType = EARWeaponUpgradeType::Magazine; + Weapon->ClientOnMagazineAdded(Info); MainInventory->RemoveItem(MagazineModIndex); } } } } -} -bool UARWeaponInventoryComponent::ServerAddMagazineMod_Validate(int8 WeaponIdx, int8 MagazineModIndex) -{ - return true; } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 0a89d4a..8aca9de 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -184,4 +184,8 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void ServerAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex); bool ServerAddMagazineMod_Validate(int8 WeaponIdx, int8 MagazineModIndex); + UFUNCTION(Client, Reliable) + void ClientAddMagazineMod(int8 WeaponIdx, int8 MagazineModIndex); + void ClientAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex); + }; From 4f0da616325209132241faece517533cedf45612 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 23:01:59 +0200 Subject: [PATCH 158/187] multicast remove weapon --- .../Weapons/ARWeaponInventoryComponent.cpp | 36 ++++++++++++++++++- .../Weapons/ARWeaponInventoryComponent.h | 3 ++ 2 files changed, 38 insertions(+), 1 deletion(-) diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index afe8202..0ad1077 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -153,6 +153,14 @@ void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 Loc } void UARWeaponInventoryComponent::OnServerItemRemoved(uint8 LocalIndex) { + FARWeaponRPC Data; + Data.Weapon.Reset(); + Data.Index = LocalIndex; + //Data.SocketName = InWeapon->Socket; + Data.Position = FVector::ZeroVector; + Data.Rotation = FRotator::ZeroRotator; + Data.AttachSlot = static_cast(LocalIndex); + MulticastRemoveWeapon(Data); } void UARWeaponInventoryComponent::MulticastAddWeapon_Implementation(const FARWeaponRPC& WeaponData) { @@ -178,12 +186,38 @@ void UARWeaponInventoryComponent::MulticastAddWeapon_Implementation(const FARWea default: break; } - } } void UARWeaponInventoryComponent::MulticastRemoveWeapon_Implementation(const FARWeaponRPC& WeaponData) { + if (AARCharacter* Character = Cast(POwner)) + { + switch (WeaponData.AttachSlot) + { + case EARWeaponPosition::Right: + Character->GetHolsteredRightWeapon()->SetChildActorClass(nullptr); + break; + case EARWeaponPosition::Left: + Character->GetHolsteredLeftWeapon()->SetChildActorClass(nullptr); + break; + case EARWeaponPosition::BottomBack: + Character->GetHolsteredBackDownWeapon()->SetChildActorClass(nullptr); + break; + case EARWeaponPosition::Side: + Character->GetHolsteredSideLeftWeapon()->SetChildActorClass(nullptr); + break; + case EARWeaponPosition::Equiped: + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + break; + default: + break; + } + } + if (WeaponData.Index == CurrentWeaponIndex) + { + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + } } void UARWeaponInventoryComponent::MulticastEquipWeapon_Implementation(int8 WeaponIndex, const FARWeaponRPC& WeaponData) diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 8aca9de..51ce148 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -55,6 +55,9 @@ struct FARWeaponRPC UPROPERTY(EditAnywhere, Category = "Attachment Test") TSoftClassPtr Weapon; + UPROPERTY() + uint8 Index; + UPROPERTY(EditAnywhere, Category = "Attachment Test") FVector Position; UPROPERTY(EditAnywhere, Category = "Attachment Test") From 082745f0d0e41cdc5a9a955abf5896984a604b6a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 30 Apr 2018 23:06:09 +0200 Subject: [PATCH 159/187] compilation fix --- .../Public/Weapons/ARWeaponInventoryComponent.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp index 0ad1077..19a53e1 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp @@ -216,7 +216,10 @@ void UARWeaponInventoryComponent::MulticastRemoveWeapon_Implementation(const FAR if (WeaponData.Index == CurrentWeaponIndex) { - Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + if (AARCharacter* Character = Cast(POwner)) + { + Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); + } } } From b7a04ed75bbb7c9987a5fa12021a6ccbf5eb19a2 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 1 May 2018 21:03:17 +0200 Subject: [PATCH 160/187] changed main source structure to match Public/Private --- .../{Public => Private}/AI/ARAICharacter.cpp | 0 .../{Public => Private}/AI/ARAIController.cpp | 0 .../{Public => Private}/ARCharacter.cpp | 4 ++-- .../ARCharacterMovementComponent.cpp | 0 .../{Public => Private}/ARGameMode.cpp | 0 .../{Public => Private}/ARGlobals.cpp | 0 .../{Public => Private}/ARItemBase.cpp | 0 .../{Public => Private}/ARItemPickupBase.cpp | 0 .../ARPlayerController.cpp | 0 .../Abilities/ARAbilityBase.cpp | 0 .../Abilities/ARAbilityManagerComponent.cpp | 0 .../Abilities/ARAbilityUIData.cpp | 0 .../Abilities/ARAvailableAbilities.cpp | 0 .../{Public => Private}/ActionRPGGame.cpp | 0 .../Attributes/ARAbilityAttributes.cpp | 0 .../Attributes/ARCharacterAttributes.cpp | 0 .../Attributes/ARGunAttributes.cpp | 0 .../Attributes/ARHealthExtension.cpp | 0 .../Calculations/ARAmmoReloadCalculation.cpp | 0 .../{Public => Private}/UI/ARHUD.cpp | 0 .../{Public => Private}/UI/ARHUDWidget.cpp | 0 .../{Public => Private}/UI/ARUIComponent.cpp | 0 .../UI/ARUMGWidgetBase.cpp | 0 .../UI/Inventory/ARInventoryScreenWidget.cpp | 0 .../UI/Inventory/ARItemView.cpp | 0 .../UI/Inventory/ARListItemView.cpp | 0 .../UI/Inventory/ARUIInventoryComponent.cpp | 11 --------- .../Inventory/Weapons/ARItemWeaponWidget.cpp | 0 .../Weapons/ARListItemWeaponWidget.cpp | 0 .../Weapons/ARWeaponContainerWidget.cpp | 0 .../Weapons/ARWeaponModificationView.cpp | 15 ++++++++++++ .../Modifications/ARItemMagazineView.cpp | 0 .../Modifications/ARListItemMagazineView.cpp | 0 .../UI/SARCrosshairBase.cpp | 0 .../UI/SARDrawTestWidget.cpp | 0 .../Weapons/ARItemWeapon.cpp | 0 .../Weapons/ARMagazineUpgradeEffect.cpp | 0 .../Weapons/ARMagazineUpgradeItem.cpp | 0 .../Weapons/ARWeaponAbilityBase.cpp | 0 .../Weapons/ARWeaponBase.cpp | 0 .../Weapons/ARWeaponInventoryComponent.cpp | 0 .../Weapons/ARWeaponUpgradeItem.cpp | 0 .../Weapons/ARWeaponsTypes.cpp | 0 .../Weapons/ARWeaponModificationView.h | 23 +++++++++++++++++++ 44 files changed, 40 insertions(+), 13 deletions(-) rename Source/ActionRPGGame/{Public => Private}/AI/ARAICharacter.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/AI/ARAIController.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ARCharacter.cpp (99%) rename Source/ActionRPGGame/{Public => Private}/ARCharacterMovementComponent.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ARGameMode.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ARGlobals.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ARItemBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ARItemPickupBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ARPlayerController.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Abilities/ARAbilityBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Abilities/ARAbilityManagerComponent.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Abilities/ARAbilityUIData.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Abilities/ARAvailableAbilities.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/ActionRPGGame.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Attributes/ARAbilityAttributes.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Attributes/ARCharacterAttributes.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Attributes/ARGunAttributes.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Attributes/ARHealthExtension.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Calculations/ARAmmoReloadCalculation.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/ARHUD.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/ARHUDWidget.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/ARUIComponent.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/ARUMGWidgetBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/ARInventoryScreenWidget.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/ARItemView.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/ARListItemView.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/ARUIInventoryComponent.cpp (95%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/Weapons/ARItemWeaponWidget.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp (100%) create mode 100644 Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/SARCrosshairBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/SARDrawTestWidget.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARItemWeapon.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARMagazineUpgradeEffect.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARMagazineUpgradeItem.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARWeaponAbilityBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARWeaponBase.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARWeaponInventoryComponent.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARWeaponUpgradeItem.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/Weapons/ARWeaponsTypes.cpp (100%) create mode 100644 Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h diff --git a/Source/ActionRPGGame/Public/AI/ARAICharacter.cpp b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp similarity index 100% rename from Source/ActionRPGGame/Public/AI/ARAICharacter.cpp rename to Source/ActionRPGGame/Private/AI/ARAICharacter.cpp diff --git a/Source/ActionRPGGame/Public/AI/ARAIController.cpp b/Source/ActionRPGGame/Private/AI/ARAIController.cpp similarity index 100% rename from Source/ActionRPGGame/Public/AI/ARAIController.cpp rename to Source/ActionRPGGame/Private/AI/ARAIController.cpp diff --git a/Source/ActionRPGGame/Public/ARCharacter.cpp b/Source/ActionRPGGame/Private/ARCharacter.cpp similarity index 99% rename from Source/ActionRPGGame/Public/ARCharacter.cpp rename to Source/ActionRPGGame/Private/ARCharacter.cpp index b3eb396..dbf8b5d 100644 --- a/Source/ActionRPGGame/Public/ARCharacter.cpp +++ b/Source/ActionRPGGame/Private/ARCharacter.cpp @@ -60,9 +60,9 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) //CameraBoom->SetupAttachment(GetMesh()); CameraBoom->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform, TEXT("headSocket")); - CameraBoom->TargetArmLength = 275; // The camera follows at this distance behind the character + CameraBoom->TargetArmLength = 285; // The camera follows at this distance behind the character CameraBoom->bUsePawnControlRotation = true; // Rotate the arm based on the controller - CameraBoom->SocketOffset = FVector(0, 25, 65); + CameraBoom->SocketOffset = FVector(0, 35, 65); CameraBoom->TargetOffset = FVector(0, 0, -45); CameraBoom->bEnableCameraLag = true; CameraBoom->bEnableCameraRotationLag = true; diff --git a/Source/ActionRPGGame/Public/ARCharacterMovementComponent.cpp b/Source/ActionRPGGame/Private/ARCharacterMovementComponent.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ARCharacterMovementComponent.cpp rename to Source/ActionRPGGame/Private/ARCharacterMovementComponent.cpp diff --git a/Source/ActionRPGGame/Public/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ARGameMode.cpp rename to Source/ActionRPGGame/Private/ARGameMode.cpp diff --git a/Source/ActionRPGGame/Public/ARGlobals.cpp b/Source/ActionRPGGame/Private/ARGlobals.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ARGlobals.cpp rename to Source/ActionRPGGame/Private/ARGlobals.cpp diff --git a/Source/ActionRPGGame/Public/ARItemBase.cpp b/Source/ActionRPGGame/Private/ARItemBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ARItemBase.cpp rename to Source/ActionRPGGame/Private/ARItemBase.cpp diff --git a/Source/ActionRPGGame/Public/ARItemPickupBase.cpp b/Source/ActionRPGGame/Private/ARItemPickupBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ARItemPickupBase.cpp rename to Source/ActionRPGGame/Private/ARItemPickupBase.cpp diff --git a/Source/ActionRPGGame/Public/ARPlayerController.cpp b/Source/ActionRPGGame/Private/ARPlayerController.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ARPlayerController.cpp rename to Source/ActionRPGGame/Private/ARPlayerController.cpp diff --git a/Source/ActionRPGGame/Public/Abilities/ARAbilityBase.cpp b/Source/ActionRPGGame/Private/Abilities/ARAbilityBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Abilities/ARAbilityBase.cpp rename to Source/ActionRPGGame/Private/Abilities/ARAbilityBase.cpp diff --git a/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.cpp rename to Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp diff --git a/Source/ActionRPGGame/Public/Abilities/ARAbilityUIData.cpp b/Source/ActionRPGGame/Private/Abilities/ARAbilityUIData.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Abilities/ARAbilityUIData.cpp rename to Source/ActionRPGGame/Private/Abilities/ARAbilityUIData.cpp diff --git a/Source/ActionRPGGame/Public/Abilities/ARAvailableAbilities.cpp b/Source/ActionRPGGame/Private/Abilities/ARAvailableAbilities.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Abilities/ARAvailableAbilities.cpp rename to Source/ActionRPGGame/Private/Abilities/ARAvailableAbilities.cpp diff --git a/Source/ActionRPGGame/Public/ActionRPGGame.cpp b/Source/ActionRPGGame/Private/ActionRPGGame.cpp similarity index 100% rename from Source/ActionRPGGame/Public/ActionRPGGame.cpp rename to Source/ActionRPGGame/Private/ActionRPGGame.cpp diff --git a/Source/ActionRPGGame/Public/Attributes/ARAbilityAttributes.cpp b/Source/ActionRPGGame/Private/Attributes/ARAbilityAttributes.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Attributes/ARAbilityAttributes.cpp rename to Source/ActionRPGGame/Private/Attributes/ARAbilityAttributes.cpp diff --git a/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.cpp b/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.cpp rename to Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp diff --git a/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.cpp b/Source/ActionRPGGame/Private/Attributes/ARGunAttributes.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Attributes/ARGunAttributes.cpp rename to Source/ActionRPGGame/Private/Attributes/ARGunAttributes.cpp diff --git a/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.cpp b/Source/ActionRPGGame/Private/Attributes/ARHealthExtension.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Attributes/ARHealthExtension.cpp rename to Source/ActionRPGGame/Private/Attributes/ARHealthExtension.cpp diff --git a/Source/ActionRPGGame/Public/Calculations/ARAmmoReloadCalculation.cpp b/Source/ActionRPGGame/Private/Calculations/ARAmmoReloadCalculation.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Calculations/ARAmmoReloadCalculation.cpp rename to Source/ActionRPGGame/Private/Calculations/ARAmmoReloadCalculation.cpp diff --git a/Source/ActionRPGGame/Public/UI/ARHUD.cpp b/Source/ActionRPGGame/Private/UI/ARHUD.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/ARHUD.cpp rename to Source/ActionRPGGame/Private/UI/ARHUD.cpp diff --git a/Source/ActionRPGGame/Public/UI/ARHUDWidget.cpp b/Source/ActionRPGGame/Private/UI/ARHUDWidget.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/ARHUDWidget.cpp rename to Source/ActionRPGGame/Private/UI/ARHUDWidget.cpp diff --git a/Source/ActionRPGGame/Public/UI/ARUIComponent.cpp b/Source/ActionRPGGame/Private/UI/ARUIComponent.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/ARUIComponent.cpp rename to Source/ActionRPGGame/Private/UI/ARUIComponent.cpp diff --git a/Source/ActionRPGGame/Public/UI/ARUMGWidgetBase.cpp b/Source/ActionRPGGame/Private/UI/ARUMGWidgetBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/ARUMGWidgetBase.cpp rename to Source/ActionRPGGame/Private/UI/ARUMGWidgetBase.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARInventoryScreenWidget.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/ARInventoryScreenWidget.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARItemView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARItemView.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/ARItemView.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/ARItemView.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARListItemView.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/ARListItemView.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp similarity index 95% rename from Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp index bab572c..ff6b112 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp @@ -240,15 +240,4 @@ void UARUIInventoryComponent::RemoveMagazineUpgrade() return; UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; - - //UARItemWeapon* Weapon = WeaponInventory->GetItem(SelectedWeapon); - - //TSoftClassPtr Item = Weapon->RemoveMagazineUpgrade(); - - - //UIFInventoryComponent* MainInventory = PC->MainInventory; - - //MainInventory->AddItemFromClass(Item, 0); - - //InventoryView->MagazineUpgrade->OnItemChanged(0, 0, nullptr); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARListItemWeaponWidget.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponContainerWidget.cpp diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp new file mode 100644 index 0000000..03cd900 --- /dev/null +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARWeaponModificationView.h" + + + + +void UARWeaponModificationView::StartModifyWeapon(class UARItemWeapon* WeaponItem) +{ + +} +void UARWeaponModificationView::StopModifyWeapon() +{ + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp rename to Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARListItemMagazineView.cpp diff --git a/Source/ActionRPGGame/Public/UI/SARCrosshairBase.cpp b/Source/ActionRPGGame/Private/UI/SARCrosshairBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/SARCrosshairBase.cpp rename to Source/ActionRPGGame/Private/UI/SARCrosshairBase.cpp diff --git a/Source/ActionRPGGame/Public/UI/SARDrawTestWidget.cpp b/Source/ActionRPGGame/Private/UI/SARDrawTestWidget.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/SARDrawTestWidget.cpp rename to Source/ActionRPGGame/Private/UI/SARDrawTestWidget.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARItemWeapon.cpp rename to Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeEffect.cpp b/Source/ActionRPGGame/Private/Weapons/ARMagazineUpgradeEffect.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeEffect.cpp rename to Source/ActionRPGGame/Private/Weapons/ARMagazineUpgradeEffect.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.cpp b/Source/ActionRPGGame/Private/Weapons/ARMagazineUpgradeItem.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.cpp rename to Source/ActionRPGGame/Private/Weapons/ARMagazineUpgradeItem.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.cpp rename to Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponBase.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponBase.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARWeaponBase.cpp rename to Source/ActionRPGGame/Private/Weapons/ARWeaponBase.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.cpp rename to Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponUpgradeItem.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponUpgradeItem.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARWeaponUpgradeItem.cpp rename to Source/ActionRPGGame/Private/Weapons/ARWeaponUpgradeItem.cpp diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponsTypes.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponsTypes.cpp similarity index 100% rename from Source/ActionRPGGame/Public/Weapons/ARWeaponsTypes.cpp rename to Source/ActionRPGGame/Private/Weapons/ARWeaponsTypes.cpp diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h new file mode 100644 index 0000000..528b181 --- /dev/null +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h @@ -0,0 +1,23 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARWeaponModificationView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARWeaponModificationView : public UARUMGWidgetBase +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UARItemMagazineView* MagazineUpgrade; + + void StartModifyWeapon(class UARItemWeapon* WeaponItem); + void StopModifyWeapon(); + +}; From 43bd898035769b68a1d3036f36e251e079be157d Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 3 May 2018 23:44:56 +0200 Subject: [PATCH 161/187] working on weapon upgrades --- Config/DefaultEngine.ini | 124 +++++++++--------- .../Private/Effects/GABlueprintLibrary.cpp | 55 +++++++- .../Private/Effects/GAGameEffect.cpp | 30 ++++- .../Public/Attributes/GAAttributeBase.h | 1 + .../Public/Effects/GABlueprintLibrary.h | 16 +++ .../Public/Effects/GAGameEffect.h | 77 +++++++++-- .../AbilityFramework/Public/GAGlobalTypes.h | 10 +- .../Private/IFInventoryComponent.cpp | 122 ++++++++++++----- .../Public/IFInventoryComponent.h | 14 ++ .../UI/Inventory/ARUIInventoryComponent.cpp | 36 +++-- .../Weapons/ARWeaponModificationView.cpp | 20 ++- .../Modifications/ARItemMagazineView.cpp | 36 ++++- .../Modifications/ARItemWeaponUpgradeView.cpp | 7 + .../Private/Weapons/ARItemWeapon.cpp | 82 ++++++++---- .../Weapons/ARWeaponInventoryComponent.cpp | 110 ++++++++++++---- Source/ActionRPGGame/Public/ARItemBase.h | 7 +- .../UI/Inventory/ARUIInventoryComponent.h | 8 ++ .../Weapons/ARWeaponModificationView.h | 12 +- .../Modifications/ARItemMagazineView.h | 11 ++ .../Modifications/ARItemWeaponUpgradeView.h | 20 +++ .../Public/Weapons/ARItemWeapon.h | 47 +++++-- .../Public/Weapons/ARMagazineUpgradeItem.h | 8 ++ .../Weapons/ARWeaponInventoryComponent.h | 31 ++++- 23 files changed, 695 insertions(+), 189 deletions(-) create mode 100644 Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.cpp create mode 100644 Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.h diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 02d58ad..340c57d 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -10,9 +10,9 @@ AppliedDefaultGraphicsPerformance=Maximum [/Script/EngineSettings.GameMapsSettings] GlobalDefaultGameMode=/Game/Prototypes/ProtGameMode.ProtGameMode_C -GameDefaultMap=/Game/Maps/StartMap.StartMap -ServerDefaultMap=/Game/Maps/StartMap.StartMap -EditorStartupMap=/Game/Maps/StartMap.StartMap +GameDefaultMap=/Game/Maps/TestMap.TestMap +ServerDefaultMap=/Game/Maps/TestMap.TestMap +EditorStartupMap=/Game/Maps/TestMap.TestMap [/Script/Engine.RendererSettings] r.AllowStaticLighting=False @@ -32,64 +32,6 @@ r.UsePreExposure=True [/Script/Engine.StreamingSettings] s.AsyncLoadingThreadEnabled=True -[/Script/Engine.CollisionProfile] --Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) --Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) --Profiles=(Name="OverlapAll",CollisionEnabled=QueryOnly,ObjectTypeName="WorldStatic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) --Profiles=(Name="BlockAllDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=,HelpMessage="WorldDynamic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) --Profiles=(Name="OverlapAllDynamic",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) --Profiles=(Name="IgnoreOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that ignores Pawn and Vehicle. All other channels will be set to default.",bCanModify=False) --Profiles=(Name="OverlapOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that overlaps Pawn, Camera, and Vehicle. All other channels will be set to default. ",bCanModify=False) --Profiles=(Name="Pawn",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Pawn",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object. Can be used for capsule of any playerable character or AI. ",bCanModify=False) --Profiles=(Name="Spectator",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="WorldStatic"),(Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore),(Channel="PhysicsBody",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Destructible",Response=ECR_Ignore)),HelpMessage="Pawn object that ignores all other actors except WorldStatic.",bCanModify=False) --Profiles=(Name="CharacterMesh",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object that is used for Character Mesh. All other channels will be set to default.",bCanModify=False) --Profiles=(Name="PhysicsActor",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=,HelpMessage="Simulating actors",bCanModify=False) --Profiles=(Name="Destructible",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Destructible",CustomResponses=,HelpMessage="Destructible actors",bCanModify=False) --Profiles=(Name="InvisibleWall",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldStatic object that is invisible.",bCanModify=False) --Profiles=(Name="InvisibleWallDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that is invisible.",bCanModify=False) --Profiles=(Name="Trigger",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that is used for trigger. All other channels will be set to default.",bCanModify=False) --Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) --Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) --Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) -+Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+Profiles=(Name="OverlapAll",CollisionEnabled=QueryOnly,ObjectTypeName="WorldStatic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+Profiles=(Name="BlockAllDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=,HelpMessage="WorldDynamic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+Profiles=(Name="OverlapAllDynamic",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+Profiles=(Name="IgnoreOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that ignores Pawn and Vehicle. All other channels will be set to default.",bCanModify=False) -+Profiles=(Name="OverlapOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that overlaps Pawn, Camera, and Vehicle. All other channels will be set to default. ",bCanModify=False) -+Profiles=(Name="Pawn",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Pawn",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object. Can be used for capsule of any playerable character or AI. ",bCanModify=False) -+Profiles=(Name="Spectator",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="WorldStatic"),(Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore),(Channel="PhysicsBody",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Destructible",Response=ECR_Ignore)),HelpMessage="Pawn object that ignores all other actors except WorldStatic.",bCanModify=False) -+Profiles=(Name="CharacterMesh",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object that is used for Character Mesh. All other channels will be set to default.",bCanModify=False) -+Profiles=(Name="PhysicsActor",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=,HelpMessage="Simulating actors",bCanModify=False) -+Profiles=(Name="Destructible",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Destructible",CustomResponses=,HelpMessage="Destructible actors",bCanModify=False) -+Profiles=(Name="InvisibleWall",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldStatic object that is invisible.",bCanModify=False) -+Profiles=(Name="InvisibleWallDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that is invisible.",bCanModify=False) -+Profiles=(Name="Trigger",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that is used for trigger. All other channels will be set to default.",bCanModify=False) -+Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) -+Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) -+Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) --DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Block,bTraceType=True,bStaticObject=False) -+DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Ignore,bTraceType=True,bStaticObject=False) --ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") --ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") --ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") --ProfileRedirects=(OldName="SkeletalMeshActor",NewName="PhysicsActor") --ProfileRedirects=(OldName="InvisibleActor",NewName="InvisibleWallDynamic") -+ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") -+ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") -+ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") -+ProfileRedirects=(OldName="SkeletalMeshActor",NewName="PhysicsActor") -+ProfileRedirects=(OldName="InvisibleActor",NewName="InvisibleWallDynamic") --CollisionChannelRedirects=(OldName="Static",NewName="WorldStatic") --CollisionChannelRedirects=(OldName="Dynamic",NewName="WorldDynamic") --CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") --CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") -+CollisionChannelRedirects=(OldName="Static",NewName="WorldStatic") -+CollisionChannelRedirects=(OldName="Dynamic",NewName="WorldDynamic") -+CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") -+CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") - [/Script/Engine.UserInterfaceSettings] bLoadWidgetsOnDedicatedServer=False UIScaleRule=ShortestSide @@ -178,4 +120,64 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 +[/Script/Engine.CollisionProfile] +-Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) +-Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="OverlapAll",CollisionEnabled=QueryOnly,ObjectTypeName="WorldStatic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="BlockAllDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=,HelpMessage="WorldDynamic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="OverlapAllDynamic",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) +-Profiles=(Name="IgnoreOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that ignores Pawn and Vehicle. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="OverlapOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that overlaps Pawn, Camera, and Vehicle. All other channels will be set to default. ",bCanModify=False) +-Profiles=(Name="Pawn",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Pawn",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object. Can be used for capsule of any playerable character or AI. ",bCanModify=False) +-Profiles=(Name="Spectator",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="WorldStatic",Response=ECR_Block),(Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore),(Channel="PhysicsBody",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Destructible",Response=ECR_Ignore)),HelpMessage="Pawn object that ignores all other actors except WorldStatic.",bCanModify=False) +-Profiles=(Name="CharacterMesh",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object that is used for Character Mesh. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="PhysicsActor",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=,HelpMessage="Simulating actors",bCanModify=False) +-Profiles=(Name="Destructible",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Destructible",CustomResponses=,HelpMessage="Destructible actors",bCanModify=False) +-Profiles=(Name="InvisibleWall",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldStatic object that is invisible.",bCanModify=False) +-Profiles=(Name="InvisibleWallDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that is invisible.",bCanModify=False) +-Profiles=(Name="Trigger",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that is used for trigger. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) +-Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Block),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) ++Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="OverlapAll",CollisionEnabled=QueryOnly,ObjectTypeName="WorldStatic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="BlockAllDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=,HelpMessage="WorldDynamic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="OverlapAllDynamic",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Overlap),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++Profiles=(Name="IgnoreOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that ignores Pawn and Vehicle. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="OverlapOnlyPawn",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Pawn",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that overlaps Pawn, Camera, and Vehicle. All other channels will be set to default. ",bCanModify=False) ++Profiles=(Name="Pawn",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Pawn",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object. Can be used for capsule of any playerable character or AI. ",bCanModify=False) ++Profiles=(Name="Spectator",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="WorldStatic"),(Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore),(Channel="PhysicsBody",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Destructible",Response=ECR_Ignore)),HelpMessage="Pawn object that ignores all other actors except WorldStatic.",bCanModify=False) ++Profiles=(Name="CharacterMesh",CollisionEnabled=QueryOnly,ObjectTypeName="Pawn",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Vehicle",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Pawn object that is used for Character Mesh. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="PhysicsActor",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=,HelpMessage="Simulating actors",bCanModify=False) ++Profiles=(Name="Destructible",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Destructible",CustomResponses=,HelpMessage="Destructible actors",bCanModify=False) ++Profiles=(Name="InvisibleWall",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldStatic object that is invisible.",bCanModify=False) ++Profiles=(Name="InvisibleWallDynamic",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore)),HelpMessage="WorldDynamic object that is invisible.",bCanModify=False) ++Profiles=(Name="Trigger",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility",Response=ECR_Ignore),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldDynamic object that is used for trigger. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) ++Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Ignore,bTraceType=True,bStaticObject=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel2,Name="Pickup",DefaultResponse=ECR_Overlap,bTraceType=True,bStaticObject=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel3,Name="Weapon",DefaultResponse=ECR_Overlap,bTraceType=True,bStaticObject=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel4,Name="PikcupObject",DefaultResponse=ECR_Ignore,bTraceType=False,bStaticObject=False) +-ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") +-ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") +-ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") +-ProfileRedirects=(OldName="SkeletalMeshActor",NewName="PhysicsActor") +-ProfileRedirects=(OldName="InvisibleActor",NewName="InvisibleWallDynamic") ++ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") ++ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") ++ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") ++ProfileRedirects=(OldName="SkeletalMeshActor",NewName="PhysicsActor") ++ProfileRedirects=(OldName="InvisibleActor",NewName="InvisibleWallDynamic") +-CollisionChannelRedirects=(OldName="Static",NewName="WorldStatic") +-CollisionChannelRedirects=(OldName="Dynamic",NewName="WorldDynamic") +-CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +-CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") ++CollisionChannelRedirects=(OldName="Static",NewName="WorldStatic") ++CollisionChannelRedirects=(OldName="Dynamic",NewName="WorldDynamic") ++CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") ++CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp index b8c4ed5..043cc0d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp @@ -1,4 +1,4 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #include "AbilityFramework.h" #include "AFAbilityComponent.h" @@ -12,6 +12,9 @@ #include "GAEffectExtension.h" +#include "AFSimpleInterface.h" +#include "AFAttributeInterface.h" + UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { @@ -368,4 +371,54 @@ void UGABlueprintLibrary::BroadcastEffectEvent(UObject* Target, FGameplayTag Eve //FAFEventData EventData; //TargetComp->NativeTriggerTagEvent(EventTag, EventData); +} +void UGABlueprintLibrary::CreateEffectSpec(UPARAM(Ref) FAFEffectSpecHandle& InOutSpec + , const FAFPropertytHandle& InEffect + , class UObject* Target + , class APawn* Instigator + , UObject* Causer) +{ + IAFAbilityInterface* TargetInterface = Cast(Target); + + FHitResult HitIn(ForceInit); + FAFContextHandle Context; + FAFEffectSpecHandle EffectSpecHandle; + Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); + + FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); + AddTagsToEffect(EffectSpec); + EffectSpecHandle = FAFEffectSpecHandle::Generate(EffectSpec); + + InOutSpec = EffectSpecHandle; +} +void UGABlueprintLibrary::ApplyEffectFromSpec(UPARAM(Ref) FAFPropertytHandle& InEffect, UPARAM(Ref) FAFEffectSpecHandle& InSpec) +{ + +} +void UGABlueprintLibrary::ModifyAttributeSimple( + UPARAM(Ref) FAFEffectSpecHandle& InSpec + , UObject* Target) +{ + if (!InSpec.IsValid()) + { + return; + } + + IAFAttributeInterface* Attr = Cast(Target); + IAFSimpleInterface* Simpl = Cast(Target); + + if (!Attr || !Simpl) + return; + + FGAEffectHandle Handle = FGAEffectHandle::GenerateHandle(); + + FGAEffect Effect = FGAEffect(InSpec.GetPtr(), Handle); + + FGAEffectMod Mod = InSpec.GetPtr()->GetModifier(); + + //Generate HAndle. + //Add to simple container. + //Modify Attribute } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp index 64304ce..4df4cec 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp @@ -87,6 +87,20 @@ float FAFEffectSpec::GetFloatFromAttributeMagnitude( return 0; } + +void FAFEffectSpec::OverrideAttributeModifier(float InValue) +{ + EffectMod.Value = InValue; +} +void FAFEffectSpec::CalculateAttributeModifier(const FGAEffectHandle& InHandle) +{ + FGAEffectContext& InContext = Context.GetRef(); + EffectMod = FAFStatics::GetAttributeModifier(SpecClass.GetDefaultObject()->AtributeModifier + , SpecClass.GetDefaultObject() + , InContext + , InHandle); +} + float FAFEffectSpec::GetDuration(const FGAEffectContext& InContext) { return GetFloatFromAttributeMagnitude(GetSpec()->Duration, InContext); @@ -95,6 +109,7 @@ float FAFEffectSpec::GetPeriod(const FGAEffectContext& InContext) { return GetFloatFromAttributeMagnitude(GetSpec()->Period, InContext); } + FGAEffectProperty::FGAEffectProperty() : ApplicationRequirement(nullptr) , Application(nullptr) @@ -210,7 +225,10 @@ void FGAEffect::PostReplicatedChange(const struct FGAEffectContainer& InArraySer { } - +FGAEffect::FGAEffect(TSharedPtr InSpec, const FGAEffectHandle& InHandle) +{ + Handle = InHandle; +} float FGAMagnitude::GetFloatValue(const FGAEffectContext& Context) { switch (CalculationType) @@ -844,4 +862,14 @@ bool FGAEffectContainer::IsEffectActive(TSubclassOf EffectCla return true; } return false; +} + +void FAFEffectContainerSimple::ApplyEffect(const FGAEffectHandle& InHandle + , const FGAEffect& InEffect) +{ + Effects.Add(InHandle, InEffect); +} +void FAFEffectContainerSimple::RemoveEffect(const FGAEffectHandle& InHandle) +{ + Effects.Remove(InHandle); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index 650b95c..c15fbc0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -77,6 +77,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") TSubclassOf ExtensionClass; + //Considering amount of bonuses TArray might be better than TMap, for cache coherency. TArray> Modifiers; FAFAttributeBase(); FAFAttributeBase(float BaseValueIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h index 62faec3..79d2fe8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h @@ -108,4 +108,20 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") static void BroadcastEffectEvent(UObject* Target, FGameplayTag EventTag); + + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static void CreateEffectSpec(UPARAM(Ref) FAFEffectSpecHandle& InOutSpec + , const FAFPropertytHandle& InEffect + , class UObject* Target + , class APawn* Instigator + , UObject* Causer); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static void ApplyEffectFromSpec(UPARAM(Ref) FAFPropertytHandle& InEffect, UPARAM(Ref) FAFEffectSpecHandle& InSpec); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static void ModifyAttributeSimple( + UPARAM(Ref) FAFEffectSpecHandle& InSpec + , UObject* Target); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h index 3f15281..c6c834a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h @@ -309,6 +309,11 @@ struct ABILITYFRAMEWORK_API FGAEffectClass FGAEffectClass(TSubclassOf InClass) : SpecClass(InClass) {} + + void Reset() + { + SpecClass = nullptr; + } const bool operator==(const FGAEffectClass& Other) const { return SpecClass == Other.SpecClass; @@ -332,7 +337,7 @@ struct ABILITYFRAMEWORK_API FGAEffectClass }; USTRUCT(BlueprintType) -struct FAFContextHandle +struct ABILITYFRAMEWORK_API FAFContextHandle { GENERATED_BODY() private: @@ -417,7 +422,7 @@ struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBas }; /* - + Dervied from GCObject because Extension property has been garbage collected. Even with UPROPERTY() and non-GC outer. */ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject @@ -427,6 +432,8 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject UGAEffectExtension* Extension; //week ptr ? TSubclassOf SpecClass; + + FGAEffectMod EffectMod; public: FGameplayTagContainer OwnedTags; @@ -445,6 +452,11 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject void OnRemoved(); void OnExecuted(); + FGAEffectMod GetModifier() + { + return EffectMod; + } + void AddOwnedTags(const FGameplayTagContainer& InTags) { OwnedTags.AppendTags(InTags); @@ -463,9 +475,13 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject const FGAMagnitude& AttributeIn , const FGAEffectContext& InContext) const; + void OverrideAttributeModifier(float InValue); + void CalculateAttributeModifier(const FGAEffectHandle& InHandle); + float GetDuration(const FGAEffectContext& InContext); float GetPeriod(const FGAEffectContext& InContext); + const TSubclassOf& GetEffectClass() { return SpecClass; @@ -478,7 +494,7 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject }; USTRUCT(BlueprintType) -struct FAFEffectSpecHandle +struct ABILITYFRAMEWORK_API FAFEffectSpecHandle { GENERATED_BODY() public: @@ -509,7 +525,11 @@ struct FAFEffectSpecHandle { return SpecPtr.IsValid(); } - + void Reset() + { + SpecPtr.Reset(); + ID = 0; + } TSharedPtr GetPtr() { return SpecPtr; @@ -522,6 +542,18 @@ struct FAFEffectSpecHandle { return SpecPtr.ToSharedRef().Get(); } + FGAEffectMod GetModifier() + { + return SpecPtr->GetModifier(); + } + void OverrideAttributeModifier(float InValue) + { + SpecPtr->OverrideAttributeModifier(InValue); + } + void CalculateAttributeModifier(const FGAEffectHandle& InHandlet) + { + SpecPtr->CalculateAttributeModifier(InHandlet); + } }; template<> struct TStructOpsTypeTraits< FAFEffectSpecHandle > : public TStructOpsTypeTraitsBase2 @@ -828,7 +860,7 @@ struct TStructOpsTypeTraits< FGAEffectProperty > : public TStructOpsTypeTraitsBa }; USTRUCT(BlueprintType) -struct FAFPropertytHandle +struct ABILITYFRAMEWORK_API FAFPropertytHandle { GENERATED_BODY() public: @@ -849,6 +881,13 @@ struct FAFPropertytHandle } }; + void Reset() + { + SpecClass.Reset(); + DataPtr.Reset(); + ID = 0; + } + FAFPropertytHandle(TSubclassOf InSpecClass) : ID(0) { @@ -986,7 +1025,7 @@ struct TStructOpsTypeTraits< FAFPropertytHandle > : public TStructOpsTypeTraitsB }; USTRUCT() -struct FAFEffectParams +struct ABILITYFRAMEWORK_API FAFEffectParams { GENERATED_BODY() //make this private and allow assign only trough constructr. @@ -1033,7 +1072,7 @@ struct FAFEffectParams }; USTRUCT(BlueprintType) -struct FAFEventData +struct ABILITYFRAMEWORK_API FAFEventData { GENERATED_BODY() public: @@ -1064,7 +1103,7 @@ struct FAFEventData }; -struct FAFStatics +struct ABILITYFRAMEWORK_API FAFStatics { static float GetFloatFromAttributeMagnitude(const FGAMagnitude& AttributeIn , const FGAEffectContext& InContext @@ -1125,6 +1164,8 @@ struct ABILITYFRAMEWORK_API FGAEffect : public FFastArraySerializerItem//, TShar FGAEffect() {} + FGAEffect(TSharedPtr InSpec, const FGAEffectHandle& InHandle); + ~FGAEffect(); @@ -1344,3 +1385,23 @@ struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsB WithCopy = false }; }; + + +/* +Simplified effect container, which do not support effect replication. +*/ +USTRUCT() +struct ABILITYFRAMEWORK_API FAFEffectContainerSimple +{ + GENERATED_BODY() +protected: + UPROPERTY(Transient) + TMap Effects; + +public: + void ApplyEffect(const FGAEffectHandle& InHandle + , const FGAEffect& InEffect); + + void RemoveEffect(const FGAEffectHandle& InHandle); + +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h index 015aabd..48e4738 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h @@ -365,7 +365,7 @@ struct TStructOpsTypeTraits< FGAEffectHandle > : public TStructOpsTypeTraitsBase }; USTRUCT() -struct FAFPredictionHandle +struct ABILITYFRAMEWORK_API FAFPredictionHandle { GENERATED_BODY() public: @@ -448,7 +448,7 @@ struct ABILITYFRAMEWORK_API FGAHashedGameplayTagContainer }; USTRUCT(BlueprintType) -struct FGAIndividualMods +struct ABILITYFRAMEWORK_API FGAIndividualMods { GENERATED_BODY() public: @@ -546,7 +546,7 @@ struct ABILITYFRAMEWORK_API FGAAttribute /* Final calculcated mod from effect, which can be modified by Calculation object. */ USTRUCT() -struct FGAEffectMod +struct ABILITYFRAMEWORK_API FGAEffectMod { GENERATED_BODY() FGAAttribute Attribute; @@ -625,7 +625,7 @@ struct FGAEffectMod }; USTRUCT(BlueprintType) -struct FAFAttributeChangedData +struct ABILITYFRAMEWORK_API FAFAttributeChangedData { GENERATED_BODY() public: @@ -761,7 +761,7 @@ struct ABILITYFRAMEWORK_API FGAEffectCueParams }; USTRUCT() -struct FAFCueHandle +struct ABILITYFRAMEWORK_API FAFCueHandle { GENERATED_BODY(); private: diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 9865855..b26bc97 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -54,7 +54,7 @@ void UIFInventoryComponent::BeginPlay() Counter++; InventoryItems.Add(NewItem); } - + FakeBackend.SetNumZeroed(MaxSlots); /* Further steps 2. Load Properties from external data source (JSON); @@ -176,28 +176,6 @@ void UIFInventoryComponent::AddAllItemsFromActor(class AIFItemActorBase* Source) } void UIFInventoryComponent::ServerAddAllItemsFromActor_Implementation(class AIFItemActorBase* Source) { - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; - typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; - - TSharedPtr Obj = MakeShareable(new FJsonObject()); - TArray> Vals; - - TSharedPtr dupa = MakeShareable(new FJsonValueString("dupa string")); - Vals.Add(dupa); - - Obj->SetArrayField("TestData", Vals); - TSharedPtr dupaData = MakeShareable(new FJsonValueString("dupa asdasd string")); - Obj->SetField("DupaData", dupaData); - - FString OutputString; - TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); - check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); - - FString asd; - - - - //ClientSendJsonData(OutputString); TArray> Items = Source->GetAllItems(); for (const TSoftClassPtr Item : Items) { @@ -294,6 +272,8 @@ void UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Implementation(cla InventoryItems[FreeSlot].Item = DuplicateObject(Item, this); ClientAddItemFromEquipmentAnySlot(Source, SourceIndex, FreeSlot); + + SendToBackend(&InventoryItems[FreeSlot]); } bool UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Validate(class UIFEquipmentComponent* Source, uint8 SourceIndex) { @@ -307,6 +287,55 @@ void UIFInventoryComponent::ClientAddItemFromEquipmentAnySlot_Implementation(cla Source->RemoveFromEquipment(SourceIndex); } +void UIFInventoryComponent::AddItemAnySlot(class UIFItemBase* Source) +{ + if (!Source) + return; + + uint8 FreeSlot = 0; + for (uint8 Idx = 0; Idx < InventoryItems.Num(); Idx++) + { + if (InventoryItems[Idx].Item == nullptr) + { + FreeSlot = Idx; + break; + } + } + + InventoryItems[FreeSlot].Item = DuplicateObject(Source, this); + Source->MarkPendingKill(); + + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + + TSharedPtr Obj = SendToBackend(&InventoryItems[FreeSlot]); + + FString OutputString; + TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); + check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + ClientAddAnySlot(OutputString, FreeSlot); +} +void UIFInventoryComponent::ClientAddAnySlot_Implementation(const FString& JsonData, uint8 InventoryIndex) +{ + TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(JsonData); + + TSharedPtr Object = MakeShareable(new FJsonObject()); + + bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); + + TArray< TSharedPtr > Array; + bool bSuccessful2 = FJsonSerializer::Deserialize(Reader, Array); + + FIFItemData Item; + FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), FIFItemData::StaticStruct(), &Item, 0, 0); + + if (Item.Item) + { + InventoryItems[InventoryIndex] = Item; + OnItemAddedEvent.Broadcast(InventoryIndex, InventoryIndex, Item.Item); + OnItemUpdatedEvent.Broadcast(InventoryIndex, InventoryIndex, Item.Item); + } +} void UIFInventoryComponent::RemoveItem(uint8 InIndex) { @@ -361,33 +390,43 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr(this, ItemClass); - //Inventory.AddItemToFreeSlot(Item); - - TSharedPtr Obj = MakeShareable(new FJsonObject()); - FJsonObjectConverter::UStructToJsonObject(FIFItemData::StaticStruct(), &Item, Obj.ToSharedRef(), 0, 0); - - FakeBackend.Add(Obj); - InventoryItems[Item.Index] = Item; - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + TSharedPtrObj = SendToBackend(&InventoryItems[Item.Index]); + FString OutputString; TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); + + + ClientSendJsonData(OutputString); } void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex) { TSubclassOf ItemClass = InItem.Get(); - UIFItemBase* Item = NewObject(this, ItemClass); + UIFItemBase* ItemObj = NewObject(this, ItemClass); + + InventoryItems[InNetIndex].Item = ItemObj; + + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + + TSharedPtr Obj = SendToBackend(&InventoryItems[InNetIndex]); + + FString OutputString; + TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); + check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + + ClientSendJsonData(OutputString); FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); @@ -405,7 +444,7 @@ void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Dat bool bSuccessful2 = FJsonSerializer::Deserialize(Reader, Array); FIFItemData Item; - FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), Item.StaticStruct(), &Item, 0, 0); + FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), FIFItemData::StaticStruct(), &Item, 0, 0); if (Item.Item) { @@ -414,4 +453,21 @@ void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Dat OnItemUpdatedEvent.Broadcast(Item.Index, Item.Index, Item.Item); } +} + +TSharedPtr UIFInventoryComponent::SendToBackend(FIFItemData* Item) +{ + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + + TSharedPtr Obj = MakeShareable(new FJsonObject()); + FJsonObjectConverter::UStructToJsonObject(FIFItemData::StaticStruct(), Item, Obj.ToSharedRef(), 0, 0); + + FString OutputString; + TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); + check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + + FakeBackend[Item->Index] = Obj; + + return Obj; } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index f2e0824..fad151c 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -190,6 +190,17 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent void ClientAddItemFromEquipmentAnySlot_Implementation(class UIFEquipmentComponent* Source, uint8 SourceIndex, uint8 InventoryIndex); + //never call on clients. + void AddItemAnySlot(class UIFItemBase* Source); + /* + Confirm that change can be made and do the same change on client. + We do not predict inventory modifications. Clients MUST wait for server to make changes and send confirmation back. + */ + UFUNCTION(Client, Reliable) + void ClientAddAnySlot(const FString& JsonData, uint8 InventoryIndex); + void ClientAddAnySlot_Implementation(const FString& JsonData, uint8 InventoryIndex); + + virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemRemoved(uint8 LocalIndex) {}; @@ -221,4 +232,7 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent UFUNCTION(Client, Reliable) void ClientSendJsonData(const FString& Data); void ClientSendJsonData_Implementation(const FString& Data); + + protected: + TSharedPtr SendToBackend(FIFItemData* Item); }; diff --git a/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp index ff6b112..82d9c87 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp @@ -13,6 +13,7 @@ #include "UI/Inventory/Weapons/ARListItemWeaponWidget.h" #include "UI/Inventory/Weapons/Modifications/ARItemMagazineView.h" #include "UI/Inventory/Weapons/Modifications/ARListItemMagazineView.h" +#include "UI/Inventory/Weapons/ARWeaponModificationView.h" // Sets default values for this component's properties UARUIInventoryComponent::UARUIInventoryComponent() @@ -30,8 +31,19 @@ void UARUIInventoryComponent::BeginPlay() { Super::BeginPlay(); - // ... - + if (WeaponModificationViewClass) + { + if (AARHUD* HUD = Cast(GetOwner())) + { + if (AARPlayerController* PC = Cast(HUD->GetOwningPlayerController())) + { + WeaponModificationView = CreateWidget(PC, WeaponModificationViewClass); + + WeaponModificationView->SetVisibility(ESlateVisibility::Collapsed); + WeaponModificationView->AddToViewport(); + } + } + } } @@ -101,7 +113,8 @@ void UARUIInventoryComponent::ShowWeaponsForSlot(class UARItemView* ForSlot) } if (AARCharacter* Character = Cast(PC->GetPawn())) { - UIFItemBase* Item = Character->WeaponInventory->GetItem(ForSlot->LocalIndex); + UARItemWeapon* Item = Character->WeaponInventory->GetItem(ForSlot->LocalIndex); + ModifiedWeapon = Item; if (Item) { InventoryView->SetWeaponName(Item->GetName()); @@ -164,6 +177,11 @@ void UARUIInventoryComponent::UnequipWeaponFromSlot(uint8 SourceNetIndex, uint8 return; Character->WeaponInventory->Unequip(SourceLocalIndex); + + if (ModifiedWeapon.IsValid()) + { + ModifiedWeapon.Reset(); + } } void UARUIInventoryComponent::ShowUpgradesForWeapon(class UARItemMagazineView* For) @@ -178,7 +196,7 @@ void UARUIInventoryComponent::ShowUpgradesForWeapon(class UARItemMagazineView* F Items = PC->MainInventory->GetLocalItemIdxs(UARMagazineUpgradeItem::StaticClass()); } } - + InventoryView->AddWeaponMods(Items, ListItemMagazinelass, PC, For); } @@ -196,14 +214,15 @@ void UARUIInventoryComponent::ModifyWeapon() return; UARItemWeapon* Weapon = Character->WeaponInventory->GetItem(SelectedWeapon); - + ModifiedWeapon = Weapon; if (!Weapon) return; - if (Weapon->MagazineModification.IsValid()) + //WeaponModificationView->StartModifyWeapon(Weapon); + + if (Weapon->MagazineModification) { - TSubclassOf Magazine = Weapon->MagazineModification.LoadSynchronous(); - InventoryView->MagazineUpgrade->OnItemChanged(0, 0, Magazine->GetDefaultObject()); + InventoryView->MagazineUpgrade->OnItemChanged(0, 0, Weapon->MagazineModification); } } @@ -240,4 +259,5 @@ void UARUIInventoryComponent::RemoveMagazineUpgrade() return; UARWeaponInventoryComponent* WeaponInventory = Character->WeaponInventory; + WeaponInventory->RemoveMagazineMod(SelectedWeapon); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp index 03cd900..fd6d3ab 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARWeaponModificationView.cpp @@ -1,15 +1,27 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARWeaponModificationView.h" +#include "Components/Button.h" +#include "Components/WrapBox.h" +#include "Weapons/ARItemWeapon.h" +#include "Weapons/ARMagazineUpgradeItem.h" - - - +void UARWeaponModificationView::NativeConstruct() +{ + Super::NativeConstruct(); + CloseUpgradeView->OnClicked.AddDynamic(this, &UARWeaponModificationView::CloseModificationView); +} void UARWeaponModificationView::StartModifyWeapon(class UARItemWeapon* WeaponItem) { - + SetVisibility(ESlateVisibility::SelfHitTestInvisible); } void UARWeaponModificationView::StopModifyWeapon() { +} + +void UARWeaponModificationView::CloseModificationView() +{ + StopModifyWeapon(); + SetVisibility(ESlateVisibility::Collapsed); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp index 4c0e397..5fd4507 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemMagazineView.cpp @@ -1,9 +1,24 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARItemMagazineView.h" +#include "Components/Image.h" +#include "ARCharacter.h" #include "UI/Inventory/ARUIInventoryComponent.h" +#include "Weapons/ARMagazineUpgradeItem.h" - +void UARItemMagazineView::NativeConstruct() +{ + Super::NativeConstruct(); + + if (GetOwningPlayer()) + { + if (AARCharacter* Character = Cast(GetOwningPlayer()->GetPawn())) + { + Character->WeaponInventory->GetOnUpgradeInstalled().AddDynamic(this, &UARItemMagazineView::OnMagazineUpgradeInstalled); + Character->WeaponInventory->GetOnUpgradeRemoved().AddDynamic(this, &UARItemMagazineView::OnMagazineUpgradeRemoved); + } + } +} FReply UARItemMagazineView::NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { @@ -21,3 +36,22 @@ FReply UARItemMagazineView::NativeOnMouseButtonDoubleClick(const FGeometry& InGe return Handled; } +void UARItemMagazineView::OnMagazineUpgradeInstalled(class UARItemWeapon* Weapon + , class UARWeaponUpgradeItem* Upgrade + , int8 WeaponIndex) +{ + if (UARMagazineUpgradeItem* Magazine = Cast(Upgrade)) + { + Icon->SetBrushFromTexture(Upgrade->Icon); + } +} + +void UARItemMagazineView::OnMagazineUpgradeRemoved(class UARItemWeapon* Weapon + , class UARWeaponUpgradeItem* Upgrade + , int8 WeaponIndex) +{ + if (UARMagazineUpgradeItem* Magazine = Cast(Upgrade)) + { + Icon->SetBrushFromTexture(nullptr); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.cpp new file mode 100644 index 0000000..1517495 --- /dev/null +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemWeaponUpgradeView.h" + + + + diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index b61023e..6ba337f 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -2,6 +2,8 @@ #include "ARItemWeapon.h" +#include "Effects/GABlueprintLibrary.h" + #include "ARCharacter.h" #include "ARPlayerController.h" #include "UI/ARHUD.h" @@ -11,49 +13,74 @@ #include "Weapons/ARMagazineUpgradeItem.h" #include "Weapons/ARWeaponInventoryComponent.h" - +#include "Weapons/ARMagazineUpgradeEffect.h" void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade) { - MagazineModification = InMagazineUpgrade->GetClass()->GetPathName(); - MagazineModificationObj = DuplicateObject(InMagazineUpgrade, this); - MagazineEffect = InMagazineUpgrade->UpgradeEffect.LoadSynchronous(); + UARWeaponInventoryComponent* WeaponComponent = Cast(GetOuter()); + + if (!WeaponComponent) + return; + + AARCharacter* Character = Cast(WeaponComponent->GetOwner()); + if (!Character) + return; + + MagazineModification = DuplicateObject(InMagazineUpgrade, this); + + //this part only on server. + if (Character->Role >= ENetRole::ROLE_Authority) + { + TSubclassOf SpecClass = InMagazineUpgrade->UpgradeEffect.LoadSynchronous(); + MagazineUpgradeValue = InMagazineUpgrade->MagazineUpgradeValue; + MagazineUpgradeProperty = SpecClass; + + AddUpgrade(MagazineUpgradeProperty, MagazineEffectHandle, MagazineSpecHandle, Character, MagazineUpgradeValue); + } OnMagazineUpdateAdded(); } void UARItemWeapon::OnMagazineUpdateAdded() { //should be called only from server. FARWeaponModInfo Info; - Info.Icon = MagazineModificationObj->Icon->GetPathName(); + Info.Icon = MagazineModification->Icon->GetPathName(); Info.UpgradeType = EARWeaponUpgradeType::Magazine; - ClientOnMagazineAdded(Info); } -TSoftClassPtr UARItemWeapon::RemoveMagazineUpgrade() +void UARItemWeapon::AddUpgrade(FAFPropertytHandle& PropertyHandle + , FGAEffectHandle& EffectHandle + , FAFEffectSpecHandle& SpecHandle + , class AARCharacter* Character + , float UpgradeValue) { - TSoftClassPtr Copy = MagazineModification; - MagazineModification.Reset(); - return Copy; + //causer MagazineUpgrade ? + UGABlueprintLibrary::CreateEffectSpec(SpecHandle, PropertyHandle, this, Character, Character); + + EffectHandle = FGAEffectHandle::GenerateHandle(); + SpecHandle.CalculateAttributeModifier(EffectHandle); + SpecHandle.OverrideAttributeModifier(UpgradeValue); + + FGAEffect Effect(SpecHandle.GetPtr(), EffectHandle); + + UpgradeContainer.ApplyEffect(EffectHandle, Effect); + + FGAEffectMod Mod = SpecHandle.GetModifier(); + AbilityInstance->ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef()); } -void UARItemWeapon::ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& ModInfo) +UARMagazineUpgradeItem* UARItemWeapon::RemoveMagazineUpgrade() { - if (UARWeaponInventoryComponent* Inv = Cast(GetOuter())) - { - if (AARCharacter* Character = Cast(Inv->GetOwner())) - { - if (AARPlayerController* PC = Cast(Character->Controller)) - { - if (AARHUD* HUD = Cast(PC->GetHUD())) - { - UTexture2D* Icon = ModInfo.Icon.LoadSynchronous(); - HUD->GetUIInventory()->GetInventoryView()->MagazineUpgrade->Icon->SetBrushFromTexture(Icon); - } - } - } - } + FGAEffectMod Mod = MagazineSpecHandle.GetModifier(); + AbilityInstance->RemoveBonus(Mod.Attribute, MagazineEffectHandle, Mod.AttributeMod); + UpgradeContainer.RemoveEffect(MagazineEffectHandle); + + MagazineUpgradeProperty.Reset(); + MagazineSpecHandle.Reset(); + + return MagazineModification; } + void UARItemWeapon::OnItemAdded(uint8 LocalIndex) { @@ -61,4 +88,9 @@ void UARItemWeapon::OnItemAdded(uint8 LocalIndex) void UARItemWeapon::OnItemRemoved(uint8 LocalIndex) { +} + +void UARItemWeapon::PostItemLoad() +{ + } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp index 19a53e1..d578611 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp @@ -92,14 +92,35 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde TArray NoInput; FAFOnAbilityReady del; { - del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability); + del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(LocalIndex)); Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); } Character->GetAbilityComp()->NativeAddAbility(InWeapon->Ability, NoInput); WeaponAbilities[LocalIndex] = InWeapon->Ability; } } -void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr InAbilityTag) +void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) +{ + UARItemWeapon* InWeapon = Cast(Item); + FARWeaponRPC Data; + Data.Weapon = InWeapon->Weapon; + //Data.SocketName = InWeapon->Socket; + Data.Position = InWeapon->HolsteredPosition; + Data.Rotation = InWeapon->HolsteredRotation; + Data.AttachSlot = static_cast(LocalIndex); + if (AARCharacter* Character = Cast(POwner)) + { + TArray NoInput; + FAFOnAbilityReady del; + { + del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(LocalIndex)); + Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); + } + WeaponAbilities[LocalIndex] = InWeapon->Ability; + } + MulticastAddWeapon(Data); +} +void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr InAbilityTag, int8 LocalIndex) { AARCharacter* Character = Cast(POwner); if (!Character) @@ -108,16 +129,16 @@ void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtrGetAbilityComp(); UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - - AARPlayerController* PC = Cast(GetOwner()); - if (PC) - { - if (AARCharacter* Character = Cast(PC->GetPawn())) - { - Character->WeaponInventory->SetAbilityToItem(CurrentWeaponIndex, Ability); - } + SetAbilityToItem(LocalIndex, Ability); +} +void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility) +{ + UARItemWeapon* ItemWeapon = GetItem(InLocalIndex); - } + if (!ItemWeapon) + return; + + ItemWeapon->AbilityInstance = Cast(InAbility); } void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) { @@ -139,18 +160,7 @@ void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) } } -void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) -{ - UARItemWeapon* InWeapon = Cast(Item); - FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; - //Data.SocketName = InWeapon->Socket; - Data.Position = InWeapon->HolsteredPosition; - Data.Rotation = InWeapon->HolsteredRotation; - Data.AttachSlot = static_cast(LocalIndex); - MulticastAddWeapon(Data); -} void UARWeaponInventoryComponent::OnServerItemRemoved(uint8 LocalIndex) { FARWeaponRPC Data; @@ -322,10 +332,7 @@ void UARWeaponInventoryComponent::MulticastHolster_Implementation(const FARWeapo CurrentWeaponIndex = -1; } } -void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility) -{ -} void UARWeaponInventoryComponent::NextWeapon() { ENetMode NetMode = GetOwner()->GetNetMode(); @@ -732,10 +739,61 @@ void UARWeaponInventoryComponent::ClientAddMagazineMod_Implementation(int8 Weapo FARWeaponModInfo Info; Info.Icon = Magazine->Icon->GetPathName(); Info.UpgradeType = EARWeaponUpgradeType::Magazine; - Weapon->ClientOnMagazineAdded(Info); MainInventory->RemoveItem(MagazineModIndex); + + OnUpgradeInstalled.Broadcast(Weapon, Magazine, WeaponIdx); } } } } +} + +void UARWeaponInventoryComponent::RemoveMagazineMod(int8 WeaponIdx) +{ + if (GetOwnerRole() < ENetRole::ROLE_Authority) + { + ServerRemoveMagazineMod(WeaponIdx); + return; + } + +} +void UARWeaponInventoryComponent::ServerRemoveMagazineMod_Implementation(int8 WeaponIdx) +{ + if (AARCharacter* Character = Cast(GetOwner())) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + UIFInventoryComponent* MainInventory = PC->MainInventory; + + UARItemWeapon* Weapon = GetItem(WeaponIdx); + if (Weapon) + { + UARMagazineUpgradeItem* MagazineUpgrade = Weapon->RemoveMagazineUpgrade(); + ServerRemoveMagazineMod(WeaponIdx); + PC->MainInventory->AddItemAnySlot(MagazineUpgrade); + ClientRemoveMagazineMod(WeaponIdx); + } + } + } +} +bool UARWeaponInventoryComponent::ServerRemoveMagazineMod_Validate(int8 WeaponIdx) +{ + return true; +} +void UARWeaponInventoryComponent::ClientRemoveMagazineMod_Implementation(int8 WeaponIdx) +{ + if (AARCharacter* Character = Cast(GetOwner())) + { + if (AARPlayerController* PC = Cast(Character->Controller)) + { + UIFInventoryComponent* MainInventory = PC->MainInventory; + + UARItemWeapon* Weapon = GetItem(WeaponIdx); + if (Weapon) + { + UARMagazineUpgradeItem* MagazineUpgrade = Weapon->RemoveMagazineUpgrade(); + OnUpgradeRemoved.Broadcast(Weapon, MagazineUpgrade, WeaponIdx); + } + } + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/ARItemBase.h b/Source/ActionRPGGame/Public/ARItemBase.h index 29fc70c..6b2256f 100644 --- a/Source/ActionRPGGame/Public/ARItemBase.h +++ b/Source/ActionRPGGame/Public/ARItemBase.h @@ -4,6 +4,7 @@ #include "CoreMinimal.h" #include "IFItemBase.h" +#include "Effects/GAGameEffect.h" #include "ARItemBase.generated.h" USTRUCT() @@ -25,5 +26,9 @@ class ACTIONRPGGAME_API UARItemBase : public UIFItemBase //obviously we want TSoftObjectPtr<> UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") UTexture2D* Icon; - + /* + Containes upgrades to THIS item. + */ + UPROPERTY(Transient) + FAFEffectContainerSimple UpgradeContainer; }; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h index cc5a916..87c742e 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h @@ -20,13 +20,21 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Views") TSubclassOf ListItemMagazinelass; + UPROPERTY(EditAnywhere, Category = "Views") + TSubclassOf WeaponModificationViewClass; UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") class UARInventoryScreenWidget* InventoryView; + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") + class UARWeaponModificationView* WeaponModificationView; + /* NetIndex of selected Weapon. */ UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") uint8 SelectedWeapon; + + TWeakObjectPtr ModifiedWeapon; + public: // Sets default values for this component's properties UARUIInventoryComponent(); diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h index 528b181..6ea9433 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARWeaponModificationView.h @@ -16,8 +16,18 @@ class ACTIONRPGGAME_API UARWeaponModificationView : public UARUMGWidgetBase public: UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) class UARItemMagazineView* MagazineUpgrade; - + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UButton* CloseUpgradeView; + + UPROPERTY(BlueprintReadOnly, Category = "Widgets", meta = (BindWidget)) + class UWrapBox* UpgradeList; + + virtual void NativeConstruct() override; void StartModifyWeapon(class UARItemWeapon* WeaponItem); void StopModifyWeapon(); + + UFUNCTION() + void CloseModificationView(); }; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h index f27f1b0..2b89b7f 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h @@ -14,7 +14,18 @@ class ACTIONRPGGAME_API UARItemMagazineView : public UARItemView { GENERATED_BODY() public: + virtual void NativeConstruct() override; + virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; + + UFUNCTION() + void OnMagazineUpgradeInstalled(class UARItemWeapon* Weapon + , class UARWeaponUpgradeItem* Upgrade + , int8 WeaponIndex); + + void OnMagazineUpgradeRemoved(class UARItemWeapon* Weapon + , class UARWeaponUpgradeItem* Upgrade + , int8 WeaponIndex); }; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.h new file mode 100644 index 0000000..cbfc72d --- /dev/null +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemWeaponUpgradeView.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Inventory/ARItemView.h" +#include "ARItemWeaponUpgradeView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARItemWeaponUpgradeView : public UARItemView +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index a78ca66..749d6e8 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -57,7 +57,6 @@ struct FARItemWeaponData : public FARItemBaseData FRotator EquipedRotation; }; - /** * */ @@ -96,30 +95,54 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UARWeaponAbilityBase* AbilityInstance; UPROPERTY(BlueprintReadOnly, Category = "Ability") - TSoftClassPtr MagazineModification; + class UARMagazineUpgradeItem* MagazineModification; + + UPROPERTY(Transient) + FAFPropertytHandle MagazineUpgradeProperty; + UPROPERTY(Transient) + FGAEffectHandle MagazineEffectHandle; + UPROPERTY(Transient) + FAFEffectSpecHandle MagazineSpecHandle; + + UPROPERTY(Transient) + FAFPropertytHandle BarrelUpgradeProperty; + UPROPERTY(Transient) + FGAEffectHandle BarrelEffectHandle; + UPROPERTY(Transient) + FAFEffectSpecHandle BarrelSpecHandle; + + UPROPERTY(Transient) + FAFPropertytHandle ScopeUpgradeProperty; + UPROPERTY(Transient) + FGAEffectHandle ScopeEffectHandle; + UPROPERTY(Transient) + FAFEffectSpecHandle ScopeSpecHandle; + + UPROPERTY(Transient) + float MagazineUpgradeValue; /* So it will actually actor as mini inventory with predefined slots. That way we should be able to generate mods on the fly and store them as json in external database. */ - UPROPERTY(BlueprintReadOnly, Category = "Ability") - class UARMagazineUpgradeItem* MagazineModificationObj; - + UPROPERTY() //replicated FARMagazineUpgradeItemData MagazineUpgrade; - FAFPropertytHandle MagazineEffect; - FGAEffectHandle MagazineEffectHandle; - void AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade); void OnMagazineUpdateAdded(); - UFUNCTION(Client, Reliable) - void ClientOnMagazineAdded(const FARWeaponModInfo& ModInfo); - void ClientOnMagazineAdded_Implementation(const FARWeaponModInfo& ModInfo); + void AddUpgrade(FAFPropertytHandle& PropertyHandle + , FGAEffectHandle& EffectHandle + , FAFEffectSpecHandle& SpecHandle + , class AARCharacter* Character + , float UpgradeValue); + - TSoftClassPtr RemoveMagazineUpgrade(); + UARMagazineUpgradeItem* RemoveMagazineUpgrade(); virtual void OnItemAdded(uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; + + virtual void PostItemLoad(); }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h index b862fa6..09361e5 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h @@ -28,6 +28,14 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem public: UPROPERTY(EditAnywhere) FARMagazineUpgradeItemData Data; + /* + An actual modifier value of this upgrade. + */ + UPROPERTY(EditAnywhere) + float MagazineUpgradeValue; + /* + Effect template + */ UPROPERTY(EditAnywhere) TSoftClassPtr UpgradeEffect; }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 51ce148..5c070ec 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -67,6 +67,8 @@ struct FARWeaponRPC }; +DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAROnUpgradeInstalled, class UARItemWeapon*, Weapon, class UARWeaponUpgradeItem*, Upgrade, int8, WeaponIndex); +DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAROnUpgradeRemoved, class UARItemWeapon*, Weapon, class UARWeaponUpgradeItem*, Upgrade, int8, WeaponIndex); /* Manages currently equipped weapons (holstered and unholstered). */ @@ -89,6 +91,9 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone int8 CurrentWeaponIndex; + FAROnUpgradeInstalled OnUpgradeInstalled; + FAROnUpgradeRemoved OnUpgradeRemoved; + public: // Sets default values for this component's properties UARWeaponInventoryComponent(); @@ -101,13 +106,24 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void InitializeWeapons(APawn* Pawn); // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; + + inline FAROnUpgradeInstalled& GetOnUpgradeInstalled() + { + return OnUpgradeInstalled; + } + inline FAROnUpgradeRemoved& GetOnUpgradeRemoved() + { + return OnUpgradeRemoved; + } + virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; virtual void OnServerItemRemoved(uint8 LocalIndex) override; - void OnWeaponReady(TSoftClassPtr InAbilityTag); + void OnWeaponReady(TSoftClassPtr InAbilityTag, int8 Index); + void SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility); UFUNCTION(NetMulticast, Reliable) void MulticastAddWeapon(const FARWeaponRPC& WeaponData); @@ -141,7 +157,7 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone { POwner = InPawn; } - void SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility); + UFUNCTION(BlueprintCallable) void NextWeapon(); UFUNCTION(BlueprintCallable) @@ -191,4 +207,15 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone void ClientAddMagazineMod(int8 WeaponIdx, int8 MagazineModIndex); void ClientAddMagazineMod_Implementation(int8 WeaponIdx, int8 MagazineModIndex); + void RemoveMagazineMod(int8 WeaponIdx); + UFUNCTION(Server, Reliable, WithValidation) + void ServerRemoveMagazineMod(int8 WeaponIdx); + + void ServerRemoveMagazineMod_Implementation(int8 WeaponIdx); + bool ServerRemoveMagazineMod_Validate(int8 WeaponIdx); + + UFUNCTION(Client, Reliable) + void ClientRemoveMagazineMod(int8 WeaponIdx); + void ClientRemoveMagazineMod_Implementation(int8 WeaponIdx); + }; From e9ac7031cb7d274553ef4796e26e440fd9742b03 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 4 May 2018 00:29:16 +0200 Subject: [PATCH 162/187] fixes --- .../UI/Inventory/ARInventoryScreenWidget.cpp | 22 ++++---------- .../UI/Inventory/ARUIInventoryComponent.cpp | 20 ------------- .../Inventory/Weapons/ARItemWeaponWidget.cpp | 29 +++++++++++++++++++ .../UI/Inventory/ARInventoryScreenWidget.h | 5 ---- .../UI/Inventory/ARUIInventoryComponent.h | 8 ----- .../UI/Inventory/Weapons/ARItemWeaponWidget.h | 8 +++++ .../Modifications/ARItemMagazineView.h | 8 ++--- 7 files changed, 47 insertions(+), 53 deletions(-) diff --git a/Source/ActionRPGGame/Private/UI/Inventory/ARInventoryScreenWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARInventoryScreenWidget.cpp index 757a8d0..b580366 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/ARInventoryScreenWidget.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/ARInventoryScreenWidget.cpp @@ -12,10 +12,12 @@ void UARInventoryScreenWidget::NativeConstruct() { Super::NativeConstruct(); - WeaponSlots.Add(RightWeaponWidget); - WeaponSlots.Add(LeftWeaponWidget); - WeaponSlots.Add(SideWeaponWidget); - WeaponSlots.Add(BottomBackWeaponWidget); + + RightWeaponWidget->Index = 0; + LeftWeaponWidget->Index = 1; + SideWeaponWidget->Index = 2; + BottomBackWeaponWidget->Index = 3; + ModifySelectedWeapon->OnClicked.AddDynamic(this, &UARInventoryScreenWidget::OnModifyWeaponClicked); } @@ -24,18 +26,6 @@ void UARInventoryScreenWidget::SetWeaponName(const FString& Name) SelectedWeapon->SetText(FText::FromString(Name)); } -void UARInventoryScreenWidget::OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) -{ - WeaponSlots[NetIndex]->OnSlotCreated(NetIndex, LocalIndex, Item); -} -void UARInventoryScreenWidget::OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) -{ - WeaponSlots[NetIndex]->OnItemChanged(NetIndex, LocalIndex, Item); -} -void UARInventoryScreenWidget::OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) -{ - WeaponSlots[NetIndex]->OnItemRemoved(NetIndex, LocalIndex, Item); -} void UARInventoryScreenWidget::OnModifyWeaponClicked() { diff --git a/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp index 82d9c87..7dabc5e 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/ARUIInventoryComponent.cpp @@ -64,13 +64,6 @@ void UARUIInventoryComponent::CreateInventoryView(AARPlayerController* PC) InventoryView->SetVisibility(ESlateVisibility::Collapsed); InventoryView->Inventory = this; InventoryView->AddToViewport(); - - if (AARCharacter* Character = Cast(PC->GetPawn())) - { - Character->WeaponInventory->GetOnItemAdded().AddUObject(this, &UARUIInventoryComponent::OnWeaponAdded); - Character->WeaponInventory->GetOnItemUpdated().AddUObject(this, &UARUIInventoryComponent::OnWeaponUpdated); - Character->WeaponInventory->GetOnItemRemoved().AddUObject(this, &UARUIInventoryComponent::OnWeaponRemoved); - } } } @@ -86,19 +79,6 @@ void UARUIInventoryComponent::ShowHideInventory() } } -void UARUIInventoryComponent::OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) -{ - InventoryView->OnWeaponAdded(NetIndex, LocalIndex, Item); -} -void UARUIInventoryComponent::OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) -{ - InventoryView->OnWeaponUpdated(NetIndex, LocalIndex, Item); -} -void UARUIInventoryComponent::OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item) -{ - InventoryView->OnWeaponRemoved(NetIndex, LocalIndex, Item); -} - void UARUIInventoryComponent::ShowWeaponsForSlot(class UARItemView* ForSlot) { SelectedWeapon = ForSlot->LocalIndex; diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index b625792..58b57a9 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -24,6 +24,12 @@ void UARItemWeaponWidget::NativeConstruct() if (AARPlayerController* PC = Cast(GetOwningPlayer())) { Inventory = PC->MainInventory; + if (AARCharacter* Character = Cast(PC->GetPawn())) + { + Character->WeaponInventory->GetOnItemAdded().AddUObject(this, &UARItemWeaponWidget::OnWeaponAdded2); + Character->WeaponInventory->GetOnItemUpdated().AddUObject(this, &UARItemWeaponWidget::OnWeaponUpdated2); + Character->WeaponInventory->GetOnItemRemoved().AddUObject(this, &UARItemWeaponWidget::OnWeaponRemoved2); + } } if (AARHUD* HUD = Cast(GetOwningPlayer()->GetHUD())) { @@ -66,3 +72,26 @@ FReply UARItemWeaponWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGe return Handled; } + + +void UARItemWeaponWidget::OnWeaponAdded2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem) +{ + if (InLocalIndex == Index) + { + OnSlotCreated(InNetIndex, InLocalIndex, InItem); + } +} +void UARItemWeaponWidget::OnWeaponUpdated2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem) +{ + if (InLocalIndex == Index) + { + OnItemChanged(InNetIndex, InLocalIndex, InItem); + } +} +void UARItemWeaponWidget::OnWeaponRemoved2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem) +{ + if (InLocalIndex == Index) + { + OnItemRemoved(InNetIndex, InLocalIndex, InItem); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h index db2dd11..092c695 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h @@ -54,8 +54,6 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase UTextBlock* SelectedWeapon; TWeakObjectPtr Inventory; -protected: - TArray WeaponSlots; public: virtual void NativeConstruct() override; @@ -128,9 +126,6 @@ class ACTIONRPGGAME_API UARInventoryScreenWidget : public UARUMGWidgetBase } } - void OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); - void OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); - void OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); protected: UFUNCTION() void OnModifyWeaponClicked(); diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h index 87c742e..f65a08e 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h @@ -50,14 +50,6 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent void CreateInventoryView(AARPlayerController* PC); void ShowHideInventory(); -protected: - UFUNCTION() - void OnWeaponAdded(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); - UFUNCTION() - void OnWeaponUpdated(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); - UFUNCTION() - void OnWeaponRemoved(uint8 NetIndex, uint8 LocalIndex, class UIFItemBase* Item); - public: void ShowWeaponsForSlot(class UARItemView* ForSlot); void RemoveWeaponFromSlot(int8 Index); diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h index 9c00952..5729429 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h @@ -17,6 +17,8 @@ class ACTIONRPGGAME_API UARItemWeaponWidget : public UARItemView TWeakObjectPtr InventoryComponent; TWeakObjectPtr WeaponInventory; + int8 Index; + public: virtual void NativeConstruct() override; public: @@ -25,4 +27,10 @@ class ACTIONRPGGAME_API UARItemWeaponWidget : public UARItemView virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; + UFUNCTION() + void OnWeaponAdded2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem); + UFUNCTION() + void OnWeaponUpdated2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem); + UFUNCTION() + void OnWeaponRemoved2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem); }; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h index 2b89b7f..7054790 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/Modifications/ARItemMagazineView.h @@ -24,8 +24,8 @@ class ACTIONRPGGAME_API UARItemMagazineView : public UARItemView void OnMagazineUpgradeInstalled(class UARItemWeapon* Weapon , class UARWeaponUpgradeItem* Upgrade , int8 WeaponIndex); - - void OnMagazineUpgradeRemoved(class UARItemWeapon* Weapon - , class UARWeaponUpgradeItem* Upgrade - , int8 WeaponIndex); + UFUNCTION() + void OnMagazineUpgradeRemoved(class UARItemWeapon* Weapon + , class UARWeaponUpgradeItem* Upgrade + , int8 WeaponIndex); }; From 12c3426694a64ca298454ad10c8e1c27855ca2e0 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 5 May 2018 01:27:55 +0200 Subject: [PATCH 163/187] still working on item upgrades. Moved all weapon upgrade functionality to WeaponAbility, added functionality to copy values from one attribute set to other --- .../Private/AFAbilityComponent.cpp | 3 +- .../Private/Abilities/GAAbilityBase.cpp | 36 +++--- .../Private/Attributes/GAAttributeBase.cpp | 10 ++ .../Private/Attributes/GAAttributesBase.cpp | 14 +++ .../Public/AFAbilityComponent.h | 12 +- .../Public/Abilities/GAAbilityBase.h | 10 +- .../Public/Attributes/GAAttributeBase.h | 1 + .../Public/Attributes/GAAttributesBase.h | 15 +++ .../Private/IFEquipmentComponent.cpp | 9 ++ .../InventoryFramework/Public/IFItemBase.h | 72 +++++++---- .../UI/Inventory/ARItemTooltipView.cpp | 7 ++ .../Inventory/Weapons/ARItemWeaponWidget.cpp | 6 + .../Private/Weapons/ARItemWeapon.cpp | 119 ++++++++++++------ .../Private/Weapons/ARWeaponAbilityBase.cpp | 54 ++++++++ .../Weapons/ARWeaponInventoryComponent.cpp | 6 +- Source/ActionRPGGame/Public/ARItemBase.h | 55 +++++++- .../Public/UI/Inventory/ARItemTooltipView.h | 20 +++ .../UI/Inventory/Weapons/ARItemWeaponWidget.h | 3 + .../Public/Weapons/ARItemWeapon.h | 92 ++------------ .../Public/Weapons/ARMagazineUpgradeItem.h | 15 +-- .../Public/Weapons/ARWeaponAbilityBase.h | 51 ++++++++ 21 files changed, 426 insertions(+), 184 deletions(-) create mode 100644 Source/ActionRPGGame/Private/UI/Inventory/ARItemTooltipView.cpp create mode 100644 Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp index 4f1273d..a6f8eba 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -40,7 +40,7 @@ void FAFReplicatedAttributeItem::PostReplicatedAdd(const struct FAFReplicatedAtt FAFReplicatedAttributeContainer& ArraySerializer = const_cast(InArraySerializer); UGAAttributesBase*& Attribute = ArraySerializer.AttributeMap.FindOrAdd(AttributeTag); Attribute = Attributes; - InArraySerializer.OnAttributeReplicated(AttributeTag); + InArraySerializer.OnAttributeReplicated(AttributeTag, Attributes); } void FAFReplicatedAttributeItem::PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer) { @@ -56,6 +56,7 @@ UGAAttributesBase* FAFReplicatedAttributeContainer::Add(const FGameplayTag InTag MarkItemDirty(Item); UGAAttributesBase*& Added = AttributeMap.FindOrAdd(InTag); Added = AttributesDup; + OnAttributeReplicated(InTag, AttributesDup); return AttributesDup; } UAFAbilityComponent::UAFAbilityComponent(const FObjectInitializer& ObjectInitializer) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp index 9b5a023..47da901 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp @@ -157,18 +157,18 @@ void UGAAbilityBase::InitAbility() { AbilityComponent = GetAbilityComp(); } - if (Attributes) + + if (GetAttributes()) { - Attributes->InitializeAttributes(GetAbilityComp()); - Attributes->InitializeAttributesFromTable(); + GetAttributes()->InitializeAttributes(GetAbilityComp()); + GetAttributes()->InitializeAttributesFromTable(); } - ENetRole role = AbilityComponent->GetOwnerRole(); ENetMode mode = AbilityComponent->GetOwner()->GetNetMode(); - if (role < ENetRole::ROLE_Authority) + { - FSimpleDelegate Delegate = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); + FAFOnAttributeReady Delegate = FAFOnAttributeReady::CreateUObject(this, &UGAAbilityBase::OnAttributeSetReplicated); AbilityComponent->RepAttributes.RegisterAttributeRepEvent(AbilityTag, Delegate); } @@ -176,11 +176,11 @@ void UGAAbilityBase::InitAbility() if (role == ENetRole::ROLE_Authority || mode == ENetMode::NM_Standalone) { - if (AbilityComponent && Attributes) + if (AbilityComponent && GetAttributes()) { - UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, Attributes);; - Attributes = nullptr; - Attributes = NewAttributes; + UGAAttributesBase* NewAttributes = AbilityComponent->AddAddtionalAttributes(AbilityTag, GetAttributes());; + SetAttributes(nullptr); + SetAttributes(NewAttributes); } } @@ -191,10 +191,14 @@ void UGAAbilityBase::InitAbility() OnAbilityInited(); } -void UGAAbilityBase::OnAttributeSetReplicated() +void UGAAbilityBase::OnAttributeSetReplicated(class UGAAttributesBase* ReplicatedAttributes) { - UGAAttributesBase* attributes = AbilityComponent->RepAttributes.AttributeMap.FindRef(AbilityTag); - Attributes = attributes; + SetAttributes(ReplicatedAttributes); + if (GetAttributes()) + { + GetAttributes()->InitializeAttributes(GetAbilityComp()); + GetAttributes()->InitializeAttributesFromTable(); + } } void UGAAbilityBase::OnAbilityInited() @@ -515,11 +519,11 @@ float UGAAbilityBase::GetAttributeValue(FGAAttribute AttributeIn) const } float UGAAbilityBase::NativeGetAttributeValue(const FGAAttribute AttributeIn) const { - return Attributes->GetCurrentAttributeValue(AttributeIn); + return GetAttributes()->GetCurrentAttributeValue(AttributeIn); } float UGAAbilityBase::GetAttributeVal(FGAAttribute AttributeIn) const { - return Attributes->GetCurrentAttributeValue(AttributeIn); + return GetAttributes()->GetCurrentAttributeValue(AttributeIn); } bool UGAAbilityBase::ApplyAttributeCost() @@ -586,7 +590,7 @@ bool UGAAbilityBase::CheckAbilityAttributeCost() { float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; - float AttributeVal = Attributes->GetFloatValue(Attribute); + float AttributeVal = GetAttributes()->GetFloatValue(Attribute); if (ModValue > AttributeVal) return false; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp index 77ff541..8b73722 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -44,7 +44,17 @@ void FAFAttributeBase::InitializeAttribute(UAFAbilityComponent* InComponent, con ExtensionClass.GetDefaultObject()->Initialize(InComponent, InAttributeName); } } +void FAFAttributeBase::CopyFromOther(FAFAttributeBase* Other) +{ + if (!Other) + return; + BaseValue = Other->BaseValue; + MinValue = Other->MinValue; + MaxValue = Other->MaxValue; + CurrentValue = Other->CurrentValue; + BonusValue = Other->BonusValue; +} void FAFAttributeBase::CalculateBonus() { SCOPE_CYCLE_COUNTER(STAT_CalculateBonus); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp index 4a59378..6f89cdc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp @@ -51,6 +51,20 @@ void UGAAttributesBase::InitializeAttributes(UAFAbilityComponent* InOwningAttrib BP_InitializeAttributes(); } +void UGAAttributesBase::CopyFromOtherAttributes(UGAAttributesBase* Other) +{ + for (TFieldIterator StrIt(GetClass(), EFieldIteratorFlags::IncludeSuper); StrIt; ++StrIt) + { + FAFAttributeBase* ThisAttribute = StrIt->ContainerPtrToValuePtr(this); + FAFAttributeBase* OtherAttribute = Other->GetAttribute(FGAAttribute(StrIt->GetFName())); + + if (ThisAttribute && OtherAttribute) + { + ThisAttribute->CopyFromOther(OtherAttribute); + } + } +} + void UGAAttributesBase::InitializeAttributesFromTable() { if (!AttributeValues) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h index 30f8ae0..5dcf71e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -120,6 +120,8 @@ struct FAFReplicatedAttributeItem : public FFastArraySerializerItem void PostReplicatedChange(const struct FAFReplicatedAttributeContainer& InArraySerializer); }; +DECLARE_DELEGATE_OneParam(FAFOnAttributeReady, class UGAAttributesBase*); + USTRUCT() struct FAFReplicatedAttributeContainer : public FFastArraySerializer { @@ -132,9 +134,9 @@ struct FAFReplicatedAttributeContainer : public FFastArraySerializer TMap AttributeMap; - TMap AttributeReplicatedEvent; + TMap AttributeReplicatedEvent; - void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FSimpleDelegate& InDelegate) + void RegisterAttributeRepEvent(const FGameplayTag& InTag, const FAFOnAttributeReady& InDelegate) { if (!AttributeReplicatedEvent.Contains(InTag)) return; @@ -142,11 +144,11 @@ struct FAFReplicatedAttributeContainer : public FFastArraySerializer AttributeReplicatedEvent.Add(InTag, InDelegate); } - void OnAttributeReplicated(const FGameplayTag& InTag) const + void OnAttributeReplicated(const FGameplayTag& InTag, UGAAttributesBase* InAttributes) const { - if (const FSimpleDelegate* Delegate = AttributeReplicatedEvent.Find(InTag)) + if (const FAFOnAttributeReady* Delegate = AttributeReplicatedEvent.Find(InTag)) { - Delegate->Execute(); + Delegate->Execute(InAttributes); //AttributeReplicatedEvent.Remove(InTag); } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h index 91519ad..f42b055 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h @@ -282,7 +282,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt void InitAbility(); public: UFUNCTION() - void OnAttributeSetReplicated(); + void OnAttributeSetReplicated(class UGAAttributesBase* ReplicatedAttributes); //called on both server and client after InitAbility(); virtual void OnAbilityInited(); @@ -452,6 +452,14 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt UFUNCTION(BlueprintPure, meta = (DisplayName = "Can Use Ability"), Category = "AbilityFramework|Abilities") bool BP_CanUseAbility(); + virtual void SetAttributes(UGAAttributesBase* InAttributes) + { + Attributes = InAttributes; + } + virtual class UGAAttributesBase* GetAttributes() const + { + return Attributes; + } /** IAFAbilityInterface Begin */ virtual class UGAAttributesBase* GetAttributes() override; virtual class UAFAbilityComponent* GetAbilityComp() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index c15fbc0..8695737 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -82,6 +82,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase FAFAttributeBase(); FAFAttributeBase(float BaseValueIn); void InitializeAttribute(UAFAbilityComponent* InComponent, const FName InAttributeName); + void CopyFromOther(FAFAttributeBase* Other); /* You should never use those tree function to set attributes. Only use them for testing/debugging and setting initial values for attributes. */ inline void SetBaseValue(float ValueIn) { BaseValue = ValueIn; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h index b5786b6..f2d1f68 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h @@ -55,6 +55,7 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject ~UGAAttributesBase(); //virtual void PostNetReceive() override; virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp); + void CopyFromOtherAttributes(UGAAttributesBase* Other); void InitializeAttributesFromTable(); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) bool BP_InitializeAttributes(); @@ -134,3 +135,17 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject void OnAttributeModified(const FGAEffectMod& InMod, const FGAEffectHandle& InHandle); }; + +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFAttributesProperty +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere) + TSubclassOf Attributes; + /* + If set, any values in Attributes will be overriden by table. + */ + UPROPERTY(EditAnywhere, BlueprintReadOnly) + UDataTable* AttributeValues; +}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp index 4fcb4dc..6bc32bd 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp @@ -54,8 +54,12 @@ void UIFEquipmentComponent::AddItemFromInventory(class UIFInventoryComponent* So return; EquipmentItems[EquipmentIndex].Item = DuplicateObject(Item, this); + OnItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); + EquipmentItems[EquipmentIndex].Item->OnServerItemAddedEquipment(EquipmentItems[EquipmentIndex].Index); + OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); + } } void UIFEquipmentComponent::ServerAddItemFromInventory_Implementation(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex) @@ -66,8 +70,10 @@ void UIFEquipmentComponent::ServerAddItemFromInventory_Implementation(class UIFI EquipmentItems[EquipmentIndex].Item = DuplicateObject(Item, this); OnServerItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); + EquipmentItems[EquipmentIndex].Item->OnServerItemAddedEquipment(EquipmentItems[EquipmentIndex].Index); ClientAddItemFromInventory(Source, SourceIndex, EquipmentIndex); OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); + } bool UIFEquipmentComponent::ServerAddItemFromInventory_Validate(class UIFInventoryComponent* Source, uint8 SourceIndex, uint8 EquipmentIndex) { @@ -80,6 +86,7 @@ void UIFEquipmentComponent::ClientAddItemFromInventory_Implementation(class UIFI return; EquipmentItems[EquipmentIndex].Item = DuplicateObject(Item, this); + EquipmentItems[EquipmentIndex].Item->OnItemAddedEquipment(EquipmentItems[EquipmentIndex].Index); OnItemAdded(EquipmentItems[EquipmentIndex].Item, EquipmentIndex); OnItemAddedEvent.Broadcast(EquipmentIndex, EquipmentIndex, EquipmentItems[EquipmentIndex].Item); Source->RemoveItem(SourceIndex); @@ -97,6 +104,7 @@ void UIFEquipmentComponent::RemoveFromEquipment(uint8 EquipmentIndex) void UIFEquipmentComponent::ServerRemoveFromEquipment_Implementation(uint8 EquipmentIndex) { + EquipmentItems[EquipmentIndex].Item->OnServerItemRemovedEquipment(EquipmentItems[EquipmentIndex].Index); if (EquipmentItems[EquipmentIndex].Item) { EquipmentItems[EquipmentIndex].Item->MarkPendingKill(); @@ -112,6 +120,7 @@ bool UIFEquipmentComponent::ServerRemoveFromEquipment_Validate(uint8 EquipmentIn void UIFEquipmentComponent::ClientRemoveFromEquipment_Implementation(uint8 EquipmentIndex) { + EquipmentItems[EquipmentIndex].Item->OnItemRemovedEquipment(EquipmentItems[EquipmentIndex].Index); if (EquipmentItems[EquipmentIndex].Item) { EquipmentItems[EquipmentIndex].Item->MarkPendingKill(); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 1bc1010..a128dfc 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -7,15 +7,6 @@ #include "UObject/NoExportTypes.h" #include "IFItemBase.generated.h" -/* - A Struct where the actuall item is contained (so it can be easy serialized/deserialized from json. - Also allows to easily embed a replicate itemsh within items. -*/ -USTRUCT(BlueprintType) -struct FIFItemBaseData -{ - GENERATED_BODY() -}; /** * @@ -58,25 +49,58 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject */ virtual void OnItemRemoved(uint8 LocalIndex) {}; + /* + Called after item has been added to inventory. + Called on server or in standalone game. + */ + virtual void OnServerItemAdded(uint8 LocalIndex) {}; + /* + Called when item changed slots within THE SAME inventory. + Called on server or in standalone game. + */ + virtual void OnServerItemChanged(uint8 LocalIndex) {}; + /* + Called after item has been removed from inventory. + Called on server or in standalone game. + */ + virtual void OnServerItemRemoved(uint8 LocalIndex) {}; + + + + /* + Called after item has been added to Equipment. + */ + virtual void OnItemAddedEquipment(uint8 LocalIndex) {}; + /* + Called when item changed slots within THE SAME Equipment; + */ + virtual void OnItemChangedEquipment(uint8 LocalIndex) {}; + /* + Called after item has been removed from Equipment; + */ + virtual void OnItemRemovedEquipment(uint8 LocalIndex) {}; + + /* + Called after item has been added to Equipment. + Called on server or in standalone game. + */ + virtual void OnServerItemAddedEquipment(uint8 LocalIndex) {}; + /* + Called when item changed slots within THE SAME Equipment; + Called on server or in standalone game. + */ + virtual void OnServerItemChangedEquipment(uint8 LocalIndex) {}; + /* + Called after item has been removed from Equipment; + Called on server or in standalone game. + */ + virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) {}; + + virtual void PreItemLoad() {}; virtual void PostItemLoad() {}; static UIFItemBase* LoadFromJSON() { return nullptr; } - template - static ItemType* CreateItemFromData(DataType InData, class UIFInventoryComponent* Owner) - { - ItemType* Item = NewObject(Owner, ItemType::StaticClass()); - Item->Data = InData; - return Item; - } - - template - static ItemType* CreateItemFromData(DataType InData, TSubclassOf ItemClass, class UIFInventoryComponent* Owner) - { - ItemType* Item = NewObject(Owner, ItemClass); - Item->Data = InData; - return Item; - } }; diff --git a/Source/ActionRPGGame/Private/UI/Inventory/ARItemTooltipView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARItemTooltipView.cpp new file mode 100644 index 0000000..aad45d9 --- /dev/null +++ b/Source/ActionRPGGame/Private/UI/Inventory/ARItemTooltipView.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemTooltipView.h" + + + + diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index 58b57a9..bee230d 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -58,6 +58,10 @@ FReply UARItemWeaponWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry, return FReply::Handled(); +} +void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + } void UARItemWeaponWidget::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) { @@ -79,6 +83,7 @@ void UARItemWeaponWidget::OnWeaponAdded2(uint8 InNetIndex, uint8 InLocalIndex, c if (InLocalIndex == Index) { OnSlotCreated(InNetIndex, InLocalIndex, InItem); + WeaponItem = Cast(InItem); } } void UARItemWeaponWidget::OnWeaponUpdated2(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* InItem) @@ -94,4 +99,5 @@ void UARItemWeaponWidget::OnWeaponRemoved2(uint8 InNetIndex, uint8 InLocalIndex, { OnItemRemoved(InNetIndex, InLocalIndex, InItem); } + WeaponItem.Reset(); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index 6ba337f..376b873 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -6,18 +6,38 @@ #include "ARCharacter.h" #include "ARPlayerController.h" +#include "Attributes/ARGunAttributes.h" #include "UI/ARHUD.h" #include "UI/Inventory/ARUIInventoryComponent.h" #include "UI/Inventory/ARInventoryScreenWidget.h" #include "UI/Inventory/Weapons/Modifications/ARItemMagazineView.h" +#include "Weapons/ARWeaponAbilityBase.h" #include "Weapons/ARMagazineUpgradeItem.h" #include "Weapons/ARWeaponInventoryComponent.h" #include "Weapons/ARMagazineUpgradeEffect.h" +void UARItemWeapon::SetAbility(class UARWeaponAbilityBase* InAbility) +{ + AbilityInstance = InAbility; + AbilityInstance->SetWeaponItem(this); + if (Attributes) + { + if (AbilityInstance) + { + AbilityInstance->GetAttributes()->CopyFromOtherAttributes(Attributes); + } + } +} void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade) { + if (!AbilityInstance) + { + return; //add log. + } + UARWeaponInventoryComponent* WeaponComponent = Cast(GetOuter()); + //might also check for PC inventory. if (!WeaponComponent) return; @@ -31,51 +51,18 @@ void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineU //this part only on server. if (Character->Role >= ENetRole::ROLE_Authority) { - TSubclassOf SpecClass = InMagazineUpgrade->UpgradeEffect.LoadSynchronous(); MagazineUpgradeValue = InMagazineUpgrade->MagazineUpgradeValue; - MagazineUpgradeProperty = SpecClass; - - AddUpgrade(MagazineUpgradeProperty, MagazineEffectHandle, MagazineSpecHandle, Character, MagazineUpgradeValue); + AbilityInstance->AddMagazineUpgrade(InMagazineUpgrade->UpgradeEffect, MagazineUpgradeValue); } OnMagazineUpdateAdded(); } void UARItemWeapon::OnMagazineUpdateAdded() { - //should be called only from server. - FARWeaponModInfo Info; - Info.Icon = MagazineModification->Icon->GetPathName(); - Info.UpgradeType = EARWeaponUpgradeType::Magazine; -} - -void UARItemWeapon::AddUpgrade(FAFPropertytHandle& PropertyHandle - , FGAEffectHandle& EffectHandle - , FAFEffectSpecHandle& SpecHandle - , class AARCharacter* Character - , float UpgradeValue) -{ - //causer MagazineUpgrade ? - UGABlueprintLibrary::CreateEffectSpec(SpecHandle, PropertyHandle, this, Character, Character); - - EffectHandle = FGAEffectHandle::GenerateHandle(); - SpecHandle.CalculateAttributeModifier(EffectHandle); - SpecHandle.OverrideAttributeModifier(UpgradeValue); - - FGAEffect Effect(SpecHandle.GetPtr(), EffectHandle); - - UpgradeContainer.ApplyEffect(EffectHandle, Effect); - - FGAEffectMod Mod = SpecHandle.GetModifier(); - AbilityInstance->ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef()); } UARMagazineUpgradeItem* UARItemWeapon::RemoveMagazineUpgrade() { - FGAEffectMod Mod = MagazineSpecHandle.GetModifier(); - AbilityInstance->RemoveBonus(Mod.Attribute, MagazineEffectHandle, Mod.AttributeMod); - UpgradeContainer.RemoveEffect(MagazineEffectHandle); - - MagazineUpgradeProperty.Reset(); - MagazineSpecHandle.Reset(); + AbilityInstance->RemoveMagazineUpgrade(); return MagazineModification; } @@ -90,7 +77,69 @@ void UARItemWeapon::OnItemRemoved(uint8 LocalIndex) } + +void UARItemWeapon::OnItemAddedEquipment(uint8 LocalIndex) +{ + +}; +void UARItemWeapon::OnItemChangedEquipment(uint8 LocalIndex) +{ +}; +void UARItemWeapon::OnItemRemovedEquipment(uint8 LocalIndex) +{ +}; + +void UARItemWeapon::OnServerItemAddedEquipment(uint8 LocalIndex) +{ +}; +void UARItemWeapon::OnServerItemChangedEquipment(uint8 LocalIndex) +{ +}; +void UARItemWeapon::OnServerItemRemovedEquipment(uint8 LocalIndex) +{ +}; + void UARItemWeapon::PostItemLoad() { +} + +TArray UARItemWeapon::GetTooltipData() +{ + TArray Data; + + UARGunAttributes* ABAttr = AbilityInstance->GetAttributesTyped(); + + FARItemTooltipData ItemName("ItemName", AbilityInstance->GetName()); + Data.Add(ItemName); + + if (ABAttr) + { + FARItemTooltipData BaseDamage("BaseDamage", FString::FormatAsNumber(ABAttr->BaseDamage.GetCurrentValue())); + Data.Add(BaseDamage); + + FARItemTooltipData CritChance("CritChance", FString::FormatAsNumber(ABAttr->CritChance.GetCurrentValue())); + Data.Add(CritChance); + + FARItemTooltipData Magazine("Magazine", FString::FormatAsNumber(ABAttr->Magazine.GetCurrentValue())); + Data.Add(Magazine); + + FARItemTooltipData RateOfFire("RateOfFire", FString::FormatAsNumber(ABAttr->RateOfFire.GetCurrentValue())); + Data.Add(RateOfFire); + + FARItemTooltipData ReloadSpeed("ReloadSpeed", FString::FormatAsNumber(ABAttr->ReloadSpeed.GetCurrentValue())); + Data.Add(ReloadSpeed); + + FARItemTooltipData HorizontalStability("HorizontalStability", FString::FormatAsNumber(ABAttr->HorizontalStability.GetCurrentValue())); + Data.Add(HorizontalStability); + + FARItemTooltipData VerticalStability("VerticalStability", FString::FormatAsNumber(ABAttr->VerticalStability.GetCurrentValue())); + Data.Add(VerticalStability); + + FARItemTooltipData Spread("Spread", FString::FormatAsNumber(ABAttr->Spread.GetCurrentValue())); + Data.Add(Spread); + + } + + return Data; } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp index a4bf8ef..0d5dc52 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp @@ -2,9 +2,23 @@ #include "ARWeaponAbilityBase.h" #include "Effects/GABlueprintLibrary.h" +#include "Weapons/ARItemWeapon.h" #include "ARCharacter.h" #include "ARWeaponBase.h" +void UARWeaponAbilityBase::SetAttributes(UGAAttributesBase* InAttributes) +{ + Attributes = InAttributes; +} +class UGAAttributesBase* UARWeaponAbilityBase::GetAttributes() const +{ + return Attributes; +} +class UGAAttributesBase* UARWeaponAbilityBase::GetAttributes() +{ + return Attributes; +} + void UARWeaponAbilityBase::OnAbilityInited() { ResetDamageEffects(); @@ -59,4 +73,44 @@ void UARWeaponAbilityBase::ApplyDamageEffect(UObject* Target, FAFFunctionModifie void UARWeaponAbilityBase::ReloadWeapon() { +} + +void UARWeaponAbilityBase::AddMagazineUpgrade(TSubclassOf InMagazineUpgrade, float UpgradeValue) +{ + MagazineUpgradeProperty = InMagazineUpgrade; + if (AARCharacter* Character = Cast(POwner)) + { + AddUpgrade(MagazineUpgradeProperty, MagazineEffectHandle, MagazineSpecHandle, Character, UpgradeValue); + } +} + +void UARWeaponAbilityBase::RemoveMagazineUpgrade() +{ + FGAEffectMod Mod = MagazineSpecHandle.GetModifier(); + RemoveBonus(Mod.Attribute, MagazineEffectHandle, Mod.AttributeMod); + UpgradeContainer.RemoveEffect(MagazineEffectHandle); + + MagazineUpgradeProperty.Reset(); + MagazineSpecHandle.Reset(); +} + +void UARWeaponAbilityBase::AddUpgrade(FAFPropertytHandle& PropertyHandle + , FGAEffectHandle& EffectHandle + , FAFEffectSpecHandle& SpecHandle + , class AARCharacter* Character + , float UpgradeValue) +{ + UGABlueprintLibrary::CreateEffectSpec(SpecHandle, PropertyHandle, this, Character, Character); + + EffectHandle = FGAEffectHandle::GenerateHandle(); + SpecHandle.CalculateAttributeModifier(EffectHandle); + SpecHandle.OverrideAttributeModifier(UpgradeValue); + + FGAEffect Effect(SpecHandle.GetPtr(), EffectHandle); + + UpgradeContainer.ApplyEffect(EffectHandle, Effect); + + FGAEffectMod Mod = SpecHandle.GetModifier(); + ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef()); + } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp index d578611..a5f566c 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp @@ -3,6 +3,7 @@ #include "ARWeaponInventoryComponent.h" #include "Engine/AssetManager.h" #include "ARItemWeapon.h" +#include "Weapons/ARWeaponAbilityBase.h" #include "ARCharacter.h" #include "ARPlayerController.h" #include "AFAbilityComponent.h" @@ -138,7 +139,7 @@ void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAA if (!ItemWeapon) return; - ItemWeapon->AbilityInstance = Cast(InAbility); + ItemWeapon->SetAbility(Cast(InAbility)); } void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) { @@ -736,9 +737,6 @@ void UARWeaponInventoryComponent::ClientAddMagazineMod_Implementation(int8 Weapo if (Weapon) { Weapon->AddMagazineUpgrade(Magazine); - FARWeaponModInfo Info; - Info.Icon = Magazine->Icon->GetPathName(); - Info.UpgradeType = EARWeaponUpgradeType::Magazine; MainInventory->RemoveItem(MagazineModIndex); OnUpgradeInstalled.Broadcast(Weapon, Magazine, WeaponIdx); diff --git a/Source/ActionRPGGame/Public/ARItemBase.h b/Source/ActionRPGGame/Public/ARItemBase.h index 6b2256f..a7b490b 100644 --- a/Source/ActionRPGGame/Public/ARItemBase.h +++ b/Source/ActionRPGGame/Public/ARItemBase.h @@ -7,14 +7,41 @@ #include "Effects/GAGameEffect.h" #include "ARItemBase.generated.h" -USTRUCT() -struct FARItemBaseData : public FIFItemBaseData + +USTRUCT(BlueprintType) +struct FARPlayerAttributeMod { GENERATED_BODY() public: - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") - TSoftObjectPtr Icon; + UPROPERTY(EditAnywhere, Category = "Mod") + FGAAttribute Attribute; + + UPROPERTY(EditAnywhere, Category = "Mod") + float Value; + + UPROPERTY(EditAnywhere, Category = "Mod") + EGAAttributeMod ModType; +}; + +USTRUCT(BlueprintType) +struct FARItemTooltipData +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly) + FString Key; + UPROPERTY(BlueprintReadOnly) + FString Value; + + FARItemTooltipData() + {}; + + FARItemTooltipData(const FString& InKey, const FString InValue) + : Key(InKey) + , Value(InValue) + {}; }; + /** * */ @@ -23,7 +50,25 @@ class ACTIONRPGGAME_API UARItemBase : public UIFItemBase { GENERATED_BODY() public: - //obviously we want TSoftObjectPtr<> + + /* + Perks (Effects with extensions), to apply to owner of this item. + */ + UPROPERTY(EditAnywhere, Category = "Apply To Player") + TArray> EffectsToApply; + + /* + Attribute modifying effects which will be applied to player. + */ + UPROPERTY(EditAnywhere, Category = "Apply To Player") + TArray AttributesModifiers; + /* + An Template from which attribute effects will be created. + Values from AttributesModifiers property will be used. + */ + UPROPERTY(EditAnywhere, Category = "Apply To Player") + TSubclassOf AttributeEffectClass; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Visual") UTexture2D* Icon; /* diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h b/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h new file mode 100644 index 0000000..e26d30d --- /dev/null +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/Inventory/ARItemView.h" +#include "ARItemTooltipView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARItemTooltipView : public UARItemView +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h index 5729429..1622e59 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h @@ -19,10 +19,13 @@ class ACTIONRPGGAME_API UARItemWeaponWidget : public UARItemView int8 Index; + TWeakObjectPtr WeaponItem; + public: virtual void NativeConstruct() override; public: virtual FReply NativeOnMouseButtonDown(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent); + virtual void NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent); virtual void NativeOnMouseLeave(const FPointerEvent& InMouseEvent) override; virtual FReply NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index 749d6e8..4fb6445 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -16,47 +16,6 @@ enum class EARWeaponUpgradeType : uint8 Magazine }; -USTRUCT() -struct FARWeaponModInfo -{ - GENERATED_BODY(); -public: - UPROPERTY() - EARWeaponUpgradeType UpgradeType; - UPROPERTY() - TSoftObjectPtr Icon; -}; - - -USTRUCT() -struct FARItemWeaponData : public FARItemBaseData -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, Category = "Ability") - TSoftClassPtr Ability; - - UPROPERTY(EditAnywhere, Category = "Visual") - TSoftClassPtr Weapon; - - /* - Values from these attributes will be copied to ability, after ability is instanced. - It's here to allow random generation and easily store that information in Database instead of storing ability. - */ - UPROPERTY(EditAnywhere, Instanced, Category = "Attributes") - class UARGunAttributes* Attributes; - - UPROPERTY(EditAnywhere, Category = "Transforms") - FVector HolsteredPosition; - UPROPERTY(EditAnywhere, Category = "Transforms") - FRotator HolsteredRotation; - - UPROPERTY(EditAnywhere, Category = "Transforms") - FVector EquipedPosition; - UPROPERTY(EditAnywhere, Category = "Transforms") - FRotator EquipedRotation; -}; - /** * */ @@ -65,15 +24,13 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase { GENERATED_BODY() public: - UPROPERTY(EditAnywhere) - FARItemWeaponData Data; - UPROPERTY(EditAnywhere, Category = "Ability") TSoftClassPtr Ability; UPROPERTY(EditAnywhere, Category = "Visual") TSoftClassPtr Weapon; + /* Values from these attributes will be copied to ability, after ability is instanced. It's here to allow random generation and easily store that information in Database instead of storing ability. @@ -97,52 +54,29 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(BlueprintReadOnly, Category = "Ability") class UARMagazineUpgradeItem* MagazineModification; - UPROPERTY(Transient) - FAFPropertytHandle MagazineUpgradeProperty; - UPROPERTY(Transient) - FGAEffectHandle MagazineEffectHandle; - UPROPERTY(Transient) - FAFEffectSpecHandle MagazineSpecHandle; - - UPROPERTY(Transient) - FAFPropertytHandle BarrelUpgradeProperty; - UPROPERTY(Transient) - FGAEffectHandle BarrelEffectHandle; - UPROPERTY(Transient) - FAFEffectSpecHandle BarrelSpecHandle; - - UPROPERTY(Transient) - FAFPropertytHandle ScopeUpgradeProperty; - UPROPERTY(Transient) - FGAEffectHandle ScopeEffectHandle; - UPROPERTY(Transient) - FAFEffectSpecHandle ScopeSpecHandle; - UPROPERTY(Transient) float MagazineUpgradeValue; - /* - So it will actually actor as mini inventory with predefined slots. - That way we should be able to generate mods on the fly and store them as json in external database. - */ - - UPROPERTY() //replicated - FARMagazineUpgradeItemData MagazineUpgrade; + void SetAbility(class UARWeaponAbilityBase* InAbility); void AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade); void OnMagazineUpdateAdded(); - void AddUpgrade(FAFPropertytHandle& PropertyHandle - , FGAEffectHandle& EffectHandle - , FAFEffectSpecHandle& SpecHandle - , class AARCharacter* Character - , float UpgradeValue); - - UARMagazineUpgradeItem* RemoveMagazineUpgrade(); virtual void OnItemAdded(uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; + virtual void OnItemAddedEquipment(uint8 LocalIndex); + virtual void OnItemChangedEquipment(uint8 LocalIndex); + virtual void OnItemRemovedEquipment(uint8 LocalIndex); + + virtual void OnServerItemAddedEquipment(uint8 LocalIndex); + virtual void OnServerItemChangedEquipment(uint8 LocalIndex); + virtual void OnServerItemRemovedEquipment(uint8 LocalIndex); + virtual void PostItemLoad(); + + virtual TArray GetTooltipData(); +protected: }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h index 09361e5..6bd15da 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h @@ -7,17 +7,6 @@ #include "ARMagazineUpgradeItem.generated.h" -USTRUCT() -struct FARMagazineUpgradeItemData : public FARItemBaseData -{ - GENERATED_BODY() - /* - replace with instance, to make procedural generation easier. - */ - UPROPERTY(EditAnywhere) - TSoftClassPtr UpgradeEffect; -}; - /** * */ @@ -26,8 +15,6 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem { GENERATED_BODY() public: - UPROPERTY(EditAnywhere) - FARMagazineUpgradeItemData Data; /* An actual modifier value of this upgrade. */ @@ -37,5 +24,5 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem Effect template */ UPROPERTY(EditAnywhere) - TSoftClassPtr UpgradeEffect; + TSubclassOf UpgradeEffect; }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h index fde9fc9..c069fe3 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h @@ -47,7 +47,49 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon") class AARWeaponBase* WeaponActor; + /* + Weapon item to which this abiliy belongs. + */ + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon") + class UARItemWeapon* WeaponItem; + + + /* + Upgrades for this ability. + */ + UPROPERTY(Transient) + FAFEffectContainerSimple UpgradeContainer; + + UPROPERTY(Transient) + FAFPropertytHandle MagazineUpgradeProperty; + UPROPERTY(Transient) + FGAEffectHandle MagazineEffectHandle; + UPROPERTY(Transient) + FAFEffectSpecHandle MagazineSpecHandle; + + UPROPERTY(Transient) + FAFPropertytHandle BarrelUpgradeProperty; + UPROPERTY(Transient) + FGAEffectHandle BarrelEffectHandle; + UPROPERTY(Transient) + FAFEffectSpecHandle BarrelSpecHandle; + + UPROPERTY(Transient) + FAFPropertytHandle ScopeUpgradeProperty; + UPROPERTY(Transient) + FGAEffectHandle ScopeEffectHandle; + UPROPERTY(Transient) + FAFEffectSpecHandle ScopeSpecHandle; + public: + inline void SetWeaponItem(class UARItemWeapon* InItem) + { + WeaponItem = InItem; + }; + + virtual void SetAttributes(UGAAttributesBase* InAttributes) override; + virtual class UGAAttributesBase* GetAttributes() const override; + virtual class UGAAttributesBase* GetAttributes() override; virtual void OnAbilityInited() override; virtual void OnAbilityInputReady() override; virtual void OnAvatarReady() override; @@ -74,4 +116,13 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapon") void ReloadWeapon(); + + void AddMagazineUpgrade(TSubclassOf InMagazineUpgrade, float UpgradeValue); + void RemoveMagazineUpgrade(); +protected: + void AddUpgrade(FAFPropertytHandle& PropertyHandle + , FGAEffectHandle& EffectHandle + , FAFEffectSpecHandle& SpecHandle + , class AARCharacter* Character + , float UpgradeValue); }; From bbb5f0b69704b640eab67031b8e191675477a312 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 5 May 2018 02:46:50 +0200 Subject: [PATCH 164/187] added some rudimentary tooltip support and fixed attribute copy --- .../Private/Attributes/GAAttributeBase.cpp | 4 ++++ .../Inventory/Weapons/ARItemWeaponWidget.cpp | 20 +++++++++++++++++++ .../Private/Weapons/ARItemWeapon.cpp | 16 +++++++-------- .../Public/UI/Inventory/ARItemTooltipView.h | 6 ++++-- .../UI/Inventory/ARUIInventoryComponent.h | 5 ++++- .../UI/Inventory/Weapons/ARItemWeaponWidget.h | 3 ++- 6 files changed, 42 insertions(+), 12 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp index 8b73722..86555d3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -54,6 +54,10 @@ void FAFAttributeBase::CopyFromOther(FAFAttributeBase* Other) MaxValue = Other->MaxValue; CurrentValue = Other->CurrentValue; BonusValue = Other->BonusValue; + + CurrentValue = BaseValue; + CalculateBonus(); + CurrentValue = GetFinalValue(); } void FAFAttributeBase::CalculateBonus() { diff --git a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp index bee230d..4b9e78d 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/Weapons/ARItemWeaponWidget.cpp @@ -13,6 +13,7 @@ #include "UI/ARHUD.h" #include "UI/Inventory/ARUIInventoryComponent.h" #include "UI/Inventory/ARInventoryScreenWidget.h" +#include "UI/Inventory/ARItemTooltipView.h" #include "UI/Inventory/Weapons/ARWeaponContainerWidget.h" #include "UI/Inventory/Weapons/ARListItemWeaponWidget.h" @@ -61,11 +62,30 @@ FReply UARItemWeaponWidget::NativeOnMouseButtonDown(const FGeometry& InGeometry, } void UARItemWeaponWidget::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { + if (!WeaponItem.IsValid()) + return; + if(!WeaponTooltip) + WeaponTooltip = CreateWidget(GetOwningPlayer(), InventoryComponent->WeaponItemTooltipViewClass); + + WeaponTooltip->OnTooltipCreated(WeaponItem->GetTooltipData()); + + SetToolTip(WeaponTooltip); + + /*FMargin margin = GetFullScreenOffset(); + FVector2D Pos(margin.Left, margin.Top); + WeaponTooltip->AddToViewport(9999); + + WeaponTooltip->SetVisibility(ESlateVisibility::HitTestInvisible); + WeaponTooltip->SetPositionInViewport(Pos);*/ } void UARItemWeaponWidget::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) { + if (!WeaponTooltip) + return; + SetToolTip(nullptr); + //WeaponTooltip->SetVisibility(ESlateVisibility::Collapsed); } FReply UARItemWeaponWidget::NativeOnMouseButtonDoubleClick(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) { diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index 376b873..a85abe7 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -115,28 +115,28 @@ TArray UARItemWeapon::GetTooltipData() if (ABAttr) { - FARItemTooltipData BaseDamage("BaseDamage", FString::FormatAsNumber(ABAttr->BaseDamage.GetCurrentValue())); + FARItemTooltipData BaseDamage("BaseDamage", FString::SanitizeFloat(ABAttr->BaseDamage.GetCurrentValue())); Data.Add(BaseDamage); - FARItemTooltipData CritChance("CritChance", FString::FormatAsNumber(ABAttr->CritChance.GetCurrentValue())); + FARItemTooltipData CritChance("CritChance", FString::SanitizeFloat(ABAttr->CritChance.GetCurrentValue())); Data.Add(CritChance); - FARItemTooltipData Magazine("Magazine", FString::FormatAsNumber(ABAttr->Magazine.GetCurrentValue())); + FARItemTooltipData Magazine("Magazine", FString::SanitizeFloat(ABAttr->Magazine.GetCurrentValue())); Data.Add(Magazine); - FARItemTooltipData RateOfFire("RateOfFire", FString::FormatAsNumber(ABAttr->RateOfFire.GetCurrentValue())); + FARItemTooltipData RateOfFire("RateOfFire", FString::SanitizeFloat(ABAttr->RateOfFire.GetCurrentValue())); Data.Add(RateOfFire); - FARItemTooltipData ReloadSpeed("ReloadSpeed", FString::FormatAsNumber(ABAttr->ReloadSpeed.GetCurrentValue())); + FARItemTooltipData ReloadSpeed("ReloadSpeed", FString::SanitizeFloat(ABAttr->ReloadSpeed.GetCurrentValue())); Data.Add(ReloadSpeed); - FARItemTooltipData HorizontalStability("HorizontalStability", FString::FormatAsNumber(ABAttr->HorizontalStability.GetCurrentValue())); + FARItemTooltipData HorizontalStability("HorizontalStability", FString::SanitizeFloat(ABAttr->HorizontalStability.GetCurrentValue())); Data.Add(HorizontalStability); - FARItemTooltipData VerticalStability("VerticalStability", FString::FormatAsNumber(ABAttr->VerticalStability.GetCurrentValue())); + FARItemTooltipData VerticalStability("VerticalStability", FString::SanitizeFloat(ABAttr->VerticalStability.GetCurrentValue())); Data.Add(VerticalStability); - FARItemTooltipData Spread("Spread", FString::FormatAsNumber(ABAttr->Spread.GetCurrentValue())); + FARItemTooltipData Spread("Spread", FString::SanitizeFloat(ABAttr->Spread.GetCurrentValue())); Data.Add(Spread); } diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h b/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h index e26d30d..68c941e 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARItemTooltipView.h @@ -3,6 +3,7 @@ #pragma once #include "CoreMinimal.h" +#include "ARItemBase.h" #include "UI/Inventory/ARItemView.h" #include "ARItemTooltipView.generated.h" @@ -13,8 +14,9 @@ UCLASS() class ACTIONRPGGAME_API UARItemTooltipView : public UARItemView { GENERATED_BODY() - - +public: + UFUNCTION(BlueprintImplementableEvent, Category = "ActionRPGGame|UI") + void OnTooltipCreated(const TArray& OutItems); }; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h index f65a08e..34d050c 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARUIInventoryComponent.h @@ -22,7 +22,10 @@ class ACTIONRPGGAME_API UARUIInventoryComponent : public UActorComponent UPROPERTY(EditAnywhere, Category = "Views") TSubclassOf WeaponModificationViewClass; - +public: + UPROPERTY(EditAnywhere, Category = "Views") + TSubclassOf WeaponItemTooltipViewClass; +protected: UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|UI|Inventory") class UARInventoryScreenWidget* InventoryView; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h index 1622e59..0ed1394 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/Weapons/ARItemWeaponWidget.h @@ -20,7 +20,8 @@ class ACTIONRPGGAME_API UARItemWeaponWidget : public UARItemView int8 Index; TWeakObjectPtr WeaponItem; - + UPROPERTY(Transient) + UARItemTooltipView* WeaponTooltip; public: virtual void NativeConstruct() override; public: From 43ff093469f2783449bd0679bfaf8c671bff004c Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sat, 5 May 2018 10:24:21 +0200 Subject: [PATCH 165/187] tooltips for items in invetory lists --- .../Public/IFItemWidget.h | 6 +-- .../Private/UI/Inventory/ARListItemView.cpp | 37 +++++++++++++++++++ .../Private/Weapons/ARItemWeapon.cpp | 9 +++-- Source/ActionRPGGame/Public/ARItemBase.h | 6 +++ .../Public/UI/Inventory/ARListItemView.h | 15 +++++++- .../Public/Weapons/ARItemWeapon.h | 2 +- 6 files changed, 67 insertions(+), 8 deletions(-) diff --git a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h index 3844791..f08bb1b 100644 --- a/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h +++ b/Plugins/InventoryFrameworkUI/Source/InventoryFrameworkUI/Public/IFItemWidget.h @@ -28,11 +28,11 @@ class INVENTORYFRAMEWORKUI_API UIFItemWidget : public UUserWidget UPROPERTY(BlueprintReadWrite, Category = "InventoryFramework") UWidget* DragVisual; public: - void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); + virtual void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); - void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); + virtual void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); - void OnItemRemoved(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); + virtual void OnItemRemoved(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "On Item Created")) void BP_OnItemCreated(class UIFItemBase* Item); diff --git a/Source/ActionRPGGame/Private/UI/Inventory/ARListItemView.cpp b/Source/ActionRPGGame/Private/UI/Inventory/ARListItemView.cpp index e6d8936..a159861 100644 --- a/Source/ActionRPGGame/Private/UI/Inventory/ARListItemView.cpp +++ b/Source/ActionRPGGame/Private/UI/Inventory/ARListItemView.cpp @@ -2,7 +2,9 @@ #include "ARListItemView.h" +#include "ARItemBase.h" #include "UI/ARHUD.h" +#include "UI/Inventory/ARUIInventoryComponent.h" #include "ARPlayerController.h" @@ -17,4 +19,39 @@ void UARListItemView::NativeConstruct() InventoryComponent = HUD->GetUIInventory(); } } +} + +void UARListItemView::OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) +{ + Super::OnSlotCreated(InNetIndex, InLocalIndex, Item); + InvItem = Cast(Item); +} +void UARListItemView::OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) +{ + Super::OnItemChanged(InNetIndex, InLocalIndex, Item); +} +void UARListItemView::OnItemRemoved(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) +{ + Super::OnItemRemoved(InNetIndex, InLocalIndex, Item); + InvItem.Reset(); +} + +void UARListItemView::NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) +{ + if (!InvItem.IsValid()) + return; + + if (!ItemTooltip) + ItemTooltip = CreateWidget(GetOwningPlayer(), InventoryComponent->WeaponItemTooltipViewClass); + + ItemTooltip->OnTooltipCreated(InvItem->GetTooltipData()); + + SetToolTip(ItemTooltip); +} +void UARListItemView::NativeOnMouseLeave(const FPointerEvent& InMouseEvent) +{ + if (!ItemTooltip) + return; + + SetToolTip(nullptr); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index a85abe7..6617467 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -108,11 +108,14 @@ TArray UARItemWeapon::GetTooltipData() { TArray Data; - UARGunAttributes* ABAttr = AbilityInstance->GetAttributesTyped(); - - FARItemTooltipData ItemName("ItemName", AbilityInstance->GetName()); + FARItemTooltipData ItemName("ItemName", GetName()); Data.Add(ItemName); + if (!AbilityInstance) + return Data; + + UARGunAttributes* ABAttr = AbilityInstance->GetAttributesTyped(); + if (ABAttr) { FARItemTooltipData BaseDamage("BaseDamage", FString::SanitizeFloat(ABAttr->BaseDamage.GetCurrentValue())); diff --git a/Source/ActionRPGGame/Public/ARItemBase.h b/Source/ActionRPGGame/Public/ARItemBase.h index a7b490b..11f6e26 100644 --- a/Source/ActionRPGGame/Public/ARItemBase.h +++ b/Source/ActionRPGGame/Public/ARItemBase.h @@ -76,4 +76,10 @@ class ACTIONRPGGAME_API UARItemBase : public UIFItemBase */ UPROPERTY(Transient) FAFEffectContainerSimple UpgradeContainer; + + virtual TArray GetTooltipData() + { + TArray Data; + return Data; + } }; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.h b/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.h index d283610..68964df 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARListItemView.h @@ -17,10 +17,23 @@ class ACTIONRPGGAME_API UARListItemView : public UIFItemWidget protected: TWeakObjectPtr Target; TWeakObjectPtr InventoryComponent; + + TWeakObjectPtr InvItem; + + UPROPERTY(Transient) + class UARItemTooltipView* ItemTooltip; public: virtual void NativeConstruct() override; inline void SetTarget(TWeakObjectPtr ForSlot) { Target = ForSlot; } inline TWeakObjectPtr GetTarget() { return Target; } - + + virtual void OnSlotCreated(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) override; + + virtual void OnItemChanged(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) override; + + virtual void OnItemRemoved(uint8 InNetIndex, uint8 InLocalIndex, class UIFItemBase* Item) override; + + virtual void NativeOnMouseEnter(const FGeometry& InGeometry, const FPointerEvent& InMouseEvent) override; + virtual void NativeOnMouseLeave(const FPointerEvent& InMouseEvent) override; }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index 4fb6445..3c3dd76 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -77,6 +77,6 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase virtual void PostItemLoad(); - virtual TArray GetTooltipData(); + virtual TArray GetTooltipData() override; protected: }; From 8d12bf7e265bee5d6fdce754683ef4c09971ed65 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 6 May 2018 00:17:42 +0200 Subject: [PATCH 166/187] prototype item serialization to Json --- ActionRPGGame.uproject | 4 + Config/DefaultEngine.ini | 84 ++--- .../Private/AFAbilityComponent.cpp | 4 + .../Private/AFAbilityTypes.cpp | 34 ++ .../Public/AFAbilityComponent.h | 6 + .../AbilityFramework/Public/AFAbilityTypes.h | 4 + .../Public/Abilities/GAAbilityBase.h | 20 +- .../Public/Attributes/GAAttributeBase.h | 10 +- .../Private/IFEquipmentComponent.cpp | 2 + .../Private/IFInventoryComponent.cpp | 69 +++- .../InventoryFramework/Private/IFTypes.cpp | 345 ++++++++++++++++++ .../Private/InventoryFramework.cpp | 2 + .../Public/IFEquipmentComponent.h | 2 +- .../Public/IFInventoryComponent.h | 5 +- .../InventoryFramework/Public/IFItemBase.h | 2 +- .../InventoryFramework/Public/IFTypes.h | 18 +- .../Private/Weapons/ARItemWeapon.cpp | 47 ++- .../Weapons/ARWeaponInventoryComponent.cpp | 24 +- .../Public/Attributes/ARGunAttributes.h | 16 +- .../Public/Weapons/ARItemWeapon.h | 28 +- .../Public/Weapons/ARMagazineUpgradeItem.h | 2 +- .../Public/Weapons/ARWeaponAbilityBase.h | 2 +- .../Weapons/ARWeaponInventoryComponent.h | 2 +- 23 files changed, 626 insertions(+), 106 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 8d791e5..e4b58e1 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -208,6 +208,10 @@ { "Name": "LiveLink", "Enabled": true + }, + { + "Name": "ReplicationGraph", + "Enabled": true } ], "TargetPlatforms": [ diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 340c57d..b2f8a4a 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -78,48 +78,6 @@ gc.BlueprintClusteringEnabled=True [/Script/NoesisRuntime.NoesisSettings] GlyphTextureSize=x4096 -[/Script/Engine.PhysicsSettings] -DefaultGravityZ=-980.000000 -DefaultTerminalVelocity=4000.000000 -DefaultFluidFriction=0.300000 -SimulateScratchMemorySize=262144 -RagdollAggregateThreshold=4 -TriangleMeshTriangleMinAreaThreshold=5.000000 -bEnableAsyncScene=True -bEnableShapeSharing=True -bEnablePCM=True -bEnableStabilization=True -bWarnMissingLocks=True -bEnable2DPhysics=False -PhysicErrorCorrection=(LinearDeltaThresholdSq=5.000000,LinearInterpAlpha=0.200000,LinearRecipFixTime=1.000000,AngularDeltaThreshold=0.628319,AngularInterpAlpha=0.100000,AngularRecipFixTime=1.000000,BodySpeedThresholdSq=0.200000) -LockedAxis=Invalid -DefaultDegreesOfFreedom=Full3D -BounceThresholdVelocity=200.000000 -FrictionCombineMode=Average -RestitutionCombineMode=Average -MaxAngularVelocity=3600.000000 -MaxDepenetrationVelocity=0.000000 -ContactOffsetMultiplier=0.020000 -MinContactOffset=2.000000 -MaxContactOffset=8.000000 -bSimulateSkeletalMeshOnDedicatedServer=True -DefaultShapeComplexity=CTF_UseSimpleAndComplex -bDefaultHasComplexCollision=True -bSuppressFaceRemapTable=False -bSupportUVFromHitResults=False -bDisableActiveActors=False -bDisableCCD=False -bEnableEnhancedDeterminism=True -MaxPhysicsDeltaTime=0.033333 -bSubstepping=True -bSubsteppingAsync=True -MaxSubstepDeltaTime=0.033000 -MaxSubsteps=2 -SyncSceneSmoothingFactor=0.000000 -AsyncSceneSmoothingFactor=0.990000 -InitialAverageFrameRate=0.016667 -PhysXTreeRebuildRate=10 - [/Script/Engine.CollisionProfile] -Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) -Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) @@ -180,4 +138,46 @@ PhysXTreeRebuildRate=10 +CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") +[/Script/Engine.PhysicsSettings] +DefaultGravityZ=-980.000000 +DefaultTerminalVelocity=4000.000000 +DefaultFluidFriction=0.300000 +SimulateScratchMemorySize=262144 +RagdollAggregateThreshold=4 +TriangleMeshTriangleMinAreaThreshold=5.000000 +bEnableAsyncScene=True +bEnableShapeSharing=True +bEnablePCM=True +bEnableStabilization=True +bWarnMissingLocks=True +bEnable2DPhysics=False +PhysicErrorCorrection=(LinearDeltaThresholdSq=5.000000,LinearInterpAlpha=0.200000,LinearRecipFixTime=1.000000,AngularDeltaThreshold=0.628319,AngularInterpAlpha=0.100000,AngularRecipFixTime=1.000000,BodySpeedThresholdSq=0.200000) +LockedAxis=Invalid +DefaultDegreesOfFreedom=Full3D +BounceThresholdVelocity=200.000000 +FrictionCombineMode=Average +RestitutionCombineMode=Average +MaxAngularVelocity=3600.000000 +MaxDepenetrationVelocity=0.000000 +ContactOffsetMultiplier=0.020000 +MinContactOffset=2.000000 +MaxContactOffset=8.000000 +bSimulateSkeletalMeshOnDedicatedServer=True +DefaultShapeComplexity=CTF_UseSimpleAndComplex +bDefaultHasComplexCollision=True +bSuppressFaceRemapTable=False +bSupportUVFromHitResults=False +bDisableActiveActors=False +bDisableCCD=False +bEnableEnhancedDeterminism=True +MaxPhysicsDeltaTime=0.033333 +bSubstepping=True +bSubsteppingAsync=True +MaxSubstepDeltaTime=0.033000 +MaxSubsteps=2 +SyncSceneSmoothingFactor=0.000000 +AsyncSceneSmoothingFactor=0.990000 +InitialAverageFrameRate=0.016667 +PhysXTreeRebuildRate=10 + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp index a6f8eba..b384135 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -479,6 +479,10 @@ void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbili } } +void UAFAbilityComponent::NativeAddAbilityFromObject(UGAAbilityBase* InAbility, TSoftClassPtr AbilityPtr) +{ + AbilityContainer.AddAbilityFromObject(InAbility, AbilityPtr); +} void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, const TArray& InInputTag) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp index 981b61a..740f0da 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp @@ -101,6 +101,40 @@ UGAAbilityBase* FAFAbilityContainer::AddAbility(TSubclassOf InClassPtr) +{ + if (AbilityIn && AbilitiesComp.IsValid()) + { + + UGAAbilityBase* ability = AbilityIn;// NewObject(AbilitiesComp->GetOwner(), AbilityIn); + ability->AbilityComponent = AbilitiesComp.Get(); + if (AbilitiesComp.IsValid()) + { + APawn* POwner = Cast(AbilitiesComp->GetOwner()); + ability->POwner = POwner; + ability->PCOwner = Cast(POwner->Controller); + ability->OwnerCamera = nullptr; + } + ability->InitAbility(); + FGameplayTag Tag = ability->AbilityTag; + + AbilitiesInputs.Add(InClassPtr, ability); + FAFAbilityItem AbilityItem(ability, InClassPtr); + MarkItemDirty(AbilityItem); + AbilityItem.Ability = ability; + AbilitiesItems.Add(AbilityItem); + TagToAbility.Add(InClassPtr, ability); + + MarkArrayDirty(); + if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone + || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) + { + AbilitiesComp->NotifyOnAbilityReady(InClassPtr); + } + } +} + void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& AbilityIn) { int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h index 5dcf71e..1f46e63 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -562,6 +562,12 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void NativeAddAbility(TSoftClassPtr InAbility, const TArray& InInputTag); + /* + Adds ability using existing instance of object. + Should only be called on authority or in standalone. + */ + void NativeAddAbilityFromObject(UGAAbilityBase* InAbility, TSoftClassPtr AbilityPtr); + UFUNCTION(Server, Reliable, WithValidation) void ServerNativeAddAbility(const FSoftObjectPath& InAbility, const TArray& InInputTag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h index a976afb..408caa2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h @@ -64,6 +64,8 @@ struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer //ActionInput, AbilityClassPtr TMap> ActionToAbility; + //maybe.. replace SoftClassPtr with FObjectKey ? + //AbilityTag, ActionInput TMap, TArray> AbilityToAction; @@ -76,6 +78,8 @@ struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer UGAAbilityBase* AddAbility(TSubclassOf AbilityIn , TSoftClassPtr InClassPtr); + void AddAbilityFromObject(class UGAAbilityBase* AbilityIn, TSoftClassPtr InClassPtr); + void RemoveAbility(const TSoftClassPtr& AbilityIn); void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h index f42b055..a7d3893 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h @@ -110,10 +110,10 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt bool bIsNameStable; //possibly map TMap ? - UPROPERTY() + UPROPERTY(Transient) TSet ActiveTasks; /* List of tasks, this ability have. */ - UPROPERTY() + UPROPERTY(Transient) TMap AbilityTasks; /* @@ -132,20 +132,20 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt UPROPERTY(EditAnywhere, BlueprintReadOnly, Instanced, Category = "AbilityFramework|Abilities") UGAAttributesBase* Attributes; - UPROPERTY() + UPROPERTY(Transient) class UWorld* World; /* Replicated to everyone because we will need it, to determine cosmetic stuff on clients. */ /* */ - UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, BlueprintReadOnly, Category = "AbilityFramework|Abilities", Transient) APawn* POwner; - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities", Transient) APlayerController* PCOwner; - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities", Transient) class AAIController* AICOwner; - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities", Transient) class UAFAbilityComponent* AbilityComponent; /* @@ -154,10 +154,10 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt It will need some common interfaces for getting data out. */ - UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Replicated, Category = "AbilityFramework|Abilities", Transient) class AActor* AvatarActor; - UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities") + UPROPERTY(BlueprintReadOnly, Category = "AbilityFramework|Abilities", Transient) UCameraComponent* OwnerCamera; FGAEffectContext DefaultContext; @@ -242,7 +242,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt FGASGenericAbilityDelegate OnNotifyOnCooldown; /* Stub, I think replicating montage directly from ability will be better, as abilities are replicated regardless. */ - UPROPERTY() + UPROPERTY(Transient) UAnimMontage* RepMontage; protected: EAFAbilityState AbilityState; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index 8695737..5d9b675 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -63,15 +63,15 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase { GENERATED_BODY() public: - UPROPERTY(EditAnywhere) + UPROPERTY(EditAnywhere, SaveGame) float BaseValue; - UPROPERTY(EditAnywhere) + UPROPERTY(EditAnywhere, SaveGame) float MinValue; - UPROPERTY(EditAnywhere) + UPROPERTY(EditAnywhere, SaveGame) float MaxValue; - UPROPERTY() + UPROPERTY(SaveGame) float CurrentValue; - UPROPERTY() + UPROPERTY(SaveGame) float BonusValue; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp index 6bc32bd..d99a042 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFEquipmentComponent.cpp @@ -45,6 +45,8 @@ void UIFEquipmentComponent::AddItemFromInventory(class UIFInventoryComponent* So { if (GetOwnerRole() < ENetRole::ROLE_Authority) { + UIFItemBase* Item = Source->GetItem(SourceIndex); + OnClientPreItemAdded(Item, EquipmentIndex); ServerAddItemFromInventory(Source, SourceIndex, EquipmentIndex); } else diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index b26bc97..bd0908b 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -5,6 +5,8 @@ #include "GameFramework/Actor.h" #include "Engine/AssetManager.h" +#include "JsonObjectConverter.h" + #include "IFItemBase.h" #include "IFItemActorBase.h" #include "IFInventoryInterface.h" @@ -12,14 +14,10 @@ #include "Net/UnrealNetwork.h" #include "Engine/ActorChannel.h" -#include "Json.h" -#include "JsonObjectConverter.h" -#include "Policies/CondensedJsonPrintPolicy.h" -#include "Serialization/JsonTypes.h" -#include "Serialization/JsonReader.h" -#include "Policies/PrettyJsonPrintPolicy.h" -#include "Serialization/JsonSerializer.h" + +DEFINE_LOG_CATEGORY(IFLog); + // Sets default values for this component's properties UIFInventoryComponent::UIFInventoryComponent() @@ -271,6 +269,10 @@ void UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Implementation(cla } InventoryItems[FreeSlot].Item = DuplicateObject(Item, this); + + InventoryItems[FreeSlot].Item->OnServerItemAdded(FreeSlot); + + OnServerItemAdded(InventoryItems[FreeSlot].Item, FreeSlot); ClientAddItemFromEquipmentAnySlot(Source, SourceIndex, FreeSlot); SendToBackend(&InventoryItems[FreeSlot]); @@ -284,6 +286,10 @@ void UIFInventoryComponent::ClientAddItemFromEquipmentAnySlot_Implementation(cla UIFItemBase* Item = Source->GetItem(SourceIndex); InventoryItems[InventoryIndex].Item = DuplicateObject(Item, this); + + InventoryItems[InventoryIndex].Item->OnItemAdded(InventoryIndex); + OnItemAdded(InventoryItems[InventoryIndex].Item, InventoryIndex); + Source->RemoveFromEquipment(SourceIndex); } @@ -313,6 +319,10 @@ void UIFInventoryComponent::AddItemAnySlot(class UIFItemBase* Source) FString OutputString; TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + + InventoryItems[FreeSlot].Item->OnServerItemAdded(FreeSlot); + OnServerItemAdded(InventoryItems[FreeSlot].Item, FreeSlot); + ClientAddAnySlot(OutputString, FreeSlot); } void UIFInventoryComponent::ClientAddAnySlot_Implementation(const FString& JsonData, uint8 InventoryIndex) @@ -334,6 +344,8 @@ void UIFInventoryComponent::ClientAddAnySlot_Implementation(const FString& JsonD InventoryItems[InventoryIndex] = Item; OnItemAddedEvent.Broadcast(InventoryIndex, InventoryIndex, Item.Item); OnItemUpdatedEvent.Broadcast(InventoryIndex, InventoryIndex, Item.Item); + InventoryItems[Item.Index].Item->OnItemAdded(Item.Index); + OnItemAdded(InventoryItems[Item.Index].Item, Item.Index); } } @@ -354,6 +366,7 @@ void UIFInventoryComponent::RemoveItem(uint8 InIndex) } void UIFInventoryComponent::ServerRemoveItem_Implementation(uint8 InIndex) { + InventoryItems[InIndex].Item->OnServerItemRemoved(InIndex); if (InventoryItems[InIndex].Item) InventoryItems[InIndex].Item->MarkPendingKill(); @@ -367,6 +380,7 @@ bool UIFInventoryComponent::ServerRemoveItem_Validate(uint8 InIndex) } void UIFInventoryComponent::ClientRemoveItem_Implementation(uint8 InIndex) { + InventoryItems[InIndex].Item->OnItemRemoved(InIndex); if (InventoryItems[InIndex].Item) InventoryItems[InIndex].Item->MarkPendingKill(); @@ -392,11 +406,13 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr(this, ItemClass); InventoryItems[Item.Index] = Item; + InventoryItems[Item.Index].Item->OnServerItemAdded(Item.Index); + OnServerItemAdded(InventoryItems[Item.Index].Item, Item.Index); typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; - TSharedPtrObj = SendToBackend(&InventoryItems[Item.Index]); + TSharedPtr Obj = SendToBackend(&InventoryItems[Item.Index]); FString OutputString; TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); @@ -405,7 +421,9 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem InventoryItems[InNetIndex].Item = ItemObj; + InventoryItems[InNetIndex].Item->OnServerItemAdded(InNetIndex); + OnServerItemAdded(InventoryItems[InNetIndex].Item, InNetIndex); + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; @@ -425,6 +446,8 @@ void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem FString OutputString; TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + + UE_LOG(IFLog, Log, TEXT("ItemLoaded %s "), *OutputString); ClientSendJsonData(OutputString); @@ -440,17 +463,27 @@ void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Dat bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); - TArray< TSharedPtr > Array; - bool bSuccessful2 = FJsonSerializer::Deserialize(Reader, Array); + TSharedPtr itemField = Object->GetObjectField("item"); + FString objClassStr = itemField->GetStringField("objectClass"); + + FSoftClassPath path(objClassStr); + + //FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + UClass* itemCls = Cast(path.TryLoad()); + UObject* OutObj = nullptr; + FIFJsonSerializer::JsonObjectToUObject(itemField, OutObj, this); FIFItemData Item; FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), FIFItemData::StaticStruct(), &Item, 0, 0); if (Item.Item) { + Item.Item->PostItemLoad(); InventoryItems[Item.Index] = Item; OnItemAddedEvent.Broadcast(Item.Index, Item.Index, Item.Item); OnItemUpdatedEvent.Broadcast(Item.Index, Item.Index, Item.Item); + InventoryItems[Item.Index].Item->OnItemAdded(Item.Index); + OnItemAdded(InventoryItems[Item.Index].Item, Item.Index); } } @@ -461,12 +494,14 @@ TSharedPtr UIFInventoryComponent::SendToBackend(FIFItemData* Item) typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; TSharedPtr Obj = MakeShareable(new FJsonObject()); - FJsonObjectConverter::UStructToJsonObject(FIFItemData::StaticStruct(), Item, Obj.ToSharedRef(), 0, 0); - - FString OutputString; - TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); - check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); - + //FJsonObjectConverter::UStructToJsonObject(FIFItemData::StaticStruct(), Item, Obj.ToSharedRef(), 0, 0); + TSharedPtr UObj = MakeShareable(new FJsonObject()); + if (Item->Item) + { + UObj = Item->Item->SaveToJson(); + } + Obj->Values.Add(FString("index"), MakeShareable(new FJsonValueNumber(Item->Index))); + Obj->Values.Add(FString("item"), MakeShareable(new FJsonValueObject(UObj))); FakeBackend[Item->Index] = Obj; return Obj; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp index 563d6c3..1a38083 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp @@ -1,7 +1,352 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "IFTypes.h" +#include "JsonObjectConverter.h" +TSharedPtr UPropertyToJsonValue(UProperty* Property, const void* Value) +{ + if (Property->ArrayDim == 1) + { + return FIFJsonSerializer::ConvertScalarUPropertyToJsonValue(Property, Value); + } + + TArray< TSharedPtr > Array; + for (int Index = 0; Index != Property->ArrayDim; ++Index) + { + Array.Add(FIFJsonSerializer::ConvertScalarUPropertyToJsonValue(Property, (char*)Value + Index * Property->ElementSize)); + } + return MakeShareable(new FJsonValueArray(Array)); +} + +TSharedPtr FIFJsonSerializer::ConvertScalarUPropertyToJsonValue(UProperty* Property, const void* Value) +{ + // See if there's a custom export callback first, so it can override default behavior + + + if (UEnumProperty* EnumProperty = Cast(Property)) + { + // export enums as strings + UEnum* EnumDef = EnumProperty->GetEnum(); + FString StringValue = EnumDef->GetNameStringByValue(EnumProperty->GetUnderlyingProperty()->GetSignedIntPropertyValue(Value)); + return MakeShareable(new FJsonValueString(StringValue)); + } + else if (UNumericProperty *NumericProperty = Cast(Property)) + { + // see if it's an enum + UEnum* EnumDef = NumericProperty->GetIntPropertyEnum(); + if (EnumDef != NULL) + { + // export enums as strings + FString StringValue = EnumDef->GetNameStringByValue(NumericProperty->GetSignedIntPropertyValue(Value)); + return MakeShareable(new FJsonValueString(StringValue)); + } + + // We want to export numbers as numbers + if (NumericProperty->IsFloatingPoint()) + { + return MakeShareable(new FJsonValueNumber(NumericProperty->GetFloatingPointPropertyValue(Value))); + } + else if (NumericProperty->IsInteger()) + { + return MakeShareable(new FJsonValueNumber(NumericProperty->GetSignedIntPropertyValue(Value))); + } + + // fall through to default + } + else if (UBoolProperty *BoolProperty = Cast(Property)) + { + // Export bools as bools + return MakeShareable(new FJsonValueBoolean(BoolProperty->GetPropertyValue(Value))); + } + else if (UStrProperty *StringProperty = Cast(Property)) + { + return MakeShareable(new FJsonValueString(StringProperty->GetPropertyValue(Value))); + } + else if (UTextProperty *TextProperty = Cast(Property)) + { + return MakeShareable(new FJsonValueString(TextProperty->GetPropertyValue(Value).ToString())); + } + else if (UArrayProperty *ArrayProperty = Cast(Property)) + { + TArray< TSharedPtr > Out; + FScriptArrayHelper Helper(ArrayProperty, Value); + for (int32 i = 0, n = Helper.Num(); i Elem = UPropertyToJsonValue(ArrayProperty->Inner, Helper.GetRawPtr(i)); + if (Elem.IsValid()) + { + // add to the array + Out.Push(Elem); + } + } + return MakeShareable(new FJsonValueArray(Out)); + } + else if (USetProperty* SetProperty = Cast(Property)) + { + TArray< TSharedPtr > Out; + FScriptSetHelper Helper(SetProperty, Value); + for (int32 i = 0, n = Helper.Num(); n; ++i) + { + if (Helper.IsValidIndex(i)) + { + TSharedPtr Elem = UPropertyToJsonValue(SetProperty->ElementProp, Helper.GetElementPtr(i)); + if (Elem.IsValid()) + { + // add to the array + Out.Push(Elem); + } + + --n; + } + } + return MakeShareable(new FJsonValueArray(Out)); + } + else if (UMapProperty* MapProperty = Cast(Property)) + { + TSharedRef Out = MakeShareable(new FJsonObject()); + + FScriptMapHelper Helper(MapProperty, Value); + for (int32 i = 0, n = Helper.Num(); n; ++i) + { + if (Helper.IsValidIndex(i)) + { + TSharedPtr KeyElement = UPropertyToJsonValue(MapProperty->KeyProp, Helper.GetKeyPtr(i)); + TSharedPtr ValueElement = UPropertyToJsonValue(MapProperty->ValueProp, Helper.GetValuePtr(i)); + if (KeyElement.IsValid() && ValueElement.IsValid()) + { + FString KeyString = KeyElement->AsString(); + if (KeyString.IsEmpty()) + { + MapProperty->KeyProp->ExportTextItem(KeyString, Helper.GetKeyPtr(i), nullptr, nullptr, 0); + if (KeyString.IsEmpty()) + { + UE_LOG(LogJson, Error, TEXT("Unable to convert key to string for property %s."), *MapProperty->GetName()) + KeyString = FString::Printf(TEXT("Unparsed Key %d"), i); + } + } + + Out->SetField(KeyString, ValueElement); + } + + --n; + } + } + + return MakeShareable(new FJsonValueObject(Out)); + } + else if (UObjectProperty* ObjectProperty = Cast(Property)) + { + TSharedRef Out = MakeShareable(new FJsonObject()); + + UObject* Object = ObjectProperty->GetObjectPropertyValue(Value); + if (Object) + { + UClass* cls = Object->GetClass(); + + if (UObjectToJsonObject(cls, Object, Out)) + { + return MakeShareable(new FJsonValueObject(Out)); + } + } + } + else if (UStructProperty *StructProperty = Cast(Property)) + { + UScriptStruct::ICppStructOps* TheCppStructOps = StructProperty->Struct->GetCppStructOps(); + // Intentionally exclude the JSON Object wrapper, which specifically needs to export JSON in an object representation instead of a string + if (StructProperty->Struct != FJsonObjectWrapper::StaticStruct() && TheCppStructOps && TheCppStructOps->HasExportTextItem()) + { + FString OutValueStr; + TheCppStructOps->ExportTextItem(OutValueStr, Value, nullptr, nullptr, PPF_None, nullptr); + return MakeShareable(new FJsonValueString(OutValueStr)); + } + + TSharedRef Out = MakeShareable(new FJsonObject()); + if (UObjectToJsonObject(StructProperty->Struct, Value, Out)) + { + return MakeShareable(new FJsonValueObject(Out)); + } + // fall through to default + } + else + { + // Default to export as string for everything else + FString StringValue; + Property->ExportTextItem(StringValue, Value, NULL, NULL, PPF_None); + return MakeShareable(new FJsonValueString(StringValue)); + } + + // invalid + return TSharedPtr(); +} + +bool FIFJsonSerializer::UStructToJsonAttributes(const UStruct* StructDefinition, const void* Struct, TMap< FString, TSharedPtr >& OutJsonAttributes) +{ + int64 SerFlag = 0; + SerFlag |= CPF_SaveGame; + + for (TFieldIterator It(StructDefinition); It; ++It) + { + UProperty* Property = *It; + + if (Property->HasAnyPropertyFlags(SerFlag)) + { + FString VariableName = Property->GetName();// StandardizeCase(); + const void* Value = Property->ContainerPtrToValuePtr(Struct); + + // convert the property to a FJsonValue + TSharedPtr JsonValue = UPropertyToJsonValue(Property, Value); + if (JsonValue.IsValid()) + { + OutJsonAttributes.Add(VariableName, JsonValue); + + //return false; + } + else + { + UClass* PropClass = Property->GetClass(); + UE_LOG(LogJson, Error, TEXT("UStructToJsonObject - Unhandled property type '%s': %s"), *PropClass->GetName(), *Property->GetPathName()); + } + } + // set the value on the output object + + } + + return true; +} + +bool FIFJsonSerializer::UObjectToJsonObject(const UStruct* StructDefinition, const void* Struct, TSharedRef OutJsonObject) +{ + OutJsonObject->Values.Add(FString("objectClass"), MakeShareable(new FJsonValueString(StructDefinition->GetPathName()))); + return UStructToJsonAttributes(StructDefinition, Struct, OutJsonObject->Values); +} +void FIFJsonSerializer::JsonObjectToUObject(TSharedPtr Object, UObject*& OutObject, UObject* Outer) +{ + FString objClassStr = Object->GetStringField("objectClass"); + + FSoftClassPath path(objClassStr); + + UClass* itemCls = Cast(path.TryLoad()); + if (itemCls) + { + OutObject = NewObject(Outer, itemCls); + for (TFieldIterator PropIt(itemCls); PropIt; ++PropIt) + { + UProperty* Property = *PropIt; + FString PropertyName = Property->GetName(); + + TSharedPtr JsonValue; + for (auto It = Object->Values.CreateConstIterator(); It; ++It) + { + // use case insensitive search sincd FName may change caseing strangely on us + if (PropertyName.Equals(It.Key(), ESearchCase::IgnoreCase)) + { + JsonValue = It.Value(); + break; + } + } + if (!JsonValue.IsValid()) + continue; + void* val = Property->ContainerPtrToValuePtr(OutObject); + if (UStructProperty* StructProp = Cast(Property)) + { + static const FName NAME_DateTime(TEXT("DateTime")); + static const FName NAME_Color(TEXT("Color")); + static const FName NAME_LinearColor(TEXT("LinearColor")); + if (JsonValue->Type == EJson::Object) + { + TSharedPtr Obj = JsonValue->AsObject(); + check(Obj.IsValid()); // should not fail if Type == EJson::Object + if (!FJsonObjectConverter::JsonObjectToUStruct(Obj.ToSharedRef(), StructProp->Struct, val, 0, 0)) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - FJsonObjectConverter::JsonObjectToUStruct failed for property %s"), *Property->GetNameCPP()); + continue; + } + } + else if (JsonValue->Type == EJson::String && StructProp->Struct->GetFName() == NAME_LinearColor) + { + FLinearColor& ColorOut = *(FLinearColor*)val; + FString ColorString = JsonValue->AsString(); + + FColor IntermediateColor; + IntermediateColor = FColor::FromHex(ColorString); + + ColorOut = IntermediateColor; + } + else if (JsonValue->Type == EJson::String && StructProp->Struct->GetFName() == NAME_Color) + { + FColor& ColorOut = *(FColor*)val; + FString ColorString = JsonValue->AsString(); + + ColorOut = FColor::FromHex(ColorString); + } + else if (JsonValue->Type == EJson::String && StructProp->Struct->GetFName() == NAME_DateTime) + { + FString DateString = JsonValue->AsString(); + FDateTime& DateTimeOut = *(FDateTime*)val; + if (DateString == TEXT("min")) + { + // min representable value for our date struct. Actual date may vary by platform (this is used for sorting) + DateTimeOut = FDateTime::MinValue(); + } + else if (DateString == TEXT("max")) + { + // max representable value for our date struct. Actual date may vary by platform (this is used for sorting) + DateTimeOut = FDateTime::MaxValue(); + } + else if (DateString == TEXT("now")) + { + // this value's not really meaningful from json serialization (since we don't know timezone) but handle it anyway since we're handling the other keywords + DateTimeOut = FDateTime::UtcNow(); + } + else if (FDateTime::ParseIso8601(*DateString, DateTimeOut)) + { + // ok + } + else if (FDateTime::Parse(DateString, DateTimeOut)) + { + // ok + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to import FDateTime for property %s"), *Property->GetNameCPP()); + continue; + } + } + } + else if (USoftClassProperty* SofftClassProp = Cast(Property)) + { + + FString dupa; + JsonValue->TryGetString(dupa); + FSoftClassPath classPath(dupa); + + UClass* dupaCls = Cast(path.TryLoad()); + SofftClassProp->SetMetaClass(dupaCls); + } + else if (UObjectProperty* ObjectProp = Cast(Property)) + { + const TSharedPtr* Obj; + JsonValue->TryGetObject(Obj); + + if (Obj) + { + TSharedPtr Objj = *Obj; + + //TSharedPtr itemField = Objj->GetObjectField("item"); + FString objClassStr2 = Objj->GetStringField("objectClass"); + if (objClassStr2.Len() > 0) + { + FSoftClassPath path(objClassStr2); + UClass* itemCls = Cast(path.TryLoad()); + UObject* Out = nullptr; + JsonObjectToUObject(Objj, Out, OutObject); + ObjectProp->SetObjectPropertyValue_InContainer(OutObject, Out); + } + } + } + } + } +} IFTypes::IFTypes() { } diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp index 56055b0..365f1d3 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/InventoryFramework.cpp @@ -2,6 +2,8 @@ #include "InventoryFramework.h" + + #define LOCTEXT_NAMESPACE "FInventoryFrameworkModule" void FInventoryFrameworkModule::StartupModule() diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h index 9e81cda..16989a0 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h @@ -77,7 +77,7 @@ class INVENTORYFRAMEWORK_API UIFEquipmentComponent : public UActorComponent void ClientRemoveFromEquipment(uint8 EquipmentIndex); void ClientRemoveFromEquipment_Implementation(uint8 EquipmentIndex); - + virtual void OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemAdded(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemRemoved(uint8 Index) {}; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index fad151c..b5b6e5a 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -3,15 +3,14 @@ #pragma once #include "CoreMinimal.h" + #include "Components/ActorComponent.h" #include "IFTypes.h" #include "IFInventoryComponent.generated.h" //NetIndex, LocalIndex - - - +DECLARE_LOG_CATEGORY_EXTERN(IFLog, Log, All); UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index a128dfc..437267a 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -100,7 +100,7 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject virtual void PreItemLoad() {}; virtual void PostItemLoad() {}; - + virtual TSharedPtr SaveToJson() { return nullptr; } static UIFItemBase* LoadFromJSON() { return nullptr; } }; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h index 01572d2..8cd0d24 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h @@ -3,6 +3,12 @@ #pragma once #include "CoreMinimal.h" +#include "Json.h" +#include "Policies/CondensedJsonPrintPolicy.h" +#include "Serialization/JsonTypes.h" +#include "Serialization/JsonReader.h" +#include "Policies/PrettyJsonPrintPolicy.h" +#include "Serialization/JsonSerializer.h" #include "IFTypes.generated.h" DECLARE_MULTICAST_DELEGATE_ThreeParams(FIFItemEvent, uint8, uint8, class UIFItemBase*); @@ -22,7 +28,7 @@ struct INVENTORYFRAMEWORK_API FIFItemData USTRUCT(BlueprintType) -struct FIFSlotAcceptedClasses +struct INVENTORYFRAMEWORK_API FIFSlotAcceptedClasses { GENERATED_BODY() public: @@ -31,6 +37,16 @@ struct FIFSlotAcceptedClasses }; +struct INVENTORYFRAMEWORK_API FIFJsonSerializer +{ + static TSharedPtr ConvertScalarUPropertyToJsonValue(UProperty* Property, const void* Value); + static bool UObjectToJsonObject(const UStruct* StructDefinition, const void* Struct, TSharedRef OutJsonObject); + static bool UStructToJsonAttributes(const UStruct* StructDefinition, const void* Struct, TMap< FString, TSharedPtr >& OutJsonAttributes); + + static void JsonObjectToUObject(TSharedPtr Object, UObject*& OutObject, UObject* Outer); +}; + + /** * */ diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index 6617467..c47abb4 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -3,6 +3,7 @@ #include "ARItemWeapon.h" #include "Effects/GABlueprintLibrary.h" +#include "IFInventoryComponent.h" #include "ARCharacter.h" #include "ARPlayerController.h" @@ -67,16 +68,47 @@ UARMagazineUpgradeItem* UARItemWeapon::RemoveMagazineUpgrade() return MagazineModification; } +void UARItemWeapon::SpawnAbility() +{ + UIFInventoryComponent* InventoryComp = Cast(GetOuter()); + if (!InventoryComp) + return; + + AARPlayerController* PC = Cast(InventoryComp->GetOwner()); + if (!PC) + return; + + AARCharacter* Character = Cast(PC->GetPawn()); + + if (!Character) + return; + + TSubclassOf ABClass = Ability.LoadSynchronous(); + if (ABClass) + { + AbilityInstance = NewObject(Character, ABClass); + AbilityInstance->GetAttributes()->CopyFromOtherAttributes(Attributes); + } +} void UARItemWeapon::OnItemAdded(uint8 LocalIndex) { - + SpawnAbility(); } void UARItemWeapon::OnItemRemoved(uint8 LocalIndex) { } - +void UARItemWeapon::OnServerItemAdded(uint8 LocalIndex) +{ + SpawnAbility(); +} +void UARItemWeapon::OnServerItemChanged(uint8 LocalIndex) +{ +} +void UARItemWeapon::OnServerItemRemoved(uint8 LocalIndex) +{ +} void UARItemWeapon::OnItemAddedEquipment(uint8 LocalIndex) { @@ -103,7 +135,18 @@ void UARItemWeapon::PostItemLoad() { } +TSharedPtr UARItemWeapon::SaveToJson() +{ + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + TSharedPtr UObj = MakeShareable(new FJsonObject()); + + FIFJsonSerializer::UObjectToJsonObject(GetClass(), this, UObj.ToSharedRef()); + + + return UObj; +} TArray UARItemWeapon::GetTooltipData() { TArray Data; diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp index a5f566c..568ce98 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp @@ -77,7 +77,18 @@ void UARWeaponInventoryComponent::SetWeapon(const FARWeaponRPC& InWeapon, UChild UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); } } - +void UARWeaponInventoryComponent::OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) +{ + UARItemWeapon* InWeapon = Cast(Item); + if (AARCharacter* Character = Cast(POwner)) + { + FAFOnAbilityReady del; + { + del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(Index)); + Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); + } + } +} void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) { UARItemWeapon* InWeapon = Cast(Item); @@ -91,12 +102,15 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde if (AARCharacter* Character = Cast(POwner)) { TArray NoInput; - FAFOnAbilityReady del; + /*FAFOnAbilityReady del; { del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(LocalIndex)); Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); + }*/ + if (!InWeapon->AbilityInstance) + { + Character->GetAbilityComp()->NativeAddAbility(InWeapon->Ability, NoInput); } - Character->GetAbilityComp()->NativeAddAbility(InWeapon->Ability, NoInput); WeaponAbilities[LocalIndex] = InWeapon->Ability; } } @@ -118,6 +132,10 @@ void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 Loc Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); } WeaponAbilities[LocalIndex] = InWeapon->Ability; + if (InWeapon->AbilityInstance) + { + Character->GetAbilityComp()->NativeAddAbilityFromObject(InWeapon->AbilityInstance, InWeapon->Ability); + } } MulticastAddWeapon(Data); } diff --git a/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h index 63874c1..e1e204b 100644 --- a/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h +++ b/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h @@ -18,21 +18,21 @@ class ACTIONRPGGAME_API UARGunAttributes : public UGAAttributesBase { GENERATED_BODY() public: - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase BaseDamage; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase CritChance; - UPROPERTY(EditAnywhere, ReplicatedUsing=OnRep_Magazine, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, ReplicatedUsing=OnRep_Magazine, Category = "Base") FAFAttributeBase Magazine; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase RateOfFire; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase ReloadSpeed; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase HorizontalStability; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase VerticalStability; - UPROPERTY(EditAnywhere, Category = "Base") + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") FAFAttributeBase Spread; UFUNCTION() diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index 3c3dd76..6958271 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -6,7 +6,7 @@ #include "UObject/NoExportTypes.h" #include "Effects/GAGameEffect.h" #include "ARMagazineUpgradeItem.h" - +#include "IFTypes.h" #include "GameplayTags.h" #include "ARItemWeapon.generated.h" @@ -35,7 +35,7 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase Values from these attributes will be copied to ability, after ability is instanced. It's here to allow random generation and easily store that information in Database instead of storing ability. */ - UPROPERTY(EditAnywhere, Instanced, Category = "Attributes") + UPROPERTY(EditAnywhere, SaveGame, Instanced, Category = "Attributes") class UARGunAttributes* Attributes; UPROPERTY(EditAnywhere, Category = "Transforms") @@ -48,10 +48,10 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(EditAnywhere, Category = "Transforms") FRotator EquipedRotation; - UPROPERTY(EditAnywhere, Category = "Ability") + UPROPERTY(BlueprintReadOnly, SaveGame, Category = "Ability") UARWeaponAbilityBase* AbilityInstance; - UPROPERTY(BlueprintReadOnly, Category = "Ability") + UPROPERTY(BlueprintReadOnly, SaveGame, Category = "Ability") class UARMagazineUpgradeItem* MagazineModification; UPROPERTY(Transient) @@ -64,19 +64,27 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UARMagazineUpgradeItem* RemoveMagazineUpgrade(); + void SpawnAbility(); + virtual void OnItemAdded(uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; - virtual void OnItemAddedEquipment(uint8 LocalIndex); - virtual void OnItemChangedEquipment(uint8 LocalIndex); - virtual void OnItemRemovedEquipment(uint8 LocalIndex); + virtual void OnServerItemAdded(uint8 LocalIndex) override; + virtual void OnServerItemChanged(uint8 LocalIndex) override; + virtual void OnServerItemRemoved(uint8 LocalIndex) override; - virtual void OnServerItemAddedEquipment(uint8 LocalIndex); - virtual void OnServerItemChangedEquipment(uint8 LocalIndex); - virtual void OnServerItemRemovedEquipment(uint8 LocalIndex); + virtual void OnItemAddedEquipment(uint8 LocalIndex) override; + virtual void OnItemChangedEquipment(uint8 LocalIndex) override; + virtual void OnItemRemovedEquipment(uint8 LocalIndex) override; + + virtual void OnServerItemAddedEquipment(uint8 LocalIndex) override; + virtual void OnServerItemChangedEquipment(uint8 LocalIndex) override; + virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) override; virtual void PostItemLoad(); + virtual TSharedPtr SaveToJson() override; virtual TArray GetTooltipData() override; + protected: }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h index 6bd15da..fe21cb6 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h @@ -18,7 +18,7 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem /* An actual modifier value of this upgrade. */ - UPROPERTY(EditAnywhere) + UPROPERTY(EditAnywhere, SaveGame) float MagazineUpgradeValue; /* Effect template diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h index c069fe3..aeeddff 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h @@ -50,7 +50,7 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase /* Weapon item to which this abiliy belongs. */ - UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Weapon") + UPROPERTY(BlueprintReadOnly, Transient, Category = "ActionRPGGame|Weapon") class UARItemWeapon* WeaponItem; diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 5c070ec..46bbc57 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -115,7 +115,7 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone { return OnUpgradeRemoved; } - + virtual void OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) override; virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; From 9a4c20310e183f604ac4464771c0e94e3696a308 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 6 May 2018 20:56:35 +0200 Subject: [PATCH 167/187] moved json UObject serialization into seprate plugin, working on inventory items serialization/event flow --- .../Private/Attributes/GAAttributesBase.cpp | 21 + .../Public/Attributes/GAAttributesBase.h | 6 + .../InventoryFramework.uplugin | 48 +- .../InventoryFramework.Build.cs | 3 +- .../Private/IFInventoryComponent.cpp | 161 +++--- .../InventoryFramework/Private/IFTypes.cpp | 541 +++++++++++------- .../Public/IFInventoryComponent.h | 7 +- .../InventoryFramework/Public/IFItemBase.h | 3 +- .../InventoryFramework/Public/IFTypes.h | 8 +- Plugins/JsonUObject/JsonUObject.uplugin | 23 + .../Source/JsonUObject/JsonUObject.Build.cs | 49 ++ .../JsonUObject/Private/JsonUODeserialize.cpp | 11 + .../JsonUObject/Private/JsonUOSerialize.cpp | 219 +++++++ .../JsonUObject/Private/JsonUObject.cpp | 20 + .../JsonUObject/Public/JsonUODeserialize.h | 15 + .../JsonUObject/Public/JsonUOSerialize.h | 25 + .../Source/JsonUObject/Public/JsonUObject.h | 15 + Source/ActionRPGGame/ActionRPGGame.Build.cs | 1 + .../Private/Weapons/ARItemWeapon.cpp | 62 +- .../Private/Weapons/ARWeaponAbilityBase.cpp | 8 +- .../Public/Attributes/ARGunAttributes.h | 27 + .../Public/Weapons/ARItemWeapon.h | 16 +- .../Public/Weapons/ARWeaponAbilityBase.h | 1 + 23 files changed, 923 insertions(+), 367 deletions(-) create mode 100644 Plugins/JsonUObject/JsonUObject.uplugin create mode 100644 Plugins/JsonUObject/Source/JsonUObject/JsonUObject.Build.cs create mode 100644 Plugins/JsonUObject/Source/JsonUObject/Private/JsonUODeserialize.cpp create mode 100644 Plugins/JsonUObject/Source/JsonUObject/Private/JsonUOSerialize.cpp create mode 100644 Plugins/JsonUObject/Source/JsonUObject/Private/JsonUObject.cpp create mode 100644 Plugins/JsonUObject/Source/JsonUObject/Public/JsonUODeserialize.h create mode 100644 Plugins/JsonUObject/Source/JsonUObject/Public/JsonUOSerialize.h create mode 100644 Plugins/JsonUObject/Source/JsonUObject/Public/JsonUObject.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp index 6f89cdc..92ad91a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp @@ -65,6 +65,27 @@ void UGAAttributesBase::CopyFromOtherAttributes(UGAAttributesBase* Other) } } +void UGAAttributesBase::CopyFromStruct(UStruct* StructType, void* StructObject) +{ + for (TFieldIterator StrIt(StructType); StrIt; ++StrIt) + { + UProperty* Property = *StrIt; + if (UStructProperty* StructProp = Cast(Property)) + { + FAFAttributeBase* StructAttr = StructProp->ContainerPtrToValuePtr(StructObject); + UProperty* ThisProp = FindProperty(FGAAttribute(Property->GetFName())); + if (ThisProp) + { + FAFAttributeBase* ThisAttribute = ThisProp->ContainerPtrToValuePtr(this); + if (StructAttr && ThisAttribute) + { + ThisAttribute->CopyFromOther(StructAttr); + } + } + } + } +} + void UGAAttributesBase::InitializeAttributesFromTable() { if (!AttributeValues) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h index f2d1f68..e609e62 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h @@ -56,6 +56,12 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject //virtual void PostNetReceive() override; virtual void InitializeAttributes(UAFAbilityComponent* InOwningAttributeComp); void CopyFromOtherAttributes(UGAAttributesBase* Other); + + /* + Copy attributes from arbitrary struct. + Struct must be composed from FAFAttributeBase (or it's derivative) fields. + */ + void CopyFromStruct(UStruct* StructType, void* StructObject); void InitializeAttributesFromTable(); UFUNCTION(BlueprintImplementableEvent, meta = (DisplayName = "Initialize Attributes")) bool BP_InitializeAttributes(); diff --git a/Plugins/InventoryFramework/InventoryFramework.uplugin b/Plugins/InventoryFramework/InventoryFramework.uplugin index 323ecd1..a36617d 100644 --- a/Plugins/InventoryFramework/InventoryFramework.uplugin +++ b/Plugins/InventoryFramework/InventoryFramework.uplugin @@ -1,23 +1,29 @@ { - "FileVersion": 3, - "Version": 1, - "VersionName": "1.0", - "FriendlyName": "InventoryFramework", - "Description": "", - "Category": "Gameplay", - "CreatedBy": "", - "CreatedByURL": "", - "DocsURL": "", - "MarketplaceURL": "", - "SupportURL": "", - "CanContainContent": true, - "IsBetaVersion": true, - "Installed": false, - "Modules": [ - { - "Name": "InventoryFramework", - "Type": "Runtime", - "LoadingPhase": "Default" - } - ] + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "InventoryFramework", + "Description": "", + "Category": "Gameplay", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": true, + "Installed": false, + "Modules": [ + { + "Name": "InventoryFramework", + "Type": "Runtime", + "LoadingPhase": "Default" + } + ], + "Plugins": [ + { + "Name": "JsonUObject", + "Enabled": true + } + ] } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs index a1fee49..702f45e 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs +++ b/Plugins/InventoryFramework/Source/InventoryFramework/InventoryFramework.Build.cs @@ -33,7 +33,8 @@ public InventoryFramework(ReadOnlyTargetRules Target) : base(Target) "Slate", "SlateCore", "Json", - "JsonUtilities" + "JsonUtilities", + "JsonUObject" // ... add private dependencies that you statically link with here ... } ); diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index bd0908b..8010b27 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -5,6 +5,8 @@ #include "GameFramework/Actor.h" #include "Engine/AssetManager.h" +#include "JsonUOSerialize.h" + #include "JsonObjectConverter.h" #include "IFItemBase.h" @@ -275,7 +277,8 @@ void UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Implementation(cla OnServerItemAdded(InventoryItems[FreeSlot].Item, FreeSlot); ClientAddItemFromEquipmentAnySlot(Source, SourceIndex, FreeSlot); - SendToBackend(&InventoryItems[FreeSlot]); + TSharedPtr Obj = ItemToJson(&InventoryItems[FreeSlot]); + SendToBackend(Obj, FreeSlot); } bool UIFInventoryComponent::ServerAddItemFromEquipmentAnySlot_Validate(class UIFEquipmentComponent* Source, uint8 SourceIndex) { @@ -311,14 +314,10 @@ void UIFInventoryComponent::AddItemAnySlot(class UIFItemBase* Source) InventoryItems[FreeSlot].Item = DuplicateObject(Source, this); Source->MarkPendingKill(); - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; - typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + TSharedPtr Obj = ItemToJson(&InventoryItems[FreeSlot]); + SendToBackend(Obj, FreeSlot); - TSharedPtr Obj = SendToBackend(&InventoryItems[FreeSlot]); - - FString OutputString; - TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); - check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + FString OutputString = JsonItemToString(Obj); InventoryItems[FreeSlot].Item->OnServerItemAdded(FreeSlot); OnServerItemAdded(InventoryItems[FreeSlot].Item, FreeSlot); @@ -327,17 +326,7 @@ void UIFInventoryComponent::AddItemAnySlot(class UIFItemBase* Source) } void UIFInventoryComponent::ClientAddAnySlot_Implementation(const FString& JsonData, uint8 InventoryIndex) { - TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(JsonData); - - TSharedPtr Object = MakeShareable(new FJsonObject()); - - bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); - - TArray< TSharedPtr > Array; - bool bSuccessful2 = FJsonSerializer::Deserialize(Reader, Array); - - FIFItemData Item; - FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), FIFItemData::StaticStruct(), &Item, 0, 0); + FIFItemData Item = JsonToItem(JsonData); if (Item.Item) { @@ -389,9 +378,7 @@ void UIFInventoryComponent::ClientRemoveItem_Implementation(uint8 InIndex) } void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem) { - TSubclassOf ItemClass = InItem.Get(); - - FIFItemData Item; + uint8 FreeIndex = 0; for (uint8 Idx = 0; Idx < InventoryItems.Num(); Idx++) @@ -402,107 +389,107 @@ void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem, uint8 InNetIndex) +{ + AddItem(InItem, InNetIndex); +} + +void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Data) +{ + FIFItemData Item = JsonToItem(Data); + if (Item.Item) + { + Item.Item->PostItemLoad(); + Item.Item->OnItemAdded(Item.Index); + + InventoryItems[Item.Index] = Item; + OnItemAddedEvent.Broadcast(Item.Index, Item.Index, Item.Item); + OnItemUpdatedEvent.Broadcast(Item.Index, Item.Index, Item.Item); + + OnItemAdded(InventoryItems[Item.Index].Item, Item.Index); + } +} + +void UIFInventoryComponent::AddItem(TSoftClassPtr InItem, uint8 ItemIndex) +{ + TSubclassOf ItemClass = InItem.Get(); + FIFItemData Item; + Item.Index = ItemIndex; Item.Item = NewObject(this, ItemClass); - + Item.Item->OnServerItemLoaded(); + InventoryItems[Item.Index] = Item; InventoryItems[Item.Index].Item->OnServerItemAdded(Item.Index); OnServerItemAdded(InventoryItems[Item.Index].Item, Item.Index); - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; - typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + TSharedPtr Obj = ItemToJson(&InventoryItems[Item.Index]); + SendToBackend(Obj, Item.Index); - TSharedPtr Obj = SendToBackend(&InventoryItems[Item.Index]); + FString OutputString = JsonItemToString(Obj); - FString OutputString; - TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); - check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); + UE_LOG(IFLog, Log, TEXT("ItemLoaded %s "), *OutputString); + ClientSendJsonData(OutputString); FStreamableManager& Manager = UAssetManager::GetStreamableManager(); Manager.Unload(InItem.ToSoftObjectPath()); +} - UE_LOG(IFLog, Log, TEXT("ItemLoaded %s "), *OutputString); - +TSharedPtr UIFInventoryComponent::ItemToJson(FIFItemData* Item) +{ + typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; + typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; + TSharedPtr Obj = MakeShareable(new FJsonObject()); + TSharedPtr UObj = MakeShareable(new FJsonObject()); + if (Item->Item) + { + FJsonUOSerialize::UObjectToJsonObject(Item->Item->GetClass(), Item->Item, UObj.ToSharedRef()); + //UObj = Item->Item->SaveToJson(); + } + Obj->Values.Add(FString("index"), MakeShareable(new FJsonValueNumber(Item->Index))); + Obj->Values.Add(FString("item"), MakeShareable(new FJsonValueObject(UObj))); + FakeBackend[Item->Index] = Obj; - ClientSendJsonData(OutputString); + return Obj; } -void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem, uint8 InNetIndex) +FString UIFInventoryComponent::JsonItemToString(TSharedPtr Object) { - TSubclassOf ItemClass = InItem.Get(); - - UIFItemBase* ItemObj = NewObject(this, ItemClass); - - InventoryItems[InNetIndex].Item = ItemObj; - - InventoryItems[InNetIndex].Item->OnServerItemAdded(InNetIndex); - OnServerItemAdded(InventoryItems[InNetIndex].Item, InNetIndex); - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; - TSharedPtr Obj = SendToBackend(&InventoryItems[InNetIndex]); - FString OutputString; TSharedRef< FPrettyJsonStringWriter > Writer = FPrettyJsonStringWriterFactory::Create(&OutputString); - check(FJsonSerializer::Serialize(Obj.ToSharedRef(), Writer)); - - UE_LOG(IFLog, Log, TEXT("ItemLoaded %s "), *OutputString); + check(FJsonSerializer::Serialize(Object.ToSharedRef(), Writer)); - ClientSendJsonData(OutputString); - - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); - Manager.Unload(InItem.ToSoftObjectPath()); + return OutputString; +} +void UIFInventoryComponent::SendToBackend(TSharedPtr JsonObj, int32 Idx) +{ + FakeBackend[Idx] = JsonObj; } -void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Data) +FIFItemData UIFInventoryComponent::JsonToItem(const FString& JsonString) { - TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(Data); + TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(JsonString); TSharedPtr Object = MakeShareable(new FJsonObject()); bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); - TSharedPtr itemField = Object->GetObjectField("item"); FString objClassStr = itemField->GetStringField("objectClass"); + int32 idx = Object->GetIntegerField("index"); FSoftClassPath path(objClassStr); - - //FStreamableManager& Manager = UAssetManager::GetStreamableManager(); + UClass* itemCls = Cast(path.TryLoad()); UObject* OutObj = nullptr; FIFJsonSerializer::JsonObjectToUObject(itemField, OutObj, this); FIFItemData Item; - FJsonObjectConverter::JsonObjectToUStruct(Object.ToSharedRef(), FIFItemData::StaticStruct(), &Item, 0, 0); - - if (Item.Item) - { - Item.Item->PostItemLoad(); - InventoryItems[Item.Index] = Item; - OnItemAddedEvent.Broadcast(Item.Index, Item.Index, Item.Item); - OnItemUpdatedEvent.Broadcast(Item.Index, Item.Index, Item.Item); - InventoryItems[Item.Index].Item->OnItemAdded(Item.Index); - OnItemAdded(InventoryItems[Item.Index].Item, Item.Index); - } - -} + Item.Index = idx; + Item.Item = Cast(OutObj); -TSharedPtr UIFInventoryComponent::SendToBackend(FIFItemData* Item) -{ - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; - typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; - - TSharedPtr Obj = MakeShareable(new FJsonObject()); - //FJsonObjectConverter::UStructToJsonObject(FIFItemData::StaticStruct(), Item, Obj.ToSharedRef(), 0, 0); - TSharedPtr UObj = MakeShareable(new FJsonObject()); - if (Item->Item) - { - UObj = Item->Item->SaveToJson(); - } - Obj->Values.Add(FString("index"), MakeShareable(new FJsonValueNumber(Item->Index))); - Obj->Values.Add(FString("item"), MakeShareable(new FJsonValueObject(UObj))); - FakeBackend[Item->Index] = Obj; - - return Obj; + return Item; } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp index 1a38083..93c31fd 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp @@ -3,222 +3,403 @@ #include "IFTypes.h" #include "JsonObjectConverter.h" -TSharedPtr UPropertyToJsonValue(UProperty* Property, const void* Value) -{ - if (Property->ArrayDim == 1) - { - return FIFJsonSerializer::ConvertScalarUPropertyToJsonValue(Property, Value); - } - TArray< TSharedPtr > Array; - for (int Index = 0; Index != Property->ArrayDim; ++Index) - { - Array.Add(FIFJsonSerializer::ConvertScalarUPropertyToJsonValue(Property, (char*)Value + Index * Property->ElementSize)); - } - return MakeShareable(new FJsonValueArray(Array)); -} - -TSharedPtr FIFJsonSerializer::ConvertScalarUPropertyToJsonValue(UProperty* Property, const void* Value) +bool FIFJsonSerializer::ConvertScalarJsonValueToUProperty(TSharedPtr JsonValue, UProperty* Property, void* OutValue) { - // See if there's a custom export callback first, so it can override default behavior - - if (UEnumProperty* EnumProperty = Cast(Property)) { - // export enums as strings - UEnum* EnumDef = EnumProperty->GetEnum(); - FString StringValue = EnumDef->GetNameStringByValue(EnumProperty->GetUnderlyingProperty()->GetSignedIntPropertyValue(Value)); - return MakeShareable(new FJsonValueString(StringValue)); + if (JsonValue->Type == EJson::String) + { + // see if we were passed a string for the enum + const UEnum* Enum = EnumProperty->GetEnum(); + check(Enum); + FString StrValue = JsonValue->AsString(); + int64 IntValue = Enum->GetValueByName(FName(*StrValue)); + if (IntValue == INDEX_NONE) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable import enum %s from string value %s for property %s"), *Enum->CppType, *StrValue, *Property->GetNameCPP()); + return false; + } + EnumProperty->GetUnderlyingProperty()->SetIntPropertyValue(OutValue, IntValue); + } + else + { + // AsNumber will log an error for completely inappropriate types (then give us a default) + EnumProperty->GetUnderlyingProperty()->SetIntPropertyValue(OutValue, (int64)JsonValue->AsNumber()); + } } else if (UNumericProperty *NumericProperty = Cast(Property)) { - // see if it's an enum - UEnum* EnumDef = NumericProperty->GetIntPropertyEnum(); - if (EnumDef != NULL) + if (NumericProperty->IsEnum() && JsonValue->Type == EJson::String) { - // export enums as strings - FString StringValue = EnumDef->GetNameStringByValue(NumericProperty->GetSignedIntPropertyValue(Value)); - return MakeShareable(new FJsonValueString(StringValue)); + // see if we were passed a string for the enum + const UEnum* Enum = NumericProperty->GetIntPropertyEnum(); + check(Enum); // should be assured by IsEnum() + FString StrValue = JsonValue->AsString(); + int64 IntValue = Enum->GetValueByName(FName(*StrValue)); + if (IntValue == INDEX_NONE) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable import enum %s from string value %s for property %s"), *Enum->CppType, *StrValue, *Property->GetNameCPP()); + return false; + } + NumericProperty->SetIntPropertyValue(OutValue, IntValue); } - - // We want to export numbers as numbers - if (NumericProperty->IsFloatingPoint()) + else if (NumericProperty->IsFloatingPoint()) { - return MakeShareable(new FJsonValueNumber(NumericProperty->GetFloatingPointPropertyValue(Value))); + // AsNumber will log an error for completely inappropriate types (then give us a default) + NumericProperty->SetFloatingPointPropertyValue(OutValue, JsonValue->AsNumber()); } else if (NumericProperty->IsInteger()) { - return MakeShareable(new FJsonValueNumber(NumericProperty->GetSignedIntPropertyValue(Value))); + if (JsonValue->Type == EJson::String) + { + // parse string -> int64 ourselves so we don't lose any precision going through AsNumber (aka double) + NumericProperty->SetIntPropertyValue(OutValue, FCString::Atoi64(*JsonValue->AsString())); + } + else + { + // AsNumber will log an error for completely inappropriate types (then give us a default) + NumericProperty->SetIntPropertyValue(OutValue, (int64)JsonValue->AsNumber()); + } + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to set numeric property type %s for property %s"), *Property->GetClass()->GetName(), *Property->GetNameCPP()); + return false; } - - // fall through to default } else if (UBoolProperty *BoolProperty = Cast(Property)) { - // Export bools as bools - return MakeShareable(new FJsonValueBoolean(BoolProperty->GetPropertyValue(Value))); + // AsBool will log an error for completely inappropriate types (then give us a default) + BoolProperty->SetPropertyValue(OutValue, JsonValue->AsBool()); } else if (UStrProperty *StringProperty = Cast(Property)) { - return MakeShareable(new FJsonValueString(StringProperty->GetPropertyValue(Value))); - } - else if (UTextProperty *TextProperty = Cast(Property)) - { - return MakeShareable(new FJsonValueString(TextProperty->GetPropertyValue(Value).ToString())); + // AsString will log an error for completely inappropriate types (then give us a default) + StringProperty->SetPropertyValue(OutValue, JsonValue->AsString()); } else if (UArrayProperty *ArrayProperty = Cast(Property)) { - TArray< TSharedPtr > Out; - FScriptArrayHelper Helper(ArrayProperty, Value); - for (int32 i = 0, n = Helper.Num(); iType == EJson::Array) { - TSharedPtr Elem = UPropertyToJsonValue(ArrayProperty->Inner, Helper.GetRawPtr(i)); - if (Elem.IsValid()) + TArray< TSharedPtr > ArrayValue = JsonValue->AsArray(); + int32 ArrLen = ArrayValue.Num(); + + // make the output array size match + FScriptArrayHelper Helper(ArrayProperty, OutValue); + Helper.Resize(ArrLen); + + // set the property values + for (int32 i = 0; i& ArrayValueItem = ArrayValue[i]; + if (ArrayValueItem.IsValid() && !ArrayValueItem->IsNull()) + { + if (!JsonValueToUProperty(ArrayValueItem, ArrayProperty->Inner, Helper.GetRawPtr(i))) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to deserialize array element [%d] for property %s"), i, *Property->GetNameCPP()); + return false; + } + } } } - return MakeShareable(new FJsonValueArray(Out)); + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import TArray from non-array JSON key for property %s"), *Property->GetNameCPP()); + return false; + } } - else if (USetProperty* SetProperty = Cast(Property)) + else if (UMapProperty* MapProperty = Cast(Property)) { - TArray< TSharedPtr > Out; - FScriptSetHelper Helper(SetProperty, Value); - for (int32 i = 0, n = Helper.Num(); n; ++i) + if (JsonValue->Type == EJson::Object) { - if (Helper.IsValidIndex(i)) + TSharedPtr ObjectValue = JsonValue->AsObject(); + + FScriptMapHelper Helper(MapProperty, OutValue); + + // set the property values + for (const auto& Entry : ObjectValue->Values) { - TSharedPtr Elem = UPropertyToJsonValue(SetProperty->ElementProp, Helper.GetElementPtr(i)); - if (Elem.IsValid()) + if (Entry.Value.IsValid() && !Entry.Value->IsNull()) { - // add to the array - Out.Push(Elem); - } + int32 NewIndex = Helper.AddDefaultValue_Invalid_NeedsRehash(); + + TSharedPtr TempKeyValue = MakeShareable(new FJsonValueString(Entry.Key)); + + const bool bKeySuccess = JsonValueToUProperty(TempKeyValue, MapProperty->KeyProp, Helper.GetKeyPtr(NewIndex)); + const bool bValueSuccess = JsonValueToUProperty(Entry.Value, MapProperty->ValueProp, Helper.GetValuePtr(NewIndex)); - --n; + if (!(bKeySuccess && bValueSuccess)) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to deserialize map element [key: %s] for property %s"), *Entry.Key, *Property->GetNameCPP()); + return false; + } + } } + + Helper.Rehash(); + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import TMap from non-object JSON key for property %s"), *Property->GetNameCPP()); + return false; } - return MakeShareable(new FJsonValueArray(Out)); } - else if (UMapProperty* MapProperty = Cast(Property)) + else if (USetProperty* SetProperty = Cast(Property)) { - TSharedRef Out = MakeShareable(new FJsonObject()); - - FScriptMapHelper Helper(MapProperty, Value); - for (int32 i = 0, n = Helper.Num(); n; ++i) + if (JsonValue->Type == EJson::Array) { - if (Helper.IsValidIndex(i)) + TArray< TSharedPtr > ArrayValue = JsonValue->AsArray(); + int32 ArrLen = ArrayValue.Num(); + + FScriptSetHelper Helper(SetProperty, OutValue); + + // set the property values + for (int32 i = 0; i < ArrLen; ++i) { - TSharedPtr KeyElement = UPropertyToJsonValue(MapProperty->KeyProp, Helper.GetKeyPtr(i)); - TSharedPtr ValueElement = UPropertyToJsonValue(MapProperty->ValueProp, Helper.GetValuePtr(i)); - if (KeyElement.IsValid() && ValueElement.IsValid()) + const TSharedPtr& ArrayValueItem = ArrayValue[i]; + if (ArrayValueItem.IsValid() && !ArrayValueItem->IsNull()) { - FString KeyString = KeyElement->AsString(); - if (KeyString.IsEmpty()) + int32 NewIndex = Helper.AddDefaultValue_Invalid_NeedsRehash(); + if (!JsonValueToUProperty(ArrayValueItem, SetProperty->ElementProp, Helper.GetElementPtr(NewIndex))) { - MapProperty->KeyProp->ExportTextItem(KeyString, Helper.GetKeyPtr(i), nullptr, nullptr, 0); - if (KeyString.IsEmpty()) - { - UE_LOG(LogJson, Error, TEXT("Unable to convert key to string for property %s."), *MapProperty->GetName()) - KeyString = FString::Printf(TEXT("Unparsed Key %d"), i); - } + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to deserialize set element [%d] for property %s"), i, *Property->GetNameCPP()); + return false; } - - Out->SetField(KeyString, ValueElement); } - - --n; } - } - return MakeShareable(new FJsonValueObject(Out)); + Helper.Rehash(); + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import TSet from non-array JSON key for property %s"), *Property->GetNameCPP()); + return false; + } } - else if (UObjectProperty* ObjectProperty = Cast(Property)) + else if (UTextProperty* TextProperty = Cast(Property)) { - TSharedRef Out = MakeShareable(new FJsonObject()); - - UObject* Object = ObjectProperty->GetObjectPropertyValue(Value); - if (Object) + if (JsonValue->Type == EJson::String) { - UClass* cls = Object->GetClass(); + // assume this string is already localized, so import as invariant + TextProperty->SetPropertyValue(OutValue, FText::FromString(JsonValue->AsString())); + } + else if (JsonValue->Type == EJson::Object) + { + TSharedPtr Obj = JsonValue->AsObject(); + check(Obj.IsValid()); // should not fail if Type == EJson::Object - if (UObjectToJsonObject(cls, Object, Out)) + // import the subvalue as a culture invariant string + FText Text; + if (!FJsonObjectConverter::GetTextFromObject(Obj.ToSharedRef(), Text)) { - return MakeShareable(new FJsonValueObject(Out)); + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import FText from JSON object with invalid keys for property %s"), *Property->GetNameCPP()); + return false; } + TextProperty->SetPropertyValue(OutValue, Text); + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import FText from JSON that was neither string nor object for property %s"), *Property->GetNameCPP()); + return false; } } else if (UStructProperty *StructProperty = Cast(Property)) { - UScriptStruct::ICppStructOps* TheCppStructOps = StructProperty->Struct->GetCppStructOps(); - // Intentionally exclude the JSON Object wrapper, which specifically needs to export JSON in an object representation instead of a string - if (StructProperty->Struct != FJsonObjectWrapper::StaticStruct() && TheCppStructOps && TheCppStructOps->HasExportTextItem()) + static const FName NAME_DateTime(TEXT("DateTime")); + static const FName NAME_Color(TEXT("Color")); + static const FName NAME_LinearColor(TEXT("LinearColor")); + if (JsonValue->Type == EJson::Object) { - FString OutValueStr; - TheCppStructOps->ExportTextItem(OutValueStr, Value, nullptr, nullptr, PPF_None, nullptr); - return MakeShareable(new FJsonValueString(OutValueStr)); + TSharedPtr Obj = JsonValue->AsObject(); + check(Obj.IsValid()); // should not fail if Type == EJson::Object + if (!JsonObjectToUStruct(Obj.ToSharedRef(), StructProperty->Struct, OutValue)) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - FJsonObjectConverter::JsonObjectToUStruct failed for property %s"), *Property->GetNameCPP()); + return false; + } } + else if (JsonValue->Type == EJson::String && StructProperty->Struct->GetFName() == NAME_LinearColor) + { + FLinearColor& ColorOut = *(FLinearColor*)OutValue; + FString ColorString = JsonValue->AsString(); + + FColor IntermediateColor; + IntermediateColor = FColor::FromHex(ColorString); - TSharedRef Out = MakeShareable(new FJsonObject()); - if (UObjectToJsonObject(StructProperty->Struct, Value, Out)) + ColorOut = IntermediateColor; + } + else if (JsonValue->Type == EJson::String && StructProperty->Struct->GetFName() == NAME_Color) { - return MakeShareable(new FJsonValueObject(Out)); + FColor& ColorOut = *(FColor*)OutValue; + FString ColorString = JsonValue->AsString(); + + ColorOut = FColor::FromHex(ColorString); + } + else if (JsonValue->Type == EJson::String && StructProperty->Struct->GetFName() == NAME_DateTime) + { + FString DateString = JsonValue->AsString(); + FDateTime& DateTimeOut = *(FDateTime*)OutValue; + if (DateString == TEXT("min")) + { + // min representable value for our date struct. Actual date may vary by platform (this is used for sorting) + DateTimeOut = FDateTime::MinValue(); + } + else if (DateString == TEXT("max")) + { + // max representable value for our date struct. Actual date may vary by platform (this is used for sorting) + DateTimeOut = FDateTime::MaxValue(); + } + else if (DateString == TEXT("now")) + { + // this value's not really meaningful from json serialization (since we don't know timezone) but handle it anyway since we're handling the other keywords + DateTimeOut = FDateTime::UtcNow(); + } + else if (FDateTime::ParseIso8601(*DateString, DateTimeOut)) + { + // ok + } + else if (FDateTime::Parse(DateString, DateTimeOut)) + { + // ok + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to import FDateTime for property %s"), *Property->GetNameCPP()); + return false; + } + } + else if (JsonValue->Type == EJson::String && StructProperty->Struct->GetCppStructOps() && StructProperty->Struct->GetCppStructOps()->HasImportTextItem()) + { + UScriptStruct::ICppStructOps* TheCppStructOps = StructProperty->Struct->GetCppStructOps(); + + FString ImportTextString = JsonValue->AsString(); + const TCHAR* ImportTextPtr = *ImportTextString; + if (!TheCppStructOps->ImportTextItem(ImportTextPtr, OutValue, PPF_None, nullptr, (FOutputDevice*)GWarn)) + { + // Fall back to trying the tagged property approach if custom ImportTextItem couldn't get it done + Property->ImportText(ImportTextPtr, OutValue, PPF_None, nullptr); + } + } + else if (JsonValue->Type == EJson::String) + { + FString ImportTextString = JsonValue->AsString(); + const TCHAR* ImportTextPtr = *ImportTextString; + Property->ImportText(ImportTextPtr, OutValue, PPF_None, nullptr); + } + else + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import UStruct from non-object JSON key for property %s"), *Property->GetNameCPP()); + return false; } - // fall through to default } else { - // Default to export as string for everything else - FString StringValue; - Property->ExportTextItem(StringValue, Value, NULL, NULL, PPF_None); - return MakeShareable(new FJsonValueString(StringValue)); + // Default to expect a string for everything else + if (Property->ImportText(*JsonValue->AsString(), OutValue, 0, NULL) == NULL) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable import property type %s from string value for property %s"), *Property->GetClass()->GetName(), *Property->GetNameCPP()); + return false; + } } - // invalid - return TSharedPtr(); + return true; } -bool FIFJsonSerializer::UStructToJsonAttributes(const UStruct* StructDefinition, const void* Struct, TMap< FString, TSharedPtr >& OutJsonAttributes) +bool FIFJsonSerializer::JsonValueToUProperty(TSharedPtr JsonValue, UProperty* Property, void* OutValue) { - int64 SerFlag = 0; - SerFlag |= CPF_SaveGame; + if (!JsonValue.IsValid()) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Invalid value JSON key")); + return false; + } + + bool bArrayOrSetProperty = Property->IsA() || Property->IsA(); + bool bJsonArray = JsonValue->Type == EJson::Array; - for (TFieldIterator It(StructDefinition); It; ++It) + if (!bJsonArray) { - UProperty* Property = *It; + if (bArrayOrSetProperty) + { + UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Attempted to import TArray from non-array JSON key")); + return false; + } - if (Property->HasAnyPropertyFlags(SerFlag)) + if (Property->ArrayDim != 1) { - FString VariableName = Property->GetName();// StandardizeCase(); - const void* Value = Property->ContainerPtrToValuePtr(Struct); + UE_LOG(LogJson, Warning, TEXT("Ignoring excess properties when deserializing %s"), *Property->GetName()); + } - // convert the property to a FJsonValue - TSharedPtr JsonValue = UPropertyToJsonValue(Property, Value); - if (JsonValue.IsValid()) - { - OutJsonAttributes.Add(VariableName, JsonValue); + return ConvertScalarJsonValueToUProperty(JsonValue, Property, OutValue); + } - //return false; - } - else + // In practice, the ArrayDim == 1 check ought to be redundant, since nested arrays of UPropertys are not supported + if (bArrayOrSetProperty && Property->ArrayDim == 1) + { + // Read into TArray + return ConvertScalarJsonValueToUProperty(JsonValue, Property, OutValue); + } + + // We're deserializing a JSON array + const auto& ArrayValue = JsonValue->AsArray(); + if (Property->ArrayDim < ArrayValue.Num()) + { + UE_LOG(LogJson, Warning, TEXT("Ignoring excess properties when deserializing %s"), *Property->GetName()); + } + + // Read into native array + int ItemsToRead = FMath::Clamp(ArrayValue.Num(), 0, Property->ArrayDim); + for (int Index = 0; Index != ItemsToRead; ++Index) + { + if (!ConvertScalarJsonValueToUProperty(ArrayValue[Index], Property, (char*)OutValue + Index * Property->ElementSize)) + { + return false; + } + } + return true; +} + +bool FIFJsonSerializer::JsonAttributesToUObject(const TMap< FString, TSharedPtr >& JsonAttributes, const UStruct* StructDefinition, void* OutStruct) +{ + // iterate over the struct properties + for (TFieldIterator PropIt(StructDefinition); PropIt; ++PropIt) + { + UProperty* Property = *PropIt; + FString PropertyName = Property->GetName(); + + // find a json value matching this property name + TSharedPtr JsonValue; + for (auto It = JsonAttributes.CreateConstIterator(); It; ++It) + { + // use case insensitive search sincd FName may change caseing strangely on us + if (PropertyName.Equals(It.Key(), ESearchCase::IgnoreCase)) { - UClass* PropClass = Property->GetClass(); - UE_LOG(LogJson, Error, TEXT("UStructToJsonObject - Unhandled property type '%s': %s"), *PropClass->GetName(), *Property->GetPathName()); + JsonValue = It.Value(); + break; } } - // set the value on the output object - + if (!JsonValue.IsValid() || JsonValue->IsNull()) + { + // we allow values to not be found since this mirrors the typical UObject mantra that all the fields are optional when deserializing + continue; + } + + void* Value = Property->ContainerPtrToValuePtr(OutStruct); + if (!JsonValueToUProperty(JsonValue, Property, Value)) + { + UE_LOG(LogJson, Error, TEXT("JsonObjectToUStruct - Unable to parse %s.%s from JSON"), *StructDefinition->GetName(), *PropertyName); + return false; + } } return true; } -bool FIFJsonSerializer::UObjectToJsonObject(const UStruct* StructDefinition, const void* Struct, TSharedRef OutJsonObject) +bool FIFJsonSerializer::JsonObjectToUStruct(const TSharedRef& JsonObject, const UStruct* StructDefinition, void* OutStruct) { - OutJsonObject->Values.Add(FString("objectClass"), MakeShareable(new FJsonValueString(StructDefinition->GetPathName()))); - return UStructToJsonAttributes(StructDefinition, Struct, OutJsonObject->Values); + return JsonAttributesToUObject(JsonObject->Values, StructDefinition, OutStruct); } + void FIFJsonSerializer::JsonObjectToUObject(TSharedPtr Object, UObject*& OutObject, UObject* Outer) { FString objClassStr = Object->GetStringField("objectClass"); @@ -233,7 +414,6 @@ void FIFJsonSerializer::JsonObjectToUObject(TSharedPtr Object, UObj { UProperty* Property = *PropIt; FString PropertyName = Property->GetName(); - TSharedPtr JsonValue; for (auto It = Object->Values.CreateConstIterator(); It; ++It) { @@ -246,92 +426,16 @@ void FIFJsonSerializer::JsonObjectToUObject(TSharedPtr Object, UObj } if (!JsonValue.IsValid()) continue; - void* val = Property->ContainerPtrToValuePtr(OutObject); - if (UStructProperty* StructProp = Cast(Property)) - { - static const FName NAME_DateTime(TEXT("DateTime")); - static const FName NAME_Color(TEXT("Color")); - static const FName NAME_LinearColor(TEXT("LinearColor")); - if (JsonValue->Type == EJson::Object) - { - TSharedPtr Obj = JsonValue->AsObject(); - check(Obj.IsValid()); // should not fail if Type == EJson::Object - if (!FJsonObjectConverter::JsonObjectToUStruct(Obj.ToSharedRef(), StructProp->Struct, val, 0, 0)) - { - UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - FJsonObjectConverter::JsonObjectToUStruct failed for property %s"), *Property->GetNameCPP()); - continue; - } - } - else if (JsonValue->Type == EJson::String && StructProp->Struct->GetFName() == NAME_LinearColor) - { - FLinearColor& ColorOut = *(FLinearColor*)val; - FString ColorString = JsonValue->AsString(); - - FColor IntermediateColor; - IntermediateColor = FColor::FromHex(ColorString); - ColorOut = IntermediateColor; - } - else if (JsonValue->Type == EJson::String && StructProp->Struct->GetFName() == NAME_Color) - { - FColor& ColorOut = *(FColor*)val; - FString ColorString = JsonValue->AsString(); - - ColorOut = FColor::FromHex(ColorString); - } - else if (JsonValue->Type == EJson::String && StructProp->Struct->GetFName() == NAME_DateTime) - { - FString DateString = JsonValue->AsString(); - FDateTime& DateTimeOut = *(FDateTime*)val; - if (DateString == TEXT("min")) - { - // min representable value for our date struct. Actual date may vary by platform (this is used for sorting) - DateTimeOut = FDateTime::MinValue(); - } - else if (DateString == TEXT("max")) - { - // max representable value for our date struct. Actual date may vary by platform (this is used for sorting) - DateTimeOut = FDateTime::MaxValue(); - } - else if (DateString == TEXT("now")) - { - // this value's not really meaningful from json serialization (since we don't know timezone) but handle it anyway since we're handling the other keywords - DateTimeOut = FDateTime::UtcNow(); - } - else if (FDateTime::ParseIso8601(*DateString, DateTimeOut)) - { - // ok - } - else if (FDateTime::Parse(DateString, DateTimeOut)) - { - // ok - } - else - { - UE_LOG(LogJson, Error, TEXT("JsonValueToUProperty - Unable to import FDateTime for property %s"), *Property->GetNameCPP()); - continue; - } - } - } - else if (USoftClassProperty* SofftClassProp = Cast(Property)) - { - - FString dupa; - JsonValue->TryGetString(dupa); - FSoftClassPath classPath(dupa); - - UClass* dupaCls = Cast(path.TryLoad()); - SofftClassProp->SetMetaClass(dupaCls); - } - else if (UObjectProperty* ObjectProp = Cast(Property)) + if(UObjectProperty* ObjectProp = Cast(Property)) { const TSharedPtr* Obj; JsonValue->TryGetObject(Obj); - + if (Obj) { TSharedPtr Objj = *Obj; - + //TSharedPtr itemField = Objj->GetObjectField("item"); FString objClassStr2 = Objj->GetStringField("objectClass"); if (objClassStr2.Len() > 0) @@ -344,6 +448,19 @@ void FIFJsonSerializer::JsonObjectToUObject(TSharedPtr Object, UObj } } } + else if(UStructProperty* StructProp = Cast(Property)) + { + void* Value = StructProp->ContainerPtrToValuePtr(OutObject); + if (!JsonValue->AsObject()) + continue; + + JsonAttributesToUObject(JsonValue->AsObject()->Values, StructProp->Struct, Value); + } + else + { + void* Value = Property->ContainerPtrToValuePtr(OutObject); + ConvertScalarJsonValueToUProperty(JsonValue, Property, Value); + } } } } diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index b5b6e5a..f01c577 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -233,5 +233,10 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent void ClientSendJsonData_Implementation(const FString& Data); protected: - TSharedPtr SendToBackend(FIFItemData* Item); + void AddItem(TSoftClassPtr InItem, uint8 ItemIndex); + TSharedPtr ItemToJson(FIFItemData* Item); + FString JsonItemToString(TSharedPtr Object); + void SendToBackend(TSharedPtr JsonObj, int32 Idx); + + FIFItemData JsonToItem(const FString& JsonString); }; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 437267a..96f1907 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -36,6 +36,8 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + virtual void OnServerItemLoaded() {}; + /* Called after item has been added to inventory. */ @@ -100,7 +102,6 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject virtual void PreItemLoad() {}; virtual void PostItemLoad() {}; - virtual TSharedPtr SaveToJson() { return nullptr; } static UIFItemBase* LoadFromJSON() { return nullptr; } }; diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h index 8cd0d24..26cc3ff 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFTypes.h @@ -39,11 +39,11 @@ struct INVENTORYFRAMEWORK_API FIFSlotAcceptedClasses struct INVENTORYFRAMEWORK_API FIFJsonSerializer { - static TSharedPtr ConvertScalarUPropertyToJsonValue(UProperty* Property, const void* Value); - static bool UObjectToJsonObject(const UStruct* StructDefinition, const void* Struct, TSharedRef OutJsonObject); - static bool UStructToJsonAttributes(const UStruct* StructDefinition, const void* Struct, TMap< FString, TSharedPtr >& OutJsonAttributes); - + static bool ConvertScalarJsonValueToUProperty(TSharedPtr JsonValue, UProperty* Property, void* OutValue); + static bool JsonObjectToUStruct(const TSharedRef& JsonObject, const UStruct* StructDefinition, void* OutStruct); + static bool JsonValueToUProperty(TSharedPtr JsonValue, UProperty* Property, void* OutValue); static void JsonObjectToUObject(TSharedPtr Object, UObject*& OutObject, UObject* Outer); + static bool JsonAttributesToUObject(const TMap< FString, TSharedPtr >& JsonAttributes, const UStruct* StructDefinition, void* OutStruct); }; diff --git a/Plugins/JsonUObject/JsonUObject.uplugin b/Plugins/JsonUObject/JsonUObject.uplugin new file mode 100644 index 0000000..312d1d7 --- /dev/null +++ b/Plugins/JsonUObject/JsonUObject.uplugin @@ -0,0 +1,23 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "JsonUObject", + "Description": "Serialize UObject to Json.", + "Category": "Other", + "CreatedBy": "", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "JsonUObject", + "Type": "Runtime", + "LoadingPhase": "Default" + } + ] +} \ No newline at end of file diff --git a/Plugins/JsonUObject/Source/JsonUObject/JsonUObject.Build.cs b/Plugins/JsonUObject/Source/JsonUObject/JsonUObject.Build.cs new file mode 100644 index 0000000..849cd84 --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/JsonUObject.Build.cs @@ -0,0 +1,49 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class JsonUObject : ModuleRules +{ + public JsonUObject(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PrivateIncludePaths.AddRange( + new string[] { + "JsonUObject/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + "Json", + "JsonUtilities" + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUODeserialize.cpp b/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUODeserialize.cpp new file mode 100644 index 0000000..450959f --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUODeserialize.cpp @@ -0,0 +1,11 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "JsonUODeserialize.h" + +JsonUODeserialize::JsonUODeserialize() +{ +} + +JsonUODeserialize::~JsonUODeserialize() +{ +} diff --git a/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUOSerialize.cpp b/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUOSerialize.cpp new file mode 100644 index 0000000..28851ca --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUOSerialize.cpp @@ -0,0 +1,219 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "JsonUOSerialize.h" +#include "JsonObjectConverter.h" + +bool FJsonUOSerialize::UObjectToJsonObject(const UStruct* StructDefinition, const void* Struct, TSharedRef OutJsonObject) +{ + OutJsonObject->Values.Add(FString("objectClass"), MakeShareable(new FJsonValueString(StructDefinition->GetPathName()))); + return UStructToJsonAttributes(StructDefinition, Struct, OutJsonObject->Values); +} + +TSharedPtr FJsonUOSerialize::ConvertScalarUPropertyToJsonValue(UProperty* Property, const void* Value) +{ + // See if there's a custom export callback first, so it can override default behavior + + + if (UEnumProperty* EnumProperty = Cast(Property)) + { + // export enums as strings + UEnum* EnumDef = EnumProperty->GetEnum(); + FString StringValue = EnumDef->GetNameStringByValue(EnumProperty->GetUnderlyingProperty()->GetSignedIntPropertyValue(Value)); + return MakeShareable(new FJsonValueString(StringValue)); + } + else if (UNumericProperty *NumericProperty = Cast(Property)) + { + // see if it's an enum + UEnum* EnumDef = NumericProperty->GetIntPropertyEnum(); + if (EnumDef != NULL) + { + // export enums as strings + FString StringValue = EnumDef->GetNameStringByValue(NumericProperty->GetSignedIntPropertyValue(Value)); + return MakeShareable(new FJsonValueString(StringValue)); + } + + // We want to export numbers as numbers + if (NumericProperty->IsFloatingPoint()) + { + return MakeShareable(new FJsonValueNumber(NumericProperty->GetFloatingPointPropertyValue(Value))); + } + else if (NumericProperty->IsInteger()) + { + return MakeShareable(new FJsonValueNumber(NumericProperty->GetSignedIntPropertyValue(Value))); + } + + // fall through to default + } + else if (UBoolProperty *BoolProperty = Cast(Property)) + { + // Export bools as bools + return MakeShareable(new FJsonValueBoolean(BoolProperty->GetPropertyValue(Value))); + } + else if (UStrProperty *StringProperty = Cast(Property)) + { + return MakeShareable(new FJsonValueString(StringProperty->GetPropertyValue(Value))); + } + else if (UTextProperty *TextProperty = Cast(Property)) + { + return MakeShareable(new FJsonValueString(TextProperty->GetPropertyValue(Value).ToString())); + } + else if (UArrayProperty *ArrayProperty = Cast(Property)) + { + TArray< TSharedPtr > Out; + FScriptArrayHelper Helper(ArrayProperty, Value); + for (int32 i = 0, n = Helper.Num(); i Elem = UPropertyToJsonValue(ArrayProperty->Inner, Helper.GetRawPtr(i)); + if (Elem.IsValid()) + { + // add to the array + Out.Push(Elem); + } + } + return MakeShareable(new FJsonValueArray(Out)); + } + else if (USetProperty* SetProperty = Cast(Property)) + { + TArray< TSharedPtr > Out; + FScriptSetHelper Helper(SetProperty, Value); + for (int32 i = 0, n = Helper.Num(); n; ++i) + { + if (Helper.IsValidIndex(i)) + { + TSharedPtr Elem = UPropertyToJsonValue(SetProperty->ElementProp, Helper.GetElementPtr(i)); + if (Elem.IsValid()) + { + // add to the array + Out.Push(Elem); + } + + --n; + } + } + return MakeShareable(new FJsonValueArray(Out)); + } + else if (UMapProperty* MapProperty = Cast(Property)) + { + TSharedRef Out = MakeShareable(new FJsonObject()); + + FScriptMapHelper Helper(MapProperty, Value); + for (int32 i = 0, n = Helper.Num(); n; ++i) + { + if (Helper.IsValidIndex(i)) + { + TSharedPtr KeyElement = UPropertyToJsonValue(MapProperty->KeyProp, Helper.GetKeyPtr(i)); + TSharedPtr ValueElement = UPropertyToJsonValue(MapProperty->ValueProp, Helper.GetValuePtr(i)); + if (KeyElement.IsValid() && ValueElement.IsValid()) + { + FString KeyString = KeyElement->AsString(); + if (KeyString.IsEmpty()) + { + MapProperty->KeyProp->ExportTextItem(KeyString, Helper.GetKeyPtr(i), nullptr, nullptr, 0); + if (KeyString.IsEmpty()) + { + UE_LOG(LogJson, Error, TEXT("Unable to convert key to string for property %s."), *MapProperty->GetName()) + KeyString = FString::Printf(TEXT("Unparsed Key %d"), i); + } + } + + Out->SetField(KeyString, ValueElement); + } + + --n; + } + } + + return MakeShareable(new FJsonValueObject(Out)); + } + else if (UObjectProperty* ObjectProperty = Cast(Property)) + { + TSharedRef Out = MakeShareable(new FJsonObject()); + + UObject* Object = ObjectProperty->GetObjectPropertyValue(Value); + if (Object) + { + UClass* cls = Object->GetClass(); + + if (UObjectToJsonObject(cls, Object, Out)) + { + return MakeShareable(new FJsonValueObject(Out)); + } + } + } + else if (UStructProperty *StructProperty = Cast(Property)) + { + UScriptStruct::ICppStructOps* TheCppStructOps = StructProperty->Struct->GetCppStructOps(); + // Intentionally exclude the JSON Object wrapper, which specifically needs to export JSON in an object representation instead of a string + if (StructProperty->Struct != FJsonObjectWrapper::StaticStruct() && TheCppStructOps && TheCppStructOps->HasExportTextItem()) + { + FString OutValueStr; + TheCppStructOps->ExportTextItem(OutValueStr, Value, nullptr, nullptr, PPF_None, nullptr); + return MakeShareable(new FJsonValueString(OutValueStr)); + } + + TSharedRef Out = MakeShareable(new FJsonObject()); + if (UObjectToJsonObject(StructProperty->Struct, Value, Out)) + { + return MakeShareable(new FJsonValueObject(Out)); + } + // fall through to default + } + else + { + // Default to export as string for everything else + FString StringValue; + Property->ExportTextItem(StringValue, Value, NULL, NULL, PPF_None); + return MakeShareable(new FJsonValueString(StringValue)); + } + + // invalid + return TSharedPtr(); +} + +TSharedPtr FJsonUOSerialize::UPropertyToJsonValue(UProperty* Property, const void* Value) +{ + if (Property->ArrayDim == 1) + { + return ConvertScalarUPropertyToJsonValue(Property, Value); + } + + TArray< TSharedPtr > Array; + for (int Index = 0; Index != Property->ArrayDim; ++Index) + { + Array.Add(ConvertScalarUPropertyToJsonValue(Property, (char*)Value + Index * Property->ElementSize)); + } + return MakeShareable(new FJsonValueArray(Array)); +} + +bool FJsonUOSerialize::UStructToJsonAttributes(const UStruct* StructDefinition, const void* Struct, TMap< FString, TSharedPtr >& OutJsonAttributes) +{ + int64 SerFlag = 0; + SerFlag |= CPF_SaveGame; + + for (TFieldIterator It(StructDefinition); It; ++It) + { + UProperty* Property = *It; + + if (Property->HasAnyPropertyFlags(SerFlag)) + { + FString VariableName = Property->GetName();// StandardizeCase(); + const void* Value = Property->ContainerPtrToValuePtr(Struct); + + // convert the property to a FJsonValue + TSharedPtr JsonValue = UPropertyToJsonValue(Property, Value); + if (JsonValue.IsValid()) + { + OutJsonAttributes.Add(VariableName, JsonValue); + + //return false; + } + else + { + UClass* PropClass = Property->GetClass(); + UE_LOG(LogJson, Error, TEXT("UStructToJsonObject - Unhandled property type '%s': %s"), *PropClass->GetName(), *Property->GetPathName()); + } + } + } + + return true; +} \ No newline at end of file diff --git a/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUObject.cpp b/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUObject.cpp new file mode 100644 index 0000000..36e12d0 --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/Private/JsonUObject.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "JsonUObject.h" + +#define LOCTEXT_NAMESPACE "FJsonUObjectModule" + +void FJsonUObjectModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FJsonUObjectModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FJsonUObjectModule, JsonUObject) \ No newline at end of file diff --git a/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUODeserialize.h b/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUODeserialize.h new file mode 100644 index 0000000..30f1800 --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUODeserialize.h @@ -0,0 +1,15 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" + +/** + * + */ +class JSONUOBJECT_API JsonUODeserialize +{ +public: + JsonUODeserialize(); + ~JsonUODeserialize(); +}; diff --git a/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUOSerialize.h b/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUOSerialize.h new file mode 100644 index 0000000..b5da09a --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUOSerialize.h @@ -0,0 +1,25 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" + +#include "Json.h" +#include "Policies/CondensedJsonPrintPolicy.h" +#include "Serialization/JsonTypes.h" +#include "Serialization/JsonReader.h" +#include "Policies/PrettyJsonPrintPolicy.h" +#include "Serialization/JsonSerializer.h" + +/** + * + */ +class JSONUOBJECT_API FJsonUOSerialize +{ +public: + static bool UObjectToJsonObject(const UStruct* StructDefinition, const void* Struct, TSharedRef OutJsonObject); +private: + static TSharedPtr ConvertScalarUPropertyToJsonValue(UProperty* Property, const void* Value); + static TSharedPtr UPropertyToJsonValue(UProperty* Property, const void* Value); + static bool UStructToJsonAttributes(const UStruct* StructDefinition, const void* Struct, TMap< FString, TSharedPtr >& OutJsonAttributes); +}; diff --git a/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUObject.h b/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUObject.h new file mode 100644 index 0000000..9589ff7 --- /dev/null +++ b/Plugins/JsonUObject/Source/JsonUObject/Public/JsonUObject.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FJsonUObjectModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 8aca1ef..42b5dee 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -32,6 +32,7 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "ActorSequence", "AbilityManager", "DraggableWindow", + "JsonUObject", "InventoryFramework", "InventoryFrameworkUI" }); diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index c47abb4..5f18d31 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -22,13 +22,12 @@ void UARItemWeapon::SetAbility(class UARWeaponAbilityBase* InAbility) { AbilityInstance = InAbility; AbilityInstance->SetWeaponItem(this); - if (Attributes) + + if (AbilityInstance) { - if (AbilityInstance) - { - AbilityInstance->GetAttributes()->CopyFromOtherAttributes(Attributes); - } + AbilityInstance->GetAttributes()->CopyFromStruct(FARGunAttributesItem::StaticStruct(), &GeneratedAttributes); } + } void UARItemWeapon::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade) { @@ -68,27 +67,36 @@ UARMagazineUpgradeItem* UARItemWeapon::RemoveMagazineUpgrade() return MagazineModification; } -void UARItemWeapon::SpawnAbility() +bool UARItemWeapon::SpawnAbility() { - UIFInventoryComponent* InventoryComp = Cast(GetOuter()); - if (!InventoryComp) - return; - - AARPlayerController* PC = Cast(InventoryComp->GetOwner()); - if (!PC) - return; - - AARCharacter* Character = Cast(PC->GetPawn()); + bool bSpawned = false; + + AARCharacter* Character = nullptr; + if (UIFInventoryComponent* InventoryComp = Cast(GetOuter())) + { + AARPlayerController* PC = Cast(InventoryComp->GetOwner()); + if (!PC) + return bSpawned; + Character = Cast(PC->GetPawn()); + } + else if(UIFEquipmentComponent* EquipComp = Cast(GetOuter())) + { + Character = Cast(EquipComp->GetOwner()); + } + if (!Character) - return; + return bSpawned; TSubclassOf ABClass = Ability.LoadSynchronous(); if (ABClass) { AbilityInstance = NewObject(Character, ABClass); - AbilityInstance->GetAttributes()->CopyFromOtherAttributes(Attributes); + AbilityInstance->GetAttributes()->CopyFromStruct(FARGunAttributesItem::StaticStruct(), &GeneratedAttributes); + bSpawned = true; } + + return bSpawned; } void UARItemWeapon::OnItemAdded(uint8 LocalIndex) @@ -133,20 +141,16 @@ void UARItemWeapon::OnServerItemRemovedEquipment(uint8 LocalIndex) void UARItemWeapon::PostItemLoad() { - + if (SpawnAbility()) + { + AbilityInstance->GetAttributes()->CopyFromStruct(FARGunAttributesItem::StaticStruct(), &GeneratedAttributes); + if (MagazineModification) + { + AbilityInstance->AddMagazineUpgrade(MagazineModification); + } + } } -TSharedPtr UARItemWeapon::SaveToJson() -{ - typedef TJsonWriter< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriter; - typedef TJsonWriterFactory< TCHAR, TPrettyJsonPrintPolicy > FPrettyJsonStringWriterFactory; - - TSharedPtr UObj = MakeShareable(new FJsonObject()); - - FIFJsonSerializer::UObjectToJsonObject(GetClass(), this, UObj.ToSharedRef()); - - return UObj; -} TArray UARItemWeapon::GetTooltipData() { TArray Data; diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp index 0d5dc52..52295cc 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp @@ -2,7 +2,10 @@ #include "ARWeaponAbilityBase.h" #include "Effects/GABlueprintLibrary.h" + #include "Weapons/ARItemWeapon.h" +#include "Weapons/ARMagazineUpgradeItem.h" + #include "ARCharacter.h" #include "ARWeaponBase.h" @@ -74,7 +77,10 @@ void UARWeaponAbilityBase::ReloadWeapon() { } - +void UARWeaponAbilityBase::AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade) +{ + AddMagazineUpgrade(InMagazineUpgrade->UpgradeEffect, InMagazineUpgrade->MagazineUpgradeValue); +} void UARWeaponAbilityBase::AddMagazineUpgrade(TSubclassOf InMagazineUpgrade, float UpgradeValue) { MagazineUpgradeProperty = InMagazineUpgrade; diff --git a/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h index e1e204b..c82f201 100644 --- a/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h +++ b/Source/ActionRPGGame/Public/Attributes/ARGunAttributes.h @@ -6,6 +6,33 @@ #include "Attributes/GAAttributesBase.h" #include "ARGunAttributes.generated.h" + +/* + Mirror of Attribute Object to be used inside Items. +*/ +USTRUCT() +struct ACTIONRPGGAME_API FARGunAttributesItem +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase BaseDamage; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase CritChance; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase Magazine; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase RateOfFire; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase ReloadSpeed; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase HorizontalStability; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase VerticalStability; + UPROPERTY(EditAnywhere, SaveGame, Category = "Base") + FAFAttributeBase Spread; +}; + /** * 1. Register FAFReplicationHandle with attribute change. * 2. If handle is valid then attribute change is also valid (for attribute prediction) diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index 6958271..e3cdb1b 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -26,17 +26,14 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase public: UPROPERTY(EditAnywhere, Category = "Ability") TSoftClassPtr Ability; - + UPROPERTY(EditAnywhere, SaveGame, Category = "Ability") + FARGunAttributesItem GeneratedAttributes; + UPROPERTY(EditAnywhere, Category = "Visual") TSoftClassPtr Weapon; - /* - Values from these attributes will be copied to ability, after ability is instanced. - It's here to allow random generation and easily store that information in Database instead of storing ability. - */ - UPROPERTY(EditAnywhere, SaveGame, Instanced, Category = "Attributes") - class UARGunAttributes* Attributes; + UPROPERTY(EditAnywhere, Category = "Transforms") FVector HolsteredPosition; @@ -48,7 +45,7 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(EditAnywhere, Category = "Transforms") FRotator EquipedRotation; - UPROPERTY(BlueprintReadOnly, SaveGame, Category = "Ability") + UPROPERTY(BlueprintReadOnly, Transient, Category = "Ability") UARWeaponAbilityBase* AbilityInstance; UPROPERTY(BlueprintReadOnly, SaveGame, Category = "Ability") @@ -64,7 +61,7 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UARMagazineUpgradeItem* RemoveMagazineUpgrade(); - void SpawnAbility(); + bool SpawnAbility(); virtual void OnItemAdded(uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; @@ -82,7 +79,6 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) override; virtual void PostItemLoad(); - virtual TSharedPtr SaveToJson() override; virtual TArray GetTooltipData() override; diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h index aeeddff..4ab038a 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponAbilityBase.h @@ -117,6 +117,7 @@ class ACTIONRPGGAME_API UARWeaponAbilityBase : public UARAbilityBase UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Weapon") void ReloadWeapon(); + void AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade); void AddMagazineUpgrade(TSubclassOf InMagazineUpgrade, float UpgradeValue); void RemoveMagazineUpgrade(); protected: From 702fdcb48cd203c29f4e29013cefdf8d658fc6fe Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 7 May 2018 00:11:04 +0200 Subject: [PATCH 168/187] working on items --- .../Private/IFInventoryComponent.cpp | 13 ++++---- .../Public/IFInventoryComponent.h | 4 +-- .../InventoryFramework/Public/IFItemBase.h | 7 +++-- .../Private/Weapons/ARItemWeapon.cpp | 30 +++++++++++-------- .../Public/Weapons/ARItemWeapon.h | 6 +++- .../Public/Weapons/ARMagazineUpgradeItem.h | 3 ++ 6 files changed, 41 insertions(+), 22 deletions(-) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 8010b27..005ba80 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -346,21 +346,22 @@ void UIFInventoryComponent::RemoveItem(uint8 InIndex) return; } //remove from backend + OnItemRemoved(InventoryItems[InIndex].Item, InIndex); if (InventoryItems[InIndex].Item) InventoryItems[InIndex].Item->MarkPendingKill(); InventoryItems[InIndex].Item = nullptr; - OnServerItemRemoved(InIndex); ClientRemoveItem(InIndex); } void UIFInventoryComponent::ServerRemoveItem_Implementation(uint8 InIndex) { + OnServerItemRemoved(InventoryItems[InIndex].Item, InIndex); InventoryItems[InIndex].Item->OnServerItemRemoved(InIndex); if (InventoryItems[InIndex].Item) InventoryItems[InIndex].Item->MarkPendingKill(); InventoryItems[InIndex].Item = nullptr; - OnServerItemRemoved(InIndex); + ClientRemoveItem(InIndex); } bool UIFInventoryComponent::ServerRemoveItem_Validate(uint8 InIndex) @@ -370,11 +371,12 @@ bool UIFInventoryComponent::ServerRemoveItem_Validate(uint8 InIndex) void UIFInventoryComponent::ClientRemoveItem_Implementation(uint8 InIndex) { InventoryItems[InIndex].Item->OnItemRemoved(InIndex); + OnItemRemoved(InventoryItems[InIndex].Item, InIndex); if (InventoryItems[InIndex].Item) InventoryItems[InIndex].Item->MarkPendingKill(); InventoryItems[InIndex].Item = nullptr; - OnItemRemoved(InIndex); + } void UIFInventoryComponent::OnItemLoadedFreeSlot(TSoftClassPtr InItem) { @@ -399,9 +401,9 @@ void UIFInventoryComponent::OnItemLoaded(TSoftClassPtr InItem void UIFInventoryComponent::ClientSendJsonData_Implementation(const FString& Data) { FIFItemData Item = JsonToItem(Data); + Item.Item->ClientPostItemDeserializeFromJson(); if (Item.Item) { - Item.Item->PostItemLoad(); Item.Item->OnItemAdded(Item.Index); InventoryItems[Item.Index] = Item; @@ -445,6 +447,7 @@ TSharedPtr UIFInventoryComponent::ItemToJson(FIFItemData* Item) TSharedPtr UObj = MakeShareable(new FJsonObject()); if (Item->Item) { + Item->Item->PreItemSerializeToJson(); FJsonUOSerialize::UObjectToJsonObject(Item->Item->GetClass(), Item->Item, UObj.ToSharedRef()); //UObj = Item->Item->SaveToJson(); } @@ -490,6 +493,6 @@ FIFItemData UIFInventoryComponent::JsonToItem(const FString& JsonString) FIFItemData Item; Item.Index = idx; Item.Item = Cast(OutObj); - + return Item; } \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index f01c577..2446e71 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -202,12 +202,12 @@ class INVENTORYFRAMEWORK_API UIFInventoryComponent : public UActorComponent virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; - virtual void OnItemRemoved(uint8 LocalIndex) {}; + virtual void OnItemRemoved(UIFItemBase* Item, uint8 LocalIndex) {}; //these function are called on server. virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) {}; virtual void OnServerItemChanged(UIFItemBase* Item, uint8 LocalIndex) {}; - virtual void OnServerItemRemoved(uint8 LocalIndex) {}; + virtual void OnServerItemRemoved(UIFItemBase* Item, uint8 LocalIndex) {}; void RemoveItem(uint8 InIndex); UFUNCTION(Server, Reliable, WithValidation) diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index 96f1907..d5c134c 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -36,6 +36,9 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject bool CallRemoteFunction(UFunction* Function, void* Parameters, FOutParmRec* OutParms, FFrame* Stack) override; + /* + Called just fater NewObject<> On server or in standalone. + */ virtual void OnServerItemLoaded() {}; /* @@ -98,10 +101,10 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject */ virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) {}; - + virtual void PreItemSerializeToJson() {}; virtual void PreItemLoad() {}; - virtual void PostItemLoad() {}; + virtual void ClientPostItemDeserializeFromJson() {}; static UIFItemBase* LoadFromJSON() { return nullptr; } }; diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index 5f18d31..da4d8f3 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -70,7 +70,10 @@ UARMagazineUpgradeItem* UARItemWeapon::RemoveMagazineUpgrade() bool UARItemWeapon::SpawnAbility() { bool bSpawned = false; - + + if (AbilityInstance) + return true; + AARCharacter* Character = nullptr; if (UIFInventoryComponent* InventoryComp = Cast(GetOuter())) { @@ -93,12 +96,24 @@ bool UARItemWeapon::SpawnAbility() { AbilityInstance = NewObject(Character, ABClass); AbilityInstance->GetAttributes()->CopyFromStruct(FARGunAttributesItem::StaticStruct(), &GeneratedAttributes); + if (MagazineModification) + { + AbilityInstance->AddMagazineUpgrade(MagazineModification); + } bSpawned = true; } return bSpawned; } - +void UARItemWeapon::OnServerItemLoaded() +{ + /* + 1. Generate Weapon Stats here. + 2. Add random perks (weapon) + 3. Add random attributes to give (Character). + 4. Add random effects to give (Character). + */ +} void UARItemWeapon::OnItemAdded(uint8 LocalIndex) { SpawnAbility(); @@ -120,7 +135,6 @@ void UARItemWeapon::OnServerItemRemoved(uint8 LocalIndex) void UARItemWeapon::OnItemAddedEquipment(uint8 LocalIndex) { - }; void UARItemWeapon::OnItemChangedEquipment(uint8 LocalIndex) { @@ -139,16 +153,8 @@ void UARItemWeapon::OnServerItemRemovedEquipment(uint8 LocalIndex) { }; -void UARItemWeapon::PostItemLoad() +void UARItemWeapon::ClientPostItemDeserializeFromJson() { - if (SpawnAbility()) - { - AbilityInstance->GetAttributes()->CopyFromStruct(FARGunAttributesItem::StaticStruct(), &GeneratedAttributes); - if (MagazineModification) - { - AbilityInstance->AddMagazineUpgrade(MagazineModification); - } - } } TArray UARItemWeapon::GetTooltipData() diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index e3cdb1b..cb8bc09 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -48,6 +48,8 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(BlueprintReadOnly, Transient, Category = "Ability") UARWeaponAbilityBase* AbilityInstance; + //possibly replace with struct containing identical fields. + //so it can be easier serialized and saved. UPROPERTY(BlueprintReadOnly, SaveGame, Category = "Ability") class UARMagazineUpgradeItem* MagazineModification; @@ -63,6 +65,8 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase bool SpawnAbility(); + virtual void OnServerItemLoaded() override; + virtual void OnItemAdded(uint8 LocalIndex) override; virtual void OnItemRemoved(uint8 LocalIndex) override; @@ -78,7 +82,7 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase virtual void OnServerItemChangedEquipment(uint8 LocalIndex) override; virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) override; - virtual void PostItemLoad(); + virtual void ClientPostItemDeserializeFromJson(); virtual TArray GetTooltipData() override; diff --git a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h index fe21cb6..1916758 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h +++ b/Source/ActionRPGGame/Public/Weapons/ARMagazineUpgradeItem.h @@ -20,6 +20,9 @@ class ACTIONRPGGAME_API UARMagazineUpgradeItem : public UARWeaponUpgradeItem */ UPROPERTY(EditAnywhere, SaveGame) float MagazineUpgradeValue; + + UPROPERTY(EditAnywhere) + EGAAttributeMod ModType; /* Effect template */ From fc17008864f1a8349c1b82e297e47890e01d01c0 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 7 May 2018 00:20:52 +0200 Subject: [PATCH 169/187] stub character equipment component --- .../Public/IFEquipmentComponent.h | 4 ++++ .../ARCharacterEquipmentComponent.cpp | 7 +++++++ .../Private/Weapons/ARItemWeapon.cpp | 4 ++++ .../Equipment/ARCharacterEquipmentComponent.h | 20 +++++++++++++++++++ 4 files changed, 35 insertions(+) create mode 100644 Source/ActionRPGGame/Private/Equipment/ARCharacterEquipmentComponent.cpp create mode 100644 Source/ActionRPGGame/Public/Equipment/ARCharacterEquipmentComponent.h diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h index 16989a0..86a3610 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h @@ -77,6 +77,10 @@ class INVENTORYFRAMEWORK_API UIFEquipmentComponent : public UActorComponent void ClientRemoveFromEquipment(uint8 EquipmentIndex); void ClientRemoveFromEquipment_Implementation(uint8 EquipmentIndex); + /* + Called on client, before request to server is send to add item to Equipment component. + Not called in standalone. + */ virtual void OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemAdded(UIFItemBase* Item, uint8 Index) {}; virtual void OnItemChanged(UIFItemBase* Item, uint8 Index) {}; diff --git a/Source/ActionRPGGame/Private/Equipment/ARCharacterEquipmentComponent.cpp b/Source/ActionRPGGame/Private/Equipment/ARCharacterEquipmentComponent.cpp new file mode 100644 index 0000000..d90b2ab --- /dev/null +++ b/Source/ActionRPGGame/Private/Equipment/ARCharacterEquipmentComponent.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARCharacterEquipmentComponent.h" + + + + diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index da4d8f3..4ebc06b 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -145,6 +145,10 @@ void UARItemWeapon::OnItemRemovedEquipment(uint8 LocalIndex) void UARItemWeapon::OnServerItemAddedEquipment(uint8 LocalIndex) { + UARWeaponInventoryComponent* WeaponComponent = Cast(GetOuter()); + if (!WeaponComponent) + return; + }; void UARItemWeapon::OnServerItemChangedEquipment(uint8 LocalIndex) { diff --git a/Source/ActionRPGGame/Public/Equipment/ARCharacterEquipmentComponent.h b/Source/ActionRPGGame/Public/Equipment/ARCharacterEquipmentComponent.h new file mode 100644 index 0000000..2679564 --- /dev/null +++ b/Source/ActionRPGGame/Public/Equipment/ARCharacterEquipmentComponent.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "IFEquipmentComponent.h" +#include "ARCharacterEquipmentComponent.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARCharacterEquipmentComponent : public UIFEquipmentComponent +{ + GENERATED_BODY() + + + + +}; From 807dd6995b25ad2cd25536233eefb77b9854573e Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 7 May 2018 21:59:11 +0200 Subject: [PATCH 170/187] added GameSparks integration --- Config/DefaultEngine.ini | 2 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 5 +- .../ActionRPGGame/Menu/ARLoginScreenView.cpp | 7 +++ Source/ActionRPGGame/Menu/ARLoginScreenView.h | 20 ++++++++ .../ActionRPGGame/Private/ARGameInstance.cpp | 45 +++++++++++++++++ Source/ActionRPGGame/Private/ARGameMode.cpp | 26 +++------- Source/ActionRPGGame/Public/ARGameInstance.h | 50 +++++++++++++++++++ 7 files changed, 135 insertions(+), 20 deletions(-) create mode 100644 Source/ActionRPGGame/Menu/ARLoginScreenView.cpp create mode 100644 Source/ActionRPGGame/Menu/ARLoginScreenView.h create mode 100644 Source/ActionRPGGame/Private/ARGameInstance.cpp create mode 100644 Source/ActionRPGGame/Public/ARGameInstance.h diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index b2f8a4a..042f2fa 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -13,6 +13,7 @@ GlobalDefaultGameMode=/Game/Prototypes/ProtGameMode.ProtGameMode_C GameDefaultMap=/Game/Maps/TestMap.TestMap ServerDefaultMap=/Game/Maps/TestMap.TestMap EditorStartupMap=/Game/Maps/TestMap.TestMap +GameInstanceClass=/Script/ActionRPGGame.ARGameInstance [/Script/Engine.RendererSettings] r.AllowStaticLighting=False @@ -180,4 +181,3 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 - diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 42b5dee..5e59711 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -34,7 +34,10 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "DraggableWindow", "JsonUObject", "InventoryFramework", - "InventoryFrameworkUI" + "InventoryFrameworkUI", + "GameSparks", + "OnlineSubsystem", + "OnlineSubsystemGameSparks" }); if (Target.Type == TargetRules.TargetType.Editor) { diff --git a/Source/ActionRPGGame/Menu/ARLoginScreenView.cpp b/Source/ActionRPGGame/Menu/ARLoginScreenView.cpp new file mode 100644 index 0000000..93dcdf1 --- /dev/null +++ b/Source/ActionRPGGame/Menu/ARLoginScreenView.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARLoginScreenView.h" + + + + diff --git a/Source/ActionRPGGame/Menu/ARLoginScreenView.h b/Source/ActionRPGGame/Menu/ARLoginScreenView.h new file mode 100644 index 0000000..d1006f2 --- /dev/null +++ b/Source/ActionRPGGame/Menu/ARLoginScreenView.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARLoginScreenView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARLoginScreenView : public UARUMGWidgetBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp new file mode 100644 index 0000000..7f11efd --- /dev/null +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -0,0 +1,45 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARGameInstance.h" + +UARGameInstance::UARGameInstance(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + GSObject = ObjectInitializer.CreateDefaultSubobject(this, TEXT("GSObject")); + GSMessageListener = ObjectInitializer.CreateDefaultSubobject(this, TEXT("GSMessageListener")); +} + + +void UARGameInstance::OnGameSparksAvailable(bool bAvailable) +{ + if (bAvailable) + { + GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Connected")); + + GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); + + GameSparks::Api::Requests::AuthenticationRequest authRequest(gs); + authRequest.SetUserName(""); + authRequest.SetPassword(""); + + authRequest.Send(AuthenticationRequest_Response); + } + +} + +//The response function to the Authentication Request +// Example response function +void UARGameInstance::AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse& response) +{ + GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, response.GetJSONString().c_str()); + //Check is response has no errors + if (!response.GetHasErrors()) { + GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Auth response successful")); + + GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); + GameSparks::Api::Requests::AccountDetailsRequest accDetRequest(gs); + //If no errors then send an accounts details request + accDetRequest.Send(); + + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp index 264ae10..806018a 100644 --- a/Source/ActionRPGGame/Private/ARGameMode.cpp +++ b/Source/ActionRPGGame/Private/ARGameMode.cpp @@ -6,9 +6,7 @@ #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "Abilities/ARAbilityBase.h" -//#include "IpConnec" -//#include "OnlineSubsystemUtils/IpConnection.h" -//#include "IPAddress.h" +#include "ARGameInstance.h" #include "SDraggableWindowWidget.h" AARGameMode::AARGameMode() { @@ -16,20 +14,12 @@ AARGameMode::AARGameMode() void AARGameMode::BeginPlay() { Super::BeginPlay(); - //if (GetNetMode() == ENetMode::NM_DedicatedServer) - { - if (UNetConnection* Conn = GetNetConnection()) - { - // UE_LOG(LogTemp, Warning, TEXT("Your message, %s \n"), *FString::FromInt(Conn->GetAddrAsInt())); - } - } - //TSharedPtr desktop = SNew(SDraggableDesktopWidget); - //GEngine->GameViewport->AddViewportWidgetContent(desktop.ToSharedRef()); + UARGameInstance* GSI = Cast(GetGameInstance()); - //TSharedPtr window = SNew(SDraggableWindowWidget); - //GEngine->GameViewport->AddViewportWidgetContent(window.ToSharedRef()); - //desktop->AddWindow(window); - //TSharedPtr window1 = SNew(SDraggableWindowWidget); - //GEngine->GameViewport->AddViewportWidgetContent(window1.ToSharedRef()); - //desktop->AddWindow(window1); + //Set the OnAvailable delegate + GSI->GetGSObject()->OnGameSparksAvailableDelegate.AddDynamic(GSI, &UARGameInstance::OnGameSparksAvailable); + //Disconnected the module just incase it's connected (Refresh) + GSI->GetGSObject()->Disconnect(); + //Connect module + GSI->GetGSObject()->Connect("key", "secret"); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/ARGameInstance.h b/Source/ActionRPGGame/Public/ARGameInstance.h new file mode 100644 index 0000000..1cce17e --- /dev/null +++ b/Source/ActionRPGGame/Public/ARGameInstance.h @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Engine/GameInstance.h" + +#include +#include +#include +#include "GameSparksModule.h" +#include "GameSparks/Private/GameSparksObject.h" +#include "GameSparks/Private/GSMessageListenersObject.h" + + +#include "ARGameInstance.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARGameInstance : public UGameInstance +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "GSObjects") + UGameSparksObject* GSObject; + UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "GSObjects") + UGSMessageListenersObject* GSMessageListener; + +public: + UARGameInstance(const FObjectInitializer& ObjectInitializer); + + inline UGameSparksObject* GetGSObject() + { + return GSObject; + } + + inline UGSMessageListenersObject* GetGSMessageListener() + { + return GSMessageListener; + } + + //Function used to determine what happens if GameSparks connects or fails to (Needs to be UFUNCTION) + UFUNCTION() + void OnGameSparksAvailable(bool bAvailable); + + //Add the response function to the Authentication request + static void AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse&); +}; From bcb6ac223f7d25d44926ace5544708900691f4b4 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 9 May 2018 21:25:27 +0200 Subject: [PATCH 171/187] fixed compilation errors/warrning for Linux server, windows server and windows client, added base menu widgets, moved secret/key into config file --- .gitignore | 1 + ActionRPGGame.uproject | 38 ++++--- Config/DefaultEngine.ini | 3 +- .../Private/Effects/GAGameEffect.cpp | 16 +-- .../Public/Effects/GAGameEffect.h | 22 ++-- .../Public/IFInventoryComponent.h | 1 + .../InventoryFramework/Public/IFItemBase.h | 24 ++--- .../Public/AnimNode_BlendLocomotionFour.cpp | 2 +- Source/ActionRPGGame/Private/ARCharacter.cpp | 4 +- .../ActionRPGGame/Private/ARGameInstance.cpp | 101 ++++++++++++++---- Source/ActionRPGGame/Private/ARGameMode.cpp | 8 -- .../Private/ARMenuPlayerController.cpp | 7 ++ .../Private/ARPlayerController.cpp | 60 ----------- .../Menu/ARMainMenuView.cpp} | 2 +- .../Private/Menu/ARMenuGameMode.cpp | 7 ++ .../ActionRPGGame/Private/Menu/ARMenuHUD.cpp | 70 ++++++++++++ .../UI/HUD/AREnemyHealthBar.cpp | 0 .../UI/HUD/ARHUDCrosshair.cpp | 0 .../UI/HUD/ARHUDCrosshairInfo.cpp | 0 .../UI/HUD/ARHUDPlayerInfo.cpp | 0 .../Private/UI/Menu/ARLoginScreenView.cpp | 50 +++++++++ .../Private/Weapons/ARItemWeapon.cpp | 22 ++-- Source/ActionRPGGame/Public/ARGameInstance.h | 34 +++++- .../Public/ARMenuPlayerController.h | 20 ++++ .../ActionRPGGame/Public/ARPlayerController.h | 7 -- .../Menu/ARMainMenuView.h} | 6 +- .../Public/Menu/ARMenuGameMode.h | 20 ++++ Source/ActionRPGGame/Public/Menu/ARMenuHUD.h | 37 +++++++ .../UI/Inventory/ARInventoryScreenWidget.h | 2 +- .../Public/UI/Menu/ARLoginScreenView.h | 43 ++++++++ .../Public/Weapons/ARItemWeapon.h | 22 ++-- 31 files changed, 457 insertions(+), 172 deletions(-) create mode 100644 Source/ActionRPGGame/Private/ARMenuPlayerController.cpp rename Source/ActionRPGGame/{Menu/ARLoginScreenView.cpp => Private/Menu/ARMainMenuView.cpp} (73%) create mode 100644 Source/ActionRPGGame/Private/Menu/ARMenuGameMode.cpp create mode 100644 Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp rename Source/ActionRPGGame/{Public => Private}/UI/HUD/AREnemyHealthBar.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/HUD/ARHUDCrosshair.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/HUD/ARHUDCrosshairInfo.cpp (100%) rename Source/ActionRPGGame/{Public => Private}/UI/HUD/ARHUDPlayerInfo.cpp (100%) create mode 100644 Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp create mode 100644 Source/ActionRPGGame/Public/ARMenuPlayerController.h rename Source/ActionRPGGame/{Menu/ARLoginScreenView.h => Public/Menu/ARMainMenuView.h} (54%) create mode 100644 Source/ActionRPGGame/Public/Menu/ARMenuGameMode.h create mode 100644 Source/ActionRPGGame/Public/Menu/ARMenuHUD.h create mode 100644 Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h diff --git a/.gitignore b/.gitignore index 34cf27d..42f855e 100644 --- a/.gitignore +++ b/.gitignore @@ -266,3 +266,4 @@ Saved/ CodeBackup/States/GASAbilityStateCooldown.h *.bin *.pak +Config/DefaultARGame.ini \ No newline at end of file diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index e4b58e1..c74e0dd 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -179,14 +179,22 @@ "Name": "GLTFImporter", "Enabled": true }, - { - "Name": "SteamAudio", - "Enabled": true - }, - { - "Name": "ResonanceAudio", - "Enabled": false - }, + { + "Name": "SteamAudio", + "Enabled": true, + "BlacklistTargets": [ + "Server", + "Client" + ] + }, + { + "Name": "ResonanceAudio", + "Enabled": false, + "BlacklistTargets": [ + "Server", + "Client" + ] + }, { "Name": "CodeView", "Enabled": true @@ -200,11 +208,15 @@ "Enabled": true, "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" }, - { - "Name": "Substance", - "Enabled": true, - "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4" - }, + { + "Name": "Substance", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4", + "BlacklistTargets": [ + "Server", + "Client" + ] + }, { "Name": "LiveLink", "Enabled": true diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 042f2fa..5d06361 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -10,10 +10,11 @@ AppliedDefaultGraphicsPerformance=Maximum [/Script/EngineSettings.GameMapsSettings] GlobalDefaultGameMode=/Game/Prototypes/ProtGameMode.ProtGameMode_C -GameDefaultMap=/Game/Maps/TestMap.TestMap +GameDefaultMap=/Game/Maps/MenuMap.MenuMap ServerDefaultMap=/Game/Maps/TestMap.TestMap EditorStartupMap=/Game/Maps/TestMap.TestMap GameInstanceClass=/Script/ActionRPGGame.ARGameInstance +TransitionMap=/Game/Maps/TransitionMap.TransitionMap [/Script/Engine.RendererSettings] r.AllowStaticLighting=False diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp index 4df4cec..3657146 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp @@ -470,9 +470,9 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( { //Hack. We need a way store handles for conditional effects. FAFPropertytHandle PropertyNew(Effect.Effect); - FGAEffectHandle Handle; - Handle = UGABlueprintLibrary::ApplyEffect(PropertyNew - , Handle + FGAEffectHandle OtherHandle; + OtherHandle = UGABlueprintLibrary::ApplyEffect(PropertyNew + , OtherHandle , InContext.Target.Get() , InContext.Instigator.Get() , InContext.Causer.Get() @@ -541,8 +541,8 @@ void FGAEffectContainer::AddEffect( Effects.Add(InHandle); FObjectKey EffectKey(SpecClass); - TArray& EffectClass = EffectByClass.FindOrAdd(EffectKey); - EffectClass.Add(InHandle); + TArray& LocalEffectClass = EffectByClass.FindOrAdd(EffectKey); + LocalEffectClass.Add(InHandle); switch (Spec->EffectAggregation) { @@ -780,7 +780,7 @@ void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProper DurationTimer.ClearTimer(Effect->PeriodTimerHandle); APawn* Instigator = Context.Instigator.Get(); - UObject* Target = Context.Target.Get(); + UObject* ObjectTarget = Context.Target.Get(); FAFPredictionHandle PredHandle = PredictionByHandle[InHandle]; HandleByPrediction.Remove(PredHandle); @@ -793,8 +793,8 @@ void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProper TSet* Effects = EffectByAttribute.Find(Spec->AtributeModifier.Attribute); if (Effects) { - IAFAbilityInterface* Target = Context.TargetInterface; - Target->RemoveBonus(Attribute, InHandle, AttributeMod); + IAFAbilityInterface* IntTarget = Context.TargetInterface; + IntTarget->RemoveBonus(Attribute, InHandle, AttributeMod); Effects->Remove(InHandle); if (Effects->Num() == 0) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h index c6c834a..64be531 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h @@ -667,12 +667,12 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty UObject* Target , const FGAEffectHandle& InHandle , const FAFContextHandle& Context - , const FAFEffectSpecHandle& Spec) + , const FAFEffectSpecHandle& InSpec) { if (bInstant) { InstantContext = Context; - InstantEffectSpec = Spec; + InstantEffectSpec = InSpec; return; } if (HandleToTarget.Contains(InHandle)) @@ -683,7 +683,7 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty AddHandle(Target, InHandle); AddContext(InHandle, Context); - AddEffectSpec(InHandle, Spec); + AddEffectSpec(InHandle, InSpec); } void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) @@ -753,10 +753,10 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { return InstantEffectSpec; } - FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); - if (Spec) + FAFEffectSpecHandle* SpecLocal = EffectSpecs.Find(InHandle); + if (SpecLocal) { - return *Spec; + return *SpecLocal; } return InstantEffectSpec; } @@ -766,10 +766,10 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { return InstantEffectSpec; } - const FAFEffectSpecHandle* Spec = EffectSpecs.Find(InHandle); - if (Spec) + const FAFEffectSpecHandle* SpecLocal = EffectSpecs.Find(InHandle); + if (SpecLocal) { - return *Spec; + return *SpecLocal; } return InstantEffectSpec; } @@ -1038,8 +1038,8 @@ struct ABILITYFRAMEWORK_API FAFEffectParams FAFEffectParams() {}; FAFEffectParams(FAFPropertytHandle InProperty) - : bRecreated(false) - , Property(InProperty) + : Property(InProperty) + , bRecreated(false) {}; FGAEffectContext & GetContext() diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h index 2446e71..c9069f6 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFInventoryComponent.h @@ -6,6 +6,7 @@ #include "Components/ActorComponent.h" #include "IFTypes.h" +#include "IFItemBase.h" #include "IFInventoryComponent.generated.h" //NetIndex, LocalIndex diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h index d5c134c..09cb1ab 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemBase.h @@ -44,62 +44,62 @@ class INVENTORYFRAMEWORK_API UIFItemBase : public UObject /* Called after item has been added to inventory. */ - virtual void OnItemAdded(uint8 LocalIndex) {}; + virtual void OnItemAdded(uint8 InIndex) {}; /* Called when item changed slots within THE SAME inventory; */ - virtual void OnItemChanged(uint8 LocalIndex) {}; + virtual void OnItemChanged(uint8 InIndex) {}; /* Called after item has been removed from inventory; */ - virtual void OnItemRemoved(uint8 LocalIndex) {}; + virtual void OnItemRemoved(uint8 InIndex) {}; /* Called after item has been added to inventory. Called on server or in standalone game. */ - virtual void OnServerItemAdded(uint8 LocalIndex) {}; + virtual void OnServerItemAdded(uint8 InIndex) {}; /* Called when item changed slots within THE SAME inventory. Called on server or in standalone game. */ - virtual void OnServerItemChanged(uint8 LocalIndex) {}; + virtual void OnServerItemChanged(uint8 InIndex) {}; /* Called after item has been removed from inventory. Called on server or in standalone game. */ - virtual void OnServerItemRemoved(uint8 LocalIndex) {}; + virtual void OnServerItemRemoved(uint8 InIndex) {}; /* Called after item has been added to Equipment. */ - virtual void OnItemAddedEquipment(uint8 LocalIndex) {}; + virtual void OnItemAddedEquipment(uint8 InIndex) {}; /* Called when item changed slots within THE SAME Equipment; */ - virtual void OnItemChangedEquipment(uint8 LocalIndex) {}; + virtual void OnItemChangedEquipment(uint8 InIndex) {}; /* Called after item has been removed from Equipment; */ - virtual void OnItemRemovedEquipment(uint8 LocalIndex) {}; + virtual void OnItemRemovedEquipment(uint8 InIndex) {}; /* Called after item has been added to Equipment. Called on server or in standalone game. */ - virtual void OnServerItemAddedEquipment(uint8 LocalIndex) {}; + virtual void OnServerItemAddedEquipment(uint8 InIndex) {}; /* Called when item changed slots within THE SAME Equipment; Called on server or in standalone game. */ - virtual void OnServerItemChangedEquipment(uint8 LocalIndex) {}; + virtual void OnServerItemChangedEquipment(uint8 InIndex) {}; /* Called after item has been removed from Equipment; Called on server or in standalone game. */ - virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) {}; + virtual void OnServerItemRemovedEquipment(uint8 InIndex) {}; virtual void PreItemSerializeToJson() {}; virtual void PreItemLoad() {}; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp index 33f85b1..b8df83b 100644 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp @@ -259,7 +259,7 @@ void FAnimNode_BlendLocomotionFour::Update_AnyThread(const FAnimationUpdateConte } - switch (Dir) + switch (static_cast(Dir)) { case EFCardinalDirection::N: { diff --git a/Source/ActionRPGGame/Private/ARCharacter.cpp b/Source/ActionRPGGame/Private/ARCharacter.cpp index dbf8b5d..338e54b 100644 --- a/Source/ActionRPGGame/Private/ARCharacter.cpp +++ b/Source/ActionRPGGame/Private/ARCharacter.cpp @@ -381,8 +381,8 @@ void AARCharacter::Tick(float DeltaSeconds) bStopDistancePredicted = true; float CurVel = CurrentVelocity.SizeSquared(); float StopDistance = (CurVel / (4*CMC->GroundFriction *CMC->BrakingFrictionFactor * CMC->BrakingDecelerationWalking)); - FVector Forward = VelocityDirection; - FVector StopLocation = (Forward*StopDistance) + CharLocation; + FVector Forward2 = VelocityDirection; + FVector StopLocation = (Forward2*StopDistance) + CharLocation; //DrawDebugSphere(GetWorld(), StopLocation, 6, 8, FColor::Green, false, 2, 0, 2); } diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index 7f11efd..9bfa3f7 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -7,39 +7,98 @@ UARGameInstance::UARGameInstance(const FObjectInitializer& ObjectInitializer) { GSObject = ObjectInitializer.CreateDefaultSubobject(this, TEXT("GSObject")); GSMessageListener = ObjectInitializer.CreateDefaultSubobject(this, TEXT("GSMessageListener")); +#if WITH_EDITOR + bConnected = false; +#endif } void UARGameInstance::OnGameSparksAvailable(bool bAvailable) { - if (bAvailable) - { - GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Connected")); +#if WITH_EDITOR + bConnected = false; +#endif + OnConnectedToGameSparks.Broadcast(); +} + +//The response function to the Authentication Request +// Example response function +void UARGameInstance::AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse& response) +{ + +} - GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); +void UARGameInstance::AttemptLogin(const FString& UserName, const FString& Password) +{ + GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Connected")); - GameSparks::Api::Requests::AuthenticationRequest authRequest(gs); - authRequest.SetUserName(""); - authRequest.SetPassword(""); + GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); - authRequest.Send(AuthenticationRequest_Response); - } + GameSparks::Api::Requests::AuthenticationRequest authRequest(gs); + authRequest.SetUserName(TCHAR_TO_UTF8(*UserName)); + authRequest.SetPassword(TCHAR_TO_UTF8(*Password)); + + auto AuthRquestResponse = [&](GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse& response) + { + GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, response.GetJSONString().c_str()); + //Check is response has no errors + if (!response.GetHasErrors()) + { + OnLoginSuccess.Broadcast(); + GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Auth response successful")); + + GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); + GameSparks::Api::Requests::AccountDetailsRequest accDetRequest(gs); + //If no errors then send an accounts details request + accDetRequest.Send(); + } + else + { + OnLoginFailed.Broadcast(); + } + }; + authRequest.Send(AuthRquestResponse); + } -//The response function to the Authentication Request -// Example response function -void UARGameInstance::AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse& response) +void UARGameInstance::Init() { - GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, response.GetJSONString().c_str()); - //Check is response has no errors - if (!response.GetHasErrors()) { - GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Auth response successful")); + Super::Init(); +#if WITH_EDITOR + //editor hax so we don't attempt to connect twice. + if (!bConnected) +#endif + { + //Set the OnAvailable delegate + GetGSObject()->OnGameSparksAvailableDelegate.AddDynamic(this, &UARGameInstance::OnGameSparksAvailable); + //Disconnected the module just incase it's connected (Refresh) + GetGSObject()->Disconnect(); + //Connect module + GetGSObject()->Connect(GSKey, GSSecret); +#if WITH_EDITOR + bConnected = true; //it will be overriden in delegate anyway. +#endif + } +} +#if WITH_EDITOR - GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); - GameSparks::Api::Requests::AccountDetailsRequest accDetRequest(gs); - //If no errors then send an accounts details request - accDetRequest.Send(); +/* Called to actually start the game when doing Play/Simulate In Editor */ +FGameInstancePIEResult UARGameInstance::StartPlayInEditorGameInstance(ULocalPlayer* LocalPlayer, const FGameInstancePIEParameters& Params) +{ + + if (!bConnected) + { + //Set the OnAvailable delegate + GetGSObject()->OnGameSparksAvailableDelegate.AddDynamic(this, &UARGameInstance::OnGameSparksAvailable); + //Disconnected the module just incase it's connected (Refresh) + GetGSObject()->Disconnect(); + //Connect module + GetGSObject()->Connect(GSKey, GSSecret); + bConnected = true; //it will be overriden in delegate anyway. } -} \ No newline at end of file + return Super::StartPlayInEditorGameInstance(LocalPlayer, Params); +} + +#endif diff --git a/Source/ActionRPGGame/Private/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp index 806018a..579895b 100644 --- a/Source/ActionRPGGame/Private/ARGameMode.cpp +++ b/Source/ActionRPGGame/Private/ARGameMode.cpp @@ -14,12 +14,4 @@ AARGameMode::AARGameMode() void AARGameMode::BeginPlay() { Super::BeginPlay(); - UARGameInstance* GSI = Cast(GetGameInstance()); - - //Set the OnAvailable delegate - GSI->GetGSObject()->OnGameSparksAvailableDelegate.AddDynamic(GSI, &UARGameInstance::OnGameSparksAvailable); - //Disconnected the module just incase it's connected (Refresh) - GSI->GetGSObject()->Disconnect(); - //Connect module - GSI->GetGSObject()->Connect("key", "secret"); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARMenuPlayerController.cpp b/Source/ActionRPGGame/Private/ARMenuPlayerController.cpp new file mode 100644 index 0000000..6560a5d --- /dev/null +++ b/Source/ActionRPGGame/Private/ARMenuPlayerController.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARMenuPlayerController.h" + + + + diff --git a/Source/ActionRPGGame/Private/ARPlayerController.cpp b/Source/ActionRPGGame/Private/ARPlayerController.cpp index 1833727..8835c03 100644 --- a/Source/ActionRPGGame/Private/ARPlayerController.cpp +++ b/Source/ActionRPGGame/Private/ARPlayerController.cpp @@ -163,66 +163,6 @@ void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAb AbilityComp->SetAbilityToAction(InAbilityTag, Inputs, FAFOnAbilityReady()); } -#if WITH_EDITOR -/* Get Screen Percentage */ -static const auto CVarScreenPercentage = IConsoleManager::Get().FindTConsoleVariableDataFloat(TEXT("r.SCreenPercentage")); -#endif WITH_EDITOR - -float AARPlayerController::GetObjectScreenRadius(AActor* InActor) -{ - float ScreenRadius; - int32 Width, Height; - FVector Viewlocation; - FRotator ViewRotation; // Not Used, but required for Function call - float CamFOV = 90.0f; //TODO: Replace With Function that returns camera FOV -#if WITH_EDITOR - float ScreenPerc = CVarScreenPercentage->GetValueOnGameThread() / 100.0f; -#endif WITH_EDITOR - - /* Get the size of the viewport, and the player cameras location. */ - GetViewportSize(Width, Height); - GetPlayerViewPoint(Viewlocation, ViewRotation); - -#if WITH_EDITOR - /* Factor in Screen Percentage & Quality Settings */ - Width *= ScreenPerc; - Height *= ScreenPerc; -#endif WITH_EDITOR - - /* Easy Way To Return The Size, Create a vector and scale it. Alternative would be to use FMath::Max3 */ - float SRad = FVector2D(Width, Height).Size(); - - /* Get Object Bounds (R) */ - float BoundingRadius = InActor->GetRootComponent()->Bounds.SphereRadius; - float DistanceToObject = FVector(InActor->GetActorLocation() - Viewlocation).Size(); - - /* Get Projected Screen Radius */ - ScreenRadius = FMath::Atan(BoundingRadius / DistanceToObject); - ScreenRadius *= SRad / FMath::DegreesToRadians(CamFOV); - - return ScreenRadius; -} -void AARPlayerController::GetObjectBoundSphere(float Distance, AActor* InActor, FVector& Origin, float& Radius, float& Scale - , float& SphereRadius) -{ - const FMinimalViewInfo& ViewInfo = PlayerCameraManager->GetLastFrameCameraCachePOV(); - FMatrix Proj = ViewInfo.CalculateProjectionMatrix(); - const float ScreenMultiple = FMath::Max(0.5f * Proj.M[0][0], 0.5f * Proj.M[1][1]); - if (ACharacter* Character = Cast(InActor)) - { - Origin = Character->GetMesh()->Bounds.Origin; - Radius = Character->GetMesh()->Bounds.SphereRadius; - Scale = ScreenMultiple; - SphereRadius = ScreenMultiple * Radius / FMath::Max(1.0f, Distance); - return; - } - - Scale = ScreenMultiple; - Origin = InActor->GetRootComponent()->Bounds.Origin; - Radius = InActor->GetRootComponent()->Bounds.SphereRadius; - SphereRadius = ScreenMultiple * Radius / FMath::Max(1.0f, Distance); -} - /* IIFInventoryInterface */ void AARPlayerController::OnInventoryReplicated(class UIFInventoryComponent* Inventory) diff --git a/Source/ActionRPGGame/Menu/ARLoginScreenView.cpp b/Source/ActionRPGGame/Private/Menu/ARMainMenuView.cpp similarity index 73% rename from Source/ActionRPGGame/Menu/ARLoginScreenView.cpp rename to Source/ActionRPGGame/Private/Menu/ARMainMenuView.cpp index 93dcdf1..f79713a 100644 --- a/Source/ActionRPGGame/Menu/ARLoginScreenView.cpp +++ b/Source/ActionRPGGame/Private/Menu/ARMainMenuView.cpp @@ -1,6 +1,6 @@ // Fill out your copyright notice in the Description page of Project Settings. -#include "ARLoginScreenView.h" +#include "ARMainMenuView.h" diff --git a/Source/ActionRPGGame/Private/Menu/ARMenuGameMode.cpp b/Source/ActionRPGGame/Private/Menu/ARMenuGameMode.cpp new file mode 100644 index 0000000..3b45f8a --- /dev/null +++ b/Source/ActionRPGGame/Private/Menu/ARMenuGameMode.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARMenuGameMode.h" + + + + diff --git a/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp b/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp new file mode 100644 index 0000000..5954c3c --- /dev/null +++ b/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp @@ -0,0 +1,70 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARMenuHUD.h" + +#include "UI/Menu/ARLoginScreenView.h" +#include "ARGameInstance.h" +#include "ARMainMenuView.h" + + +void AARMenuHUD::BeginPlay() +{ + Super::BeginPlay(); + + if (APlayerController* PC = GetOwningPlayerController()) + { + if (LoginScreenClass) + { + LoginScreen = CreateWidget(PC, LoginScreenClass); + LoginScreen->AddToViewport(); + } + + if (MainMenuScreenClass) + { + MainMenuScreen = CreateWidget(PC, MainMenuScreenClass); + MainMenuScreen->AddToViewport(); + + MainMenuScreen->SetVisibility(ESlateVisibility::Collapsed); + } + + if (UARGameInstance* GI = Cast(PC->GetGameInstance())) + { + GI->OnLoginSuccess.AddDynamic(this, &AARMenuHUD::OnLoginSuccess); + } + } +} + +void AARMenuHUD::EndPlay(const EEndPlayReason::Type EndPlayReason) +{ + Super::EndPlay(EndPlayReason); + + if (LoginScreen) + { + LoginScreen->RemoveFromParent(); + LoginScreen->RemoveFromViewport(); + LoginScreen->SetVisibility(ESlateVisibility::Collapsed); + LoginScreen->MarkPendingKill(); + } + + if (MainMenuScreen) + { + MainMenuScreen->RemoveFromParent(); + MainMenuScreen->RemoveFromViewport(); + MainMenuScreen->SetVisibility(ESlateVisibility::Collapsed); + MainMenuScreen->MarkPendingKill(); + } +} + +void AARMenuHUD::OnLoginSuccess() +{ + if (APlayerController* PC = GetOwningPlayerController()) + { + if (UARGameInstance* GI = Cast(PC->GetGameInstance())) + { + GI->OnLoginSuccess.RemoveDynamic(this, &AARMenuHUD::OnLoginSuccess); + + LoginScreen->SetVisibility(ESlateVisibility::Collapsed); + MainMenuScreen->SetVisibility(ESlateVisibility::Visible); + } + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.cpp b/Source/ActionRPGGame/Private/UI/HUD/AREnemyHealthBar.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.cpp rename to Source/ActionRPGGame/Private/UI/HUD/AREnemyHealthBar.cpp diff --git a/Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshair.cpp b/Source/ActionRPGGame/Private/UI/HUD/ARHUDCrosshair.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshair.cpp rename to Source/ActionRPGGame/Private/UI/HUD/ARHUDCrosshair.cpp diff --git a/Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshairInfo.cpp b/Source/ActionRPGGame/Private/UI/HUD/ARHUDCrosshairInfo.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/HUD/ARHUDCrosshairInfo.cpp rename to Source/ActionRPGGame/Private/UI/HUD/ARHUDCrosshairInfo.cpp diff --git a/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.cpp b/Source/ActionRPGGame/Private/UI/HUD/ARHUDPlayerInfo.cpp similarity index 100% rename from Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.cpp rename to Source/ActionRPGGame/Private/UI/HUD/ARHUDPlayerInfo.cpp diff --git a/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp b/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp new file mode 100644 index 0000000..e81dee3 --- /dev/null +++ b/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp @@ -0,0 +1,50 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARLoginScreenView.h" +#include "ARGameInstance.h" + + + +void UARLoginScreenView::NativeConstruct() +{ + Super::NativeConstruct(); + + LoginButton->OnClicked.AddDynamic(this, &UARLoginScreenView::OnLoginClicked); +} + +void UARLoginScreenView::OnLoginClicked() +{ + if (UserNameBox->GetText().IsEmpty()) + { + WarrningText->SetText(FText::FromString("Enter User Name")); + return; + } + if (PasswordBox->GetText().IsEmpty()) + { + WarrningText->SetText(FText::FromString("Enter User Name")); + return; + } + + if (UARGameInstance* GI = Cast(GetOwningPlayer()->GetGameInstance())) + { + GI->OnLoginSuccess.AddDynamic(this, &UARLoginScreenView::OnLoginSuccess); + GI->OnLoginFailed.AddDynamic(this, &UARLoginScreenView::OnLoginFailed); + GI->AttemptLogin(UserNameBox->GetText().ToString(), PasswordBox->GetText().ToString()); + } +} + +void UARLoginScreenView::OnLoginSuccess() +{ + if (UARGameInstance* GI = Cast(GetOwningPlayer()->GetGameInstance())) + { + WarrningText->SetText(FText::FromString("Login Success")); + GI->OnLoginSuccess.RemoveDynamic(this, &UARLoginScreenView::OnLoginSuccess); + GI->OnLoginFailed.RemoveDynamic(this, &UARLoginScreenView::OnLoginFailed); + } +} + + +void UARLoginScreenView::OnLoginFailed() +{ + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index 4ebc06b..41990b8 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -114,46 +114,46 @@ void UARItemWeapon::OnServerItemLoaded() 4. Add random effects to give (Character). */ } -void UARItemWeapon::OnItemAdded(uint8 LocalIndex) +void UARItemWeapon::OnItemAdded(uint8 InIndex) { SpawnAbility(); } -void UARItemWeapon::OnItemRemoved(uint8 LocalIndex) +void UARItemWeapon::OnItemRemoved(uint8 InIndex) { } -void UARItemWeapon::OnServerItemAdded(uint8 LocalIndex) +void UARItemWeapon::OnServerItemAdded(uint8 InIndex) { SpawnAbility(); } -void UARItemWeapon::OnServerItemChanged(uint8 LocalIndex) +void UARItemWeapon::OnServerItemChanged(uint8 InIndex) { } -void UARItemWeapon::OnServerItemRemoved(uint8 LocalIndex) +void UARItemWeapon::OnServerItemRemoved(uint8 InIndex) { } -void UARItemWeapon::OnItemAddedEquipment(uint8 LocalIndex) +void UARItemWeapon::OnItemAddedEquipment(uint8 InIndex) { }; -void UARItemWeapon::OnItemChangedEquipment(uint8 LocalIndex) +void UARItemWeapon::OnItemChangedEquipment(uint8 InIndex) { }; -void UARItemWeapon::OnItemRemovedEquipment(uint8 LocalIndex) +void UARItemWeapon::OnItemRemovedEquipment(uint8 InIndex) { }; -void UARItemWeapon::OnServerItemAddedEquipment(uint8 LocalIndex) +void UARItemWeapon::OnServerItemAddedEquipment(uint8 InIndex) { UARWeaponInventoryComponent* WeaponComponent = Cast(GetOuter()); if (!WeaponComponent) return; }; -void UARItemWeapon::OnServerItemChangedEquipment(uint8 LocalIndex) +void UARItemWeapon::OnServerItemChangedEquipment(uint8 InIndex) { }; -void UARItemWeapon::OnServerItemRemovedEquipment(uint8 LocalIndex) +void UARItemWeapon::OnServerItemRemovedEquipment(uint8 InIndex) { }; diff --git a/Source/ActionRPGGame/Public/ARGameInstance.h b/Source/ActionRPGGame/Public/ARGameInstance.h index 1cce17e..e2cfb7a 100644 --- a/Source/ActionRPGGame/Public/ARGameInstance.h +++ b/Source/ActionRPGGame/Public/ARGameInstance.h @@ -15,10 +15,14 @@ #include "ARGameInstance.generated.h" + +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FAROnConnectedToGS); +DECLARE_DYNAMIC_MULTICAST_DELEGATE(FARLoginAttemptEvent); + /** * */ -UCLASS() +UCLASS(Config=ARGame) class ACTIONRPGGAME_API UARGameInstance : public UGameInstance { GENERATED_BODY() @@ -28,6 +32,24 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "GSObjects") UGSMessageListenersObject* GSMessageListener; + UPROPERTY(Config) + FString GSKey; + UPROPERTY(Config) + FString GSSecret; +public: + UPROPERTY(BlueprintReadOnly, BlueprintAssignable) + FAROnConnectedToGS OnConnectedToGameSparks; + + UPROPERTY(BlueprintReadOnly, BlueprintAssignable) + FARLoginAttemptEvent OnLoginSuccess; + + UPROPERTY(BlueprintReadOnly, BlueprintAssignable) + FARLoginAttemptEvent OnLoginFailed; + +#if WITH_EDITOR + //editor hax so we don't attempt to connect twice. + bool bConnected; +#endif public: UARGameInstance(const FObjectInitializer& ObjectInitializer); @@ -41,10 +63,20 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance return GSMessageListener; } + + void AttemptLogin(const FString& UserName, const FString& Password); //Function used to determine what happens if GameSparks connects or fails to (Needs to be UFUNCTION) UFUNCTION() void OnGameSparksAvailable(bool bAvailable); //Add the response function to the Authentication request static void AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse&); + + virtual void Init() override; +#if WITH_EDITOR + + /* Called to actually start the game when doing Play/Simulate In Editor */ + virtual FGameInstancePIEResult StartPlayInEditorGameInstance(ULocalPlayer* LocalPlayer, const FGameInstancePIEParameters& Params) override; + +#endif }; diff --git a/Source/ActionRPGGame/Public/ARMenuPlayerController.h b/Source/ActionRPGGame/Public/ARMenuPlayerController.h new file mode 100644 index 0000000..0939dff --- /dev/null +++ b/Source/ActionRPGGame/Public/ARMenuPlayerController.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/PlayerController.h" +#include "ARMenuPlayerController.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARMenuPlayerController : public APlayerController +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Public/ARPlayerController.h b/Source/ActionRPGGame/Public/ARPlayerController.h index b1b2bde..4938da7 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.h +++ b/Source/ActionRPGGame/Public/ARPlayerController.h @@ -68,13 +68,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I void ClientPossesed(APawn* InPawn); void ClientPossesed_Implementation(APawn* InPawn); - UFUNCTION(BlueprintPure, Category = "Hud") - float GetObjectScreenRadius(AActor* InActor); - - UFUNCTION(BlueprintPure, Category = "Hud") - void GetObjectBoundSphere(float Distance, AActor* InActor, FVector& Origin, float& Radius, float& Scale - , float& SphereRadius); - /* IIFInventoryInterface */ virtual void OnInventoryReplicated(class UIFInventoryComponent* Inventory) override; /* IIFInventoryInterface */ diff --git a/Source/ActionRPGGame/Menu/ARLoginScreenView.h b/Source/ActionRPGGame/Public/Menu/ARMainMenuView.h similarity index 54% rename from Source/ActionRPGGame/Menu/ARLoginScreenView.h rename to Source/ActionRPGGame/Public/Menu/ARMainMenuView.h index d1006f2..84200c8 100644 --- a/Source/ActionRPGGame/Menu/ARLoginScreenView.h +++ b/Source/ActionRPGGame/Public/Menu/ARMainMenuView.h @@ -3,14 +3,14 @@ #pragma once #include "CoreMinimal.h" -#include "UI/ARUMGWidgetBase.h" -#include "ARLoginScreenView.generated.h" +#include "Blueprint/UserWidget.h" +#include "ARMainMenuView.generated.h" /** * */ UCLASS() -class ACTIONRPGGAME_API UARLoginScreenView : public UARUMGWidgetBase +class ACTIONRPGGAME_API UARMainMenuView : public UUserWidget { GENERATED_BODY() diff --git a/Source/ActionRPGGame/Public/Menu/ARMenuGameMode.h b/Source/ActionRPGGame/Public/Menu/ARMenuGameMode.h new file mode 100644 index 0000000..6759159 --- /dev/null +++ b/Source/ActionRPGGame/Public/Menu/ARMenuGameMode.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/GameModeBase.h" +#include "ARMenuGameMode.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARMenuGameMode : public AGameModeBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h b/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h new file mode 100644 index 0000000..ac1aa86 --- /dev/null +++ b/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h @@ -0,0 +1,37 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/HUD.h" +#include "ARMenuHUD.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARMenuHUD : public AHUD +{ + GENERATED_BODY() + +protected: + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf LoginScreenClass; + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf MainMenuScreenClass; + + UPROPERTY(BlueprintReadOnly) + class UARLoginScreenView* LoginScreen; + + UPROPERTY(BlueprintReadOnly) + class UARMainMenuView* MainMenuScreen; + +public: + virtual void BeginPlay() override; + + virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; + + UFUNCTION() + void OnLoginSuccess(); + +}; diff --git a/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h b/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h index 092c695..62b4aef 100644 --- a/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h +++ b/Source/ActionRPGGame/Public/UI/Inventory/ARInventoryScreenWidget.h @@ -11,7 +11,7 @@ #include "IFItemWidget.h" #include "UI/ARUIComponent.h" - +#include "ARPlayerController.h" #include "ARInventoryScreenWidget.generated.h" /** diff --git a/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h b/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h new file mode 100644 index 0000000..2441966 --- /dev/null +++ b/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h @@ -0,0 +1,43 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" + +#include "Components/EditableTextBox.h" +#include "Components/Button.h" +#include "Components/TextBlock.h" +#include "UI/ARUMGWidgetBase.h" +#include "ARLoginScreenView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARLoginScreenView : public UARUMGWidgetBase +{ + GENERATED_BODY() + +public: + virtual void NativeConstruct() override; + +protected: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UEditableTextBox* UserNameBox; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UEditableTextBox* PasswordBox; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UButton* LoginButton; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UTextBlock* WarrningText; + + UFUNCTION() + void OnLoginClicked(); + + UFUNCTION() + void OnLoginSuccess(); + + UFUNCTION() + void OnLoginFailed(); +}; diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index cb8bc09..450c99e 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -67,20 +67,20 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase virtual void OnServerItemLoaded() override; - virtual void OnItemAdded(uint8 LocalIndex) override; - virtual void OnItemRemoved(uint8 LocalIndex) override; + virtual void OnItemAdded(uint8 InIndex) override; + virtual void OnItemRemoved(uint8 InIndex) override; - virtual void OnServerItemAdded(uint8 LocalIndex) override; - virtual void OnServerItemChanged(uint8 LocalIndex) override; - virtual void OnServerItemRemoved(uint8 LocalIndex) override; + virtual void OnServerItemAdded(uint8 InIndex) override; + virtual void OnServerItemChanged(uint8 InIndex) override; + virtual void OnServerItemRemoved(uint8 InIndex) override; - virtual void OnItemAddedEquipment(uint8 LocalIndex) override; - virtual void OnItemChangedEquipment(uint8 LocalIndex) override; - virtual void OnItemRemovedEquipment(uint8 LocalIndex) override; + virtual void OnItemAddedEquipment(uint8 InIndex) override; + virtual void OnItemChangedEquipment(uint8 InIndex) override; + virtual void OnItemRemovedEquipment(uint8 InIndex) override; - virtual void OnServerItemAddedEquipment(uint8 LocalIndex) override; - virtual void OnServerItemChangedEquipment(uint8 LocalIndex) override; - virtual void OnServerItemRemovedEquipment(uint8 LocalIndex) override; + virtual void OnServerItemAddedEquipment(uint8 InIndex) override; + virtual void OnServerItemChangedEquipment(uint8 InIndex) override; + virtual void OnServerItemRemovedEquipment(uint8 InIndex) override; virtual void ClientPostItemDeserializeFromJson(); From 75b8f40a454bbc02aca5f23aeb16a7238236e1c4 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 11 May 2018 22:58:09 +0200 Subject: [PATCH 172/187] compilation fixes with latest master and clang --- ActionRPGGame.uproject | 64 +++++++++++-------- Config/DefaultEngine.ini | 2 +- .../Tasks/GAAbilityTask_TargetData.h | 2 +- .../Tasks/GAAbilityTask_TargetDataCircle.h | 3 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 30 +++++---- .../ActionRPGGame/Private/ARGameInstance.cpp | 7 -- Source/ActionRPGGame/Private/ARGameMode.cpp | 52 +++++++++++++++ Source/ActionRPGGame/Public/ARCharacter.h | 1 - Source/ActionRPGGame/Public/ARGameInstance.h | 2 - 9 files changed, 111 insertions(+), 52 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index c74e0dd..d87508a 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -179,22 +179,22 @@ "Name": "GLTFImporter", "Enabled": true }, - { - "Name": "SteamAudio", - "Enabled": true, - "BlacklistTargets": [ - "Server", - "Client" - ] - }, - { - "Name": "ResonanceAudio", - "Enabled": false, - "BlacklistTargets": [ - "Server", - "Client" - ] - }, + { + "Name": "SteamAudio", + "Enabled": true, + "BlacklistTargets": [ + "Server", + "Client" + ] + }, + { + "Name": "ResonanceAudio", + "Enabled": false, + "BlacklistTargets": [ + "Server", + "Client" + ] + }, { "Name": "CodeView", "Enabled": true @@ -208,15 +208,15 @@ "Enabled": true, "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/8901af6d589b40b68d763b44c9ced66c" }, - { - "Name": "Substance", - "Enabled": true, - "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4", - "BlacklistTargets": [ - "Server", - "Client" - ] - }, + { + "Name": "Substance", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/2f6439c2f9584f49809d9b13b16c2ba4", + "BlacklistTargets": [ + "Server", + "Client" + ] + }, { "Name": "LiveLink", "Enabled": true @@ -224,6 +224,20 @@ { "Name": "ReplicationGraph", "Enabled": true + }, + { + "Name": "GameLiftServerSDK", + "Enabled": true, + "BlacklistTargets": [ + "Client" + ], + "SupportedTargetPlatforms": [ + "Linux" + ] + }, + { + "Name": "WmfMedia", + "Enabled": false } ], "TargetPlatforms": [ diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 5d06361..1e3ce37 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -57,7 +57,7 @@ bForceSettingsInAllMaps=False [/Script/Engine.ProxyLODMeshSimplificationSettings] r.ProxyLODMeshReductionModule=ProxyLODMeshReduction -[/Script/Engine.NavigationSystem] +[/Script/Engine.NavigationSystemV1] bAutoCreateNavigationData=True bAllowClientSideNavigation=False bInitialBuildingLocked=False diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h index 2ce9ab4..2546286 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetData.h @@ -48,7 +48,7 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetData : public UGAAbilityTask, pu virtual void Activate() override; UFUNCTION() - void OnConfirm(); + virtual void OnConfirm(); UFUNCTION() void OnCastEndedConfirm(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h index ea39110..f8f162b 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataCircle.h @@ -35,6 +35,5 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataCircle : public UGAAbilityTa // void FinishSpawningActor(UObject* WorldContextObject, class UGASAbilityTargetingObject* SpawnedActor); // - UFUNCTION() - void OnConfirm(); + virtual void OnConfirm() override; }; diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 5e59711..4b86a48 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -4,11 +4,12 @@ public class ActionRPGGame : ModuleRules { - public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) - { - PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; - - PrivateIncludePaths.AddRange( + public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; + PublicDefinitions.Add("BOOST_SYSTEM_NOEXCEPT"); + //PublicDefinitions.Add("_HAS_EXCEPTIONS 0"); + PrivateIncludePaths.AddRange( new string[] { // ... add other private include paths required here ... } @@ -35,19 +36,22 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "JsonUObject", "InventoryFramework", "InventoryFrameworkUI", - "GameSparks", - "OnlineSubsystem", - "OnlineSubsystemGameSparks" + "GameSparks", + "OnlineSubsystem", + "OnlineSubsystemGameSparks" }); + if (Target.Type == TargetRules.TargetType.Editor) { PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" }); PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); } - - //if (Target.Type == TargetRules.TargetType.Server) - //{ - // PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); - //} + if (Target.Type == TargetRules.TargetType.Server) + { + if (Target.Platform == UnrealTargetPlatform.Linux) + { + PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); + } + } } } diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index 9bfa3f7..0242d13 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -21,13 +21,6 @@ void UARGameInstance::OnGameSparksAvailable(bool bAvailable) OnConnectedToGameSparks.Broadcast(); } -//The response function to the Authentication Request -// Example response function -void UARGameInstance::AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse& response) -{ - -} - void UARGameInstance::AttemptLogin(const FString& UserName, const FString& Password) { GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Connected")); diff --git a/Source/ActionRPGGame/Private/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp index 579895b..da55627 100644 --- a/Source/ActionRPGGame/Private/ARGameMode.cpp +++ b/Source/ActionRPGGame/Private/ARGameMode.cpp @@ -8,10 +8,62 @@ #include "Abilities/ARAbilityBase.h" #include "ARGameInstance.h" #include "SDraggableWindowWidget.h" + +#if WITH_SERVER_CODE && PLATFORM_LINUX +#include "GameLiftServerSDK.h" +#endif + AARGameMode::AARGameMode() { + } void AARGameMode::BeginPlay() { Super::BeginPlay(); +#if WITH_SERVER_CODE && PLATFORM_LINUX +#if WITH_GAMELIFT + + //Getting the module first. + FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); + + //InitSDK establishes a local connection with GameLift's agent to enable further communication. + gameLiftSdkModule->InitSDK(); + + //When a game session is created, GameLift sends an activation request to the game server and passes along the game session object containing game properties and other settings. + //Here is where a game server should take action based on the game session object. + //Once the game server is ready to receive incoming player connections, it should invoke GameLiftServerAPI.ActivateGameSession() + auto onGameSession = [=](Aws::GameLift::Server::Model::GameSession gameSession) + { + gameLiftSdkModule->ActivateGameSession(); + }; + + FProcessParameters* params = new FProcessParameters(); + params->OnStartGameSession.BindLambda(onGameSession); + + //OnProcessTerminate callback. GameLift invokes this callback before shutting down an instance hosting this game server. + //It gives this game server a chance to save its state, communicate with services, etc., before being shut down. + //In this case, we simply tell GameLift we are indeed going to shut down. + params->OnTerminate.BindLambda([=]() {gameLiftSdkModule->ProcessEnding(); }); + + //This is the HealthCheck callback. + //GameLift invokes this callback every 60 seconds or so. + //Here, a game server might want to check the health of dependencies and such. + //Simply return true if healthy, false otherwise. + //The game server has 60 seconds to respond with its health status. GameLift defaults to 'false' if the game server doesn't respond in time. + //In this case, we're always healthy! + params->OnHealthCheck.BindLambda([]() {return true; }); + + //This game server tells GameLift that it listens on port 7777 for incoming player connections. + params->port = 7777; + + //Here, the game server tells GameLift what set of files to upload when the game session ends. + //GameLift uploads everything specified here for the developers to fetch later. + TArray logfiles; + logfiles.Add(TEXT("aLogFile.txt")); + params->logParameters = logfiles; + + //Calling ProcessReady tells GameLift this game server is ready to receive incoming game sessions! + gameLiftSdkModule->ProcessReady(*params); +#endif +#endif } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/ARCharacter.h b/Source/ActionRPGGame/Public/ARCharacter.h index 7586627..f6d9845 100644 --- a/Source/ActionRPGGame/Public/ARCharacter.h +++ b/Source/ActionRPGGame/Public/ARCharacter.h @@ -291,7 +291,6 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio void ClientPossesedBy(AController* NewController); void ClientPossesedBy_Implementation(AController* NewController); - UFUNCTION() virtual void OnRep_Controller() override; /* IIFInventoryInterface */ diff --git a/Source/ActionRPGGame/Public/ARGameInstance.h b/Source/ActionRPGGame/Public/ARGameInstance.h index e2cfb7a..397ed8d 100644 --- a/Source/ActionRPGGame/Public/ARGameInstance.h +++ b/Source/ActionRPGGame/Public/ARGameInstance.h @@ -69,8 +69,6 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance UFUNCTION() void OnGameSparksAvailable(bool bAvailable); - //Add the response function to the Authentication request - static void AuthenticationRequest_Response(GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse&); virtual void Init() override; #if WITH_EDITOR From ced2faa68bebaeb9246b428260bc308d6ea1da15 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 15 May 2018 00:09:03 +0200 Subject: [PATCH 173/187] compilation fixes and further integration with backend --- ActionRPGGame.uproject | 15 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 40 ++- .../ActionRPGGame/Private/ARGameInstance.cpp | 269 +++++++++++++++++- Source/ActionRPGGame/Private/ARGameMode.cpp | 49 +--- .../ActionRPGGame/Private/ARGameSession.cpp | 40 +++ .../ActionRPGGame/Private/ARGameStateBase.cpp | 7 + .../Private/ARPlayerStateBase.cpp | 7 + Source/ActionRPGGame/Public/ARGameInstance.h | 58 ++++ Source/ActionRPGGame/Public/ARGameSession.h | 31 ++ Source/ActionRPGGame/Public/ARGameStateBase.h | 20 ++ .../ActionRPGGame/Public/ARPlayerStateBase.h | 20 ++ 11 files changed, 504 insertions(+), 52 deletions(-) create mode 100644 Source/ActionRPGGame/Private/ARGameSession.cpp create mode 100644 Source/ActionRPGGame/Private/ARGameStateBase.cpp create mode 100644 Source/ActionRPGGame/Private/ARPlayerStateBase.cpp create mode 100644 Source/ActionRPGGame/Public/ARGameSession.h create mode 100644 Source/ActionRPGGame/Public/ARGameStateBase.h create mode 100644 Source/ActionRPGGame/Public/ARPlayerStateBase.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index d87508a..b9c20cf 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -1,6 +1,6 @@ { "FileVersion": 3, - "EngineAssociation": "{AB02FCC6-45E0-8362-E7EB-B98E6E6B9DF2}", + "EngineAssociation": "", "Category": "", "Description": "", "Modules": [ @@ -235,9 +235,20 @@ "Linux" ] }, + { + "Name": "GameLiftClientSDK", + "Enabled": true, + "BlacklistTargets": [ + "Server" + ] + }, { "Name": "WmfMedia", - "Enabled": false + "Enabled": false, + "BlacklistTargets": [ + "Server", + "Client" + ] } ], "TargetPlatforms": [ diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 4b86a48..6d68820 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -8,7 +8,7 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; PublicDefinitions.Add("BOOST_SYSTEM_NOEXCEPT"); - //PublicDefinitions.Add("_HAS_EXCEPTIONS 0"); + PrivateIncludePaths.AddRange( new string[] { // ... add other private include paths required here ... @@ -46,12 +46,50 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" }); PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); } + if (Target.Type == TargetRules.TargetType.Server) { if (Target.Platform == UnrealTargetPlatform.Linux) { + PublicDefinitions.Add("LINUX_GAMELIFT=1"); + PublicDefinitions.Add("GAMESPARKS_SERVER=1"); PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); } + else + { + PublicDefinitions.Add("LINUX_GAMELIFT=0"); + PublicDefinitions.Add("GAMESPARKS_SERVER=0"); + } + } + else + { + PublicDefinitions.Add("LINUX_GAMELIFT=0"); + PublicDefinitions.Add("GAMESPARKS_SERVER=0"); + } + + if ( (Target.Type == TargetRules.TargetType.Client) || (Target.Type == TargetRules.TargetType.Editor)) + { + if (Target.Platform == UnrealTargetPlatform.Win64) + { + PublicDefinitions.Add("GAMELIFT_CLIENT=1"); + PublicDefinitions.Add("GAMESPARKS_CLIENT=1"); + if (Target.Type == TargetRules.TargetType.Client) + { + bEnableExceptions = true; + } + PublicDependencyModuleNames.AddRange(new string[] { "AWSCore", "GameLiftClientSDK" }); + } + else + { + PublicDefinitions.Add("GAMELIFT_CLIENT=0"); + PublicDefinitions.Add("GAMESPARKS_CLIENT=0"); + } + } + else + { + PublicDefinitions.Add("GAMELIFT_CLIENT=0"); + PublicDefinitions.Add("GAMESPARKS_CLIENT=0"); } } } + diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index 0242d13..be22931 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -1,6 +1,11 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARGameInstance.h" +#include "Engine/World.h" +#include "Engine/Engine.h" +#include "Kismet/GameplayStatics.h" +#include "Json.h" + UARGameInstance::UARGameInstance(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) @@ -10,6 +15,14 @@ UARGameInstance::UARGameInstance(const FObjectInitializer& ObjectInitializer) #if WITH_EDITOR bConnected = false; #endif + +#if GAMELIFT_CLIENT + AccessKey = "Local"; + Secret = "Local"; + Region = "Local"; + LocalPort = 8080; + bIsUsingGameLiftLocal = true; +#endif } @@ -69,17 +82,43 @@ void UARGameInstance::Init() GetGSObject()->Disconnect(); //Connect module GetGSObject()->Connect(GSKey, GSSecret); + #if WITH_EDITOR bConnected = true; //it will be overriden in delegate anyway. #endif } +#if LINUX_GAMELIFT + InitGameLift(); +#endif + +#if GAMELIFT_CLIENT + Aws::Client::ClientConfiguration ClientConfig; + Aws::Auth::AWSCredentials Credentials; + + ClientConfig.connectTimeoutMs = 10000; + ClientConfig.requestTimeoutMs = 10000; + ClientConfig.region = TCHAR_TO_UTF8(*Region); + + // GameLiftLocal + if (bIsUsingGameLiftLocal) + { + ClientConfig.scheme = Aws::Http::Scheme::HTTP; + const FString HostAddress = FString::Printf(TEXT("localhost:%i"), LocalPort); + ClientConfig.endpointOverride = TCHAR_TO_UTF8(*HostAddress); + UE_LOG(LogTemp, Warning, TEXT("GameLift is currently configured to use GameLift Local.")); + + } + + Credentials = Aws::Auth::AWSCredentials(TCHAR_TO_UTF8(*AccessKey), TCHAR_TO_UTF8(*Secret)); + GameLiftClient = new Aws::GameLift::GameLiftClient(Credentials, ClientConfig); +#endif + } #if WITH_EDITOR /* Called to actually start the game when doing Play/Simulate In Editor */ FGameInstancePIEResult UARGameInstance::StartPlayInEditorGameInstance(ULocalPlayer* LocalPlayer, const FGameInstancePIEParameters& Params) { - if (!bConnected) { @@ -91,7 +130,235 @@ FGameInstancePIEResult UARGameInstance::StartPlayInEditorGameInstance(ULocalPlay GetGSObject()->Connect(GSKey, GSSecret); bConnected = true; //it will be overriden in delegate anyway. } + return Super::StartPlayInEditorGameInstance(LocalPlayer, Params); } #endif + +#if LINUX_GAMELIFT +void UARGameInstance::InitGameLift() +{ + //Getting the module first. + FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); + + //InitSDK establishes a local connection with GameLift's agent to enable further communication. + gameLiftSdkModule->InitSDK(); + + //When a game session is created, GameLift sends an activation request to the game server and passes along the game session object containing game properties and other settings. + //Here is where a game server should take action based on the game session object. + //Once the game server is ready to receive incoming player connections, it should invoke GameLiftServerAPI.ActivateGameSession() + auto onGameSession = [=](Aws::GameLift::Server::Model::GameSession gameSession) + { + this->OnGameSessionStarted(gameSession); + }; + + FProcessParameters* params = new FProcessParameters(); + params->OnStartGameSession.BindLambda(onGameSession); + + //OnProcessTerminate callback. GameLift invokes this callback before shutting down an instance hosting this game server. + //It gives this game server a chance to save its state, communicate with services, etc., before being shut down. + //In this case, we simply tell GameLift we are indeed going to shut down. + params->OnTerminate.BindLambda([=]() {gameLiftSdkModule->ProcessEnding(); }); + + //This is the HealthCheck callback. + //GameLift invokes this callback every 60 seconds or so. + //Here, a game server might want to check the health of dependencies and such. + //Simply return true if healthy, false otherwise. + //The game server has 60 seconds to respond with its health status. GameLift defaults to 'false' if the game server doesn't respond in time. + //In this case, we're always healthy! + params->OnHealthCheck.BindLambda([]() {return true; }); + //FString Address = GetWorld()->GetAddressURL(); + //FString portString = Address.RightChop(4); + int32 port = GetWorld()->URL.Port; //FCString::Atoi(*portString); + UE_LOG(LogTemp, Warning, TEXT("Current Server Address %d "), port); + //This game server tells GameLift that it listens on port 7777 for incoming player connections. + params->port = port; + + //Here, the game server tells GameLift what set of files to upload when the game session ends. + //GameLift uploads everything specified here for the developers to fetch later. + TArray logfiles; + logfiles.Add(TEXT("aLogFile.txt")); + params->logParameters = logfiles; + + //Calling ProcessReady tells GameLift this game server is ready to receive incoming game sessions! + gameLiftSdkModule->ProcessReady(*params); + +} + +void UARGameInstance::OnGameSessionStarted(Aws::GameLift::Server::Model::GameSession InGameSession) +{ + auto func2 = [&]() + { + int outNum = 0;; + const Aws::GameLift::Server::Model::GameProperty* props = InGameSession.GetGameProperties(outNum); + FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); + + gameLiftSdkModule->ActivateGameSession(); + + FString MapName = FString(props[0].GetValue()); + UE_LOG(LogTemp, Warning, TEXT("%s"), *MapName); + UGameplayStatics::OpenLevel(this, *MapName); + }; + AsyncTask(ENamedThreads::GameThread, func2); +} +#endif + +void UARGameInstance::ConnectToHub() +{ +#if GAMELIFT_CLIENT + using namespace Aws::GameLift::Model; + SearchGameSessionsRequest SearchRequest; + //SearchRequest. + Aws::GameLift::SearchGameSessionsResponseReceivedHandler SearchHandler; + + SearchHandler = std::bind(&UARGameInstance::OnSessionsSearched, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); + + GameLiftClient->SearchGameSessionsAsync(SearchRequest, SearchHandler); + + + +#endif +} + + +void UARGameInstance::ConnectToWorld() +{ +#if GAMELIFT_CLIENT + +#endif +} + +#if GAMELIFT_CLIENT + +void UARGameInstance::OnSessionsSearched(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::SearchGameSessionsRequest& Request, const Aws::GameLift::Model::SearchGameSessionsOutcome& Outcome, const std::shared_ptr& Context) +{ + if (Outcome.IsSuccess()) + { + using namespace Aws::GameLift::Model; + SearchGameSessionsResult SearchResult = Outcome.GetResult(); + + const Aws::Vector& Sessions = SearchResult.GetGameSessions(); + + for (const GameSession& Session : Sessions) + { + if (Session.GetCurrentPlayerSessionCount() < 8) + { + Aws::GameLift::Model::CreatePlayerSessionRequest PlayerRequest; + PlayerRequest.SetGameSessionId(Session.GetGameSessionId()); + PlayerRequest.SetPlayerId("TestPlayer"); + + Aws::GameLift::CreatePlayerSessionResponseReceivedHandler Handler; + Handler = std::bind(&UARGameInstance::OnCreatePlayerSession, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); + + GameLiftClient->CreatePlayerSessionAsync(PlayerRequest, Handler); + break; + } + } + + } + else + { + using namespace Aws::GameLift::Model; + CreateGameSessionRequest CreateRequest; + CreateRequest.SetFleetId("Local"); + CreateRequest.SetMaximumPlayerSessionCount(8); + GameProperty MapName; + MapName.SetKey("MapName"); + MapName.SetValue("TestMap"); //reasons,, + + CreateRequest.AddGameProperties(MapName); + + Aws::GameLift::CreateGameSessionResponseReceivedHandler Handler; + + + Handler = std::bind(&UARGameInstance::OnSessionCreated, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); + + GameLiftClient->CreateGameSessionAsync(CreateRequest, Handler); + } +} + +void UARGameInstance::OnSessionCreated(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreateGameSessionRequest& Request, const Aws::GameLift::Model::CreateGameSessionOutcome& Outcome, const std::shared_ptr& Context) +{ + if (Outcome.IsSuccess()) + { + using namespace Aws::GameLift::Model; + CreateGameSessionResult Result = Outcome.GetResult(); + GameSession Session = Result.GetGameSession(); + + Aws::GameLift::Model::CreatePlayerSessionRequest PlayerRequest; + PlayerRequest.SetGameSessionId(Session.GetGameSessionId()); + PlayerRequest.SetPlayerId("TestPlayer"); + + Aws::GameLift::CreatePlayerSessionResponseReceivedHandler Handler; + Handler = std::bind(&UARGameInstance::OnCreatePlayerSession, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); + + GameLiftClient->CreatePlayerSessionAsync(PlayerRequest, Handler); + + } +} + +void UARGameInstance::OnCreatePlayerSession(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreatePlayerSessionRequest& Request, const Aws::GameLift::Model::CreatePlayerSessionOutcome& Outcome, const std::shared_ptr& Context) +{ + using namespace Aws::GameLift::Model; + const FString ServerIpAddress = FString(Outcome.GetResult().GetPlayerSession().GetIpAddress().c_str()); + const FString ServerPort = FString::FromInt(Outcome.GetResult().GetPlayerSession().GetPort()); + + FString FullAddress = ServerIpAddress + ":" + ServerPort; + + GEngine->SetClientTravel(GetWorld(), *FullAddress, ETravelType::TRAVEL_Absolute); +} + +#endif + +void UARGameInstance::TestGSRequest() +{ + GSRequestData scriptData; + scriptData.AddString("eventKey", "SearchGameSessions"); + GameSparks::Api::Requests::LogEventRequest request(UGameSparksModule::GetModulePtr()->GetGSInstance()); + request.SetEventKey("SearchGameSessions"); + + auto func = [=](GS& gs, GameSparks::Api::Responses::LogEventResponse response) + { + this->OnScriptMessageReceived(response); + }; + request.Send(func); +} +void UARGameInstance::OnScriptMessageReceived(GameSparks::Api::Responses::LogEventResponse response) +{ + TSharedPtr PlayerSessions = GetGameLiftResponseFromGS("PlayerSession", response); + GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, response.GetJSONString().c_str()); + FString PlayerID = PlayerSessions->GetStringField("PlayerId"); + FString IP = PlayerSessions->GetStringField("IpAddress"); + int32 Port = PlayerSessions->GetIntegerField("Port"); + + FString Options = FString::Printf(TEXT("%s:%d?PlayerId=%s"), *IP, Port, *PlayerID); + + TArray OutParams; + Options.ParseIntoArray(OutParams, TEXT("?")); + + + GEngine->SetClientTravel(GetWorld(), *Options, ETravelType::TRAVEL_Absolute); +} + +TSharedPtr UARGameInstance::GetGameLiftResponseFromGS(const FString& Field, GameSparks::Api::Responses::LogEventResponse response) +{ + gsstl::string str = response.GetJSONString(); + FString data(str.data()); + + UE_LOG(LogTemp, Warning, TEXT("GameLift Response Data %s "), *data); + + TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(data); + + TSharedPtr Object = MakeShareable(new FJsonObject()); + bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); + + TSharedPtr scriptData = Object->GetObjectField("scriptData"); + TSharedPtr respo = scriptData->GetObjectField("response"); + TSharedPtr searchGameSessions = respo->GetObjectField("searchGameSessions"); + TSharedPtr json = searchGameSessions->GetObjectField("json"); + TSharedPtr GameSession= json->GetObjectField(Field); + + + return GameSession; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp index da55627..104e074 100644 --- a/Source/ActionRPGGame/Private/ARGameMode.cpp +++ b/Source/ActionRPGGame/Private/ARGameMode.cpp @@ -9,9 +9,7 @@ #include "ARGameInstance.h" #include "SDraggableWindowWidget.h" -#if WITH_SERVER_CODE && PLATFORM_LINUX -#include "GameLiftServerSDK.h" -#endif + AARGameMode::AARGameMode() { @@ -20,50 +18,5 @@ AARGameMode::AARGameMode() void AARGameMode::BeginPlay() { Super::BeginPlay(); -#if WITH_SERVER_CODE && PLATFORM_LINUX -#if WITH_GAMELIFT - - //Getting the module first. - FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); - - //InitSDK establishes a local connection with GameLift's agent to enable further communication. - gameLiftSdkModule->InitSDK(); - - //When a game session is created, GameLift sends an activation request to the game server and passes along the game session object containing game properties and other settings. - //Here is where a game server should take action based on the game session object. - //Once the game server is ready to receive incoming player connections, it should invoke GameLiftServerAPI.ActivateGameSession() - auto onGameSession = [=](Aws::GameLift::Server::Model::GameSession gameSession) - { - gameLiftSdkModule->ActivateGameSession(); - }; - - FProcessParameters* params = new FProcessParameters(); - params->OnStartGameSession.BindLambda(onGameSession); - - //OnProcessTerminate callback. GameLift invokes this callback before shutting down an instance hosting this game server. - //It gives this game server a chance to save its state, communicate with services, etc., before being shut down. - //In this case, we simply tell GameLift we are indeed going to shut down. - params->OnTerminate.BindLambda([=]() {gameLiftSdkModule->ProcessEnding(); }); - - //This is the HealthCheck callback. - //GameLift invokes this callback every 60 seconds or so. - //Here, a game server might want to check the health of dependencies and such. - //Simply return true if healthy, false otherwise. - //The game server has 60 seconds to respond with its health status. GameLift defaults to 'false' if the game server doesn't respond in time. - //In this case, we're always healthy! - params->OnHealthCheck.BindLambda([]() {return true; }); - - //This game server tells GameLift that it listens on port 7777 for incoming player connections. - params->port = 7777; - - //Here, the game server tells GameLift what set of files to upload when the game session ends. - //GameLift uploads everything specified here for the developers to fetch later. - TArray logfiles; - logfiles.Add(TEXT("aLogFile.txt")); - params->logParameters = logfiles; - //Calling ProcessReady tells GameLift this game server is ready to receive incoming game sessions! - gameLiftSdkModule->ProcessReady(*params); -#endif -#endif } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARGameSession.cpp b/Source/ActionRPGGame/Private/ARGameSession.cpp new file mode 100644 index 0000000..483f9e3 --- /dev/null +++ b/Source/ActionRPGGame/Private/ARGameSession.cpp @@ -0,0 +1,40 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARGameSession.h" + + + + +FString AARGameSession::ApproveLogin(const FString& Options) +{ + FString Output = Super::ApproveLogin(Options); + + TArray OutParams; + Options.ParseIntoArray(OutParams, TEXT("?")); + + int32 Idx = Options.Find("PlayerId="); + int32 KeyIdx = Idx + 9; + + TArray OutPlayerId; + FString Left; + FString PlayerId; + for (FString& str : OutParams) + { + if (str.Split("PlayerId=", &Left, &PlayerId)) + { + break; + } + } + +#if LINUX_GAMELIFT + //AcceptPlayerSession + FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); + FGameLiftGenericOutcome out = gameLiftSdkModule->AcceptPlayerSession(PlayerId); + + FString ErrorName = out.GetError().m_errorName; + FString ErrorMessage = out.GetError().m_errorMessage; +#endif + + + return Output; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARGameStateBase.cpp b/Source/ActionRPGGame/Private/ARGameStateBase.cpp new file mode 100644 index 0000000..1949c9e --- /dev/null +++ b/Source/ActionRPGGame/Private/ARGameStateBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARGameStateBase.h" + + + + diff --git a/Source/ActionRPGGame/Private/ARPlayerStateBase.cpp b/Source/ActionRPGGame/Private/ARPlayerStateBase.cpp new file mode 100644 index 0000000..485b8e3 --- /dev/null +++ b/Source/ActionRPGGame/Private/ARPlayerStateBase.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARPlayerStateBase.h" + + + + diff --git a/Source/ActionRPGGame/Public/ARGameInstance.h b/Source/ActionRPGGame/Public/ARGameInstance.h index 397ed8d..da961f1 100644 --- a/Source/ActionRPGGame/Public/ARGameInstance.h +++ b/Source/ActionRPGGame/Public/ARGameInstance.h @@ -12,6 +12,30 @@ #include "GameSparks/Private/GameSparksObject.h" #include "GameSparks/Private/GSMessageListenersObject.h" +#if LINUX_GAMELIFT +#include "GameLiftServerSDK.h" +#include "aws/gamelift/server/model/GameProperty.h" +#include "aws/gamelift/server/model/GameSession.h" +#include "aws/gamelift/server/model/Player.h" +#include "aws/gamelift/server/model/PlayerSession.h" +#include "aws/gamelift/server/model/PlayerSessionStatus.h" +#endif + + +#if GAMELIFT_CLIENT +#include "aws/core/client/AWSError.h" +#include "aws/core/http/HttpRequest.h" +#include "aws/gamelift/GameLiftClient.h" +#include "aws/gamelift/GameLiftErrors.h" +#include "aws/core/utils/Outcome.h" +#include "aws/gamelift/model/DescribeGameSessionDetailsRequest.h" +#include "aws/gamelift/model/CreateGameSessionResult.h" +#include "aws/gamelift/model/CreateGameSessionRequest.h" +#include "aws/gamelift/model/CreatePlayerSessionRequest.h" +#include "aws/gamelift/model/SearchGameSessionsRequest.h" +#include "aws/gamelift/model/SearchGameSessionsResult.h" +#include "aws/core/auth/AWSCredentialsProvider.h" +#endif #include "ARGameInstance.generated.h" @@ -46,6 +70,15 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance UPROPERTY(BlueprintReadOnly, BlueprintAssignable) FARLoginAttemptEvent OnLoginFailed; +#if GAMELIFT_CLIENT + Aws::GameLift::GameLiftClient* GameLiftClient; + FString AccessKey; + FString Secret; + FString Region; + int32 LocalPort; + bool bIsUsingGameLiftLocal; +#endif + #if WITH_EDITOR //editor hax so we don't attempt to connect twice. bool bConnected; @@ -77,4 +110,29 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance virtual FGameInstancePIEResult StartPlayInEditorGameInstance(ULocalPlayer* LocalPlayer, const FGameInstancePIEParameters& Params) override; #endif + +#if LINUX_GAMELIFT + void InitGameLift(); + void OnGameSessionStarted(Aws::GameLift::Server::Model::GameSession InGameSession); +#endif + + + UFUNCTION(BlueprintCallable, Category = "GameLift|Test") + void ConnectToHub(); + + UFUNCTION(BlueprintCallable, Category = "GameLift|Test") + void ConnectToWorld(); +#if GAMELIFT_CLIENT + void OnSessionsSearched(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::SearchGameSessionsRequest& Request, const Aws::GameLift::Model::SearchGameSessionsOutcome& Outcome, const std::shared_ptr& Context); + void OnSessionCreated(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreateGameSessionRequest& Request, const Aws::GameLift::Model::CreateGameSessionOutcome& Outcome, const std::shared_ptr& Context); + void OnCreatePlayerSession(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreatePlayerSessionRequest& Request, const Aws::GameLift::Model::CreatePlayerSessionOutcome& Outcome, const std::shared_ptr& Context); +#endif + + UFUNCTION(BlueprintCallable, Category = "GameLift|Test") + void TestGSRequest(); + + void OnScriptMessageReceived(GameSparks::Api::Responses::LogEventResponse response); + +protected: + TSharedPtr GetGameLiftResponseFromGS(const FString& Field, GameSparks::Api::Responses::LogEventResponse response); }; diff --git a/Source/ActionRPGGame/Public/ARGameSession.h b/Source/ActionRPGGame/Public/ARGameSession.h new file mode 100644 index 0000000..6995bb7 --- /dev/null +++ b/Source/ActionRPGGame/Public/ARGameSession.h @@ -0,0 +1,31 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/GameSession.h" + +#if LINUX_GAMELIFT +#include "GameLiftServerSDK.h" +#include "GameLiftServerSDKModels.h" +#include "aws/gamelift/server/model/GameProperty.h" +#include "aws/gamelift/server/model/GameSession.h" +#include "aws/gamelift/server/model/Player.h" +#include "aws/gamelift/server/model/PlayerSession.h" +#include "aws/gamelift/server/model/PlayerSessionStatus.h" +#endif + +#include "ARGameSession.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARGameSession : public AGameSession +{ + GENERATED_BODY() + + virtual FString ApproveLogin(const FString& Options) override; + + +}; diff --git a/Source/ActionRPGGame/Public/ARGameStateBase.h b/Source/ActionRPGGame/Public/ARGameStateBase.h new file mode 100644 index 0000000..f628bbc --- /dev/null +++ b/Source/ActionRPGGame/Public/ARGameStateBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/GameStateBase.h" +#include "ARGameStateBase.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARGameStateBase : public AGameStateBase +{ + GENERATED_BODY() + + + + +}; diff --git a/Source/ActionRPGGame/Public/ARPlayerStateBase.h b/Source/ActionRPGGame/Public/ARPlayerStateBase.h new file mode 100644 index 0000000..3557415 --- /dev/null +++ b/Source/ActionRPGGame/Public/ARPlayerStateBase.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/PlayerState.h" +#include "ARPlayerStateBase.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API AARPlayerStateBase : public APlayerState +{ + GENERATED_BODY() + + + + +}; From 7f301d45680eb5749771f29445e90d4402ddf699 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 15 May 2018 23:13:48 +0200 Subject: [PATCH 174/187] fixed some asset loading issues in cooked build --- Config/DefaultEngine.ini | 1 + Config/DefaultGame.ini | 3 +- .../AbilityFramework/Private/AFCueManager.cpp | 24 ++++++++++++-- .../ActionRPGGame/Private/ARGameInstance.cpp | 20 ++++++++++++ .../ActionRPGGame/Private/ActionRPGGame.cpp | 15 --------- .../Weapons/ARWeaponInventoryComponent.cpp | 31 ++++++++++--------- .../Weapons/ARWeaponInventoryComponent.h | 2 +- 7 files changed, 62 insertions(+), 34 deletions(-) diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 1e3ce37..351c7e5 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -182,3 +182,4 @@ AsyncSceneSmoothingFactor=0.990000 InitialAverageFrameRate=0.016667 PhysXTreeRebuildRate=10 + diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index f26d702..b30c396 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -16,10 +16,11 @@ bGenerateChunks=True +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/AbilityFrameworkDebugger")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="EffectCue",AssetBaseClass=/Script/AbilityFramework.GAEffectCue,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/AbilityFrameworkDebugger")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="EffectCue",AssetBaseClass=/Script/AbilityFramework.GAEffectCue,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/Game/Prototypes/Abilities")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) bOnlyCookProductionAssets=False bShouldManagerDetermineTypeAndName=False bShouldGuessTypeAndNameInEditor=True bShouldAcquireMissingChunksOnLoad=False +MetaDataTagsForAssetRegistry=() diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp index c988060..795be8d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp @@ -173,6 +173,26 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, ActiveCues.Add(InHandle, actor); actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.GetActor(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); } + else + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + + TArray AssetData; + FARFilter Filter; + Filter.TagsAndValues.Add("EffectCueTagSearch", CueTag.ToString()); + AssetRegistryModule.Get().GetAssets(Filter, AssetData); + FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("EffectCue"), AssetData[0].AssetName); + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams, InHandle); + + Manager->LoadPrimaryAsset(PrimaryAssetId, + TArray(), + del); + } + } return;//don't try to load asset, we already have pooled instance. } @@ -300,9 +320,9 @@ void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag } } - { + /*{ Manager->UnloadPrimaryAsset(InPrimaryAssetId); - } + }*/ } } diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index be22931..66061a2 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -6,6 +6,11 @@ #include "Kismet/GameplayStatics.h" #include "Json.h" +#include "Modules/ModuleManager.h" +#include "AssetRegistryModule.h" +#include "Engine/AssetManager.h" +#include "Abilities/GAAbilityBase.h" +#include "Effects/GAEffectCue.h" UARGameInstance::UARGameInstance(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) @@ -71,6 +76,21 @@ void UARGameInstance::AttemptLogin(const FString& UserName, const FString& Passw void UARGameInstance::Init() { Super::Init(); + + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + //AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); + TArray< FString > ContentPaths; + TArray RootPaths; + FPackageName::QueryRootContentPaths(ContentPaths); + AssetRegistry.ScanPathsSynchronous(ContentPaths); + + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); + Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("EffectCue"), ContentPaths, AGAEffectCue::StaticClass(), true); + } + #if WITH_EDITOR //editor hax so we don't attempt to connect twice. if (!bConnected) diff --git a/Source/ActionRPGGame/Private/ActionRPGGame.cpp b/Source/ActionRPGGame/Private/ActionRPGGame.cpp index c2b4241..1363bec 100644 --- a/Source/ActionRPGGame/Private/ActionRPGGame.cpp +++ b/Source/ActionRPGGame/Private/ActionRPGGame.cpp @@ -2,26 +2,11 @@ #include "ActionRPGGame.h" #include "Modules/ModuleManager.h" -#include "AssetRegistryModule.h" -#include "Engine/AssetManager.h" -#include "Abilities/GAAbilityBase.h" #if WITH_EDITOR #include "IAbilityFrameworkEditor.h" #endif void FActionRPGGameModule::StartupModule() { - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - //AssetRegistryModule.Get().OnFilesLoaded().AddUObject(this, &UARUIAbilityManagerComponent::FinishedLoadinFiles); - TArray< FString > ContentPaths; - TArray RootPaths; - FPackageName::QueryRootContentPaths(ContentPaths); - AssetRegistry.ScanPathsSynchronous(ContentPaths); - - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); - } #if WITH_EDITOR FModuleManager::Get().LoadModule(TEXT("AbilityFrameworkEditor")); //FModuleManager::LoadModuleChecked(TEXT("AbilityFrameworkEditor")); diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp index 568ce98..729553d 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp @@ -62,20 +62,21 @@ void UARWeaponInventoryComponent::TickComponent(float DeltaTime, ELevelTick Tick void UARWeaponInventoryComponent::SetWeapon(const FARWeaponRPC& InWeapon, UChildActorComponent* Component) { - if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) + //if (InWeapon.Weapon.IsValid() || InWeapon.Weapon.IsNull()) { - Component->SetChildActorClass(InWeapon.Weapon.Get()); + TSubclassOf WpnClass = TSoftClassPtr(InWeapon.Weapon).LoadSynchronous(); + Component->SetChildActorClass(WpnClass); Component->SetRelativeLocation(FVector(0, 0, 0)); Component->SetRelativeRotation(FRotator(0, 0, 0)); Component->SetRelativeLocation(InWeapon.Position); Component->SetRelativeRotation(InWeapon.Rotation); } - else + /*else { FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponInventoryComponent::AsynWeaponLoaded, Component, InWeapon); UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); - } + }*/ } void UARWeaponInventoryComponent::OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) { @@ -93,7 +94,7 @@ void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalInde { UARItemWeapon* InWeapon = Cast(Item); FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; + Data.Weapon = InWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; Data.Position = InWeapon->HolsteredPosition; Data.Rotation = InWeapon->HolsteredRotation; @@ -118,7 +119,7 @@ void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 Loc { UARItemWeapon* InWeapon = Cast(Item); FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; + Data.Weapon = InWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; Data.Position = InWeapon->HolsteredPosition; Data.Rotation = InWeapon->HolsteredRotation; @@ -304,7 +305,7 @@ void UARWeaponInventoryComponent::Unequip(int8 WeaponIndex) Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); } FARWeaponRPC Data; - Data.Weapon = EquipedWeapon->Weapon; + Data.Weapon = EquipedWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; Data.Position = EquipedWeapon->HolsteredPosition; Data.Rotation = EquipedWeapon->HolsteredRotation; @@ -324,7 +325,7 @@ void UARWeaponInventoryComponent::Holster() Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); } FARWeaponRPC Data; - Data.Weapon = EquipedWeapon->Weapon; + Data.Weapon = EquipedWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; Data.Position = EquipedWeapon->HolsteredPosition; Data.Rotation = EquipedWeapon->HolsteredRotation; @@ -400,7 +401,7 @@ void UARWeaponInventoryComponent::NextWeapon() InWeapon = FindNextValid(); } FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; + Data.Weapon = InWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; @@ -486,7 +487,7 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(int8 WeaponInd if (OldWeapon) { FARWeaponRPC OldData; - OldData.Weapon = OldWeapon->Weapon; + OldData.Weapon = OldWeapon->Weapon.ToString(); OldData.Position = OldWeapon->HolsteredPosition; OldData.Rotation = OldWeapon->HolsteredRotation; OldData.AttachSlot = static_cast(OldGroup); @@ -500,7 +501,7 @@ void UARWeaponInventoryComponent::ServerNextWeapon_Implementation(int8 WeaponInd InWeapon = FindNextValid(); } FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; + Data.Weapon = InWeapon->Weapon.ToString(); Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; Data.AttachSlot = EARWeaponPosition::Equiped; @@ -542,7 +543,7 @@ void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(int8 Weapo if (OldWeapon) { FARWeaponRPC OldData; - OldData.Weapon = OldWeapon->Weapon; + OldData.Weapon = OldWeapon->Weapon.ToString(); OldData.Position = OldWeapon->HolsteredPosition; OldData.Rotation = OldWeapon->HolsteredRotation; OldData.AttachSlot = static_cast(CurrentIndex); @@ -555,7 +556,7 @@ void UARWeaponInventoryComponent::ServerPreviousWeapon_Implementation(int8 Weapo InWeapon = FindNextValid(); } FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; + Data.Weapon = InWeapon->Weapon.ToString(); Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; Data.AttachSlot = EARWeaponPosition::Equiped; @@ -617,7 +618,7 @@ void UARWeaponInventoryComponent::HandleClientPrediction(int8 WeaponIndex, bool InWeapon = FindNextValid(); } FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon; + Data.Weapon = InWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; Data.Position = InWeapon->EquipedPosition; Data.Rotation = InWeapon->EquipedRotation; @@ -698,7 +699,7 @@ UARItemWeapon* UARWeaponInventoryComponent::FindPreviousValid() void UARWeaponInventoryComponent::AsynWeaponLoaded(UChildActorComponent* Component, FARWeaponRPC InWeapon) { - Component->SetChildActorClass(InWeapon.Weapon.Get()); + Component->SetChildActorClass(TSoftClassPtr(InWeapon.Weapon).LoadSynchronous()); Component->SetRelativeLocation(FVector(0,0,0)); Component->SetRelativeRotation(FRotator(0,0,0)); diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index 46bbc57..d903047 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -53,7 +53,7 @@ struct FARWeaponRPC GENERATED_BODY() public: UPROPERTY(EditAnywhere, Category = "Attachment Test") - TSoftClassPtr Weapon; + FSoftClassPath Weapon; UPROPERTY() uint8 Index; From 154c48e029df36e25ba533cf0ed8b60695fc7756 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 16 May 2018 21:27:37 +0200 Subject: [PATCH 175/187] fixed effect cues no loaded into asset registry in cooked builds --- ActionRPGGame.uproject | 5 +++ Config/DefaultEngine.ini | 3 +- Config/DefaultGame.ini | 4 +-- .../EffectCueEditor/GAEffectCueBlueprint.cpp | 33 ------------------- .../EffectCueEditor/GAEffectCueBlueprint.h | 32 ------------------ .../GAEffectCueBlueprintFactory.cpp | 2 +- 6 files changed, 10 insertions(+), 69 deletions(-) delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp delete mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index b9c20cf..0989e49 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -248,6 +248,11 @@ "BlacklistTargets": [ "Server", "Client" + ], + "BlacklistTargetConfigurations": [ + "Debug", + "Development", + "DebugGame" ] } ], diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 351c7e5..fad1ee0 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -117,10 +117,11 @@ GlyphTextureSize=x4096 +Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) +Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) +Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Ignore,bTraceType=True,bStaticObject=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Block,bTraceType=True,bStaticObject=False) +DefaultChannelResponses=(Channel=ECC_GameTraceChannel2,Name="Pickup",DefaultResponse=ECR_Overlap,bTraceType=True,bStaticObject=False) +DefaultChannelResponses=(Channel=ECC_GameTraceChannel3,Name="Weapon",DefaultResponse=ECR_Overlap,bTraceType=True,bStaticObject=False) +DefaultChannelResponses=(Channel=ECC_GameTraceChannel4,Name="PikcupObject",DefaultResponse=ECR_Ignore,bTraceType=False,bStaticObject=False) ++EditProfiles=(Name="Pawn",CustomResponses=((Channel="Enemy",Response=ECR_Overlap))) -ProfileRedirects=(OldName="BlockingVolume",NewName="InvisibleWall") -ProfileRedirects=(OldName="InterpActor",NewName="IgnoreOnlyPawn") -ProfileRedirects=(OldName="StaticMeshComponent",NewName="BlockAllDynamic") diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index b30c396..7c6d19a 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -15,8 +15,8 @@ bGenerateChunks=True -PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game"))) +PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) +PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/AbilityFrameworkDebugger")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="EffectCue",AssetBaseClass=/Script/AbilityFramework.GAEffectCue,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game"),(Path="/Game/Prototypes/Abilities")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="EffectCue",AssetBaseClass=/Script/AbilityFramework.GAEffectCue,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) bOnlyCookProductionAssets=False bShouldManagerDetermineTypeAndName=False bShouldGuessTypeAndNameInEditor=True diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp deleted file mode 100644 index dcbb00a..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.cpp +++ /dev/null @@ -1,33 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "../AbilityFrameworkEditor.h" -#include "GAEffectCueBlueprint.h" - -////////////////////////////////////////////////////////////////////////// -// UGameplayAbilityBlueprint - -UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectInitializer) - : Super(ObjectInitializer) -{ -} - -#if WITH_EDITOR - -/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ -UGAEffectCueBlueprint* UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint) -{ - UGAEffectCueBlueprint* ParentBP = NULL; - - // Determine if there is a gameplay ability blueprint in the ancestry of this class - for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) - { - if (UGAEffectCueBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) - { - ParentBP = TestBP; - } - } - - return ParentBP; -} - -#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h deleted file mode 100644 index e3a7eaf..0000000 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprint.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once -#include "CoreMinimal.h" -#include "UObject/ObjectMacros.h" -#include "Engine/Blueprint.h" -#include "GAEffectCueBlueprint.generated.h" - -/** - * Game Effect Blueprint - */ - -UCLASS(BlueprintType) -class ABILITYFRAMEWORKEDITOR_API UGAEffectCueBlueprint : public UBlueprint -{ - GENERATED_UCLASS_BODY() -UPROPERTY() - class UGAEffectCueSequence* Animation; -#if WITH_EDITOR - - // UBlueprint interface - virtual bool SupportedByDefaultBlueprintFactory() const override - { - return false; - } - // End of UBlueprint interface - - /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ - static UGAEffectCueBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint); - -#endif -}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp index f37eefc..d548866 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp @@ -28,7 +28,7 @@ #include "Kismet2/KismetEditorUtilities.h" #include "BlueprintEditorSettings.h" -#include "GAEffectCueBlueprint.h" +#include "Effects/GAEffectCueBlueprint.h" #include "Effects/GAEffectCue.h" #include "GAEffectCueGraph.h" #include "GAEffectCueGraphSchema.h" From 050286b4cb3f272fbf5eca30aeba553494d4c731 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 16 May 2018 21:34:35 +0200 Subject: [PATCH 176/187] missing files --- .../Private/AFAttributeInterface.cpp | 7 ++++ .../Private/AFSimpleInterface.cpp | 7 ++++ .../Private/Effects/GAEffectCueBlueprint.cpp | 33 +++++++++++++++++++ .../Public/AFAttributeInterface.h | 29 ++++++++++++++++ .../Public/AFSimpleInterface.h | 28 ++++++++++++++++ .../Public/Effects/GAEffectCueBlueprint.h | 32 ++++++++++++++++++ 6 files changed, 136 insertions(+) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/AFSimpleInterface.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/AFSimpleInterface.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeInterface.cpp new file mode 100644 index 0000000..a771935 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAttributeInterface.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFAttributeInterface.h" + + +// Add default functionality here for any IAFAttributeInterface functions that are not pure virtual. diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFSimpleInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFSimpleInterface.cpp new file mode 100644 index 0000000..bb19175 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFSimpleInterface.cpp @@ -0,0 +1,7 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFSimpleInterface.h" + + +// Add default functionality here for any IAFSimpleInterface functions that are not pure virtual. diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp new file mode 100644 index 0000000..a9f021e --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp @@ -0,0 +1,33 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#include "AbilityFramework.h" +#include "GAEffectCueBlueprint.h" + +////////////////////////////////////////////////////////////////////////// +// UGameplayAbilityBlueprint + +UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ +} + +#if WITH_EDITOR + +/** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ +UGAEffectCueBlueprint* UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint) +{ + UGAEffectCueBlueprint* ParentBP = NULL; + + // Determine if there is a gameplay ability blueprint in the ancestry of this class + for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) + { + if (UGAEffectCueBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + { + ParentBP = TestBP; + } + } + + return ParentBP; +} + +#endif \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeInterface.h new file mode 100644 index 0000000..9e24c00 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAttributeInterface.h @@ -0,0 +1,29 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/Interface.h" +#include "AFAttributeInterface.generated.h" + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UAFAttributeInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class ABILITYFRAMEWORK_API IAFAttributeInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + virtual void ModifyAttribute(const FGAEffectMod& InAttributeMod + , const FGAEffectHandle& InHandle) = 0; + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFSimpleInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFSimpleInterface.h new file mode 100644 index 0000000..94768fe --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFSimpleInterface.h @@ -0,0 +1,28 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/Interface.h" +#include "AFSimpleInterface.generated.h" + +// This class does not need to be modified. +UINTERFACE(MinimalAPI) +class UAFSimpleInterface : public UInterface +{ + GENERATED_BODY() +}; + +/** + * + */ +class ABILITYFRAMEWORK_API IAFSimpleInterface +{ + GENERATED_BODY() + + // Add interface functions to this class. This is the class that will be inherited to implement this interface. +public: + + virtual void ApplyEffect(const FGAEffectHandle& InHandle + , const FGAEffect& InEffect) = 0; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h new file mode 100644 index 0000000..7bc9807 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Engine/Blueprint.h" +#include "GAEffectCueBlueprint.generated.h" + +/** + * Game Effect Blueprint + */ + +UCLASS(BlueprintType) +class ABILITYFRAMEWORK_API UGAEffectCueBlueprint : public UBlueprint +{ + GENERATED_UCLASS_BODY() +UPROPERTY() + class UGAEffectCueSequence* Animation; +#if WITH_EDITOR + + // UBlueprint interface + virtual bool SupportedByDefaultBlueprintFactory() const override + { + return false; + } + // End of UBlueprint interface + + /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ + static UGAEffectCueBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint); + +#endif +}; From 85c30a9e0a07eb7eefb1de0d68c19e189c33a417 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Fri, 18 May 2018 01:28:49 +0200 Subject: [PATCH 177/187] added registartion screen, and termination of game session when there is zero players --- .../ActionRPGGame/Private/ARGameInstance.cpp | 17 ++++++ Source/ActionRPGGame/Private/ARGameMode.cpp | 30 +++++++++++ .../ActionRPGGame/Private/ARGameSession.cpp | 37 +++++++++++-- .../ActionRPGGame/Private/Menu/ARMenuHUD.cpp | 9 ++++ .../Private/Menu/ARRegisterView.cpp | 53 +++++++++++++++++++ .../Private/UI/Menu/ARLoginScreenView.cpp | 16 +++++- Source/ActionRPGGame/Public/ARGameInstance.h | 4 +- Source/ActionRPGGame/Public/ARGameMode.h | 2 + Source/ActionRPGGame/Public/ARGameSession.h | 2 +- .../ActionRPGGame/Public/ARPlayerController.h | 3 ++ Source/ActionRPGGame/Public/Menu/ARMenuHUD.h | 12 ++++- .../Public/Menu/ARRegisterView.h | 47 ++++++++++++++++ .../Public/UI/Menu/ARLoginScreenView.h | 6 +++ 13 files changed, 228 insertions(+), 10 deletions(-) create mode 100644 Source/ActionRPGGame/Private/Menu/ARRegisterView.cpp create mode 100644 Source/ActionRPGGame/Public/Menu/ARRegisterView.h diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index 66061a2..f4477b9 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -73,6 +73,23 @@ void UARGameInstance::AttemptLogin(const FString& UserName, const FString& Passw } +void UARGameInstance::RegisterNewPlayer(const FString& UserName, const FString& DisplayName, const FString& Password) +{ +#if GAMESPARKS_CLIENT + GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); + GameSparks::Api::Requests::RegistrationRequest regRequest(gs); + regRequest.SetUserName(TCHAR_TO_UTF8(*UserName)); + regRequest.SetDisplayName(TCHAR_TO_UTF8(*DisplayName)); + regRequest.SetPassword(TCHAR_TO_UTF8(*DisplayName)); + + auto RegRequestResponse = [&](GameSparks::Core::GS&, const GameSparks::Api::Responses::RegistrationResponse& Response) + { + GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, Response.GetJSONString().c_str()); + }; + regRequest.Send(RegRequestResponse); +#endif +} + void UARGameInstance::Init() { Super::Init(); diff --git a/Source/ActionRPGGame/Private/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp index 104e074..e3f81b3 100644 --- a/Source/ActionRPGGame/Private/ARGameMode.cpp +++ b/Source/ActionRPGGame/Private/ARGameMode.cpp @@ -8,6 +8,7 @@ #include "Abilities/ARAbilityBase.h" #include "ARGameInstance.h" #include "SDraggableWindowWidget.h" +#include "ARPlayerController.h" @@ -19,4 +20,33 @@ void AARGameMode::BeginPlay() { Super::BeginPlay(); +} + +FString AARGameMode::InitNewPlayer(APlayerController* NewPlayerController + , const FUniqueNetIdRepl& UniqueId + , const FString& Options + , const FString& Portal) +{ + FString ReturnString = Super::InitNewPlayer(NewPlayerController, UniqueId, Options, Portal); + + TArray OutParams; + Options.ParseIntoArray(OutParams, TEXT("?")); + + TArray OutPlayerId; + FString Left; + FString PlayerId; + for (FString& str : OutParams) + { + if (str.Split("PlayerId=", &Left, &PlayerId)) + { + break; + } + } + + if (AARPlayerController* PC = Cast(NewPlayerController)) + { + PC->GameLiftId = PlayerId; + } + + return ReturnString; } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARGameSession.cpp b/Source/ActionRPGGame/Private/ARGameSession.cpp index 483f9e3..75f8006 100644 --- a/Source/ActionRPGGame/Private/ARGameSession.cpp +++ b/Source/ActionRPGGame/Private/ARGameSession.cpp @@ -1,8 +1,9 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARGameSession.h" - - +#include "ARGameInstance.h" +#include "ARGameMode.h" +#include "ARPlayerController.h" FString AARGameSession::ApproveLogin(const FString& Options) @@ -12,9 +13,6 @@ FString AARGameSession::ApproveLogin(const FString& Options) TArray OutParams; Options.ParseIntoArray(OutParams, TEXT("?")); - int32 Idx = Options.Find("PlayerId="); - int32 KeyIdx = Idx + 9; - TArray OutPlayerId; FString Left; FString PlayerId; @@ -37,4 +35,33 @@ FString AARGameSession::ApproveLogin(const FString& Options) return Output; +} + +void AARGameSession::UnregisterPlayer(const APlayerController* ExitingPlayer) +{ +#if LINUX_GAMELIFT + if (const AARPlayerController* PC = Cast(ExitingPlayer)) + { + FString GLId = PC->GameLiftId; + FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); + FGameLiftGenericOutcome out = gameLiftSdkModule->RemovePlayerSession(GLId); + + FString ErrorName = out.GetError().m_errorName; + FString ErrorMessage = out.GetError().m_errorMessage; + } +#endif + + Super::UnregisterPlayer(ExitingPlayer); + + /*AARGameMode* GM = Cast(GetOuter()); + int32 NumPlayer = GM->GetNumPlayers(); + if (NumPlayer <= 0) + { +#if LINUX_GAMELIFT + FString GLId = PC->GameLiftId; + FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); + gameLiftSdkModule->TerminateGameSession(); +#endif + }*/ + } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp b/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp index 5954c3c..756cc8a 100644 --- a/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp +++ b/Source/ActionRPGGame/Private/Menu/ARMenuHUD.cpp @@ -5,6 +5,7 @@ #include "UI/Menu/ARLoginScreenView.h" #include "ARGameInstance.h" #include "ARMainMenuView.h" +#include "ARRegisterView.h" void AARMenuHUD::BeginPlay() @@ -27,6 +28,14 @@ void AARMenuHUD::BeginPlay() MainMenuScreen->SetVisibility(ESlateVisibility::Collapsed); } + if (RegisterViewClass) + { + RegisterView = CreateWidget(PC, RegisterViewClass); + RegisterView->AddToViewport(); + + RegisterView->SetVisibility(ESlateVisibility::Collapsed); + } + if (UARGameInstance* GI = Cast(PC->GetGameInstance())) { GI->OnLoginSuccess.AddDynamic(this, &AARMenuHUD::OnLoginSuccess); diff --git a/Source/ActionRPGGame/Private/Menu/ARRegisterView.cpp b/Source/ActionRPGGame/Private/Menu/ARRegisterView.cpp new file mode 100644 index 0000000..6484bc4 --- /dev/null +++ b/Source/ActionRPGGame/Private/Menu/ARRegisterView.cpp @@ -0,0 +1,53 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARRegisterView.h" +#include "ARGameInstance.h" + + + +void UARRegisterView::NativeConstruct() +{ + Super::NativeConstruct(); + + RegisterButton->OnClicked.AddDynamic(this, &UARRegisterView::OnRegisterClicked); +} + + +void UARRegisterView::OnRegisterClicked() +{ + FString UserName = UserNameBox->GetText().ToString(); + FString DisplayName = DisplayNameBox->GetText().ToString(); + FString Password = PasswordBox->GetText().ToString(); + + if (UserName.Len() <= 0) + { + WarrningText->SetText(FText::FromString("Invalid Username")); + return; + } + if (DisplayName.Len() <= 0) + { + WarrningText->SetText(FText::FromString("Invalid DisplayName")); + return; + } + if (Password.Len() <= 0) + { + WarrningText->SetText(FText::FromString("Invalid Password")); + return; + } + + if (UARGameInstance* GI = Cast(GetOwningPlayer()->GetGameInstance())) + { + RegisterButton->SetVisibility(ESlateVisibility::HitTestInvisible); + GI->RegisterNewPlayer(UserName, DisplayName, Password); + } +} + +void UARRegisterView::OnRegisterSuccess() +{ + +} + +void UARRegisterView::OnRegisterFailed() +{ + +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp b/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp index e81dee3..1aa1d13 100644 --- a/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp +++ b/Source/ActionRPGGame/Private/UI/Menu/ARLoginScreenView.cpp @@ -2,7 +2,8 @@ #include "ARLoginScreenView.h" #include "ARGameInstance.h" - +#include "Menu/ARRegisterView.h" +#include "ARMenuHUD.h" void UARLoginScreenView::NativeConstruct() @@ -10,6 +11,7 @@ void UARLoginScreenView::NativeConstruct() Super::NativeConstruct(); LoginButton->OnClicked.AddDynamic(this, &UARLoginScreenView::OnLoginClicked); + RegisterButton->OnClicked.AddDynamic(this, &UARLoginScreenView::OnRegisterClicked); } void UARLoginScreenView::OnLoginClicked() @@ -47,4 +49,16 @@ void UARLoginScreenView::OnLoginSuccess() void UARLoginScreenView::OnLoginFailed() { +} + +void UARLoginScreenView::OnRegisterClicked() +{ + if (!GetOwningPlayer()) + return; + + AARMenuHUD* Hud = Cast(GetOwningPlayer()->GetHUD()); + if (!Hud) + return; + + Hud->GetRegisterView()->SetVisibility(ESlateVisibility::Visible); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/ARGameInstance.h b/Source/ActionRPGGame/Public/ARGameInstance.h index da961f1..ad22eed 100644 --- a/Source/ActionRPGGame/Public/ARGameInstance.h +++ b/Source/ActionRPGGame/Public/ARGameInstance.h @@ -98,6 +98,7 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance void AttemptLogin(const FString& UserName, const FString& Password); + void RegisterNewPlayer(const FString& UserName, const FString& DisplayName, const FString& Password); //Function used to determine what happens if GameSparks connects or fails to (Needs to be UFUNCTION) UFUNCTION() void OnGameSparksAvailable(bool bAvailable); @@ -116,12 +117,11 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance void OnGameSessionStarted(Aws::GameLift::Server::Model::GameSession InGameSession); #endif - UFUNCTION(BlueprintCallable, Category = "GameLift|Test") void ConnectToHub(); - UFUNCTION(BlueprintCallable, Category = "GameLift|Test") void ConnectToWorld(); + #if GAMELIFT_CLIENT void OnSessionsSearched(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::SearchGameSessionsRequest& Request, const Aws::GameLift::Model::SearchGameSessionsOutcome& Outcome, const std::shared_ptr& Context); void OnSessionCreated(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreateGameSessionRequest& Request, const Aws::GameLift::Model::CreateGameSessionOutcome& Outcome, const std::shared_ptr& Context); diff --git a/Source/ActionRPGGame/Public/ARGameMode.h b/Source/ActionRPGGame/Public/ARGameMode.h index 0965d82..410fc14 100644 --- a/Source/ActionRPGGame/Public/ARGameMode.h +++ b/Source/ActionRPGGame/Public/ARGameMode.h @@ -14,6 +14,8 @@ class AARGameMode : public AGameModeBase AARGameMode(); virtual void BeginPlay() override; + + virtual FString InitNewPlayer(APlayerController* NewPlayerController, const FUniqueNetIdRepl& UniqueId, const FString& Options, const FString& Portal = TEXT("")) override; }; diff --git a/Source/ActionRPGGame/Public/ARGameSession.h b/Source/ActionRPGGame/Public/ARGameSession.h index 6995bb7..6416397 100644 --- a/Source/ActionRPGGame/Public/ARGameSession.h +++ b/Source/ActionRPGGame/Public/ARGameSession.h @@ -26,6 +26,6 @@ class ACTIONRPGGAME_API AARGameSession : public AGameSession GENERATED_BODY() virtual FString ApproveLogin(const FString& Options) override; - + virtual void UnregisterPlayer(const APlayerController* ExitingPlayer) override; }; diff --git a/Source/ActionRPGGame/Public/ARPlayerController.h b/Source/ActionRPGGame/Public/ARPlayerController.h index 4938da7..de975b2 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.h +++ b/Source/ActionRPGGame/Public/ARPlayerController.h @@ -52,6 +52,9 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I TSoftClassPtr SetAbilityGroup02; bool bInputBount; + + UPROPERTY() + FString GameLiftId; public: AARPlayerController(const FObjectInitializer& ObjectInitializer); virtual void BeginPlay() override; diff --git a/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h b/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h index ac1aa86..a8bdb6b 100644 --- a/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h +++ b/Source/ActionRPGGame/Public/Menu/ARMenuHUD.h @@ -19,6 +19,8 @@ class ACTIONRPGGAME_API AARMenuHUD : public AHUD TSubclassOf LoginScreenClass; UPROPERTY(EditAnywhere, Category = "Widgets") TSubclassOf MainMenuScreenClass; + UPROPERTY(EditAnywhere, Category = "Widgets") + TSubclassOf RegisterViewClass; UPROPERTY(BlueprintReadOnly) class UARLoginScreenView* LoginScreen; @@ -26,12 +28,20 @@ class ACTIONRPGGAME_API AARMenuHUD : public AHUD UPROPERTY(BlueprintReadOnly) class UARMainMenuView* MainMenuScreen; + UPROPERTY(BlueprintReadOnly) + class UARRegisterView* RegisterView; + public: + + inline class UARRegisterView* GetRegisterView() + { + return RegisterView; + } + virtual void BeginPlay() override; virtual void EndPlay(const EEndPlayReason::Type EndPlayReason) override; UFUNCTION() void OnLoginSuccess(); - }; diff --git a/Source/ActionRPGGame/Public/Menu/ARRegisterView.h b/Source/ActionRPGGame/Public/Menu/ARRegisterView.h new file mode 100644 index 0000000..ec08a49 --- /dev/null +++ b/Source/ActionRPGGame/Public/Menu/ARRegisterView.h @@ -0,0 +1,47 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" + +#include "Components/EditableTextBox.h" +#include "Components/Button.h" +#include "Components/TextBlock.h" + +#include "ARRegisterView.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARRegisterView : public UUserWidget +{ + GENERATED_BODY() + +public: + virtual void NativeConstruct() override; + +protected: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UEditableTextBox* UserNameBox; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UEditableTextBox* DisplayNameBox; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UEditableTextBox* PasswordBox; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UButton* RegisterButton; + + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UTextBlock* WarrningText; + + + UFUNCTION() + void OnRegisterClicked(); + + UFUNCTION() + void OnRegisterSuccess(); + + UFUNCTION() + void OnRegisterFailed(); +}; diff --git a/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h b/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h index 2441966..7710ca3 100644 --- a/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h +++ b/Source/ActionRPGGame/Public/UI/Menu/ARLoginScreenView.h @@ -29,6 +29,9 @@ class ACTIONRPGGAME_API UARLoginScreenView : public UARUMGWidgetBase UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UButton* LoginButton; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UButton* RegisterButton; + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) UTextBlock* WarrningText; @@ -40,4 +43,7 @@ class ACTIONRPGGAME_API UARLoginScreenView : public UARUMGWidgetBase UFUNCTION() void OnLoginFailed(); + + UFUNCTION() + void OnRegisterClicked(); }; From 65b41e99cd77a182f31c35fe6b7aaa4fb290bd0a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 20 May 2018 23:39:55 +0200 Subject: [PATCH 178/187] added item spawner, enemy spawner, fixed replication error --- Config/DefaultEngine.ini | 86 +++++----- .../Private/AFAbilityComponent.cpp | 30 +++- .../GAAbilityTask_TargetDataLineTrace.cpp | 61 ++++++- .../Private/Attributes/GAAttributeBase.cpp | 38 +---- .../Private/Attributes/GAAttributesBase.cpp | 1 + .../Private/Effects/GABlueprintLibrary.cpp | 47 +++++- .../Public/AFAbilityComponent.h | 7 +- .../Tasks/GAAbilityTask_TargetDataLineTrace.h | 8 +- .../Public/Attributes/GAAttributeBase.h | 23 ++- .../Public/Effects/GAGameEffect.h | 8 +- .../AbilityFramework/Public/GAGlobalTypes.h | 16 +- .../Private/IFInventoryComponent.cpp | 2 + .../Public/IFItemActorBase.h | 1 + .../Private/AI/ARAICharacter.cpp | 5 +- .../ActionRPGGame/Private/AREnemySpawner.cpp | 80 +++++++++ .../Private/ARItemPickupBase.cpp | 7 +- .../Private/ARItemSpawnerBase.cpp | 56 +++++++ .../Private/ARPlayerController.cpp | 32 +++- .../Attributes/ARCharacterAttributes.cpp | 8 + Source/ActionRPGGame/Private/UI/ARHUD.cpp | 157 ++++++++++++++++++ .../Private/UI/ARUIComponent.cpp | 10 +- .../Private/UI/HUD/AREnemyHealthBar.cpp | 25 --- .../Private/UI/HUD/ARHUDEnemyHealthBar.cpp | 9 + .../UI/HUD/ARHUDFloatingCombatText.cpp | 105 ++++++++++++ .../ActionRPGGame/Public/AI/ARAICharacter.h | 6 + Source/ActionRPGGame/Public/AREnemySpawner.h | 55 ++++++ .../ActionRPGGame/Public/ARItemPickupBase.h | 12 +- .../ActionRPGGame/Public/ARItemSpawnerBase.h | 46 +++++ .../ActionRPGGame/Public/ARPlayerController.h | 2 + .../Public/Attributes/ARCharacterAttributes.h | 5 +- Source/ActionRPGGame/Public/UI/ARHUD.h | 40 ++++- .../ActionRPGGame/Public/UI/ARUIComponent.h | 9 +- .../Public/UI/HUD/AREnemyHealthBar.h | 24 --- .../Public/UI/HUD/ARHUDEnemyHealthBar.h | 24 +++ .../Public/UI/HUD/ARHUDFloatingCombatText.h | 98 +++++++++++ 35 files changed, 967 insertions(+), 176 deletions(-) create mode 100644 Source/ActionRPGGame/Private/AREnemySpawner.cpp create mode 100644 Source/ActionRPGGame/Private/ARItemSpawnerBase.cpp delete mode 100644 Source/ActionRPGGame/Private/UI/HUD/AREnemyHealthBar.cpp create mode 100644 Source/ActionRPGGame/Private/UI/HUD/ARHUDEnemyHealthBar.cpp create mode 100644 Source/ActionRPGGame/Private/UI/HUD/ARHUDFloatingCombatText.cpp create mode 100644 Source/ActionRPGGame/Public/AREnemySpawner.h create mode 100644 Source/ActionRPGGame/Public/ARItemSpawnerBase.h delete mode 100644 Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.h create mode 100644 Source/ActionRPGGame/Public/UI/HUD/ARHUDEnemyHealthBar.h create mode 100644 Source/ActionRPGGame/Public/UI/HUD/ARHUDFloatingCombatText.h diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index fad1ee0..4be865b 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -80,6 +80,48 @@ gc.BlueprintClusteringEnabled=True [/Script/NoesisRuntime.NoesisSettings] GlyphTextureSize=x4096 +[/Script/Engine.PhysicsSettings] +DefaultGravityZ=-980.000000 +DefaultTerminalVelocity=4000.000000 +DefaultFluidFriction=0.300000 +SimulateScratchMemorySize=262144 +RagdollAggregateThreshold=4 +TriangleMeshTriangleMinAreaThreshold=5.000000 +bEnableAsyncScene=True +bEnableShapeSharing=True +bEnablePCM=True +bEnableStabilization=True +bWarnMissingLocks=True +bEnable2DPhysics=False +PhysicErrorCorrection=(LinearDeltaThresholdSq=5.000000,LinearInterpAlpha=0.200000,LinearRecipFixTime=1.000000,AngularDeltaThreshold=0.628319,AngularInterpAlpha=0.100000,AngularRecipFixTime=1.000000,BodySpeedThresholdSq=0.200000) +LockedAxis=Invalid +DefaultDegreesOfFreedom=Full3D +BounceThresholdVelocity=200.000000 +FrictionCombineMode=Average +RestitutionCombineMode=Average +MaxAngularVelocity=3600.000000 +MaxDepenetrationVelocity=0.000000 +ContactOffsetMultiplier=0.020000 +MinContactOffset=2.000000 +MaxContactOffset=8.000000 +bSimulateSkeletalMeshOnDedicatedServer=True +DefaultShapeComplexity=CTF_UseSimpleAndComplex +bDefaultHasComplexCollision=True +bSuppressFaceRemapTable=False +bSupportUVFromHitResults=False +bDisableActiveActors=False +bDisableCCD=False +bEnableEnhancedDeterminism=True +MaxPhysicsDeltaTime=0.033333 +bSubstepping=True +bSubsteppingAsync=True +MaxSubstepDeltaTime=0.033000 +MaxSubsteps=2 +SyncSceneSmoothingFactor=0.000000 +AsyncSceneSmoothingFactor=0.990000 +InitialAverageFrameRate=0.016667 +PhysXTreeRebuildRate=10 + [/Script/Engine.CollisionProfile] -Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) -Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) @@ -117,7 +159,7 @@ GlyphTextureSize=x4096 +Profiles=(Name="Ragdoll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="PhysicsBody",CustomResponses=((Channel="Pawn",Response=ECR_Ignore),(Channel="Visibility",Response=ECR_Ignore)),HelpMessage="Simulating Skeletal Mesh Component. All other channels will be set to default.",bCanModify=False) +Profiles=(Name="Vehicle",CollisionEnabled=QueryAndPhysics,ObjectTypeName="Vehicle",CustomResponses=,HelpMessage="Vehicle object that blocks Vehicle, WorldStatic, and WorldDynamic. All other channels will be set to default.",bCanModify=False) +Profiles=(Name="UI",CollisionEnabled=QueryOnly,ObjectTypeName="WorldDynamic",CustomResponses=((Channel="WorldStatic",Response=ECR_Overlap),(Channel="Pawn",Response=ECR_Overlap),(Channel="Visibility"),(Channel="WorldDynamic",Response=ECR_Overlap),(Channel="Camera",Response=ECR_Overlap),(Channel="PhysicsBody",Response=ECR_Overlap),(Channel="Vehicle",Response=ECR_Overlap),(Channel="Destructible",Response=ECR_Overlap)),HelpMessage="WorldStatic object that overlaps all actors by default. All new custom channels will use its own default response. ",bCanModify=False) -+DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Block,bTraceType=True,bStaticObject=False) ++DefaultChannelResponses=(Channel=ECC_GameTraceChannel1,Name="Enemy",DefaultResponse=ECR_Ignore,bTraceType=True,bStaticObject=False) +DefaultChannelResponses=(Channel=ECC_GameTraceChannel2,Name="Pickup",DefaultResponse=ECR_Overlap,bTraceType=True,bStaticObject=False) +DefaultChannelResponses=(Channel=ECC_GameTraceChannel3,Name="Weapon",DefaultResponse=ECR_Overlap,bTraceType=True,bStaticObject=False) +DefaultChannelResponses=(Channel=ECC_GameTraceChannel4,Name="PikcupObject",DefaultResponse=ECR_Ignore,bTraceType=False,bStaticObject=False) @@ -141,46 +183,4 @@ GlyphTextureSize=x4096 +CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") -[/Script/Engine.PhysicsSettings] -DefaultGravityZ=-980.000000 -DefaultTerminalVelocity=4000.000000 -DefaultFluidFriction=0.300000 -SimulateScratchMemorySize=262144 -RagdollAggregateThreshold=4 -TriangleMeshTriangleMinAreaThreshold=5.000000 -bEnableAsyncScene=True -bEnableShapeSharing=True -bEnablePCM=True -bEnableStabilization=True -bWarnMissingLocks=True -bEnable2DPhysics=False -PhysicErrorCorrection=(LinearDeltaThresholdSq=5.000000,LinearInterpAlpha=0.200000,LinearRecipFixTime=1.000000,AngularDeltaThreshold=0.628319,AngularInterpAlpha=0.100000,AngularRecipFixTime=1.000000,BodySpeedThresholdSq=0.200000) -LockedAxis=Invalid -DefaultDegreesOfFreedom=Full3D -BounceThresholdVelocity=200.000000 -FrictionCombineMode=Average -RestitutionCombineMode=Average -MaxAngularVelocity=3600.000000 -MaxDepenetrationVelocity=0.000000 -ContactOffsetMultiplier=0.020000 -MinContactOffset=2.000000 -MaxContactOffset=8.000000 -bSimulateSkeletalMeshOnDedicatedServer=True -DefaultShapeComplexity=CTF_UseSimpleAndComplex -bDefaultHasComplexCollision=True -bSuppressFaceRemapTable=False -bSupportUVFromHitResults=False -bDisableActiveActors=False -bDisableCCD=False -bEnableEnhancedDeterminism=True -MaxPhysicsDeltaTime=0.033333 -bSubstepping=True -bSubsteppingAsync=True -MaxSubstepDeltaTime=0.033000 -MaxSubsteps=2 -SyncSceneSmoothingFactor=0.000000 -AsyncSceneSmoothingFactor=0.990000 -InitialAverageFrameRate=0.016667 -PhysXTreeRebuildRate=10 - diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp index b384135..29b29a8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -99,13 +99,39 @@ void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHa Data.Target = Context.Target; Data.Location = Context.HitResult.Location; OnAttributeModifed.Broadcast(Data); - NotifyInstigatorTargetAttributeChanged(Data, Context); + Context.InstigatorComp->NotifyInstigatorTargetAttributeChanged(Data, Context); //add default replication (PropertyRep) that attribute changed. }; void UAFAbilityComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, const FGAEffectContext& InContext) { - InContext.InstigatorComp->OnTargetAttributeModifed.Broadcast(InData); + ENetMode NM = GetOwner()->GetNetMode(); + + switch (NM) + { + case NM_Standalone: + ClientNotifyAttributeModifier(InData); + break; + case NM_DedicatedServer: + ServerOnTargetAttributeModifed.Broadcast(InData); + ClientNotifyAttributeModifier(InData); + break; + case NM_ListenServer: + ServerOnTargetAttributeModifed.Broadcast(InData); + ClientNotifyAttributeModifier(InData); + break; + case NM_Client: + ClientNotifyAttributeModifier(InData); + break; + case NM_MAX: + break; + default: + break; + } +} +void UAFAbilityComponent::ClientNotifyAttributeModifier_Implementation(const FAFAttributeChangedData& InData) +{ + OnTargetAttributeModifed.Broadcast(InData); } void UAFAbilityComponent::GetAttributeStructTest(FGAAttribute Name) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp index 38115e5..e1d2875 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.cpp @@ -41,6 +41,7 @@ void UGAAbilityTask_TargetDataLineTrace::Activate() { case EAFConfirmType::Instant: { + HitData = LineTrace(); LocalHitResult = HitData; //OnClient... Is called on both Client and server and is result of local simulation @@ -51,13 +52,13 @@ void UGAAbilityTask_TargetDataLineTrace::Activate() //for hits. if (IsServerOrStandalone()) { - OnClientReceiveTargetData.Broadcast(HitData); + //OnClientReceiveTargetData.Broadcast(HitData); OnServerReceiveTargetData.Broadcast(HitData); - EndTask(); + } else { - OnClientReceiveTargetData.Broadcast(HitData); + OnClientUnconfirmedTargetData.Broadcast(HitData); } break; } @@ -78,7 +79,7 @@ void UGAAbilityTask_TargetDataLineTrace::Activate() break; } } - if (HitData.IsValidBlockingHit()) + //if (HitData.IsValidBlockingHit()) { if (AbilityComponent->GetOwnerRole() < ROLE_Authority) { @@ -92,15 +93,21 @@ void UGAAbilityTask_TargetDataLineTrace::Activate() TraceData.ExactPing = ExactPing; TraceData.HitActor = HitData.GetActor(); TraceData.HitLocation = HitData.Location; - ServerConfirmHitInfo(TraceData); + } } + if (AbilityComponent->GetOwnerRole() == ROLE_Authority) + { + EndTask(); + } + } void UGAAbilityTask_TargetDataLineTrace::ServerConfirmHitInfo_Implementation(FAFLineTraceData TraceData) { int test = 0; + UE_LOG(AbilityFramework, Log, TEXT("%s Server Confirm Hit"), *GetName()); FAFLineTraceConfirmData ConfirmData; ConfirmData.bConfirmed = true; ConfirmData.HitActor = LocalHitResult.GetActor(); @@ -116,15 +123,18 @@ void UGAAbilityTask_TargetDataLineTrace::ClientConfirmHitInfo_Implementation(FAF { if (ConfirmData.bConfirmed) { - OnServerReceiveTargetData.Broadcast(LocalHitResult); + UE_LOG(AbilityFramework, Log, TEXT("%s Client Hit Confirmed"), *GetName()); + OnClientReceiveTargetData.Broadcast(LocalHitResult); } else { + UE_LOG(AbilityFramework, Log, TEXT("%s Client Hit Overrided"), *GetName()); LocalHitResult.Actor = ConfirmData.HitActor; LocalHitResult.Location = ConfirmData.HitLocation; LocalHitResult.ImpactPoint = ConfirmData.HitLocation; - OnServerReceiveTargetData.Broadcast(LocalHitResult); + OnClientReceiveTargetData.Broadcast(LocalHitResult); } + EndTask(); } // --------------------------------------------------------------------------------------- @@ -132,13 +142,46 @@ void UGAAbilityTask_TargetDataLineTrace::ClientConfirmHitInfo_Implementation(FAF void UGAAbilityTask_TargetDataLineTrace::OnConfirm() { FHitResult Hit = LineTrace(); - OnConfirmed.Broadcast(Hit); + //OnConfirmed.Broadcast(Hit); + Ability->OnConfirmDelegate.RemoveAll(this); } void UGAAbilityTask_TargetDataLineTrace::OnCastEndedConfirm() { FHitResult Hit = LineTrace(); - OnClientReceiveTargetData.Broadcast(Hit); + LocalHitResult = Hit; + //OnClient... Is called on both Client and server and is result of local simulation + //unconfirmed by server. This result might get overrided when data from server arrive to client + //it's good to spawn some cosmetic effects, but shouldn't be used to actually confirm hit result on client. + + //OnServer.. is confirmed by server that we got hit (or not), and should be used to show client confirmation + //for hits. + if (AbilityComponent->GetOwnerRole() < ROLE_Authority) + { + APlayerController* PC = Ability->PCOwner; + APawn* P = Ability->POwner; + + PC->PlayerState->RecalculateAvgPing(); + float ExactPing = PC->PlayerState->ExactPing; + + FAFLineTraceData TraceData; + TraceData.ExactPing = ExactPing; + TraceData.HitActor = Hit.GetActor(); + TraceData.HitLocation = Hit.Location; + ServerConfirmHitInfo(TraceData); + + } + + if (IsServerOrStandalone()) + { + //OnClientReceiveTargetData.Broadcast(HitData); + OnServerReceiveTargetData.Broadcast(Hit); + EndTask(); + } + else + { + OnClientUnconfirmedTargetData.Broadcast(Hit); + } bIsTickable = false; EndTask(); } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp index 86555d3..9687149 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -18,14 +18,14 @@ DEFINE_STAT(STAT_FinalBonusByTag); //} FAFAttributeBase::FAFAttributeBase() : CurrentValue(0), - BonusValue(0) + BaseBonusValue(0) { Modifiers.AddDefaulted(7); }; FAFAttributeBase::FAFAttributeBase(float BaseValueIn) : BaseValue(BaseValueIn), CurrentValue(BaseValue), - BonusValue(0) + BaseBonusValue(0) { Modifiers.AddDefaulted(7); }; @@ -53,7 +53,7 @@ void FAFAttributeBase::CopyFromOther(FAFAttributeBase* Other) MinValue = Other->MinValue; MaxValue = Other->MaxValue; CurrentValue = Other->CurrentValue; - BonusValue = Other->BonusValue; + BaseBonusValue = Other->BaseBonusValue; CurrentValue = BaseValue; CalculateBonus(); @@ -87,35 +87,15 @@ void FAFAttributeBase::CalculateBonus() { DivideBonus += ModIt->Value.Value; } - //for (ModIt; ModIt; ++ModIt) - //{ - // const FGAEffectMod& mod = ModIt->Value; - // switch (mod.AttributeMod) - // { - // case EGAAttributeMod::Add: - // AdditiveBonus += mod.Value; - // break; - // case EGAAttributeMod::Subtract: - // SubtractBonus += mod.Value; - // break; - // case EGAAttributeMod::Multiply: - // MultiplyBonus += mod.Value; - // break; - // case EGAAttributeMod::Divide: - // DivideBonus += mod.Value; - // break; - // default: - // break; - // } - //} - float OldBonus = BonusValue; + + float OldBonus = BaseBonusValue; //calculate final bonus from modifiers values. //we don't handle stacking here. It's checked and handled before effect is added. - BonusValue = (AdditiveBonus - SubtractBonus); - BonusValue = (BonusValue * MultiplyBonus); - BonusValue = (BonusValue / DivideBonus); + BaseBonusValue = (AdditiveBonus - SubtractBonus); + BaseBonusValue = (BaseBonusValue * MultiplyBonus); + BaseBonusValue = (BaseBonusValue / DivideBonus); //this is absolute maximum (not clamped right now). - float addValue = BonusValue - OldBonus; + float addValue = BaseBonusValue - OldBonus; //reset to max = 200 CurrentValue = CurrentValue + addValue; /* diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp index 92ad91a..cae8b06 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp @@ -295,6 +295,7 @@ float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty) { FAFAttributeBase* attr = nullptr; + UGAAttributesBase* atrObj = this; attr = GetAttribute(ModIn.Attribute); float OutVal = -1; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp index 043cc0d..bee30fc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp @@ -11,7 +11,7 @@ #include "AFEffectCustomApplication.h" #include "GAEffectExtension.h" - +#include "Engine/Engine.h" #include "AFSimpleInterface.h" #include "AFAttributeInterface.h" @@ -55,6 +55,23 @@ FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation( return ApplyEffectFromHit(InEffect, Handle, Target, Instigator, Causer, Modifier); } +FString NetModeToString(ENetMode NetMode) +{ + switch (NetMode) + { + case ENetMode::NM_Client: + return FString("Client"); + case ENetMode::NM_DedicatedServer: + return FString("Server"); + case ENetMode::NM_ListenServer: + return FString("ListenServer"); + case ENetMode::NM_Standalone: + return FString("Standalone"); + } + + return FString("Invalid"); +} + FGAEffectHandle UGABlueprintLibrary::ApplyEffect( FAFPropertytHandle& InEffect , const FGAEffectHandle& Handle @@ -64,6 +81,10 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( , const FHitResult& HitIn , const FAFFunctionModifier& Modifier) { + ENetMode NetMode = GEngine->GetNetMode(Instigator->GetWorld()); + + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect START, NetMode %s"), *NetModeToString(NetMode)); + UE_LOG(GameAttributesEffects, Error, TEXT("-----")); IAFAbilityInterface* Ability = Cast(Causer); if (!Ability) { @@ -90,17 +111,19 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( //only reused Spec and Context if effect is instant ? if (Handle.IsValid() && !bPeriodicEffect) { + Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + FAFContextHandle ExistingContext = InEffect.GetContext(Handle); - if (ExistingContext.IsValid()) + /*if (ExistingContext.IsValid()) { Context = ExistingContext; Context.SetTarget(Target); bReusedParams = true; - } - FAFEffectSpecHandle SpecHandle = InEffect.GetEffectSpec(Handle); + }*/ + /*FAFEffectSpecHandle SpecHandle = InEffect.GetEffectSpec(Handle); EffectSpecHandle = SpecHandle; bReusedParams = true; - bReusedSpec = true; + bReusedSpec = true;*/ } else { @@ -121,7 +144,7 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); return FGAEffectHandle(); } - + if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) { @@ -144,23 +167,33 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( IAFAbilityInterface* InstigatorInterface = Cast(Instigator); FAFEffectParams Params(InEffect); - + if (Params.EffectSpec.GetPtr()) + { + UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + } if (!bReusedSpec) { FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); AddTagsToEffect(EffectSpec); Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); + UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *EffectSpec->GetContext().GetPtr()->Target->GetName()); } else { Params.EffectSpec = EffectSpecHandle; + Params.EffectSpec.SetContext(Context); } + UE_LOG(GameAttributesEffects, Log, TEXT(" Post Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); Params.bRecreated = bReusedParams; Params.bPeriodicEffect = bPeriodicEffect; Params.Context = Context; FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); + + UE_LOG(GameAttributesEffects, Error, TEXT("-----")); + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect END")); + return NewHandle; } FGAEffectHandle UGABlueprintLibrary::ApplyEffect( diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h index 1f46e63..49113cd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -240,9 +240,10 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public UPROPERTY(BlueprintAssignable, Category = "Game Attributes") FGAOnAttributeModifed OnAttributeModifed; + UPROPERTY(BlueprintAssignable, Category = "Game Attributes") + FGAOnAttributeModifed ServerOnTargetAttributeModifed; UPROPERTY(BlueprintAssignable, Category = "Game Attributes") FGAOnAttributeModifed OnTargetAttributeModifed; - TMap AttributeChanged; @@ -339,6 +340,10 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, const FGAEffectContext& InContext); + + UFUNCTION(Client, Unreliable) + void ClientNotifyAttributeModifier(const FAFAttributeChangedData& InData); + void ClientNotifyAttributeModifier_Implementation(const FAFAttributeChangedData& InData); FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return DefaultAttributes->GetAttribute(AttributeIn); }; void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) { DefaultAttributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; float NativeGetAttributeValue(const FGAAttribute AttributeIn) const { return 0; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h index bf137c2..4e317fc 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/Tasks/GAAbilityTask_TargetDataLineTrace.h @@ -46,12 +46,12 @@ class ABILITYFRAMEWORK_API UGAAbilityTask_TargetDataLineTrace : public UGAAbilit { GENERATED_BODY() public: - UPROPERTY(BlueprintAssignable) - FAFOnTargetReceived OnConfirmed; - UPROPERTY(BlueprintAssignable) FAFOnTargetReceived OnClientReceiveTargetData; - + + UPROPERTY(BlueprintAssignable) + FAFOnTargetReceived OnClientUnconfirmedTargetData; + UPROPERTY(BlueprintAssignable) FAFOnTargetReceived OnServerReceiveTargetData; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index 5d9b675..98ab568 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -63,16 +63,29 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase { GENERATED_BODY() public: + UPROPERTY(EditAnywhere, SaveGame) float BaseValue; + /* + Bonus Value applied to BaseValue of Attribute. It should never be directly modified outside of AbilityFramework. + */ + UPROPERTY(SaveGame) + float BaseBonusValue; + UPROPERTY(EditAnywhere, SaveGame) float MinValue; + UPROPERTY(EditAnywhere, SaveGame) float MaxValue; + /* + Bonus to the MaxValue. + */ UPROPERTY(SaveGame) - float CurrentValue; + float BonusMaxValue; + UPROPERTY(SaveGame) - float BonusValue; + float CurrentValue; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Value") TSubclassOf ExtensionClass; @@ -91,9 +104,13 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase //used internally. NEver call it directly. inline void SetCurrentValue(float ValueIn) { CurrentValue = ValueIn; } + /* + Gets current absolute maximum of value of the attribute. + BaseValue + BonusValue, clamped by MaxValue. + */ inline float GetFinalValue() { - return FMath::Clamp(BaseValue + BonusValue, MinValue, MaxValue); + return FMath::Clamp(BaseValue + BaseBonusValue, MinValue, MaxValue); }; inline float GetCurrentValue() { return CurrentValue; }; void CalculateBonus(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h index 64be531..97da961 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h @@ -451,12 +451,17 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject void OnExpired(); void OnRemoved(); void OnExecuted(); - + FAFContextHandle GetContext() + { + return Context; + } FGAEffectMod GetModifier() { return EffectMod; } + inline void SetContext(const FAFContextHandle& InContext) { Context = InContext; } + void AddOwnedTags(const FGameplayTagContainer& InTags) { OwnedTags.AppendTags(InTags); @@ -554,6 +559,7 @@ struct ABILITYFRAMEWORK_API FAFEffectSpecHandle { SpecPtr->CalculateAttributeModifier(InHandlet); } + inline void SetContext(const FAFContextHandle& InContext) { SpecPtr->SetContext(InContext); } }; template<> struct TStructOpsTypeTraits< FAFEffectSpecHandle > : public TStructOpsTypeTraitsBase2 diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h index 48e4738..e54a0ff 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h @@ -549,8 +549,10 @@ USTRUCT() struct ABILITYFRAMEWORK_API FGAEffectMod { GENERATED_BODY() +public: FGAAttribute Attribute; - float Value; + UPROPERTY() + float Value; EGAAttributeMod AttributeMod; struct FGAEffectHandle Handle; FGameplayTagContainer AttributeTags; @@ -629,12 +631,16 @@ struct ABILITYFRAMEWORK_API FAFAttributeChangedData { GENERATED_BODY() public: - FGAEffectMod Mod; + UPROPERTY() + FGAEffectMod Mod; + UPROPERTY() TWeakObjectPtr Target; - //HitLocation of applicable; - FVector Location; - float NewValue; + UPROPERTY() + FVector Location; + + UPROPERTY() + float NewValue; }; /* diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp index 005ba80..5310b43 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFInventoryComponent.cpp @@ -165,6 +165,7 @@ void UIFInventoryComponent::AddAllItemsFromActor(class AIFItemActorBase* Source) return; } TArray> Items = Source->GetAllItems(); + Source->OnItemPicked(); for (const TSoftClassPtr Item : Items) { FStreamableManager& Manager = UAssetManager::GetStreamableManager(); @@ -185,6 +186,7 @@ void UIFInventoryComponent::ServerAddAllItemsFromActor_Implementation(class AIFI Manager.RequestAsyncLoad(Item.ToSoftObjectPath(), Delegate); } + Source->OnItemPicked(); } bool UIFInventoryComponent::ServerAddAllItemsFromActor_Validate(class AIFItemActorBase* Sourcex) { diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h index 2958dbf..ea167bc 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFItemActorBase.h @@ -27,6 +27,7 @@ class INVENTORYFRAMEWORK_API AIFItemActorBase : public AActor // Called every frame virtual void Tick(float DeltaTime) override; + virtual void OnItemPicked() {}; protected: TArray> GetAllItems(); diff --git a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp index 0c6de26..d395427 100644 --- a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp +++ b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp @@ -18,7 +18,10 @@ void AARAICharacter::BeginPlay() Super::BeginPlay(); } - +void AARAICharacter::OnSpawned(class AAREnemySpawner* InSpawnedBy) +{ + SpawnedBy = InSpawnedBy; +} // Called every frame void AARAICharacter::Tick(float DeltaTime) { diff --git a/Source/ActionRPGGame/Private/AREnemySpawner.cpp b/Source/ActionRPGGame/Private/AREnemySpawner.cpp new file mode 100644 index 0000000..82bc88c --- /dev/null +++ b/Source/ActionRPGGame/Private/AREnemySpawner.cpp @@ -0,0 +1,80 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AREnemySpawner.h" +#include "Engine/World.h" +#include "AI/ARAICharacter.h" + + +// Sets default values +AAREnemySpawner::AAREnemySpawner() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + MaxSpawned = 7; + BatchSpawn = 1; + TimeBetweenSpawns = 0.3; + MinRespawn = 4; +} + +// Called when the game starts or when spawned +void AAREnemySpawner::BeginPlay() +{ + Super::BeginPlay(); + SetupSpawner(); +} + +void AAREnemySpawner::SetupSpawner() +{ + if (Role == ROLE_Authority) + { + FTimerDelegate Delegate = FTimerDelegate::CreateUObject(this, &AAREnemySpawner::HandleSpawn); + + FTimerManager& Timer = GetWorld()->GetTimerManager(); + Timer.SetTimer(SpawnerHandle, Delegate, TimeBetweenSpawns, true); + } +} + +// Called every frame +void AAREnemySpawner::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); +} + +void AAREnemySpawner::OnEnemyKilled(AARAICharacter* InEnemy) +{ + SpawnedEnemies.Remove(InEnemy); + if (SpawnedEnemies.Num() < MinRespawn) + { + SetupSpawner(); + } +} + +void AAREnemySpawner::HandleSpawn() +{ + if (SpawnPositions.Num() < MaxSpawned) + { + return; + } + if (SpawnedEnemies.Num() >= MaxSpawned) + { + FTimerManager& Timer = GetWorld()->GetTimerManager(); + Timer.ClearTimer(SpawnerHandle); + return; + } + + + FActorSpawnParameters SpawnParams; + SpawnParams.SpawnCollisionHandlingOverride = ESpawnActorCollisionHandlingMethod::AlwaysSpawn; + + for (int32 Idx = 0; Idx < BatchSpawn; Idx++) + { + FTransform Transform; + const FVector SpawnPos = SpawnPositions[SpawnedEnemies.Num()] + GetActorLocation(); + Transform.SetLocation(SpawnPos); + Transform.SetScale3D(FVector(1)); + + AARAICharacter* Enemy = GetWorld()->SpawnActor(EnemyClass, Transform, SpawnParams); + Enemy->OnSpawned(this); + SpawnedEnemies.Add(Enemy); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARItemPickupBase.cpp b/Source/ActionRPGGame/Private/ARItemPickupBase.cpp index 5496dfe..d6185c1 100644 --- a/Source/ActionRPGGame/Private/ARItemPickupBase.cpp +++ b/Source/ActionRPGGame/Private/ARItemPickupBase.cpp @@ -1,13 +1,14 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARItemPickupBase.h" - +#include "ARItemSpawnerBase.h" // Sets default values AARItemPickupBase::AARItemPickupBase() { // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. PrimaryActorTick.bCanEverTick = true; + bReplicates = true; } @@ -25,3 +26,7 @@ void AARItemPickupBase::Tick(float DeltaTime) } +void AARItemPickupBase::OnItemPicked() +{ + SpawnedBy->OnItemPicked(); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARItemSpawnerBase.cpp b/Source/ActionRPGGame/Private/ARItemSpawnerBase.cpp new file mode 100644 index 0000000..23b6552 --- /dev/null +++ b/Source/ActionRPGGame/Private/ARItemSpawnerBase.cpp @@ -0,0 +1,56 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARItemSpawnerBase.h" +#include "TimerManager.h" +#include "Engine/World.h" +#include "ARItemPickupBase.h" + + +// Sets default values +AARItemSpawnerBase::AARItemSpawnerBase() +{ + // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. + PrimaryActorTick.bCanEverTick = true; + +} + +// Called when the game starts or when spawned +void AARItemSpawnerBase::BeginPlay() +{ + Super::BeginPlay(); + if (Role == ENetRole::ROLE_Authority) + { + FActorSpawnParameters SpawnParams; + const FVector Location = GetActorLocation(); + + AARItemPickupBase* SpawnedItem = GetWorld()->SpawnActor(ItemsToSpawn, Location, GetActorRotation(), SpawnParams); + SpawnedItem->SetSpawnedBy(this); + } +} + +// Called every frame +void AARItemSpawnerBase::Tick(float DeltaTime) +{ + Super::Tick(DeltaTime); + +} + +void AARItemSpawnerBase::OnItemPicked() +{ + if (RespawnTime <= KINDA_SMALL_NUMBER) + return; + + FTimerManager& Timer = GetWorld()->GetTimerManager(); + + FTimerDelegate Delegate = FTimerDelegate::CreateUObject(this, &AARItemSpawnerBase::HandleRespawn); + Timer.SetTimer(RespawnHandle, Delegate, RespawnTime, false, RespawnTime); + +} +void AARItemSpawnerBase::HandleRespawn() +{ + FActorSpawnParameters SpawnParams; + const FVector Location = GetActorLocation(); + + AARItemPickupBase* SpawnedItem = GetWorld()->SpawnActor(ItemsToSpawn, Location, GetActorRotation(), SpawnParams); + SpawnedItem->SetSpawnedBy(this); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARPlayerController.cpp b/Source/ActionRPGGame/Private/ARPlayerController.cpp index 8835c03..3788048 100644 --- a/Source/ActionRPGGame/Private/ARPlayerController.cpp +++ b/Source/ActionRPGGame/Private/ARPlayerController.cpp @@ -7,6 +7,9 @@ #include "Engine/AssetManager.h" #include "ARAbilityBase.h" #include "ARCharacter.h" +#include "Engine/GameViewportClient.h" +#include "Engine/LocalPlayer.h" +#include "Components/CapsuleComponent.h" #include "Abilities/ARAbilityManagerComponent.h" @@ -172,4 +175,31 @@ void AARPlayerController::OnInventoryReplicated(class UIFInventoryComponent* Inv UIComponent->InitializeInventory(); } } -/* IIFInventoryInterface */ \ No newline at end of file +/* IIFInventoryInterface */ + +float AARPlayerController::ComputeBoundsScreenSize(UCapsuleComponent* InTarget) +{ + ULocalPlayer const* const LP = GetLocalPlayer(); + FVector4 ViewOrigin; + FMatrix ProjMatrix; + if (LP && LP->ViewportClient) + { + // get the projection data + FSceneViewProjectionData ProjectionData; + if (LP->GetProjectionData(LP->ViewportClient->Viewport, eSSP_FULL, /*out*/ ProjectionData)) + { + ViewOrigin = ProjectionData.ViewOrigin; + ProjMatrix = ProjectionData.ProjectionMatrix; + } + } + const float Dist = FVector::Dist(InTarget->Bounds.Origin, ViewOrigin); + + // Get projection multiple accounting for view scaling. + const float ScreenMultiple = FMath::Max(0.5f * ProjMatrix.M[0][0], 0.5f * ProjMatrix.M[1][1]); + + // Calculate screen-space projected radius + const float ScreenRadius = ScreenMultiple * InTarget->Bounds.SphereRadius / FMath::Max(1.0f, Dist); + + // For clarity, we end up comparing the diameter + return ScreenRadius * 2.0f; +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp b/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp index 7a48ba8..565d175 100644 --- a/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp +++ b/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp @@ -13,4 +13,12 @@ void UARCharacterAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeP DOREPLIFETIME(UARCharacterAttributes, Stamina); DOREPLIFETIME(UARCharacterAttributes, Ammo); DOREPLIFETIME(UARCharacterAttributes, MachineGunAmmo); +} + +void UARCharacterAttributes::OnRep_Health() +{ + if (Health.CurrentValue) + { + + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/ARHUD.cpp b/Source/ActionRPGGame/Private/UI/ARHUD.cpp index e3bbfdb..da28782 100644 --- a/Source/ActionRPGGame/Private/UI/ARHUD.cpp +++ b/Source/ActionRPGGame/Private/UI/ARHUD.cpp @@ -1,13 +1,28 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARHUD.h" +#include "Engine/GameViewportClient.h" +#include "Engine/LocalPlayer.h" +#include "Camera/CameraComponent.h" +#include "Kismet/GameplayStatics.h" +#include "ARCharacter.h" +#include "Attributes/ARCharacterAttributes.h" #include "UI/Inventory/ARUIInventoryComponent.h" + +#include "AFAbilityInterface.h" +#include "AFAbilityComponent.h" +#include "UI/HUD/ARHUDEnemyHealthBar.h" +#include "UI/HUD/ARHUDFloatingCombatText.h" + #include "ARPlayerController.h" AARHUD::AARHUD(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { UIInventoryComponent = ObjectInitializer.CreateDefaultSubobject(this, TEXT("UIInventoryComponent")); + DistanceScaleEnemyBar = 1000.0f; + HUDFloatingCombatTextClass = UARHUDFloatingCombatText::StaticClass(); + } void AARHUD::BeginPlay() @@ -16,10 +31,152 @@ void AARHUD::BeginPlay() if (AARPlayerController* PC = Cast(PlayerOwner)) { UIInventoryComponent->CreateInventoryView(PC); + + ARPC = PC; + ARCharacter = Cast(GetOwningPawn()); + if (HUDEnemyHealthBarClass) + { + HUDEnemyHealthBar = CreateWidget(PC, HUDEnemyHealthBarClass); + HUDEnemyHealthBar->AddToViewport(); + HUDEnemyHealthBar->SetVisibility(ESlateVisibility::Collapsed); + } + + if (HUDFloatingCombatTextClass) + { + FloatingCombatText = CreateWidget(PC, HUDFloatingCombatTextClass); + FloatingCombatText->AddToViewport(); + FloatingCombatText->SetVisibility(ESlateVisibility::HitTestInvisible); + FloatingCombatText->PC = ARPC; + FloatingCombatText->FCTMoveSpeed = FCTMoveSpeed; + FloatingCombatText->FCTLifeTime = FCTLifeTime; + FloatingCombatText->Font = FCTFont; + FloatingCombatText->Init(100); + } + + if (ARCharacter) + { + UAFAbilityComponent* ABComp = ARCharacter->GetAbilityComp(); + ABComp->OnTargetAttributeModifed.AddDynamic(this, &AARHUD::OnEnemyDamageCaused); + } + } +} + +void AARHUD::Tick(float InDeltaTime) +{ + Super::Tick(InDeltaTime); + + if (ARCharacter) + { + SetEnemyHitResult(); + UpdateEnemyBarInfo(); + FloatingCombatText->Update(InDeltaTime); + } + else + { + ARCharacter = Cast(GetOwningPawn()); } } void AARHUD::ShowHideInventory() { UIInventoryComponent->ShowHideInventory(); +} +float AARHUD::ComputeBoundsScreenSize(AActor* InTarget) +{ + ULocalPlayer const* const LP = ARPC->GetLocalPlayer(); + FVector4 ViewOrigin; + FMatrix ProjMatrix; + if (LP && LP->ViewportClient) + { + // get the projection data + FSceneViewProjectionData ProjectionData; + if (LP->GetProjectionData(LP->ViewportClient->Viewport, eSSP_FULL, /*out*/ ProjectionData)) + { + ViewOrigin = ProjectionData.ViewOrigin; + ProjMatrix = ProjectionData.ProjectionMatrix; + } + } + FBox Bounds = InTarget->GetComponentsBoundingBox(); + const float Dist = FVector::Dist(InTarget->GetActorLocation(), ViewOrigin); + + // Get projection multiple accounting for view scaling. + const float ScreenMultiple = FMath::Max(0.5f * ProjMatrix.M[0][0], 0.5f * ProjMatrix.M[1][1]); + + // Calculate screen-space projected radius + const float ScreenRadius = ScreenMultiple * Bounds.GetExtent().Z / FMath::Max(1.0f, Dist); + + // For clarity, we end up comparing the diameter + return ScreenRadius * 2.0f; +} +void AARHUD::SetEnemyHitResult() +{ + FVector Start = ARCharacter->GetFollowCamera()->GetComponentLocation(); + FVector Forward = ARCharacter->GetFollowCamera()->GetForwardVector(); + FVector End = (Forward * 10000.0) + Start; + ECollisionChannel CollisionChannel = UEngineTypes::ConvertToCollisionChannel(EnemyChannel); + FCollisionQueryParams Params; + Params.AddIgnoredActor(ARCharacter); + Params.bTraceComplex = false; + Params.OwnerTag = TEXT("HUDLineTrace"); + //make async ? + GetWorld()->LineTraceSingleByChannel(EnemyHitResult, Start, End, CollisionChannel, Params); +} +void AARHUD::UpdateEnemyBarInfo() +{ + if (EnemyHitResult.GetActor()) + { + AActor* Target = EnemyHitResult.GetActor(); + HUDEnemyHealthBar->SetVisibility(ESlateVisibility::HitTestInvisible); + FVector ActorLocation = EnemyHitResult.GetActor()->GetActorLocation(); + FVector2D ScreeLoc; + + UGameplayStatics::ProjectWorldToScreen(ARPC, ActorLocation, ScreeLoc, false); + + float Distance = FVector::Dist(ActorLocation, ARCharacter->GetActorLocation()); + Distance = DistanceScaleEnemyBar / Distance; + Distance = FMath::Clamp(Distance, 0.7, 1); + + float ScreenSize = ComputeBoundsScreenSize(Target); + FVector Extent = Target->GetComponentsBoundingBox().GetExtent(); + + float OffsetY = (Extent.Z * 7) * ScreenSize; + ScreeLoc.Y = ScreeLoc.Y - OffsetY; + + HUDEnemyHealthBar->SetPositionInViewport(ScreeLoc, true); + + FVector2D NewScale(Distance, Distance); + HUDEnemyHealthBar->SetRenderScale(NewScale); + if(IAFAbilityInterface* TargetInt = Cast(Target)) + { + UARCharacterAttributes* Attributes = TargetInt->GetAttributesTyped(); + if (Attributes) + { + float Percent = Attributes->Health.GetCurrentValue() / Attributes->Health.GetFinalValue(); + HUDEnemyHealthBar->UpdateHealth(Percent); + } + } + + } + else + { + HUDEnemyHealthBar->SetVisibility(ESlateVisibility::Collapsed); + } +} + +void AARHUD::OnEnemyDamageCaused(const FAFAttributeChangedData& InMod) +{ + AActor* Target = EnemyHitResult.GetActor(); + if (Target) + { + FVector2D ScreeLoc; + + UGameplayStatics::ProjectWorldToScreen(ARPC, EnemyHitResult.Location, ScreeLoc, false); + FloatingCombatText->SetInfo(InMod.Mod.Value, ScreeLoc); + } + else + { + FVector2D ScreeLoc; + UGameplayStatics::ProjectWorldToScreen(ARPC, InMod.Location, ScreeLoc, false); + FloatingCombatText->SetInfo(InMod.Mod.Value, ScreeLoc); + } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/ARUIComponent.cpp b/Source/ActionRPGGame/Private/UI/ARUIComponent.cpp index d21e789..33dc503 100644 --- a/Source/ActionRPGGame/Private/UI/ARUIComponent.cpp +++ b/Source/ActionRPGGame/Private/UI/ARUIComponent.cpp @@ -10,13 +10,14 @@ #include "Inventory/Weapons/ARItemWeaponWidget.h" #include "Inventory/ARInventoryScreenWidget.h" + + // Sets default values for this component's properties UARUIComponent::UARUIComponent() { // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features // off to improve performance if you don't need them. PrimaryComponentTick.bCanEverTick = true; - EnemyHealthBarClass = UAREnemyHealthBar::StaticClass(); bAutoRegister = true; bWantsInitializeComponent = true; // ... @@ -43,13 +44,6 @@ void UARUIComponent::BeginPlay() CrosshairWidget->AddToViewport(); } - if (EnemyHealthBarClass) - { - EnemyHealthBarWidget = CreateWidget(MyPC, EnemyHealthBarClass); - EnemyHealthBarWidget->SetVisibility(ESlateVisibility::Collapsed); - EnemyHealthBarWidget->AddToViewport(); - } - if (HUDWidgetClass) { HUDWidget = CreateWidget(MyPC, HUDWidgetClass); diff --git a/Source/ActionRPGGame/Private/UI/HUD/AREnemyHealthBar.cpp b/Source/ActionRPGGame/Private/UI/HUD/AREnemyHealthBar.cpp deleted file mode 100644 index 945c0ca..0000000 --- a/Source/ActionRPGGame/Private/UI/HUD/AREnemyHealthBar.cpp +++ /dev/null @@ -1,25 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AREnemyHealthBar.h" - - - - -void UAREnemyHealthBar::ReleaseSlateResources(bool bReleaseChildren) -{ - Super::ReleaseSlateResources(bReleaseChildren); -/* - MyTextBlock.Reset(); - HealthBar.Reset();*/ -} - -//TSharedRef UAREnemyHealthBar::RebuildWidget() -//{ -// MyTextBlock = SNew(STextBlock); -// MyTextBlock->SetText(FText::FromString("Test Widget")); -// -// HealthBar = SNew(SProgressBar); -// -// -// return MyTextBlock.ToSharedRef(); -//} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/HUD/ARHUDEnemyHealthBar.cpp b/Source/ActionRPGGame/Private/UI/HUD/ARHUDEnemyHealthBar.cpp new file mode 100644 index 0000000..8651abd --- /dev/null +++ b/Source/ActionRPGGame/Private/UI/HUD/ARHUDEnemyHealthBar.cpp @@ -0,0 +1,9 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHUDEnemyHealthBar.h" +#include "Components/ProgressBar.h" + +void UARHUDEnemyHealthBar::UpdateHealth(float NormalizedHealth) +{ + HealthBar->SetPercent(NormalizedHealth); +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/HUD/ARHUDFloatingCombatText.cpp b/Source/ActionRPGGame/Private/UI/HUD/ARHUDFloatingCombatText.cpp new file mode 100644 index 0000000..062259b --- /dev/null +++ b/Source/ActionRPGGame/Private/UI/HUD/ARHUDFloatingCombatText.cpp @@ -0,0 +1,105 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "ARHUDFloatingCombatText.h" +#include "Engine/Engine.h" + +#include "SlateOptMacros.h" + +#include "Slate.h" +#include "SlateCore.h" + +#include "Engine/GameViewportClient.h" +#include "Blueprint/WidgetLayoutLibrary.h" +#include "ARPlayerController.h" + +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION +void SFCTWidget::Construct(const FArguments& InArgs) +{ + + TAttribute fontInfo = TAttribute::Create(TAttribute::FGetter::CreateSP(this, &SFCTWidget::GetFontInfo)); + ChildSlot + [ + SNew(STextBlock).Text(this, &SFCTWidget::GetText).Font(fontInfo) + ]; +} +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +SFCTWidget::~SFCTWidget() +{ + +} +FSlateFontInfo SFCTWidget::GetFontInfo() const +{ + return Font; +} +FText SFCTWidget::GetText() const +{ + return Text; +} + +void UARHUDFloatingCombatText::Init(int32 Num) +{ + + Canvas = SNew(SConstraintCanvas); + GEngine->GameViewport->AddViewportWidgetContent(Canvas.ToSharedRef()); + for (int32 Idx = 0; Idx < Num; Idx++) + { + FARHUDFCTUpdate Update; + Update.Widget = SNew(SFCTWidget); + Update.Widget->Font = Font; + + Update.Slot = &Canvas->AddSlot() + [ + Update.Widget.ToSharedRef() + ]; + Update.Widget->SetVisibility(EVisibility::Collapsed); + Widgets.Add(Update); + } +} + +void UARHUDFloatingCombatText::Update(float InDeltaTime) +{ + for (uint8 Idx = 0; Idx < Widgets.Num(); Idx++) + { + if (Widgets[Idx].bUsed) + { + Widgets[Idx].CurrentTime += InDeltaTime; + Widgets[Idx].CurrentPosition = Widgets[Idx].CurrentPosition + (Widgets[Idx].Direction * InDeltaTime * FCTMoveSpeed); + + float Scale = UWidgetLayoutLibrary::GetViewportScale(this); + + FMargin Pos(Widgets[Idx].CurrentPosition.X / Scale, Widgets[Idx].CurrentPosition.Y / Scale, Widgets[Idx].Widget->GetDesiredSize().X, Widgets[Idx].Widget->GetDesiredSize().Y); + Widgets[Idx].Slot->Offset(Pos); + + if (Widgets[Idx].CurrentTime > FCTLifeTime) + { + Widgets[Idx].bUsed = false; + Widgets[Idx].CurrentTime = 0; + + Widgets[Idx].Widget->SetVisibility(EVisibility::Collapsed); + + } + } + } +} + +void UARHUDFloatingCombatText::SetInfo(float InDamage, FVector2D ScreenPosition, FLinearColor TextColor) +{ + for (uint8 Idx = 0; Idx < Widgets.Num(); Idx++) + { + if (!Widgets[Idx].bUsed) + { + Widgets[Idx].bUsed = true; + Widgets[Idx].CurrentTime = 0; + Widgets[Idx].CurrentPosition = ScreenPosition; + float RandomX = FMath::FRandRange(-1, 1); + float RandomY = FMath::FRandRange(-1, 1); + Widgets[Idx].Direction = FVector2D(RandomX, RandomY); + Widgets[Idx].Widget->TextColor = FSlateColor(TextColor); + Widgets[Idx].Widget->SetText(FText::AsNumber(InDamage)); + Widgets[Idx].Widget->SetVisibility(EVisibility::HitTestInvisible); + + break; + } + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/AI/ARAICharacter.h b/Source/ActionRPGGame/Public/AI/ARAICharacter.h index bf5e5c8..2a2ee70 100644 --- a/Source/ActionRPGGame/Public/AI/ARAICharacter.h +++ b/Source/ActionRPGGame/Public/AI/ARAICharacter.h @@ -16,11 +16,16 @@ UCLASS() class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInterface { GENERATED_BODY() + friend class AAREnemySpawner; protected: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFAbilityComponent* Abilities; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFEffectsComponent* EffectsComponent; + + UPROPERTY(BlueprintReadOnly, Category = "ActionRPGGame|Spawn") + class AAREnemySpawner* SpawnedBy; + public: // Sets default values for this character's properties AARAICharacter(); @@ -29,6 +34,7 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt // Called when the game starts or when spawned virtual void BeginPlay() override; + virtual void OnSpawned(class AAREnemySpawner* InSpawnedBy); public: // Called every frame virtual void Tick(float DeltaTime) override; diff --git a/Source/ActionRPGGame/Public/AREnemySpawner.h b/Source/ActionRPGGame/Public/AREnemySpawner.h new file mode 100644 index 0000000..835c4c2 --- /dev/null +++ b/Source/ActionRPGGame/Public/AREnemySpawner.h @@ -0,0 +1,55 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "AREnemySpawner.generated.h" + +UCLASS() +class ACTIONRPGGAME_API AAREnemySpawner : public AActor +{ + GENERATED_BODY() +protected: + UPROPERTY(EditAnywhere, Category = "Enemy") + TSubclassOf EnemyClass; + UPROPERTY(EditAnywhere, Category = "Enemy") + int32 MaxSpawned; + UPROPERTY(EditAnywhere, Category = "Enemy") + int32 BatchSpawn; + UPROPERTY(EditAnywhere, Category = "Enemy") + float TimeBetweenSpawns; + + UPROPERTY(EditAnywhere, meta = (MakeEditWidget), Category = "Enemy") + TArray SpawnPositions; + + /* + If enemy count reaches this number start respawning. + */ + UPROPERTY(EditAnywhere, Category = "Enemy") + int32 MinRespawn; + + TSet SpawnedEnemies; + + FTimerHandle SpawnerHandle; + +public: + // Sets default values for this actor's properties + AAREnemySpawner(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + + void SetupSpawner(); + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + void OnEnemyKilled(AARAICharacter* InEnemy); + + UFUNCTION() + void HandleSpawn(); + +}; diff --git a/Source/ActionRPGGame/Public/ARItemPickupBase.h b/Source/ActionRPGGame/Public/ARItemPickupBase.h index 3b4055c..bec8494 100644 --- a/Source/ActionRPGGame/Public/ARItemPickupBase.h +++ b/Source/ActionRPGGame/Public/ARItemPickupBase.h @@ -3,14 +3,16 @@ #pragma once #include "CoreMinimal.h" -#include "GameFramework/Actor.h" +#include "IFItemActorBase.h" #include "ARItemPickupBase.generated.h" UCLASS() -class ACTIONRPGGAME_API AARItemPickupBase : public AActor +class ACTIONRPGGAME_API AARItemPickupBase : public AIFItemActorBase { GENERATED_BODY() - + + UPROPERTY() + class AARItemSpawnerBase* SpawnedBy; public: // Sets default values for this actor's properties AARItemPickupBase(); @@ -23,6 +25,8 @@ class ACTIONRPGGAME_API AARItemPickupBase : public AActor // Called every frame virtual void Tick(float DeltaTime) override; + inline void SetSpawnedBy(class AARItemSpawnerBase* InSpawnedBy) { SpawnedBy = InSpawnedBy; } + - + virtual void OnItemPicked() override; }; diff --git a/Source/ActionRPGGame/Public/ARItemSpawnerBase.h b/Source/ActionRPGGame/Public/ARItemSpawnerBase.h new file mode 100644 index 0000000..9766480 --- /dev/null +++ b/Source/ActionRPGGame/Public/ARItemSpawnerBase.h @@ -0,0 +1,46 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameFramework/Actor.h" +#include "ARItemSpawnerBase.generated.h" + + +/* + 1. Should only store templates. + 2. Should ask databse about item to spawn. + 3. Should not be placed manually. +*/ +UCLASS() +class ACTIONRPGGAME_API AARItemSpawnerBase : public AActor +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Items") + TSubclassOf ItemsToSpawn; + + /* + If <= 0, no respawn. Otherwise time after item will be respawned. + */ + UPROPERTY(EditAnywhere, Category = "Items") + float RespawnTime; + + FTimerHandle RespawnHandle; +public: + // Sets default values for this actor's properties + AARItemSpawnerBase(); + +protected: + // Called when the game starts or when spawned + virtual void BeginPlay() override; + +public: + // Called every frame + virtual void Tick(float DeltaTime) override; + + void OnItemPicked(); + UFUNCTION() + void HandleRespawn(); + +}; diff --git a/Source/ActionRPGGame/Public/ARPlayerController.h b/Source/ActionRPGGame/Public/ARPlayerController.h index de975b2..a26ee10 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.h +++ b/Source/ActionRPGGame/Public/ARPlayerController.h @@ -75,4 +75,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I virtual void OnInventoryReplicated(class UIFInventoryComponent* Inventory) override; /* IIFInventoryInterface */ + UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|HUD") + float ComputeBoundsScreenSize(UCapsuleComponent* InTarget); }; diff --git a/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h index a79dd2a..6e4a9b4 100644 --- a/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h +++ b/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h @@ -15,7 +15,7 @@ class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase GENERATED_BODY() public: - UPROPERTY(EditAnywhere, Replicated, Category = "Base") + UPROPERTY(EditAnywhere, ReplicatedUsing=OnRep_Health, Category = "Base") FAFAttributeBase Health; UPROPERTY(EditAnywhere, Replicated, Category = "Base") FAFAttributeBase Shield; @@ -34,4 +34,7 @@ class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase FAFAttributeBase ShotgunAmmo; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase ArrowAmmo; + + UFUNCTION() + void OnRep_Health(); }; diff --git a/Source/ActionRPGGame/Public/UI/ARHUD.h b/Source/ActionRPGGame/Public/UI/ARHUD.h index 72f6116..94d1cd6 100644 --- a/Source/ActionRPGGame/Public/UI/ARHUD.h +++ b/Source/ActionRPGGame/Public/UI/ARHUD.h @@ -16,12 +16,42 @@ class ACTIONRPGGAME_API AARHUD : public AHUD protected: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIInventoryComponent* UIInventoryComponent; - + + UPROPERTY(EditAnywhere, Category = "Enemy Info") + + TSubclassOf HUDEnemyHealthBarClass; + UPROPERTY(EditAnywhere, Category = "Enemy Info") + TEnumAsByte EnemyChannel; + UPROPERTY(EditAnywhere, Category = "Enemy Info") + float DistanceScaleEnemyBar; + + UPROPERTY(BlueprintReadOnly, Category = "Enemy Info") + class UARHUDEnemyHealthBar* HUDEnemyHealthBar; + + UPROPERTY(EditAnywhere, Category = "Floating Combat Text") + TSubclassOf HUDFloatingCombatTextClass; + UPROPERTY(BlueprintReadOnly, Category = "Floating Combat Text") + class UARHUDFloatingCombatText* FloatingCombatText; + UPROPERTY(EditAnywhere, Category = "Floating Combat Text") + float FCTMoveSpeed; + UPROPERTY(EditAnywhere, Category = "Floating Combat Text") + float FCTLifeTime; + UPROPERTY(EditAnywhere, Category = "Floating Combat Text") + FSlateFontInfo FCTFont; + + UPROPERTY() + class AARCharacter* ARCharacter; + UPROPERTY() + class AARPlayerController* ARPC; + + FHitResult EnemyHitResult; public: AARHUD(const FObjectInitializer& ObjectInitializer); virtual void BeginPlay() override; + virtual void Tick(float InDeltaTime) override; + inline UARUIInventoryComponent* GetUIInventory() { return UIInventoryComponent; @@ -29,4 +59,12 @@ class ACTIONRPGGAME_API AARHUD : public AHUD void ShowHideInventory(); + +protected: + float ComputeBoundsScreenSize(AActor* InTarget); + void SetEnemyHitResult(); + void UpdateEnemyBarInfo(); + + UFUNCTION() + void OnEnemyDamageCaused(const FAFAttributeChangedData& InMod); }; diff --git a/Source/ActionRPGGame/Public/UI/ARUIComponent.h b/Source/ActionRPGGame/Public/UI/ARUIComponent.h index cfb1668..839e92c 100644 --- a/Source/ActionRPGGame/Public/UI/ARUIComponent.h +++ b/Source/ActionRPGGame/Public/UI/ARUIComponent.h @@ -4,7 +4,6 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" -#include "UI/HUD/AREnemyHealthBar.h" #include "ARHUDWidget.h" #include "SARDrawTestWidget.h" @@ -28,18 +27,16 @@ class ACTIONRPGGAME_API UARUIComponent : public UActorComponent UUserWidget* CrosshairWidget; UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf EnemyHealthBarClass; + TSubclassOf HUDWidgetClass; + - UPROPERTY(BlueprintReadOnly, Category = "Widgets") - UAREnemyHealthBar* EnemyHealthBarWidget; - UPROPERTY(EditAnywhere, Category = "Widgets") - TSubclassOf HUDWidgetClass; public: UPROPERTY(BlueprintReadOnly, Category = "Widgets") UARHUDWidget* HUDWidget; + TSharedPtr DrawWidget; TSharedPtr CrosshairWidget2; public: diff --git a/Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.h b/Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.h deleted file mode 100644 index ab149f2..0000000 --- a/Source/ActionRPGGame/Public/UI/HUD/AREnemyHealthBar.h +++ /dev/null @@ -1,24 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Blueprint/UserWidget.h" -#include "Widgets/Text/STextBlock.h" -#include "Widgets/Notifications/SProgressBar.h" -#include "AREnemyHealthBar.generated.h" - -/** - * - */ -UCLASS() -class ACTIONRPGGAME_API UAREnemyHealthBar : public UUserWidget -{ - GENERATED_BODY() -public: - virtual void ReleaseSlateResources(bool bReleaseChildren) override; - //virtual TSharedRef RebuildWidget() override; -protected: -// TSharedPtr MyTextBlock; -// TSharedPtr HealthBar; -}; diff --git a/Source/ActionRPGGame/Public/UI/HUD/ARHUDEnemyHealthBar.h b/Source/ActionRPGGame/Public/UI/HUD/ARHUDEnemyHealthBar.h new file mode 100644 index 0000000..d381655 --- /dev/null +++ b/Source/ActionRPGGame/Public/UI/HUD/ARHUDEnemyHealthBar.h @@ -0,0 +1,24 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Notifications/SProgressBar.h" +#include "ARHUDEnemyHealthBar.generated.h" + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHUDEnemyHealthBar : public UUserWidget +{ + GENERATED_BODY() +protected: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + class UProgressBar* HealthBar; + +public: + void UpdateHealth(float NormalizedHealth); +}; diff --git a/Source/ActionRPGGame/Public/UI/HUD/ARHUDFloatingCombatText.h b/Source/ActionRPGGame/Public/UI/HUD/ARHUDFloatingCombatText.h new file mode 100644 index 0000000..3e50403 --- /dev/null +++ b/Source/ActionRPGGame/Public/UI/HUD/ARHUDFloatingCombatText.h @@ -0,0 +1,98 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Blueprint/UserWidget.h" +#include "Containers/Queue.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SConstraintCanvas.h" +#include "Widgets/SCanvas.h" +#include "Widgets/SCompoundWidget.h" +#include "Components/TextBlock.h" + +#include "ARHUDFloatingCombatText.generated.h" +UCLASS() +class ACTIONRPGGAME_API UARFCTText : public UUserWidget +{ + GENERATED_BODY() +public: + UPROPERTY(BlueprintReadOnly, meta = (BindWidget)) + UTextBlock* Text; + + void SetText(const FText& InText) + { + Text->SetText(InText); + } +}; + +class SFCTWidget : public SCompoundWidget +{ + SLATE_BEGIN_ARGS(SFCTWidget) {} + SLATE_END_ARGS() + +public: + FSlateFontInfo Font; + FText Text; + FSlateColor TextColor; +public: + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs); + ~SFCTWidget(); + inline void SetText(const FText& InText) { Text = InText; }; + FSlateFontInfo GetFontInfo() const; + FText GetText() const; +}; + +struct FARHUDFCTUpdate +{ + + TSharedPtr Widget; + + float CurrentTime; + bool bUsed; + FVector2D CurrentPosition; + FVector2D Direction; + SConstraintCanvas::FSlot* Slot; + FARHUDFCTUpdate() + : CurrentTime(0) + , bUsed(false) + , CurrentPosition(FVector2D::ZeroVector) + , Direction(FVector2D::ZeroVector) + {}; +}; + +/** + * + */ +UCLASS() +class ACTIONRPGGAME_API UARHUDFloatingCombatText : public UUserWidget +{ + GENERATED_BODY() + friend class AARHUD; + + UPROPERTY(EditAnywhere) + TSubclassOf UARFCTTextClass; + UPROPERTY() + class AARPlayerController* PC; + + float FCTMoveSpeed; + float FCTLifeTime; + /* Pool of available widgets */ + TQueue UnsedWidgtes; + /* Pool of used Widgets which are updateing. */ + TArray Widgets; + + TSharedPtr Canvas; + + FSlateFontInfo Font; + + +public: + void Init(int32 Num); + + void Update(float InDeltaTime); + + void SetInfo(float InDamage, FVector2D ScreenPosition, FLinearColor TextColor = FLinearColor::White); + +}; From b136345a062405929d1ca934eff8300f29cd9c06 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 21 May 2018 21:38:13 +0200 Subject: [PATCH 179/187] modified attribute modify function to take Context Handle, modifier Attribute extension class to take context into pre/post virtual functions, fixed clang warning, made AI killable, with HealthExtension class --- .../Private/AFAbilityComponent.cpp | 8 +++-- .../Private/Attributes/GAAttributeBase.cpp | 33 +++++++++++++++---- .../Private/Attributes/GAAttributesBase.cpp | 8 +++-- .../Private/Effects/GAEffectExecution.cpp | 3 +- .../Public/AFAbilityComponent.h | 5 ++- .../Public/AFAbilityInterface.h | 2 +- .../Public/Abilities/GAAbilityBase.h | 5 +-- .../Public/Attributes/GAAttributeBase.h | 2 +- .../Public/Attributes/GAAttributeExtension.h | 5 +-- .../Public/Attributes/GAAttributesBase.h | 5 ++- .../Public/Effects/GAGameEffect.h | 13 +++++++- .../Public/AnimNode_BlendLocomotionFour.cpp | 20 +++++------ .../Private/AI/ARAICharacter.cpp | 13 ++++++-- Source/ActionRPGGame/Private/ARCharacter.cpp | 4 +-- .../Attributes/ARCharacterAttributes.cpp | 5 +++ .../Private/Attributes/ARHealthExtension.cpp | 17 +++++++++- .../Private/Weapons/ARWeaponAbilityBase.cpp | 4 ++- .../ActionRPGGame/Public/AI/ARAICharacter.h | 7 ++-- Source/ActionRPGGame/Public/ARCharacter.h | 2 +- .../Public/Attributes/ARCharacterAttributes.h | 5 +++ .../Public/Attributes/ARHealthExtension.h | 5 +-- 21 files changed, 126 insertions(+), 45 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp index 29b29a8..6fa8fc5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -83,8 +83,10 @@ void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribu } } -void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - ,FGAEffectProperty& InProperty) +void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn + , const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty + , const FAFContextHandle& InContext) { //OnAttributePreModifed.Broadcast(ModIn, 0); //Add log. @@ -92,7 +94,7 @@ void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHa { return; } - float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty); + float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty, InContext); FAFAttributeChangedData Data; FGAEffectContext& Context = InProperty.GetContext(HandleIn).GetRef(); Data.Mod = ModIn; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp index 9687149..97a3787 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -17,15 +17,16 @@ DEFINE_STAT(STAT_FinalBonusByTag); // //} FAFAttributeBase::FAFAttributeBase() - : CurrentValue(0), - BaseBonusValue(0) + : BaseBonusValue(0) + , CurrentValue(0) { Modifiers.AddDefaulted(7); }; FAFAttributeBase::FAFAttributeBase(float BaseValueIn) - : BaseValue(BaseValueIn), - CurrentValue(BaseValue), - BaseBonusValue(0) + : BaseValue(BaseValueIn) + , BaseBonusValue(0) + , CurrentValue(BaseValue) + { Modifiers.AddDefaulted(7); }; @@ -159,16 +160,26 @@ bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) return false; } float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - FGAEffectProperty& InProperty) + FGAEffectProperty& InProperty, const FAFContextHandle& InContext) { //FString name = GetTypeName(); if (ExtensionClass) { ExtensionClass.GetDefaultObject()->OnPreAttributeModify(CurrentValue); + FGAEffectContext* Context = InContext.GetPtr(); + if (InContext.IsValid()) + { + ExtensionClass.GetDefaultObject()->PreAttributeModify(InContext.GetRef() + , CurrentValue); + } + } float returnValue = -1; bool isPeriod = InProperty.GetPeriod() > 0; bool IsDuration = InProperty.GetDuration() > 0; + + float PreValue = CurrentValue; + if ( !InProperty.GetIsInstant()) { FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); @@ -221,7 +232,15 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& } if (ExtensionClass) { - ExtensionClass.GetDefaultObject()->OnPreAttributeModify(returnValue); + ExtensionClass.GetDefaultObject()->OnPostAttributeModify(returnValue); + + if (InContext.IsValid()) + { + ExtensionClass.GetDefaultObject()->PostAttributeModify( + InContext.GetRef() + , PreValue + , returnValue); + } } return returnValue; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp index cae8b06..10c7d3d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp @@ -291,8 +291,10 @@ void UGAAttributesBase::ModifyAttribute(const FGAEffect& EffectIn) } -float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn, - const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty) +float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn + , const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty + , const FAFContextHandle& InContext) { FAFAttributeBase* attr = nullptr; UGAAttributesBase* atrObj = this; @@ -301,7 +303,7 @@ float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn, float OutVal = -1; if (attr) { - OutVal = attr->Modify(ModIn, HandleIn, InProperty); + OutVal = attr->Modify(ModIn, HandleIn, InProperty, InContext); } OnAttributeModified(ModIn, HandleIn); return OutVal; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp index bcfbe5e..0a782b8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp @@ -20,5 +20,6 @@ void UGAEffectExecution::ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffec const FAFFunctionModifier& Modifier) { PreModifyAttribute(HandleIn, ModIn, Params.GetContext()); - Params.GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty()); + FAFContextHandle ContextHandle = Params.GetContextHandle(); + Params.GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty(), ContextHandle); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h index 49113cd..5053109 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -337,7 +337,10 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Attributes") float GetAttributeValue(FGAAttribute AttributeIn) const { return DefaultAttributes->GetCurrentAttributeValue(AttributeIn); }; - void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + void ModifyAttribute(FGAEffectMod& ModIn + , const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty + , const FAFContextHandle& InContext);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, const FGAEffectContext& InContext); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h index f5ede8f..497cdb4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h @@ -35,7 +35,7 @@ class IAFAbilityInterface virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) {}; + struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) {}; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h index a7d3893..66daae9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h @@ -471,14 +471,15 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override { return Attributes->GetAttribute(AttributeIn); }; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn - , FGAEffectProperty& InProperty) override + , FGAEffectProperty& InProperty + , const FAFContextHandle& InContext) override { if (!Attributes) { UE_LOG(AFAbilities, Log, TEXT("ModifyAttribute Ability Attributes INVALID")); return; } - Attributes->ModifyAttribute(ModIn, HandleIn, InProperty); + Attributes->ModifyAttribute(ModIn, HandleIn, InProperty, InContext); }; virtual FAFPredictionHandle GetPredictionHandle() override; /* IAFAbilityInterface End **/ diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index 98ab568..3a4194c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -115,7 +115,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase inline float GetCurrentValue() { return CurrentValue; }; void CalculateBonus(); bool CheckIfStronger(const FGAEffectMod& InMod); - float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); + float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty, const FAFContextHandle& InContext); void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); void SetExtensionClass(TSubclassOf InExtensionClass) { ExtensionClass = InExtensionClass; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h index 34b4b7c..cc748f5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h @@ -23,8 +23,9 @@ class ABILITYFRAMEWORK_API UGAAttributeExtension : public UObject void OnPreAttributeModify(float InValue); void OnPostAttributeModify(float InValue); - virtual void PreAttributeModify() {}; - virtual void PostAttributeModify() {}; + virtual void PreAttributeModify(const FGAEffectContext& InContext, float PreValue) {}; + virtual void PostAttributeModify(const FGAEffectContext& InContext, float PreValue, float PostValue) {}; + virtual float CalculateBonusValueByTags(const FGAIndividualMods& Mods) { return 0; } virtual float CalculateCurentValue() { return 0; } virtual bool CanModifyAttribute() { return true; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h index e609e62..bcf6ad5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h @@ -122,7 +122,10 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject void SetNetAddressable(); void ModifyAttribute(const FGAEffect& EffectIn); - float ModifyAttribute(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty); + float ModifyAttribute(const FGAEffectMod& ModIn + , const FGAEffectHandle& HandleIn + , FGAEffectProperty& InProperty + , const FAFContextHandle& InContext); void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod); protected: bool bNetAddressable; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h index 97da961..5d4d5c2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h @@ -369,7 +369,10 @@ struct ABILITYFRAMEWORK_API FAFContextHandle { return DataPtr.IsValid(); } - + bool IsValid() const + { + return DataPtr.IsValid(); + } FGAEffectContext& GetRef() { return DataPtr.ToSharedRef().Get(); @@ -1048,6 +1051,14 @@ struct ABILITYFRAMEWORK_API FAFEffectParams , bRecreated(false) {}; + FAFContextHandle& GetContextHandle() + { + return Context; + } + const FAFContextHandle& GetContextHandle() const + { + return Context; + } FGAEffectContext & GetContext() { return Context.GetRef(); diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp index b8df83b..68006cf 100644 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp @@ -123,7 +123,7 @@ void FAnimNode_BlendLocomotionFour::Update_AnyThread(const FAnimationUpdateConte FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); - int32 Dir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; + int32 LocalDir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; DotBlendTime = FMath::Abs(FVector::DotProduct(LocalVelocity, LocalAcceleration)); BlendTime[0] = DotBlendTime; BlendTime[1] = DotBlendTime; @@ -154,15 +154,15 @@ void FAnimNode_BlendLocomotionFour::Update_AnyThread(const FAnimationUpdateConte // scale by the weight difference since we want always consistency: // - if you're moving from 0 to full weight 1, it will use the normal blend time // - if you're moving from 0.5 to full weight 1, it will get there in half the time - const float RemainingBlendTime = LastChildIndexIsInvalid ? 0.0f : (BlendTime[ChildIndex] * WeightDifference); + const float LocalRemainingBlendTime = LastChildIndexIsInvalid ? 0.0f : (BlendTime[ChildIndex] * WeightDifference); for (int32 i = 0; i < RemainingBlendTimes.Num(); ++i) { - RemainingBlendTimes[i] = RemainingBlendTime; + RemainingBlendTimes[i] = LocalRemainingBlendTime; } // If we have a valid previous child and we're instantly blending - update that pose with zero weight - if (RemainingBlendTime == 0.0f && !LastChildIndexIsInvalid) + if (LocalRemainingBlendTime == 0.0f && !LastChildIndexIsInvalid) { BlendPose[LastActiveChildIndex].Update(Context.FractionalWeight(0.0f)); } @@ -171,7 +171,7 @@ void FAnimNode_BlendLocomotionFour::Update_AnyThread(const FAnimationUpdateConte { FAlphaBlend& Blend = Blends[i]; - Blend.SetBlendTime(RemainingBlendTime); + Blend.SetBlendTime(LocalRemainingBlendTime); if (i == ChildIndex) { @@ -259,7 +259,7 @@ void FAnimNode_BlendLocomotionFour::Update_AnyThread(const FAnimationUpdateConte } - switch (static_cast(Dir)) + switch (static_cast(LocalDir)) { case EFCardinalDirection::N: { @@ -338,8 +338,8 @@ void FAnimNode_BlendLocomotionFour::Evaluate_AnyThread(FPoseContext& Output) FPoseContext EvaluateContext(Output); - FPoseLink& CurrentPose = BlendPose[PoseIndex]; - CurrentPose.Evaluate(EvaluateContext); + FPoseLink& LocalCurrentPose = BlendPose[PoseIndex]; + LocalCurrentPose.Evaluate(EvaluateContext); FilteredPoses[i].CopyBonesFrom(EvaluateContext.Pose); FilteredCurve[i] = EvaluateContext.Curve; @@ -362,8 +362,8 @@ void FAnimNode_BlendLocomotionFour::Evaluate_AnyThread(FPoseContext& Output) { int32 PoseIndex = PosesToEvaluate[i]; - FPoseLink& CurrentPose = BlendPose[PoseIndex]; - CurrentPose.Evaluate(Output); + FPoseLink& LocalCurrentPose = BlendPose[PoseIndex]; + LocalCurrentPose.Evaluate(Output); } //Output.ResetToRefPose(); diff --git a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp index d395427..bf5e0d3 100644 --- a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp +++ b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp @@ -1,7 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARAICharacter.h" - +#include "AREnemySpawner.h" // Sets default values AARAICharacter::AARAICharacter() @@ -36,6 +36,13 @@ void AARAICharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputCompo } +void AARAICharacter::Kill() +{ + SpawnedBy->OnEnemyKilled(this); + + Destroy(); +} + /* IAFAbilityInterface- BEGIN */ class UAFAbilityComponent* AARAICharacter::GetAbilityComp() { @@ -55,9 +62,9 @@ float AARAICharacter::GetAttributeValue(FGAAttribute AttributeIn) const } void AARAICharacter::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) + struct FGAEffectProperty& InProperty, const FAFContextHandle& InContex) { - Abilities->ModifyAttribute(ModIn, HandleIn, InProperty); + Abilities->ModifyAttribute(ModIn, HandleIn, InProperty, InContex); } FAFAttributeBase* AARAICharacter::GetAttribute(FGAAttribute AttributeIn) diff --git a/Source/ActionRPGGame/Private/ARCharacter.cpp b/Source/ActionRPGGame/Private/ARCharacter.cpp index 338e54b..a124508 100644 --- a/Source/ActionRPGGame/Private/ARCharacter.cpp +++ b/Source/ActionRPGGame/Private/ARCharacter.cpp @@ -484,9 +484,9 @@ float AARCharacter::GetAttributeValue(FGAAttribute AttributeIn) const } void AARCharacter::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) + struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) { - Abilities->ModifyAttribute(ModIn, HandleIn, InProperty); + Abilities->ModifyAttribute(ModIn, HandleIn, InProperty, InContext); } FAFAttributeBase* AARCharacter::GetAttribute(FGAAttribute AttributeIn) diff --git a/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp b/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp index 565d175..4bd7ad0 100644 --- a/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp +++ b/Source/ActionRPGGame/Private/Attributes/ARCharacterAttributes.cpp @@ -2,6 +2,11 @@ #include "Net/UnrealNetwork.h" +UARCharacterAttributes::UARCharacterAttributes(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} void UARCharacterAttributes::GetLifetimeReplicatedProps(TArray< class FLifetimeProperty > & OutLifetimeProps) const { diff --git a/Source/ActionRPGGame/Private/Attributes/ARHealthExtension.cpp b/Source/ActionRPGGame/Private/Attributes/ARHealthExtension.cpp index f6284d1..1986eaf 100644 --- a/Source/ActionRPGGame/Private/Attributes/ARHealthExtension.cpp +++ b/Source/ActionRPGGame/Private/Attributes/ARHealthExtension.cpp @@ -1,7 +1,22 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARHealthExtension.h" +#include "AFAbilityComponent.h" +#include "AI/ARAICharacter.h" +void UARHealthExtension::PreAttributeModify(const FGAEffectContext& InContext, float PreValue) +{ + +} +void UARHealthExtension::PostAttributeModify(const FGAEffectContext& InContext, float PreValue, float PostValue) +{ + AARAICharacter* AIChar = Cast(InContext.Target.Get()); + if (!AIChar) + return; - + if (PostValue <= 0) + { + AIChar->Kill(); + } +} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp index 52295cc..6392148 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp @@ -116,7 +116,9 @@ void UARWeaponAbilityBase::AddUpgrade(FAFPropertytHandle& PropertyHandle UpgradeContainer.ApplyEffect(EffectHandle, Effect); + FAFContextHandle Context = FAFContextHandle::Generate(&DefaultContext); + FGAEffectMod Mod = SpecHandle.GetModifier(); - ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef()); + ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef(), Context); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/AI/ARAICharacter.h b/Source/ActionRPGGame/Public/AI/ARAICharacter.h index 2a2ee70..aa4d8c0 100644 --- a/Source/ActionRPGGame/Public/AI/ARAICharacter.h +++ b/Source/ActionRPGGame/Public/AI/ARAICharacter.h @@ -35,7 +35,10 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt virtual void BeginPlay() override; virtual void OnSpawned(class AAREnemySpawner* InSpawnedBy); -public: + + +public: + virtual void Kill(); // Called every frame virtual void Tick(float DeltaTime) override; @@ -56,7 +59,7 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) override; + struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) override; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; diff --git a/Source/ActionRPGGame/Public/ARCharacter.h b/Source/ActionRPGGame/Public/ARCharacter.h index f6d9845..e9873f3 100644 --- a/Source/ActionRPGGame/Public/ARCharacter.h +++ b/Source/ActionRPGGame/Public/ARCharacter.h @@ -239,7 +239,7 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty) override; + struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) override; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; diff --git a/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h b/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h index 6e4a9b4..edbf0d0 100644 --- a/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h +++ b/Source/ActionRPGGame/Public/Attributes/ARCharacterAttributes.h @@ -34,7 +34,12 @@ class ACTIONRPGGAME_API UARCharacterAttributes : public UGAAttributesBase FAFAttributeBase ShotgunAmmo; UPROPERTY(EditAnywhere, Category = "Base") FAFAttributeBase ArrowAmmo; +public: + + UARCharacterAttributes(const FObjectInitializer& ObjectInitializer); UFUNCTION() void OnRep_Health(); + + }; diff --git a/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.h b/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.h index ab8f2d5..57126e9 100644 --- a/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.h +++ b/Source/ActionRPGGame/Public/Attributes/ARHealthExtension.h @@ -9,12 +9,13 @@ /** * */ -UCLASS() +UCLASS(BlueprintType, Blueprintable) class ACTIONRPGGAME_API UARHealthExtension : public UGAAttributeExtension { GENERATED_BODY() - + virtual void PreAttributeModify(const FGAEffectContext& InContext, float PreValue) override; + virtual void PostAttributeModify(const FGAEffectContext& InContext, float PreValue, float PostValue) override; }; From f8a8fa8bb2b8439145035f651fb79ebb25008863 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Mon, 4 Jun 2018 23:55:13 +0200 Subject: [PATCH 180/187] work around to broken SetMasterPoseComponent which does not properly update MasterBonesMap and causes modular character to be break in editor/game --- Source/ActionRPGGame/Private/ARCharacter.cpp | 52 ++++++++++++++++---- 1 file changed, 42 insertions(+), 10 deletions(-) diff --git a/Source/ActionRPGGame/Private/ARCharacter.cpp b/Source/ActionRPGGame/Private/ARCharacter.cpp index a124508..275cc9e 100644 --- a/Source/ActionRPGGame/Private/ARCharacter.cpp +++ b/Source/ActionRPGGame/Private/ARCharacter.cpp @@ -88,39 +88,38 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) Head = CreateDefaultSubobject(TEXT("Head")); Head->SetupAttachment(GetMesh()); - Head->SetMasterPoseComponent(GetMesh()); - + Shoulders = CreateDefaultSubobject(TEXT("Shoulders")); Shoulders->SetupAttachment(GetMesh()); - Shoulders->SetMasterPoseComponent(GetMesh()); + Arms = CreateDefaultSubobject(TEXT("Arms")); Arms->SetupAttachment(GetMesh()); - Arms->SetMasterPoseComponent(GetMesh()); + Hands = CreateDefaultSubobject(TEXT("Hands")); Hands->SetupAttachment(GetMesh()); - Hands->SetMasterPoseComponent(GetMesh()); + Torso = CreateDefaultSubobject(TEXT("Torso")); Torso->SetupAttachment(GetMesh()); - Torso->SetMasterPoseComponent(GetMesh()); + Legs = CreateDefaultSubobject(TEXT("Legs")); Legs->SetupAttachment(GetMesh()); - Legs->SetMasterPoseComponent(GetMesh()); + Feets = CreateDefaultSubobject(TEXT("Feets")); Feets->SetupAttachment(GetMesh()); - Feets->SetMasterPoseComponent(GetMesh()); + Backpack = CreateDefaultSubobject(TEXT("Backpack")); Backpack->SetupAttachment(GetMesh()); - Backpack->SetMasterPoseComponent(GetMesh()); + LegsCloth = CreateDefaultSubobject(TEXT("LegsCloth")); LegsCloth->SetupAttachment(GetMesh()); - //LegsCloth->SetMasterPoseComponent(GetMesh()); + WeaponHolsteredRight = CreateDefaultSubobject(TEXT("WeaponHolsteredRight")); //HolsteredRightWeapon->AttachToComponent(GetMesh(), FAttachmentTransformRules::KeepRelativeTransform); @@ -150,10 +149,43 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) // Note: The skeletal mesh and anim blueprint references on the Mesh component (inherited from Character) // are set in the derived blueprint asset named MyCharacter (to avoid direct content references in C++) } +void AARCharacter::OnConstruction(const FTransform& Transform) +{ + Head->SetMasterPoseComponent(GetMesh()); + Head->UpdateMasterBoneMap(); + Shoulders->SetMasterPoseComponent(GetMesh()); + Shoulders->UpdateMasterBoneMap(); + + Arms->SetMasterPoseComponent(GetMesh()); + Arms->UpdateMasterBoneMap(); + + Hands->SetMasterPoseComponent(GetMesh()); + Hands->UpdateMasterBoneMap(); + + Torso->SetMasterPoseComponent(GetMesh()); + Torso->UpdateMasterBoneMap(); + + Legs->SetMasterPoseComponent(GetMesh()); + Legs->UpdateMasterBoneMap(); + + Feets->SetMasterPoseComponent(GetMesh()); + Feets->UpdateMasterBoneMap(); + + Backpack->SetMasterPoseComponent(GetMesh()); + Backpack->UpdateMasterBoneMap(); +} +void AARCharacter::PostInitializeComponents() +{ + Super::PostInitializeComponents(); + +} void AARCharacter::BeginPlay() { Super::BeginPlay(); + + + //LegsCloth->SetMasterPoseComponent(GetMesh()); WeaponInventory->SetIsReplicated(true); WeaponInventory->InitializeWeapons(this); } From d88f73d40179e3305b8c1113ba8049025db393b4 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 5 Jun 2018 00:06:32 +0200 Subject: [PATCH 181/187] missing header --- Source/ActionRPGGame/Public/ARCharacter.h | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Source/ActionRPGGame/Public/ARCharacter.h b/Source/ActionRPGGame/Public/ARCharacter.h index e9873f3..80c563b 100644 --- a/Source/ActionRPGGame/Public/ARCharacter.h +++ b/Source/ActionRPGGame/Public/ARCharacter.h @@ -180,6 +180,8 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio float OldOrient; public: AARCharacter(const FObjectInitializer& ObjectInitializer); + virtual void OnConstruction(const FTransform& Transform) override; + virtual void PostInitializeComponents() override; float GetAnimOrient() final; EFCardinalDirection GetCardianlDirection() final; float GetAnimOrientN() final; From b3a9d9a4110626e824aaf03b0ee320de915aea9d Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 13 Jun 2018 00:01:33 +0200 Subject: [PATCH 182/187] new plugin --- Plugins/uFire/Source/uFire/Private/uFire.cpp | 20 +++++++ Plugins/uFire/Source/uFire/Public/uFire.h | 15 ++++++ Plugins/uFire/Source/uFire/uFire.Build.cs | 55 ++++++++++++++++++++ Plugins/uFire/uFire.uplugin | 23 ++++++++ 4 files changed, 113 insertions(+) create mode 100644 Plugins/uFire/Source/uFire/Private/uFire.cpp create mode 100644 Plugins/uFire/Source/uFire/Public/uFire.h create mode 100644 Plugins/uFire/Source/uFire/uFire.Build.cs create mode 100644 Plugins/uFire/uFire.uplugin diff --git a/Plugins/uFire/Source/uFire/Private/uFire.cpp b/Plugins/uFire/Source/uFire/Private/uFire.cpp new file mode 100644 index 0000000..29ffa31 --- /dev/null +++ b/Plugins/uFire/Source/uFire/Private/uFire.cpp @@ -0,0 +1,20 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#include "uFire.h" + +#define LOCTEXT_NAMESPACE "FuFireModule" + +void FuFireModule::StartupModule() +{ + // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module +} + +void FuFireModule::ShutdownModule() +{ + // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, + // we call this function before unloading the module. +} + +#undef LOCTEXT_NAMESPACE + +IMPLEMENT_MODULE(FuFireModule, uFire) \ No newline at end of file diff --git a/Plugins/uFire/Source/uFire/Public/uFire.h b/Plugins/uFire/Source/uFire/Public/uFire.h new file mode 100644 index 0000000..df4530b --- /dev/null +++ b/Plugins/uFire/Source/uFire/Public/uFire.h @@ -0,0 +1,15 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + +class FuFireModule : public IModuleInterface +{ +public: + + /** IModuleInterface implementation */ + virtual void StartupModule() override; + virtual void ShutdownModule() override; +}; diff --git a/Plugins/uFire/Source/uFire/uFire.Build.cs b/Plugins/uFire/Source/uFire/uFire.Build.cs new file mode 100644 index 0000000..544ed10 --- /dev/null +++ b/Plugins/uFire/Source/uFire/uFire.Build.cs @@ -0,0 +1,55 @@ +// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. + +using UnrealBuildTool; + +public class uFire : ModuleRules +{ + public uFire(ReadOnlyTargetRules Target) : base(Target) + { + PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; + + PublicIncludePaths.AddRange( + new string[] { + "uFire/Public" + // ... add public include paths required here ... + } + ); + + + PrivateIncludePaths.AddRange( + new string[] { + "uFire/Private", + // ... add other private include paths required here ... + } + ); + + + PublicDependencyModuleNames.AddRange( + new string[] + { + "Core", + // ... add other public dependencies that you statically link with here ... + } + ); + + + PrivateDependencyModuleNames.AddRange( + new string[] + { + "CoreUObject", + "Engine", + "Slate", + "SlateCore", + // ... add private dependencies that you statically link with here ... + } + ); + + + DynamicallyLoadedModuleNames.AddRange( + new string[] + { + // ... add any modules that your module loads dynamically here ... + } + ); + } +} diff --git a/Plugins/uFire/uFire.uplugin b/Plugins/uFire/uFire.uplugin new file mode 100644 index 0000000..abc9609 --- /dev/null +++ b/Plugins/uFire/uFire.uplugin @@ -0,0 +1,23 @@ +{ + "FileVersion": 3, + "Version": 1, + "VersionName": "1.0", + "FriendlyName": "uFire", + "Description": "Firebase REST/gRPC API integration.", + "Category": "Other", + "CreatedBy": "Lukasz 'iniside' Baran", + "CreatedByURL": "", + "DocsURL": "", + "MarketplaceURL": "", + "SupportURL": "", + "CanContainContent": true, + "IsBetaVersion": false, + "Installed": false, + "Modules": [ + { + "Name": "uFire", + "Type": "Developer", + "LoadingPhase": "Default" + } + ] +} \ No newline at end of file From 19c0e9ce1f51d8b9576cfbf393326feffa2b998a Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 13 Jun 2018 17:27:47 +0200 Subject: [PATCH 183/187] removing GameLift and GameSparks --- ActionRPGGame.uproject | 48 +-- .../DefaultEditorPerProjectUserSettings.ini | 2 +- Config/DefaultEngine.ini | 89 ++--- .../InventoryFramework/Private/IFTypes.cpp | 4 +- Source/ActionRPGGame.Target.cs | 2 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 44 ++- .../ActionRPGGame/Private/ARGameInstance.cpp | 331 +----------------- Source/ActionRPGGame/Private/ARGameMode.cpp | 1 - .../ActionRPGGame/Private/ARGameSession.cpp | 35 +- .../Abilities/ARAbilityManagerComponent.cpp | 4 - .../ActionRPGGame/Private/ActionRPGGame.cpp | 13 + Source/ActionRPGGame/Public/ARGameInstance.h | 83 +---- Source/ActionRPGGame/Public/ARGameSession.h | 10 - .../Abilities/ARAbilityManagerComponent.h | 2 - Source/ActionRPGGameClient.Target.cs | 2 +- Source/ActionRPGGameEditor.Target.cs | 2 +- 16 files changed, 135 insertions(+), 537 deletions(-) diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index 0989e49..c95d7ce 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -77,11 +77,18 @@ "Enabled": true }, { - "Name": "OnlineSubsystemAmazon", + "Name": "OnlineFramework", "Enabled": true }, { - "Name": "OnlineFramework", + "Name": "ActionRPGGameUI", + "Enabled": true, + "BlacklistTargets": [ + "Server" + ] + }, + { + "Name": "GRPC", "Enabled": true }, { @@ -226,34 +233,33 @@ "Enabled": true }, { - "Name": "GameLiftServerSDK", - "Enabled": true, - "BlacklistTargets": [ - "Client" - ], + "Name": "NiagaraExtras", + "Enabled": true + }, + { + "Name": "MagicLeapMedia", + "Enabled": false, "SupportedTargetPlatforms": [ - "Linux" + "Lumin" ] }, { - "Name": "GameLiftClientSDK", - "Enabled": true, - "BlacklistTargets": [ - "Server" + "Name": "MagicLeapEmulator", + "Enabled": false, + "SupportedTargetPlatforms": [ + "Lumin" ] }, { - "Name": "WmfMedia", + "Name": "MagicLeap", "Enabled": false, - "BlacklistTargets": [ - "Server", - "Client" - ], - "BlacklistTargetConfigurations": [ - "Debug", - "Development", - "DebugGame" + "SupportedTargetPlatforms": [ + "Lumin" ] + }, + { + "Name": "AppleVision", + "Enabled": false } ], "TargetPlatforms": [ diff --git a/Config/DefaultEditorPerProjectUserSettings.ini b/Config/DefaultEditorPerProjectUserSettings.ini index ac90d36..8916a8c 100644 --- a/Config/DefaultEditorPerProjectUserSettings.ini +++ b/Config/DefaultEditorPerProjectUserSettings.ini @@ -2,7 +2,7 @@ ContentBrowserTab1.SelectedPaths=/Game/ThirdPersonCPP [/Script/UnrealEd.EditorExperimentalSettings] -bProceduralFoliage=False +bProceduralFoliage=True bEnableLocalizationDashboard=True bEnableTranslationPicker=False bEnableEditorUtilityBlueprints=False diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 4be865b..376bd43 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -28,7 +28,6 @@ r.GenerateLandscapeGIData=True r.TemporalAA.Upsampling=False bDefaultParticleCutouts=True r.SupportMaterialLayers=True -r.GBufferFormat=3 r.UsePreExposure=True [/Script/Engine.StreamingSettings] @@ -80,48 +79,6 @@ gc.BlueprintClusteringEnabled=True [/Script/NoesisRuntime.NoesisSettings] GlyphTextureSize=x4096 -[/Script/Engine.PhysicsSettings] -DefaultGravityZ=-980.000000 -DefaultTerminalVelocity=4000.000000 -DefaultFluidFriction=0.300000 -SimulateScratchMemorySize=262144 -RagdollAggregateThreshold=4 -TriangleMeshTriangleMinAreaThreshold=5.000000 -bEnableAsyncScene=True -bEnableShapeSharing=True -bEnablePCM=True -bEnableStabilization=True -bWarnMissingLocks=True -bEnable2DPhysics=False -PhysicErrorCorrection=(LinearDeltaThresholdSq=5.000000,LinearInterpAlpha=0.200000,LinearRecipFixTime=1.000000,AngularDeltaThreshold=0.628319,AngularInterpAlpha=0.100000,AngularRecipFixTime=1.000000,BodySpeedThresholdSq=0.200000) -LockedAxis=Invalid -DefaultDegreesOfFreedom=Full3D -BounceThresholdVelocity=200.000000 -FrictionCombineMode=Average -RestitutionCombineMode=Average -MaxAngularVelocity=3600.000000 -MaxDepenetrationVelocity=0.000000 -ContactOffsetMultiplier=0.020000 -MinContactOffset=2.000000 -MaxContactOffset=8.000000 -bSimulateSkeletalMeshOnDedicatedServer=True -DefaultShapeComplexity=CTF_UseSimpleAndComplex -bDefaultHasComplexCollision=True -bSuppressFaceRemapTable=False -bSupportUVFromHitResults=False -bDisableActiveActors=False -bDisableCCD=False -bEnableEnhancedDeterminism=True -MaxPhysicsDeltaTime=0.033333 -bSubstepping=True -bSubsteppingAsync=True -MaxSubstepDeltaTime=0.033000 -MaxSubsteps=2 -SyncSceneSmoothingFactor=0.000000 -AsyncSceneSmoothingFactor=0.990000 -InitialAverageFrameRate=0.016667 -PhysXTreeRebuildRate=10 - [/Script/Engine.CollisionProfile] -Profiles=(Name="NoCollision",CollisionEnabled=NoCollision,ObjectTypeName="WorldStatic",CustomResponses=((Channel="Visibility",Response=ECR_Ignore),(Channel="Camera",Response=ECR_Ignore)),HelpMessage="No collision",bCanModify=False) -Profiles=(Name="BlockAll",CollisionEnabled=QueryAndPhysics,ObjectTypeName="WorldStatic",CustomResponses=,HelpMessage="WorldStatic object that blocks all actors by default. All new custom channels will use its own default response. ",bCanModify=False) @@ -183,4 +140,50 @@ PhysXTreeRebuildRate=10 +CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") +[/Script/Engine.PhysicsSettings] +DefaultGravityZ=-980.000000 +DefaultTerminalVelocity=4000.000000 +DefaultFluidFriction=0.300000 +SimulateScratchMemorySize=262144 +RagdollAggregateThreshold=4 +TriangleMeshTriangleMinAreaThreshold=5.000000 +bEnableAsyncScene=True +bEnableShapeSharing=True +bEnablePCM=True +bEnableStabilization=True +bWarnMissingLocks=True +bEnable2DPhysics=False +PhysicErrorCorrection=(PingExtrapolation=0.100000,ErrorPerLinearDifference=1.000000,ErrorPerAngularDifference=1.000000,MaxRestoredStateError=1.000000,PositionLerp=0.000000,AngleLerp=0.400000,LinearVelocityCoefficient=100.000000,AngularVelocityCoefficient=10.000000,ErrorAccumulationSeconds=0.500000,ErrorAccumulationDistanceSq=15.000000,ErrorAccumulationSimilarity=100.000000) +LockedAxis=Invalid +DefaultDegreesOfFreedom=Full3D +BounceThresholdVelocity=200.000000 +FrictionCombineMode=Average +RestitutionCombineMode=Average +MaxAngularVelocity=3600.000000 +MaxDepenetrationVelocity=0.000000 +ContactOffsetMultiplier=0.020000 +MinContactOffset=2.000000 +MaxContactOffset=8.000000 +bSimulateSkeletalMeshOnDedicatedServer=True +DefaultShapeComplexity=CTF_UseSimpleAndComplex +bDefaultHasComplexCollision=True +bSuppressFaceRemapTable=False +bSupportUVFromHitResults=False +bDisableActiveActors=False +bDisableKinematicStaticPairs=False +bDisableKinematicKinematicPairs=False +bDisableCCD=False +bEnableEnhancedDeterminism=True +MaxPhysicsDeltaTime=0.033333 +bSubstepping=True +bSubsteppingAsync=True +MaxSubstepDeltaTime=0.033000 +MaxSubsteps=2 +SyncSceneSmoothingFactor=0.000000 +AsyncSceneSmoothingFactor=0.990000 +InitialAverageFrameRate=0.016667 +PhysXTreeRebuildRate=10 +ClientBroadphaseSettings=(bUseMBP=False,MBPBounds=(Min=(X=0.000000,Y=0.000000,Z=0.000000),Max=(X=0.000000,Y=0.000000,Z=0.000000),IsValid=0),MBPNumSubdivs=2) +ServerBroadphaseSettings=(bUseMBP=False,MBPBounds=(Min=(X=0.000000,Y=0.000000,Z=0.000000),Max=(X=0.000000,Y=0.000000,Z=0.000000),IsValid=0),MBPNumSubdivs=2) + diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp index 93c31fd..0f425c7 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Private/IFTypes.cpp @@ -440,8 +440,8 @@ void FIFJsonSerializer::JsonObjectToUObject(TSharedPtr Object, UObj FString objClassStr2 = Objj->GetStringField("objectClass"); if (objClassStr2.Len() > 0) { - FSoftClassPath path(objClassStr2); - UClass* itemCls = Cast(path.TryLoad()); + FSoftClassPath pathLocal(objClassStr2); + UClass* itemClsLocal = Cast(pathLocal.TryLoad()); UObject* Out = nullptr; JsonObjectToUObject(Objj, Out, OutObject); ObjectProp->SetObjectPropertyValue_InContainer(OutObject, Out); diff --git a/Source/ActionRPGGame.Target.cs b/Source/ActionRPGGame.Target.cs index dac994a..ca32280 100644 --- a/Source/ActionRPGGame.Target.cs +++ b/Source/ActionRPGGame.Target.cs @@ -9,5 +9,5 @@ public ActionRPGGameTarget(TargetInfo Target) : base(Target) { Type = TargetType.Game; ExtraModuleNames.Add("ActionRPGGame"); - } + } } diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index 6d68820..b80eea2 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -8,7 +8,8 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = PCHUsageMode.UseExplicitOrSharedPCHs; PublicDefinitions.Add("BOOST_SYSTEM_NOEXCEPT"); - + PublicDefinitions.Add("GPR_FORBID_UNREACHABLE_CODE=1"); + PublicDefinitions.Add("GOOGLE_PROTOBUF_NO_RTTI=1"); PrivateIncludePaths.AddRange( new string[] { // ... add other private include paths required here ... @@ -19,24 +20,16 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "CoreUObject", "Engine", "InputCore", - "Slate", - "SlateCore", "Json", "JsonUtilities", - "UMG", "GameplayTags", "AbilityFramework", "AssetRegistry", "OrionAnimation", - //"Sockets", - //"OnlineSubsystemUtils", "ActorSequence", "AbilityManager", - "DraggableWindow", "JsonUObject", "InventoryFramework", - "InventoryFrameworkUI", - "GameSparks", "OnlineSubsystem", "OnlineSubsystemGameSparks" }); @@ -46,49 +39,52 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "SourceControl", "Matinee", "PropertyEditor", "ShaderCore", "AbilityFrameworkEditor" }); PrivateDependencyModuleNames.AddRange(new string[] { "AbilityFrameworkEditor" }); } - + PublicDependencyModuleNames.AddRange(new string[] { "GRPC" }); + PublicDefinitions.Add("GPR_GCOV=1"); //hax if (Target.Type == TargetRules.TargetType.Server) { if (Target.Platform == UnrealTargetPlatform.Linux) { - PublicDefinitions.Add("LINUX_GAMELIFT=1"); - PublicDefinitions.Add("GAMESPARKS_SERVER=1"); - PublicDependencyModuleNames.AddRange(new string[] { "GameLiftServerSDK" }); + PublicDefinitions.Add("WITH_AGONES=1"); + PublicDefinitions.Add("ENABLE_GRPC=1"); //hack + PublicDependencyModuleNames.AddRange(new string[] { "Agones" }); + } else { - PublicDefinitions.Add("LINUX_GAMELIFT=0"); - PublicDefinitions.Add("GAMESPARKS_SERVER=0"); + PublicDefinitions.Add("WITH_AGONES=0"); + PublicDefinitions.Add("ENABLE_GRPC=0"); //hack } } else { - PublicDefinitions.Add("LINUX_GAMELIFT=0"); - PublicDefinitions.Add("GAMESPARKS_SERVER=0"); + PublicDefinitions.Add("WITH_AGONES=0"); + PublicDefinitions.Add("ENABLE_GRPC=0"); //hack } if ( (Target.Type == TargetRules.TargetType.Client) || (Target.Type == TargetRules.TargetType.Editor)) { + PublicDependencyModuleNames.AddRange(new string[] { + "Slate", + "SlateCore", + "UMG", + "InventoryFrameworkUI", + "DraggableWindow" + }); + if (Target.Platform == UnrealTargetPlatform.Win64) { - PublicDefinitions.Add("GAMELIFT_CLIENT=1"); - PublicDefinitions.Add("GAMESPARKS_CLIENT=1"); if (Target.Type == TargetRules.TargetType.Client) { bEnableExceptions = true; } - PublicDependencyModuleNames.AddRange(new string[] { "AWSCore", "GameLiftClientSDK" }); } else { - PublicDefinitions.Add("GAMELIFT_CLIENT=0"); - PublicDefinitions.Add("GAMESPARKS_CLIENT=0"); } } else { - PublicDefinitions.Add("GAMELIFT_CLIENT=0"); - PublicDefinitions.Add("GAMESPARKS_CLIENT=0"); } } } diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index f4477b9..e1d23fa 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -12,82 +12,32 @@ #include "Abilities/GAAbilityBase.h" #include "Effects/GAEffectCue.h" +#if WITH_AGONES +#include "IAgones.h" +#endif + UARGameInstance::UARGameInstance(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { - GSObject = ObjectInitializer.CreateDefaultSubobject(this, TEXT("GSObject")); - GSMessageListener = ObjectInitializer.CreateDefaultSubobject(this, TEXT("GSMessageListener")); -#if WITH_EDITOR - bConnected = false; -#endif -#if GAMELIFT_CLIENT - AccessKey = "Local"; - Secret = "Local"; - Region = "Local"; - LocalPort = 8080; - bIsUsingGameLiftLocal = true; -#endif } void UARGameInstance::OnGameSparksAvailable(bool bAvailable) { -#if WITH_EDITOR - bConnected = false; -#endif + OnConnectedToGameSparks.Broadcast(); } void UARGameInstance::AttemptLogin(const FString& UserName, const FString& Password) { - GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Connected")); - - GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); - GameSparks::Api::Requests::AuthenticationRequest authRequest(gs); - authRequest.SetUserName(TCHAR_TO_UTF8(*UserName)); - authRequest.SetPassword(TCHAR_TO_UTF8(*Password)); - - auto AuthRquestResponse = [&](GameSparks::Core::GS&, const GameSparks::Api::Responses::AuthenticationResponse& response) - { - GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, response.GetJSONString().c_str()); - //Check is response has no errors - if (!response.GetHasErrors()) - { - OnLoginSuccess.Broadcast(); - GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Red, TEXT("Auth response successful")); - - GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); - GameSparks::Api::Requests::AccountDetailsRequest accDetRequest(gs); - //If no errors then send an accounts details request - accDetRequest.Send(); - } - else - { - OnLoginFailed.Broadcast(); - } - }; - - authRequest.Send(AuthRquestResponse); } void UARGameInstance::RegisterNewPlayer(const FString& UserName, const FString& DisplayName, const FString& Password) { -#if GAMESPARKS_CLIENT - GameSparks::Core::GS& gs = UGameSparksModule::GetModulePtr()->GetGSInstance(); - GameSparks::Api::Requests::RegistrationRequest regRequest(gs); - regRequest.SetUserName(TCHAR_TO_UTF8(*UserName)); - regRequest.SetDisplayName(TCHAR_TO_UTF8(*DisplayName)); - regRequest.SetPassword(TCHAR_TO_UTF8(*DisplayName)); - auto RegRequestResponse = [&](GameSparks::Core::GS&, const GameSparks::Api::Responses::RegistrationResponse& Response) - { - GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, Response.GetJSONString().c_str()); - }; - regRequest.Send(RegRequestResponse); -#endif } void UARGameInstance::Init() @@ -108,294 +58,45 @@ void UARGameInstance::Init() Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("EffectCue"), ContentPaths, AGAEffectCue::StaticClass(), true); } -#if WITH_EDITOR - //editor hax so we don't attempt to connect twice. - if (!bConnected) +#if WITH_AGONES + //if (IAgones::Get().AgonesSDK->Connect()) + //{ + // grpc::Status statuc = IAgones::Get().AgonesSDK->Ready(); + // FTimerDelegate HealthCheckDel = FTimerDelegate::CreateUObject(this, &UARGameInstance::HealthCheck); + // TimerManager->SetTimer(HealthCheckHandle, HealthCheckDel, 1, true, 1); + //} #endif - { - //Set the OnAvailable delegate - GetGSObject()->OnGameSparksAvailableDelegate.AddDynamic(this, &UARGameInstance::OnGameSparksAvailable); - //Disconnected the module just incase it's connected (Refresh) - GetGSObject()->Disconnect(); - //Connect module - GetGSObject()->Connect(GSKey, GSSecret); - -#if WITH_EDITOR - bConnected = true; //it will be overriden in delegate anyway. -#endif - } -#if LINUX_GAMELIFT - InitGameLift(); -#endif - -#if GAMELIFT_CLIENT - Aws::Client::ClientConfiguration ClientConfig; - Aws::Auth::AWSCredentials Credentials; - - ClientConfig.connectTimeoutMs = 10000; - ClientConfig.requestTimeoutMs = 10000; - ClientConfig.region = TCHAR_TO_UTF8(*Region); - - // GameLiftLocal - if (bIsUsingGameLiftLocal) - { - ClientConfig.scheme = Aws::Http::Scheme::HTTP; - const FString HostAddress = FString::Printf(TEXT("localhost:%i"), LocalPort); - ClientConfig.endpointOverride = TCHAR_TO_UTF8(*HostAddress); - UE_LOG(LogTemp, Warning, TEXT("GameLift is currently configured to use GameLift Local.")); - - } - - Credentials = Aws::Auth::AWSCredentials(TCHAR_TO_UTF8(*AccessKey), TCHAR_TO_UTF8(*Secret)); - GameLiftClient = new Aws::GameLift::GameLiftClient(Credentials, ClientConfig); -#endif - } #if WITH_EDITOR /* Called to actually start the game when doing Play/Simulate In Editor */ FGameInstancePIEResult UARGameInstance::StartPlayInEditorGameInstance(ULocalPlayer* LocalPlayer, const FGameInstancePIEParameters& Params) { - if (!bConnected) - - { - //Set the OnAvailable delegate - GetGSObject()->OnGameSparksAvailableDelegate.AddDynamic(this, &UARGameInstance::OnGameSparksAvailable); - //Disconnected the module just incase it's connected (Refresh) - GetGSObject()->Disconnect(); - //Connect module - GetGSObject()->Connect(GSKey, GSSecret); - bConnected = true; //it will be overriden in delegate anyway. - } - return Super::StartPlayInEditorGameInstance(LocalPlayer, Params); } #endif -#if LINUX_GAMELIFT -void UARGameInstance::InitGameLift() -{ - //Getting the module first. - FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); - - //InitSDK establishes a local connection with GameLift's agent to enable further communication. - gameLiftSdkModule->InitSDK(); - - //When a game session is created, GameLift sends an activation request to the game server and passes along the game session object containing game properties and other settings. - //Here is where a game server should take action based on the game session object. - //Once the game server is ready to receive incoming player connections, it should invoke GameLiftServerAPI.ActivateGameSession() - auto onGameSession = [=](Aws::GameLift::Server::Model::GameSession gameSession) - { - this->OnGameSessionStarted(gameSession); - }; - - FProcessParameters* params = new FProcessParameters(); - params->OnStartGameSession.BindLambda(onGameSession); - - //OnProcessTerminate callback. GameLift invokes this callback before shutting down an instance hosting this game server. - //It gives this game server a chance to save its state, communicate with services, etc., before being shut down. - //In this case, we simply tell GameLift we are indeed going to shut down. - params->OnTerminate.BindLambda([=]() {gameLiftSdkModule->ProcessEnding(); }); - - //This is the HealthCheck callback. - //GameLift invokes this callback every 60 seconds or so. - //Here, a game server might want to check the health of dependencies and such. - //Simply return true if healthy, false otherwise. - //The game server has 60 seconds to respond with its health status. GameLift defaults to 'false' if the game server doesn't respond in time. - //In this case, we're always healthy! - params->OnHealthCheck.BindLambda([]() {return true; }); - //FString Address = GetWorld()->GetAddressURL(); - //FString portString = Address.RightChop(4); - int32 port = GetWorld()->URL.Port; //FCString::Atoi(*portString); - UE_LOG(LogTemp, Warning, TEXT("Current Server Address %d "), port); - //This game server tells GameLift that it listens on port 7777 for incoming player connections. - params->port = port; - - //Here, the game server tells GameLift what set of files to upload when the game session ends. - //GameLift uploads everything specified here for the developers to fetch later. - TArray logfiles; - logfiles.Add(TEXT("aLogFile.txt")); - params->logParameters = logfiles; - - //Calling ProcessReady tells GameLift this game server is ready to receive incoming game sessions! - gameLiftSdkModule->ProcessReady(*params); - -} - -void UARGameInstance::OnGameSessionStarted(Aws::GameLift::Server::Model::GameSession InGameSession) -{ - auto func2 = [&]() - { - int outNum = 0;; - const Aws::GameLift::Server::Model::GameProperty* props = InGameSession.GetGameProperties(outNum); - FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); - - gameLiftSdkModule->ActivateGameSession(); - - FString MapName = FString(props[0].GetValue()); - UE_LOG(LogTemp, Warning, TEXT("%s"), *MapName); - UGameplayStatics::OpenLevel(this, *MapName); - }; - AsyncTask(ENamedThreads::GameThread, func2); -} -#endif - void UARGameInstance::ConnectToHub() { -#if GAMELIFT_CLIENT - using namespace Aws::GameLift::Model; - SearchGameSessionsRequest SearchRequest; - //SearchRequest. - Aws::GameLift::SearchGameSessionsResponseReceivedHandler SearchHandler; - SearchHandler = std::bind(&UARGameInstance::OnSessionsSearched, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); - - GameLiftClient->SearchGameSessionsAsync(SearchRequest, SearchHandler); - - - -#endif } void UARGameInstance::ConnectToWorld() { -#if GAMELIFT_CLIENT -#endif } -#if GAMELIFT_CLIENT -void UARGameInstance::OnSessionsSearched(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::SearchGameSessionsRequest& Request, const Aws::GameLift::Model::SearchGameSessionsOutcome& Outcome, const std::shared_ptr& Context) +void UARGameInstance::TestGSRequest() { - if (Outcome.IsSuccess()) - { - using namespace Aws::GameLift::Model; - SearchGameSessionsResult SearchResult = Outcome.GetResult(); - - const Aws::Vector& Sessions = SearchResult.GetGameSessions(); - - for (const GameSession& Session : Sessions) - { - if (Session.GetCurrentPlayerSessionCount() < 8) - { - Aws::GameLift::Model::CreatePlayerSessionRequest PlayerRequest; - PlayerRequest.SetGameSessionId(Session.GetGameSessionId()); - PlayerRequest.SetPlayerId("TestPlayer"); - - Aws::GameLift::CreatePlayerSessionResponseReceivedHandler Handler; - Handler = std::bind(&UARGameInstance::OnCreatePlayerSession, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); - - GameLiftClient->CreatePlayerSessionAsync(PlayerRequest, Handler); - break; - } - } - - } - else - { - using namespace Aws::GameLift::Model; - CreateGameSessionRequest CreateRequest; - CreateRequest.SetFleetId("Local"); - CreateRequest.SetMaximumPlayerSessionCount(8); - GameProperty MapName; - MapName.SetKey("MapName"); - MapName.SetValue("TestMap"); //reasons,, - - CreateRequest.AddGameProperties(MapName); - - Aws::GameLift::CreateGameSessionResponseReceivedHandler Handler; - - - Handler = std::bind(&UARGameInstance::OnSessionCreated, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); - - GameLiftClient->CreateGameSessionAsync(CreateRequest, Handler); - } } -void UARGameInstance::OnSessionCreated(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreateGameSessionRequest& Request, const Aws::GameLift::Model::CreateGameSessionOutcome& Outcome, const std::shared_ptr& Context) -{ - if (Outcome.IsSuccess()) - { - using namespace Aws::GameLift::Model; - CreateGameSessionResult Result = Outcome.GetResult(); - GameSession Session = Result.GetGameSession(); - - Aws::GameLift::Model::CreatePlayerSessionRequest PlayerRequest; - PlayerRequest.SetGameSessionId(Session.GetGameSessionId()); - PlayerRequest.SetPlayerId("TestPlayer"); - - Aws::GameLift::CreatePlayerSessionResponseReceivedHandler Handler; - Handler = std::bind(&UARGameInstance::OnCreatePlayerSession, this, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3, std::placeholders::_4); - - GameLiftClient->CreatePlayerSessionAsync(PlayerRequest, Handler); - } -} - -void UARGameInstance::OnCreatePlayerSession(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreatePlayerSessionRequest& Request, const Aws::GameLift::Model::CreatePlayerSessionOutcome& Outcome, const std::shared_ptr& Context) +void UARGameInstance::HealthCheck() { - using namespace Aws::GameLift::Model; - const FString ServerIpAddress = FString(Outcome.GetResult().GetPlayerSession().GetIpAddress().c_str()); - const FString ServerPort = FString::FromInt(Outcome.GetResult().GetPlayerSession().GetPort()); - - FString FullAddress = ServerIpAddress + ":" + ServerPort; - - GEngine->SetClientTravel(GetWorld(), *FullAddress, ETravelType::TRAVEL_Absolute); -} - +#if WITH_AGONES + IAgones::Get().AgonesSDK->Health(); #endif - -void UARGameInstance::TestGSRequest() -{ - GSRequestData scriptData; - scriptData.AddString("eventKey", "SearchGameSessions"); - GameSparks::Api::Requests::LogEventRequest request(UGameSparksModule::GetModulePtr()->GetGSInstance()); - request.SetEventKey("SearchGameSessions"); - - auto func = [=](GS& gs, GameSparks::Api::Responses::LogEventResponse response) - { - this->OnScriptMessageReceived(response); - }; - request.Send(func); -} -void UARGameInstance::OnScriptMessageReceived(GameSparks::Api::Responses::LogEventResponse response) -{ - TSharedPtr PlayerSessions = GetGameLiftResponseFromGS("PlayerSession", response); - GEngine->AddOnScreenDebugMessage(-1, 20.f, FColor::Red, response.GetJSONString().c_str()); - FString PlayerID = PlayerSessions->GetStringField("PlayerId"); - FString IP = PlayerSessions->GetStringField("IpAddress"); - int32 Port = PlayerSessions->GetIntegerField("Port"); - - FString Options = FString::Printf(TEXT("%s:%d?PlayerId=%s"), *IP, Port, *PlayerID); - - TArray OutParams; - Options.ParseIntoArray(OutParams, TEXT("?")); - - - GEngine->SetClientTravel(GetWorld(), *Options, ETravelType::TRAVEL_Absolute); } - -TSharedPtr UARGameInstance::GetGameLiftResponseFromGS(const FString& Field, GameSparks::Api::Responses::LogEventResponse response) -{ - gsstl::string str = response.GetJSONString(); - FString data(str.data()); - - UE_LOG(LogTemp, Warning, TEXT("GameLift Response Data %s "), *data); - - TSharedRef< TJsonReader<> > Reader = TJsonReaderFactory<>::Create(data); - - TSharedPtr Object = MakeShareable(new FJsonObject()); - bool bSuccessful = FJsonSerializer::Deserialize(Reader, Object); - - TSharedPtr scriptData = Object->GetObjectField("scriptData"); - TSharedPtr respo = scriptData->GetObjectField("response"); - TSharedPtr searchGameSessions = respo->GetObjectField("searchGameSessions"); - TSharedPtr json = searchGameSessions->GetObjectField("json"); - TSharedPtr GameSession= json->GetObjectField(Field); - - - return GameSession; -} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/ARGameMode.cpp b/Source/ActionRPGGame/Private/ARGameMode.cpp index e3f81b3..eaac6da 100644 --- a/Source/ActionRPGGame/Private/ARGameMode.cpp +++ b/Source/ActionRPGGame/Private/ARGameMode.cpp @@ -7,7 +7,6 @@ #include "Engine/AssetManager.h" #include "Abilities/ARAbilityBase.h" #include "ARGameInstance.h" -#include "SDraggableWindowWidget.h" #include "ARPlayerController.h" diff --git a/Source/ActionRPGGame/Private/ARGameSession.cpp b/Source/ActionRPGGame/Private/ARGameSession.cpp index 75f8006..bacda6e 100644 --- a/Source/ActionRPGGame/Private/ARGameSession.cpp +++ b/Source/ActionRPGGame/Private/ARGameSession.cpp @@ -6,6 +6,7 @@ #include "ARPlayerController.h" + FString AARGameSession::ApproveLogin(const FString& Options) { FString Output = Super::ApproveLogin(Options); @@ -24,44 +25,10 @@ FString AARGameSession::ApproveLogin(const FString& Options) } } -#if LINUX_GAMELIFT - //AcceptPlayerSession - FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); - FGameLiftGenericOutcome out = gameLiftSdkModule->AcceptPlayerSession(PlayerId); - - FString ErrorName = out.GetError().m_errorName; - FString ErrorMessage = out.GetError().m_errorMessage; -#endif - - return Output; } void AARGameSession::UnregisterPlayer(const APlayerController* ExitingPlayer) { -#if LINUX_GAMELIFT - if (const AARPlayerController* PC = Cast(ExitingPlayer)) - { - FString GLId = PC->GameLiftId; - FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); - FGameLiftGenericOutcome out = gameLiftSdkModule->RemovePlayerSession(GLId); - - FString ErrorName = out.GetError().m_errorName; - FString ErrorMessage = out.GetError().m_errorMessage; - } -#endif - Super::UnregisterPlayer(ExitingPlayer); - - /*AARGameMode* GM = Cast(GetOuter()); - int32 NumPlayer = GM->GetNumPlayers(); - if (NumPlayer <= 0) - { -#if LINUX_GAMELIFT - FString GLId = PC->GameLiftId; - FGameLiftServerSDKModule* gameLiftSdkModule = &FModuleManager::LoadModuleChecked(FName("GameLiftServerSDK")); - gameLiftSdkModule->TerminateGameSession(); -#endif - }*/ - } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp index d4abf78..ea3f337 100644 --- a/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp +++ b/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp @@ -1,12 +1,8 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "ARAbilityManagerComponent.h" -#include "Blueprint/UserWidget.h" #include "GameFramework/PlayerController.h" -#include "Layout/Visibility.h" -#include "DWBPFunctionLibrary.h" -#include "SDraggableWindowWidget.h" #include "ARPlayerController.h" // Sets default values for this component's properties diff --git a/Source/ActionRPGGame/Private/ActionRPGGame.cpp b/Source/ActionRPGGame/Private/ActionRPGGame.cpp index 1363bec..7c59797 100644 --- a/Source/ActionRPGGame/Private/ActionRPGGame.cpp +++ b/Source/ActionRPGGame/Private/ActionRPGGame.cpp @@ -2,11 +2,24 @@ #include "ActionRPGGame.h" #include "Modules/ModuleManager.h" + +#if ENABLE_GRPC +#include "IGRPC.h" +#include "grpc++/grpc++.h" +#endif + #if WITH_EDITOR #include "IAbilityFrameworkEditor.h" #endif void FActionRPGGameModule::StartupModule() { +#if ENABLE_GRPC + FModuleManager::Get().LoadModule(TEXT("GRPC")); + grpc::string out = grpc::Version(); + FString ver = FString(ANSI_TO_TCHAR(out.c_str())); + UE_LOG(LogTemp, Warning, TEXT("ActionRPGGame GRPC Version: %s "), *ver); +#endif + #if WITH_EDITOR FModuleManager::Get().LoadModule(TEXT("AbilityFrameworkEditor")); //FModuleManager::LoadModuleChecked(TEXT("AbilityFrameworkEditor")); diff --git a/Source/ActionRPGGame/Public/ARGameInstance.h b/Source/ActionRPGGame/Public/ARGameInstance.h index ad22eed..9968b9d 100644 --- a/Source/ActionRPGGame/Public/ARGameInstance.h +++ b/Source/ActionRPGGame/Public/ARGameInstance.h @@ -5,41 +5,7 @@ #include "CoreMinimal.h" #include "Engine/GameInstance.h" -#include -#include -#include -#include "GameSparksModule.h" -#include "GameSparks/Private/GameSparksObject.h" -#include "GameSparks/Private/GSMessageListenersObject.h" - -#if LINUX_GAMELIFT -#include "GameLiftServerSDK.h" -#include "aws/gamelift/server/model/GameProperty.h" -#include "aws/gamelift/server/model/GameSession.h" -#include "aws/gamelift/server/model/Player.h" -#include "aws/gamelift/server/model/PlayerSession.h" -#include "aws/gamelift/server/model/PlayerSessionStatus.h" -#endif - - -#if GAMELIFT_CLIENT -#include "aws/core/client/AWSError.h" -#include "aws/core/http/HttpRequest.h" -#include "aws/gamelift/GameLiftClient.h" -#include "aws/gamelift/GameLiftErrors.h" -#include "aws/core/utils/Outcome.h" -#include "aws/gamelift/model/DescribeGameSessionDetailsRequest.h" -#include "aws/gamelift/model/CreateGameSessionResult.h" -#include "aws/gamelift/model/CreateGameSessionRequest.h" -#include "aws/gamelift/model/CreatePlayerSessionRequest.h" -#include "aws/gamelift/model/SearchGameSessionsRequest.h" -#include "aws/gamelift/model/SearchGameSessionsResult.h" -#include "aws/core/auth/AWSCredentialsProvider.h" -#endif - #include "ARGameInstance.generated.h" - - DECLARE_DYNAMIC_MULTICAST_DELEGATE(FAROnConnectedToGS); DECLARE_DYNAMIC_MULTICAST_DELEGATE(FARLoginAttemptEvent); @@ -51,11 +17,6 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance { GENERATED_BODY() protected: - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "GSObjects") - UGameSparksObject* GSObject; - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "GSObjects") - UGSMessageListenersObject* GSMessageListener; - UPROPERTY(Config) FString GSKey; UPROPERTY(Config) @@ -69,34 +30,9 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance UPROPERTY(BlueprintReadOnly, BlueprintAssignable) FARLoginAttemptEvent OnLoginFailed; - -#if GAMELIFT_CLIENT - Aws::GameLift::GameLiftClient* GameLiftClient; - FString AccessKey; - FString Secret; - FString Region; - int32 LocalPort; - bool bIsUsingGameLiftLocal; -#endif - -#if WITH_EDITOR - //editor hax so we don't attempt to connect twice. - bool bConnected; -#endif public: UARGameInstance(const FObjectInitializer& ObjectInitializer); - inline UGameSparksObject* GetGSObject() - { - return GSObject; - } - - inline UGSMessageListenersObject* GetGSMessageListener() - { - return GSMessageListener; - } - - void AttemptLogin(const FString& UserName, const FString& Password); void RegisterNewPlayer(const FString& UserName, const FString& DisplayName, const FString& Password); //Function used to determine what happens if GameSparks connects or fails to (Needs to be UFUNCTION) @@ -112,27 +48,20 @@ class ACTIONRPGGAME_API UARGameInstance : public UGameInstance #endif -#if LINUX_GAMELIFT - void InitGameLift(); - void OnGameSessionStarted(Aws::GameLift::Server::Model::GameSession InGameSession); -#endif - UFUNCTION(BlueprintCallable, Category = "GameLift|Test") void ConnectToHub(); UFUNCTION(BlueprintCallable, Category = "GameLift|Test") void ConnectToWorld(); -#if GAMELIFT_CLIENT - void OnSessionsSearched(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::SearchGameSessionsRequest& Request, const Aws::GameLift::Model::SearchGameSessionsOutcome& Outcome, const std::shared_ptr& Context); - void OnSessionCreated(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreateGameSessionRequest& Request, const Aws::GameLift::Model::CreateGameSessionOutcome& Outcome, const std::shared_ptr& Context); - void OnCreatePlayerSession(const Aws::GameLift::GameLiftClient* Client, const Aws::GameLift::Model::CreatePlayerSessionRequest& Request, const Aws::GameLift::Model::CreatePlayerSessionOutcome& Outcome, const std::shared_ptr& Context); -#endif UFUNCTION(BlueprintCallable, Category = "GameLift|Test") void TestGSRequest(); - void OnScriptMessageReceived(GameSparks::Api::Responses::LogEventResponse response); - protected: - TSharedPtr GetGameLiftResponseFromGS(const FString& Field, GameSparks::Api::Responses::LogEventResponse response); +#if WITH_AGONES + FTimerHandle HealthCheckHandle; +#endif + UFUNCTION() + void HealthCheck(); + }; diff --git a/Source/ActionRPGGame/Public/ARGameSession.h b/Source/ActionRPGGame/Public/ARGameSession.h index 6416397..3851601 100644 --- a/Source/ActionRPGGame/Public/ARGameSession.h +++ b/Source/ActionRPGGame/Public/ARGameSession.h @@ -5,16 +5,6 @@ #include "CoreMinimal.h" #include "GameFramework/GameSession.h" -#if LINUX_GAMELIFT -#include "GameLiftServerSDK.h" -#include "GameLiftServerSDKModels.h" -#include "aws/gamelift/server/model/GameProperty.h" -#include "aws/gamelift/server/model/GameSession.h" -#include "aws/gamelift/server/model/Player.h" -#include "aws/gamelift/server/model/PlayerSession.h" -#include "aws/gamelift/server/model/PlayerSessionStatus.h" -#endif - #include "ARGameSession.generated.h" /** diff --git a/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h index 254e746..eb790bd 100644 --- a/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h +++ b/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h @@ -8,8 +8,6 @@ #include "Abilities/GAAbilityBase.h" #include "AMAbilityManagerComponent.h" -#include "DWTypes.h" - #include "ARAbilityManagerComponent.generated.h" diff --git a/Source/ActionRPGGameClient.Target.cs b/Source/ActionRPGGameClient.Target.cs index a64ca18..6e4eedd 100644 --- a/Source/ActionRPGGameClient.Target.cs +++ b/Source/ActionRPGGameClient.Target.cs @@ -9,5 +9,5 @@ public ActionRPGGameClientTarget(TargetInfo Target) : base(Target) { Type = TargetType.Client; ExtraModuleNames.Add("ActionRPGGame"); - } + } } diff --git a/Source/ActionRPGGameEditor.Target.cs b/Source/ActionRPGGameEditor.Target.cs index 8a3d1a2..86bd66f 100644 --- a/Source/ActionRPGGameEditor.Target.cs +++ b/Source/ActionRPGGameEditor.Target.cs @@ -9,6 +9,6 @@ public ActionRPGGameEditorTarget(TargetInfo Target) : base(Target) { Type = TargetType.Editor; ExtraModuleNames.Add("ActionRPGGame"); - ExtraModuleNames.Add("ActionRPGGameEditor"); + ExtraModuleNames.Add("ActionRPGGameEditor"); } } From 374ade6f3a6b5de57d47fd5a4288cc1281cd281e Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Wed, 13 Jun 2018 22:46:08 +0200 Subject: [PATCH 184/187] fix spawned crash --- Source/ActionRPGGame/Private/AI/ARAICharacter.cpp | 3 ++- Source/ActionRPGGame/Private/AREnemySpawner.cpp | 5 ++++- Source/ActionRPGGame/Private/ARGameInstance.cpp | 12 ++++++------ 3 files changed, 12 insertions(+), 8 deletions(-) diff --git a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp index bf5e0d3..6db016c 100644 --- a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp +++ b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp @@ -38,7 +38,8 @@ void AARAICharacter::SetupPlayerInputComponent(UInputComponent* PlayerInputCompo void AARAICharacter::Kill() { - SpawnedBy->OnEnemyKilled(this); + if(SpawnedBy) + SpawnedBy->OnEnemyKilled(this); Destroy(); } diff --git a/Source/ActionRPGGame/Private/AREnemySpawner.cpp b/Source/ActionRPGGame/Private/AREnemySpawner.cpp index 82bc88c..bbd5aa0 100644 --- a/Source/ActionRPGGame/Private/AREnemySpawner.cpp +++ b/Source/ActionRPGGame/Private/AREnemySpawner.cpp @@ -42,7 +42,10 @@ void AAREnemySpawner::Tick(float DeltaTime) void AAREnemySpawner::OnEnemyKilled(AARAICharacter* InEnemy) { - SpawnedEnemies.Remove(InEnemy); + if (SpawnedEnemies.Num() > 0) + { + SpawnedEnemies.Remove(InEnemy); + } if (SpawnedEnemies.Num() < MinRespawn) { SetupSpawner(); diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index e1d23fa..83f4946 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -59,12 +59,12 @@ void UARGameInstance::Init() } #if WITH_AGONES - //if (IAgones::Get().AgonesSDK->Connect()) - //{ - // grpc::Status statuc = IAgones::Get().AgonesSDK->Ready(); - // FTimerDelegate HealthCheckDel = FTimerDelegate::CreateUObject(this, &UARGameInstance::HealthCheck); - // TimerManager->SetTimer(HealthCheckHandle, HealthCheckDel, 1, true, 1); - //} + if (IAgones::Get().AgonesSDK->Connect()) + { + grpc::Status statuc = IAgones::Get().AgonesSDK->Ready(); + FTimerDelegate HealthCheckDel = FTimerDelegate::CreateUObject(this, &UARGameInstance::HealthCheck); + TimerManager->SetTimer(HealthCheckHandle, HealthCheckDel, 1, true, 1); + } #endif } #if WITH_EDITOR From 3ba55e21cbbf2eefce82ccd3475070ecaedc34eb Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Thu, 14 Jun 2018 21:20:00 +0200 Subject: [PATCH 185/187] fix crash when there is no target --- .../Private/Effects/GABlueprintLibrary.cpp | 15 ++++++++++++--- 1 file changed, 12 insertions(+), 3 deletions(-) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp index bee30fc..be0a89d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp @@ -169,21 +169,30 @@ FGAEffectHandle UGABlueprintLibrary::ApplyEffect( FAFEffectParams Params(InEffect); if (Params.EffectSpec.GetPtr()) { - UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + if (Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target.IsValid()) + { + UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + } } if (!bReusedSpec) { FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); AddTagsToEffect(EffectSpec); Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); - UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *EffectSpec->GetContext().GetPtr()->Target->GetName()); + if (EffectSpec->GetContext().GetPtr()->Target.IsValid()) + { + UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *EffectSpec->GetContext().GetPtr()->Target->GetName()); + } } else { Params.EffectSpec = EffectSpecHandle; Params.EffectSpec.SetContext(Context); } - UE_LOG(GameAttributesEffects, Log, TEXT(" Post Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + if (Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target.IsValid()) + { + UE_LOG(GameAttributesEffects, Log, TEXT(" Post Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + } Params.bRecreated = bReusedParams; Params.bPeriodicEffect = bPeriodicEffect; Params.Context = Context; From cf2216a424f19733985656a02a9776d14dc02325 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Sun, 1 Jul 2018 19:58:13 +0200 Subject: [PATCH 186/187] syncing changes with perforce, ability is now identified by handle instead by asset pointe --- ActionRPGGame.uproject | 17 +- Agones/Agones.uplugin | 25 + Agones/Resources/Icon128.png | Bin 0 -> 12739 bytes Agones/Source/Agones/Agones.Build.cs | 80 +++ Agones/Source/Agones/Private/Agones.cpp | 49 ++ Agones/Source/Agones/Private/sdk.cc | 62 ++ Agones/Source/Agones/Private/sdk.grpc.pb.cc | 136 +++++ Agones/Source/Agones/Private/sdk.pb.cc | 342 +++++++++++ Agones/Source/Agones/Public/IAgones.h | 38 ++ Agones/Source/Agones/Public/sdk.grpc.pb.h | 307 ++++++++++ Agones/Source/Agones/Public/sdk.h | 50 ++ Agones/Source/Agones/Public/sdk.pb.h | 202 +++++++ Config/DefaultEngine.ini | 16 + Config/DefaultGame.ini | 40 +- Config/DefaultInput.ini | 7 +- .../Private/AFAbilityComponent.cpp | 278 +++------ .../Private/AFAbilityTypes.cpp | 215 ++----- .../Private/AFBlueprintFunctionLibrary.cpp | 4 +- .../Private/Abilities/GAAbilityBase.cpp | 14 +- .../Private/Attributes/GAAttributeBase.cpp | 10 +- .../Attributes/GAAttributeExtension.cpp | 17 +- .../Public/AFAbilityComponent.h | 107 ++-- .../AbilityFramework/Public/AFAbilityTypes.h | 124 ++-- .../Public/Abilities/GAAbilityBase.h | 8 +- .../Public/Attributes/GAAttributeBase.h | 7 +- .../Public/Attributes/GAAttributeExtension.h | 7 +- .../AbilityFrameworkDebugger.uplugin | 37 -- .../AbilityFrameworkDebugger.Build.cs | 58 -- .../Public/AFDAbilityGiveTrigger.cpp | 107 ---- .../Public/AFDAbilityGiveTrigger.h | 83 --- .../Public/AFDBlueprintFunctionLibrary.cpp | 11 - .../Public/AFDBlueprintFunctionLibrary.h | 20 - .../Public/AFDManager.cpp | 41 -- .../Public/AFDManager.h | 38 -- .../Public/Abilities/AFDAbilityBase.cpp | 7 - .../Public/Abilities/AFDAbilityBase.h | 20 - .../Public/AbilityFrameworkDebugger.cpp | 45 -- .../Public/AbilityFrameworkDebugger.h | 22 - .../Public/SAFDAttributes.cpp | 74 --- .../Public/SAFDAttributes.h | 39 -- .../Public/SAFDDesktopWidget.cpp | 203 ------- .../Public/SAFDDesktopWidget.h | 54 -- .../Public/SAFDEffectInspector.cpp | 16 - .../Public/SAFDEffectInspector.h | 20 - .../Public/SAFDEffects.cpp | 105 ---- .../Public/SAFDEffects.h | 82 --- .../Public/SAFDViewportMouseCapture.cpp | 22 - .../Public/SAFDViewportMouseCapture.h | 24 - Plugins/AbilityManager/AbilityManager.uplugin | 34 -- .../AbilityManager/AbilityManager.Build.cs | 49 -- .../Public/AMAbilityManagerComponent.cpp | 451 -------------- .../Public/AMAbilityManagerComponent.h | 201 ------- .../Source/AbilityManager/Public/AMTypes.cpp | 3 - .../Source/AbilityManager/Public/AMTypes.h | 95 --- .../AbilityManager/Public/AbilityManager.cpp | 20 - .../AbilityManager/Public/AbilityManager.h | 15 - .../AbilityManagerEditor.Build.cs | 52 -- .../Public/AMAbilityInputProperty.cpp | 36 -- .../Public/AMAbilityInputProperty.h | 18 - .../Public/AbilityManagerEditor.cpp | 20 - .../Public/AbilityManagerEditor.h | 15 - .../Public/IFEquipmentComponent.h | 9 +- .../Public/AnimNode_BlendLocomotionFour.cpp | 548 ------------------ .../Public/OrionAnimComponent.cpp | 34 -- .../Public/OrionAnimComponent.h | 13 +- .../OrionAnimation/Public/OrionAnimation.cpp | 20 - .../OrionAnimation/Public/OrionInterface.cpp | 6 - Plugins/uFire/Source/uFire/uFire.Build.cs | 7 +- Source/ActionRPGGame/ActionRPGGame.Build.cs | 10 +- Source/ActionRPGGame/Private/ARCharacter.cpp | 243 +------- .../Private/ARCharacterMovementComponent.cpp | 2 - .../Private/ARPlayerController.cpp | 49 +- .../Abilities/ARAbilityManagerComponent.cpp | 109 ---- .../Private/UI/HUD/ARHUDPlayerInfo.cpp | 5 - .../Private/Weapons/ARItemWeapon.cpp | 5 + .../Weapons/ARWeaponInventoryComponent.cpp | 119 ++-- Source/ActionRPGGame/Public/ARCharacter.h | 106 +--- .../Public/ARCharacterMovementComponent.h | 3 - .../ActionRPGGame/Public/ARPlayerController.h | 8 +- .../Abilities/ARAbilityManagerComponent.h | 54 -- Source/ActionRPGGame/Public/ActionRPGGame.h | 2 + .../Public/UI/HUD/ARHUDPlayerInfo.h | 4 - .../Public/Weapons/ARItemWeapon.h | 8 +- .../Weapons/ARWeaponInventoryComponent.h | 7 +- 84 files changed, 1749 insertions(+), 3921 deletions(-) create mode 100644 Agones/Agones.uplugin create mode 100644 Agones/Resources/Icon128.png create mode 100644 Agones/Source/Agones/Agones.Build.cs create mode 100644 Agones/Source/Agones/Private/Agones.cpp create mode 100644 Agones/Source/Agones/Private/sdk.cc create mode 100644 Agones/Source/Agones/Private/sdk.grpc.pb.cc create mode 100644 Agones/Source/Agones/Private/sdk.pb.cc create mode 100644 Agones/Source/Agones/Public/IAgones.h create mode 100644 Agones/Source/Agones/Public/sdk.grpc.pb.h create mode 100644 Agones/Source/Agones/Public/sdk.h create mode 100644 Agones/Source/Agones/Public/sdk.pb.h delete mode 100644 Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp delete mode 100644 Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h delete mode 100644 Plugins/AbilityManager/AbilityManager.uplugin delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp delete mode 100644 Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp delete mode 100644 Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp delete mode 100644 Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp delete mode 100644 Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h diff --git a/ActionRPGGame.uproject b/ActionRPGGame.uproject index c95d7ce..633f105 100644 --- a/ActionRPGGame.uproject +++ b/ActionRPGGame.uproject @@ -10,8 +10,6 @@ "LoadingPhase": "Default", "AdditionalDependencies": [ "AbilityFramework", - "AbilityFrameworkDebugger", - "AbilityManager", "InventoryFramework", "Engine", "AIModule", @@ -29,8 +27,6 @@ "AdditionalDependencies": [ "AbilityFramework", "AbilityFrameworkEditor", - "AbilityFrameworkDebugger", - "AbilityManager", "InventoryFramework", "Engine", "AIModule", @@ -48,14 +44,6 @@ "Name": "AbilityFramework", "Enabled": true }, - { - "Name": "AbilityFrameworkDebugger", - "Enabled": true - }, - { - "Name": "AbilityManager", - "Enabled": true - }, { "Name": "InventoryFramework", "Enabled": true @@ -260,6 +248,11 @@ { "Name": "AppleVision", "Enabled": false + }, + { + "Name": "RootMotionExtractor", + "Enabled": true, + "MarketplaceURL": "com.epicgames.launcher://ue/marketplace/content/4b450f82f56040338a4d5744b3eda4f9" } ], "TargetPlatforms": [ diff --git a/Agones/Agones.uplugin b/Agones/Agones.uplugin new file mode 100644 index 0000000..ac3651f --- /dev/null +++ b/Agones/Agones.uplugin @@ -0,0 +1,25 @@ +{ + "FileVersion" : 3, + + "FriendlyName" : "Agones Plugin", + "Version" : 1, + "VersionName" : "1.0", + "CreatedBy" : "Epic Games, Inc.", + "CreatedByURL" : "http://epicgames.com", + "Description" : "Integration with Kuberenetes Agones.", + "Category" : "Dedicated Server", + "EnabledByDefault" : false, + + "Modules": [ + { + "Name": "Agones", + "Type": "Runtime" + } + ] + "Plugins": [ + { + "Name": "GRPC", + "Enabled": true + } + ] +} diff --git a/Agones/Resources/Icon128.png b/Agones/Resources/Icon128.png new file mode 100644 index 0000000000000000000000000000000000000000..3033ae0eddc8c201daf7a3ffffe1ff15e776a7f3 GIT binary patch literal 12739 zcmbtaV|OJ?vpunG+qP}nP9{z!wr$%^CbsQlVxHK}6We#*-*7)v?^WNrtM{tfRjZSO{V?;eX#4=)H#E#Am7S?v=0D$L4o|>h)+Bv4c%g&>yTx4LXoP#O`G_k5^Odxs^ zB`paIvTP(t(K?38Ac}+pINn5IBv^cWU@V3TJ$y9m8q^UAq{9~2Mo+2!!-e*;Q`Dlkzq6da36s21R0qpAT$erE_tuTe@9n` zd`kN-Qdv#>o#Z?cL3+>(PEcA}jD*y)GFWuzoFH>@E!-T=?5V32O+iw;XaKy zLq*9)hD4D?VSfeUI~&u~1dCFK&omIw8Z#{m6R;1cScRuJA~FtXbRY^iBE6eH=MPf% z1i^rdOhBWVkZeSPm_}=p#Y1Cdg}sstN`s@ukP}ZvqN|X~C2>fzs79+3Ye*B^3pj)F zMCeO)CGkxFSc5;qd!$%WgPK$Xmf>5)I{$FthDsL0&Hr*`$xgs5%$av?!4-(*EIOU9 zwnExS5EL6{9yr5>VjHnzW*i$9ZRDnhNimyhB&~t39>ZL`9nNN3Mmk3*~JD+mw|hLR*@iY!x*D zjS1N&Qf!2a95qUem8vrlRHm_1eGzq0a`Cq+**Se>4!bliS<2+bFWV+4o>Y2bx{0u( zyrbbGwj;bFl6yVaJX2w((pR+uYSq6svN*@c$LzIPtb|!kuhyu_Q@&KgQ?sn(`x8-R`Nu(BsMKHQ zD+*F)SbkVZtW>42(de*ej2O-gr`eO9#1^4C+%1S>gtBpF-PfJAJM)X6J4T?YvWQ2F zO_oioS@j{+LI~#0lM_NT4GT&C$rw_NACt><@`E{{%`wuY`j zvt(^vEyZegZFdDqMWwUFQFWBNIhrS=^1+#1_q8`>1jh;^P? z&XSZRmSv|)$U|gIlw9x>V}>AO4&K=IMDLNT>ywkgzW3r&UQTn)(AA&K`fJW>>+6WE zf@$^wntUBLm-*odu|1XJ1tGYCG-lh~8h<4*r69}JQ!*wqrX;OeU_*PEN7akT4VK`u zpmV{Y;2}TP4(pDN(KOdU`$YSc(y&9mQP{3n0NKy4AMc+9Kt&)0h$UE5kVudo=*O$K zFG+vA5bvh>bJO~jNNi!J2!=>PaBcAMU@eK&#D9skBrm6#vq`hoh+)e9XRGs2CMPB_ z!~XD8VG&_k;X?6_k=nQmEEyag3tM6?yW;QS>Eb&%mMls<^$fBcw1QQPHvAi0UF=;# zV~iF$(<|C}+A?->_&kiXb)3KL`gT9B9wH9%4&V-buriq@3>>|RW``cbDljVa4tlyiRsf4D&9-eDtIUVm(;`IMLx<_ zMt|HHN>!QIBaa}zox_`tne9$&&nm#%%My~Dl;|W{MWT?>W_e+GV&OhjV;XFW0a~6vh=O;T1`Fe=yRT(E4h`$lmH(C&OHCwKpo+UP!GG?eZyF=Qv{PSob21w0MSrbu~;$x zkojnS5vq%-I)6?7us5hxw0F812U`UDf+9m~19mR25G)F)t0t_{T}mO26ZL)P-FPq{ za3W~L<&GVYIf{E7oxi~Bz7QhtZn($#)a*ko5xEms5-{0_X5VK^=BQv+jNs83pNoChzZSl-XY=B4HN`7^$48E+Q1`J9@~?%E(Z+;kzk z?k`IG#GLZ=@XhMqcevg+Z62d(b!cVR^BUP-xL)vorz|OrcjtCz*LCXKc3yk;w)$AS zoa5zl&2B&Tdfj3Etghtq2yFL0cssm|zC7(>Zu>h^ea%jFuX|8k*Y+s&7(EJKiL8rl zN300xeQ&MZYz5d1coaS?Y)QR9hK0<1Cp{$~i9sY}B}|1QgkR=!3-a(B2swY9e^!Xi z{hFi9$NDb*o~pybWb%JqxdhHGWG)nC+-Icp+xwP%T?|~})NhUrjS==uda|(?K5Bkk z4SH;O5ZsjPA}JmD5(iNKSiLnqsm)h>q~N5a{D6aHK75+7F>LKTtwY-(Nrf_p&f9{Y^~VC7+~K`5}mzYp6U>$MED^X{0`KeyUSvgn+F9t=%Bqg;4I@0eJP*!UU zrj|#@>E6Aw@QF@q6mlxn|H9YleLTB(+;q4ZA6MDenQ_G<5dF;leC&i2ynfXCx~(zC zV)^w8KJI~4Kn6bZg6*~1t4i7|t(%fagp!0{TF6V7`FErpJ{=z-pFKJqvOv3iW`f>TsE@#_pKj?$1ZT z&)-v_fZlRzRpDdy>7uo(f>XYj$gHuW z8CE4t#D1>e&s|IKqs+2Q{9$3LyiwcDU!=T%$x$MCoKjV*UkiVzGws&YtK4woAfI&O zWXt5Yo1DT1?#S~GF?oHw=h^+DmPs4!bM)&%(!l6&yuYE3olz8kn*i>#GIVWJ_eZy# zCXeB+IYSGCjNPBi&iY?!G7|9D&}T**fvHVpBKYGbhbJ>!eHVY}zCE9WZ^}^P=!sEs zt-R5zDO>-EiW0?M%?f=+7B&HeT1_!FRrCrfBERP-sRB_Na2R}H0IYnoh?WOdedh&j z+wW~@OCu%^zYl-^&o#7PtXZ4@#j+Z9_Qr!n1Y5y2pR4y>@wvtA5~s^mOQEkIs-t?h zv*r){W0BJhh3~YrdwnD^uCC{NpIL)Vj~n0maHM2 zY#Hg3GfcN?k#24!|NWjvKsPgw^?7(B^R5->x%XPz%v*g|s$6|XF0jXfXho7>>0ut8 zz(C2QRMj4k8w>P7U3Isp?=+nX_v!X|e?FkSwM+cc?{~X3=-0sO{P|YtOP32uCT7)f z-WJf_`Ghv!J z7}E#rVGC$VgaWQ-T=D+}T%b@;z|jIg;;)L&afN=WZ;r5b?&$af_5kJUBQ65mVi3bh z5CDD{(L@0sg`bEyLVceIX-ijnEcO|#wp4I?vi_Fd_lyKgS|p-MmR!~OrS@o7OQadq z^#GzdrkmOBv!Pv{o8*}5>xt5PROx*a+7Q#3V%=&rhvmu@8}(`p*-_L{)gZ~vV2xVk zoNVLQH%lQk`t)yQnR<)TCC~U~0N{Ug-W|``{Z_2&x}!t}1-fl&44fnP_Q_uyOs&@U zwzpTju#)e261Nb~gNX)NCSLAzT>#sEj^J+m*Lo*Y{>1wViLwF04!Iv)U+j8cqo;1x zTfDYs7F?iTJA&~E6`WQ|r3z=|l? zkd05oNL3N; zrvbgeFiZQMJF%zX_JCtALBG}TR?olnS3rCIO9Cu?-@6J{f=UfeP_QrxH`!LoR__qW z5|I*>3f(7{FL@J-)yvDJlvpC6=LE9h;r7dLmYU11o4dx``qX0Ub-V4xkoLX@piaLR z8yi}R>vO45%h%&BDxfVmsHV|l&iF^Ft^PkBIIBKj1Yre0fh9*eZ3t*$Fb{NDI=PSv zU>A71ZCHK#@@4El4aPHkNmAHs{{{u+M~4-ee53~2G>6y!`yyHl*iq6n(z&z6_jT8qEh(Jko}511Uq|hhyS*j%qYegsPrHWxR~$tDO;&W}?OC^hX*A2U z;-(?3{PMb?S z=8hJ%gSK%MGIUEsdUpyn>)#BG7@-V_j^0g!hR&j*_KV2cF=E0#y8flImQ|Z%d%dIX zuGf`aUnH>0)g^X3&qZ6g!3xzK8Hmen-W{jO>~E#=rF9T~4Cu}cQF|?iJ4zBbB#6Li z$gc0FdYYRpsi$DzzUJjJ9woxk+>1#E6DI8Pl=-wx*84K~;dpo-n;_@29`s!<=E*ze zlub5#jn35O?iXLK-=GA(=R1w}a2ru&V>)GAkl$))DB`$R721Mu`W8) zV?mc%r=}aN92~<}x~)LIY~uYxaNxz^ox4f17&nr4#TlnrbtpI6^nTvOWg# zzcGjwT?N9Z{4o28w;*>Iz>KALoBfa@d1kamKv3-#gX-*SgdVBEc0WLO^?V3+rnzTy z5t`Kt**R4S1>FB5Y*y*tbjPRLTu7R@^{dz7Zksu|+Fb9m<=S+=9(v&CuW#)*^db~p zQVqF;H0n3I9OEkJwf_iDEmBI5SM>GyW$|v?W}d;XbkKQU0S1T<9;|7*Odibd*IP>I zM%Q{>Hj-oRL48;kF#XmjI*BY$oxCXth9&Kf@Kf?ji-?I9s|n9yDVK^5u=KV2^q4O9 zYG5lcVh8fYi*e>0H~DEb-gMdW_&;K|*_)NdrW-nJa^@KrWavL%_`Sf_T=$b=!KZps zziT3GIj668_#LLlIp7PjyD|f__^#3$?qpfNFKV1t5OTD9IZ_mn4nlu#N1IR`J+FW6 z95k-m5Q}1$fip<(wuc$-NcUvFjO?V&Kg}=eAm-ZMt7s0Iz$k zM2*xJpZJl`-@UL59)qR~dvAub&8U^iJ$M%zo0cldkf;;XdQ^&GH$-l z9iL~f;~DA6q}0wkWcP|q3J>?erriumPo2I;GaQdOfR2y1DD>4)>b1kI_UlIvd6xah z_72@1!{u&TaD`;deIdnX!PeC1s44W-oOYeBU0nUgU1(B>0Uxe>!BhwUl9M)b^LJQI zH>=a#hRV}w8nK(lNkjS`x%6*Sk~cJ!C#G1)81b+~G*3?KoDMIw^QSol!hm706t$n8 z#d*gTbX|cEc2=w6n63%s6kf2L_GYhfMo#XA?=j=JR6SZDY z2`XG&W?4=h4;rmYZdFmAff{ljbn)V=a1lK|nu%)_R zU!|B}JjN;39fxMR|_j1ky za%_bWmv(LH|L8{%)NeP|BZ*BbNoi5NgwyqZt_Oh#g3nY1Yd4>|tH@R;jxscp$K8|9 zb)}lrEn}6J`(A{4?$@3VZd^OB=hql{cp?iBXI81`@?3Vb94Qt{T>iD1CF-n!pN$jiBmz9 zro&#>*@-+`wUwb5V*$;Tl0lBbMl%|l?LC+0_bxwAWy8Ka4&rWp+9@|uN|v8Q$<#j^ zzaBaXG7SAksi5X`e;^g4RfQ3)NHg2`WjRv*mD?ruN~x~cvVSG63{;kd)%Q^kipcLQ zXteZX2{I6MzV=OOjs6r>SZvT1O6_KwW$jL~X5iK2yc~1#g?2Er_P#4JkOcnj!80&A zHFa>p5gPwobez-Q4LB_zM5FL?>!^W0eF37OJiob#1Ot|DQn%}~<8{+zx7*jv*UhI% zi%uX6E208ZZlhq+3R!Obe)y{~inLm{OeNFA;=hr8q3(d6S~ax8y5HEAga8es{C4Bc zAElAx2EO{M9&5R4rIWBPY7ry^5@~6;swclYWTDFy(jchF&haPhs6YIPIL>r0?g6*| zN%g%JQRM(TP^GZ;tml`On)mp)+v1XBpKb&{a+U11JD>9Wg`eVXh%;L#j;n62EQWLQ zXlc`AQ)MM^(`aXGvi`0`a(KI*nT4I7C(xyq;6XCUf@{}8SvzHc5DRpe`<*OFO3p38 zce|O++Dgz_w@XyE6Q8zUfVAv^G}o&<$dtPZ-<;MUY}WUfUz{WDe#L$c*D&7dYp*op zqWChEk;j`gdu=`!bY8q)-r#8WI!A~ni4=pGSE~KdTfRi-UqE-orAzx;bF@{nVwD~p zOW^-4H6DTZlU{y_1fy^$k1w-~3fPcy%*{R@bfbGJ==|k(V%ezS{M#Wa*Xr^2{z|rX zCa$Oia~=NdA;xx@xttQ4fcG;j>5%IBmcM;#X~|{m z1Pn_7WQz9nHICnD#`t9T3^X@1x7P{+>l7+zumuxC*h-uPmET~x07IF@QReuDhe8A= za;NzTDOc_L;6_Nbv((Bp)mebfDjQ+dp8N6wj?r)BbTzN_8UN>s9FkDOTDeYd`NA#R z0_|Vd5#x$OSB5%cgVC)2>;7zh{^%@fQ(@^dT(q~)F+dj3!Q0*gXb@Oisoi#czF0o) zdtstniKc)id?-Mhd8h>^DKZTqHT5^6&L`{%#FK^+r=o+L+j*YCBYOXYis19N_Gq&m zjo**73)gP-$uZ&ILF&hv6K6z~{ z@i1pykCNw%X|SJt?C)s>4{YC>G$LWt&gvsDcy%$5tMuMiHqV8oJ)sLLVv#__vMPcR zKi)f|M7>rEbQazn=&L>aIrPiXQmXSjWV+sL_PQm-a6~o`o(Z=pk=eEbFOHY#H7vnD zc~`}0)*Q{vvN%{vqN*4h-%+bx`6vFoMI!w3I039vRz8)+=8|^$yEz*ksx}3>#ZZZ< zh!(@%i~Pp;@JUr74UXZ)ZMccV!S71E^KP8&>_|P9YXl{g2#X{G8o|25MXSs#Ig}P; z+^Tl`h~s*}qFms!Xxu@sD+1SuT~E!iEZA|eAPJG>(R|9#mD|8!H@ z@Q&YO6J$etp&m_vixH4p<7nz>dUQ4qRbEl?qcw-RG(3eEX!d;X3!*icjn3yxuo1ql z=^!^mr5KJZK4DCs+wQIN+5tbnQ4b!Q9wTz8lYnEGpbno8Rf!n8Mfv=_D|CX#wWY9f z|3?dUnNH(B-L(4=Y_;L>KF!>$zF|Agh!){xFPiVsPB(DvaupP*p;g2yeg?9ZH_7

XO}?_ zq1gWxTcKXwdui#Iz=a&pfp;=a624fKynfr9vmV_{|cJYc2 zE59(gbPUR{)Cc6krMPr4EI1{`M1sjC_g{oi1OuOrhFdX0zDI`Z3_T~wgwLhrk&&x7 z$wO`0w1YBkn&qi@@C{T~gBk-Xw#LK(8mDA58ks8NQZ8bwD0Eg**vbz1niEKgut<-J z6BiJQufIj7{QgcSD19!sdl388h(hf?Hs?0>2aKswa2Xgn_WRn)XH9{i%u>FDw*qlpWf**u zd|!N+OVVuA<*kKLr#op#9t6MZ&P7PG#Jo-SpDny9D8a|k;Z-RMkk$P(gA;%&?wSi?+sht6T)vW!_{E6j74Cu zNy2C`-^H9OqQdr#Vw^!piv&a=Eq$N|&9Nau1*u?VW&)5Df=)#(p#Ek4?|rh-J1Bo< zihxAm@KQGoIHESEa&f}IM5_sJEW9YLrzTP{nG!4l4XB$kP$gfy80E_Id`L*eyjOFW zeP#)2KxjD~3XmR}^H9|zYt{!{dcYA7b4HxJERc)@8>IzkMw6V*@Ee{=d_qeLElHT# zJ2PXkeC;%wI+2ytpXZzZn3daZE4eSLTI%>?T)DAT6m7cW@z_}&lZaRiGEK@3jtwb` z?HNa}zz|1<0jB-Ea1&TGs02$mK81ik?qz~f=o1A^YHd)I_g5CK!GNPv7zCZF2s%2{ zDv6u3{Ddod2|$Z~S_tqwj~?ig>|7#QBAJuVNlBEAu&U1lD0G+w;~NTjhyER`z^3K$szLOc zw69kEEMQR*Fv*RFqWBMw06Qr+`3?(Wpr0M{)U=);&>qK;fP3o}f_XegO?OlVbVy~7 zru7F>E%_pPx+u?e(xYhy4ete$meWc$_A?4R8G9d;l~sd2WNw}`SA@$khjQgK-{k$( zDc^2DWU8K+&vkKA_47?6$2QD+U&A=^>uw4Az#0bN7qy)Q>5OwW8}E*42F9)(#cF5}Ot_HT;X_4Fy48nN#~BPL1?nqOUsjXCnU6BwB^MSZA+ z(&>>-U&Vu=yhOSOaLpTwI!r|p7+z?aG^0eflZLP?YyJmLPhmJacRj@cMSJyP?%Ma^}rsR&1o>ZWe;uRr1%UG9YeUYvY#o4pm1}+4VM#rS0PSo zD|;0E`X~vAheFEe`KW6+N*jV^e|n`KsQlZ%ra|5|pViuSx6m0nDdn2^n z^d+(Mp)TB{A)MRH`)FR+4z}9SAR1w5GapsJE6MPrM7DHI1+15|w1^N@~JP*=-9W@5VBD_T+Z%l`&h@>;nH%3 zZL3+%{Ma!pY2%SKa9sk4P#;0IMasHQX9_OXnjCG0A}Ky$n5uNf8#hTKD~04zvv{`M6L|9gC@cr2_40Q=x!PXTpqA%T!k;>msw1f@^63G4b!{Vs}C`<#lqmjPU z53m+0n7RCqQQgGzugTPVixAZqscDD}2`B@Fp_NK23n}!BASNA-8;6htG(>p3Wp`=< zp^1fEE)j4aX9>zvHV4U@>9F9yJtXUKI7!C-21D(Lpog9a^kOBe6aTOc@s~5KYi!*c>L^gP}cNY$qiC#W5eEp z+l~1SQq}fxIcd{cV+Ao83G-L*(Il1p8XEttTO3c?{SlmOCKn>yw9o6%DXyo1DRX02 zwKvFsoiGxgbD38yegOUtarUP~Z%=?8S3n}CbP2pG147$CGriqXdF5auTqw$pSiG5b7QA%*u-!9o{v}H*s@mLr93xOt^yIx(HbWs|&?yCDMdofFl z9@)%!h>L*?CZa`inQ1Ss;kXlgVVw`sLYApK$ zrEqMJ{L0Sr@dIyqyqJ?dwOzq1!&8ydJ$qZiDhZZ?So0kGz!G26)T~LI{2IDvuFqXF ztE6y~BL;=h<_P-Vm&={I$lrr?W`wbw%D0BxwgD0##LDHWdR-l6K-lYLc2@4LpT>B= zrsz6h9gGAF+g~68y)iw6QGt^qxqe3{m_RLr6Dwy6N&$*A|1V#ZS>!7maXyzW$r9}{ zZq6~s(Sv_fUF#dKD6Wm1KryEn#TwHWR9BtOB*b^x>pbZ&fPzU>;t0Z(o(@QCpFK>jwV@8UQywHd##0$ z0Dm?&w1#*O0nixr1_nJZ8em)IXRiCOiQxfNn45PCCLcdfd{=`Va8&&LIUH959S~3# z{N4?d_9c)=_OxCB243aQFIe^ybw>TPAr_H5`+6f45r^4<+T50jrOddvb;l~%^eXh| zJSuLUJ=bzIS;W8yhr=l09+3Dh-?zX~0y0Lm5+;zC03DElq(oG^UT1_C#G_Xna%0;* zpwA)^z>c=`_;g4Hri2mS!;i;hBisb-#yCZZz^S9Uj(LjHSLgmK!1fPN-+=As#IoW) zTaUWgrgEmZB-p>aS%o)D6d0EzW@zm4IjWV4jp`;f*Y~+FQuahtG%P?jL@>#Sz~qBh zkBiUie>Z4RXZM)S?`7>-Hf=9aErI_qna;2Fe{TDQGdt%b3D~3Q$KO~O&0)Mg-Km4O zb-Eq3DSNY2Y(if%=JB5(@-QL4{Voo*hRe6TT~5g9@z^*F>dI}c&U8dUb3B5{$sua( z?GC6@|G6^AQ}9zW%6{sl>EeTrRdz+PM}Bft0B70Utwjx6as0DPUtWy>yF!_wFq(J_ z$6`o57yX8tSoG%bR5KH@TXQ#9JiauL-2jFC-`uMk*;)&-`(Vc7En5u1dW~_+&S_t! zFmi1?SAUflefFUPc3_@C;!@#R(^VITud{tT*T3CAX@=KBLWp=FJe_CXbRpU=)<1iq zlR=G?JKvNATMiG6!BPSTC6Ik%$w7Pivc%pTzk5ih2sRNoYvhJ?2yp3|c?ERxW@8nl zWd9A)=I0Y--;9RS*cp(P+^x9@%{R>!)nmN``RaW{a`eE+Caz2w`4S<@G02cs-y$mP z`-rfm5*pyhK)@FmaAAgee}N(t5_Z-|{mvPD4i=gJJ39t<=Pflf_WO5lTa41tV$BeO z;}yi)z#R*r_g5zTQ14|(k=0-lrIOGu=S`LfD9{9@@z{K%wmRcWdfDiojXkCW3(rf; zNr=4kQZ$+NlX-}vr-4L~O3D!2p2|VqZdZ-V>vuBbyDVC-Z?TXA-V|GA?B7G9i9>vjAQ8z=<|n8KLdDeR^jKL~Q(PK5Ir zn!{g6g(ic_4^N+I<}6=R@^^ojc$v43=3f+ceAZ6%K_?R{g8>sFNg(mx6Kf{i@{HYFDN2%8tQ!fT0e z2Ja5z&4#{PVmypP1&GFdCcRgz5S*lB;+(bX2}f5` zupKPx{$oA@g5F{c4XvBZwyO4Y9sw}&Du)|ToF#!2m=)c_NFK8PbuLYQOL|izao;0N z9P9lbR~0zpK7}}@%zY)NVgb0I&0F$Go?mW4R5<2mOW?j1#Wc9-Y~~?Y5vJ!CncMfv zp@N{M8h$J`8`0gP)frO#DOrZ~31Ywk<{c)AFCD;~hJI?8-dmnwkq90kDGDbmbaMe6 z8CMW3#xxEbb2rivlnN9eaBp~bdH0uOL!lj2R*Ei?U4`+09)m!!3>F#6ZW)ViP0ON4 zNrdzGW+529XXi;OWh&m`Qw%|p$j4+~EzJZnyQVJ6LcN2?x5_oQb|Ro)%6f{n*_TX-uLsuN8mCEyF+bkjL-2 z#)_Ka*Wc3NtKNRC1{kM zPf}JWH7jM+O|fOD3VZdGuKr{~^Viy<>&3oHX4&4Azx|dZ|J+P^(M?}+&4Y*0zb+ds z7GXy)H#IDXOH0U_a8YYy*eF9|fHvpP{j1G39@FUTfzpIo5BN`dw%wF}K(WKsbfyT4 z0<;Go1UUh=7LXL3nzD{9BG1}~aydS}(x%BzY#2R>X|33%d}wO=23meSf-C-8)bh3h z6(B>eJ2FvB2o{zE0Fa%0>4HL!puPpL046XC6B#xJWUNUmaa<)Mre(cnkpor5i>RFkiw@$QK z!8|(~9?1Vd$oTX&rLXQl*aKR$@BmjUkitH#AoGU*PZvn%`}G3?@Q<5sM^ht9{WaitForConnected(gpr_time_add(gpr_now(GPR_CLOCK_REALTIME), gpr_time_from_seconds(30, GPR_TIMESPAN)))) { + return false; + } + + stub = stable::agones::dev::sdk::SDK::NewStub(channel); + + // make the health connection + stable::agones::dev::sdk::Empty response; + health = stub->Health(new grpc::ClientContext(), &response); + + return true; + } + + grpc::Status SDK::Ready() { + grpc::ClientContext *context = new grpc::ClientContext(); + context->set_deadline(gpr_time_add(gpr_now(GPR_CLOCK_REALTIME), gpr_time_from_seconds(30, GPR_TIMESPAN))); + stable::agones::dev::sdk::Empty request; + stable::agones::dev::sdk::Empty response; + + return stub->Ready(context, request, &response); + } + + bool SDK::Health() { + stable::agones::dev::sdk::Empty request; + return health->Write(request); + } + + grpc::Status SDK::Shutdown() { + grpc::ClientContext *context = new grpc::ClientContext(); + context->set_deadline(gpr_time_add(gpr_now(GPR_CLOCK_REALTIME), gpr_time_from_seconds(30, GPR_TIMESPAN))); + stable::agones::dev::sdk::Empty request; + stable::agones::dev::sdk::Empty response; + + return stub->Shutdown(context, request, &response); + } +} \ No newline at end of file diff --git a/Agones/Source/Agones/Private/sdk.grpc.pb.cc b/Agones/Source/Agones/Private/sdk.grpc.pb.cc new file mode 100644 index 0000000..664bf89 --- /dev/null +++ b/Agones/Source/Agones/Private/sdk.grpc.pb.cc @@ -0,0 +1,136 @@ +// Copyright 2018 Google Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +// This code was autogenerated. Do not edit directly. +// Generated by the gRPC C++ plugin. +// If you make any local change, they will be lost. +// source: sdk.proto + +#include "sdk.pb.h" +#include "sdk.grpc.pb.h" + +#include +#include +#include +#include +#include +#include +#include +#include +namespace stable { +namespace agones { +namespace dev { +namespace sdk { + +static const char* SDK_method_names[] = { + "/stable.agones.dev.sdk.SDK/Ready", + "/stable.agones.dev.sdk.SDK/Shutdown", + "/stable.agones.dev.sdk.SDK/Health", +}; + +std::unique_ptr< SDK::Stub> SDK::NewStub(const std::shared_ptr< ::grpc::ChannelInterface>& channel, const ::grpc::StubOptions& options) { + std::unique_ptr< SDK::Stub> stub(new SDK::Stub(channel)); + return stub; +} + +SDK::Stub::Stub(const std::shared_ptr< ::grpc::ChannelInterface>& channel) + : channel_(channel), rpcmethod_Ready_(SDK_method_names[0], ::grpc::internal::RpcMethod::NORMAL_RPC, channel) + , rpcmethod_Shutdown_(SDK_method_names[1], ::grpc::internal::RpcMethod::NORMAL_RPC, channel) + , rpcmethod_Health_(SDK_method_names[2], ::grpc::internal::RpcMethod::CLIENT_STREAMING, channel) + {} + +::grpc::Status SDK::Stub::Ready(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::stable::agones::dev::sdk::Empty* response) { + return ::grpc::internal::BlockingUnaryCall(channel_.get(), rpcmethod_Ready_, context, request, response); +} + +::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* SDK::Stub::AsyncReadyRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return ::grpc::internal::ClientAsyncResponseReaderFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), cq, rpcmethod_Ready_, context, request, true); +} + +::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* SDK::Stub::PrepareAsyncReadyRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return ::grpc::internal::ClientAsyncResponseReaderFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), cq, rpcmethod_Ready_, context, request, false); +} + +::grpc::Status SDK::Stub::Shutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::stable::agones::dev::sdk::Empty* response) { + return ::grpc::internal::BlockingUnaryCall(channel_.get(), rpcmethod_Shutdown_, context, request, response); +} + +::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* SDK::Stub::AsyncShutdownRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return ::grpc::internal::ClientAsyncResponseReaderFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), cq, rpcmethod_Shutdown_, context, request, true); +} + +::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* SDK::Stub::PrepareAsyncShutdownRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return ::grpc::internal::ClientAsyncResponseReaderFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), cq, rpcmethod_Shutdown_, context, request, false); +} + +::grpc::ClientWriter< ::stable::agones::dev::sdk::Empty>* SDK::Stub::HealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response) { + return ::grpc::internal::ClientWriterFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), rpcmethod_Health_, context, response); +} + +::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>* SDK::Stub::AsyncHealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq, void* tag) { + return ::grpc::internal::ClientAsyncWriterFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), cq, rpcmethod_Health_, context, response, true, tag); +} + +::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>* SDK::Stub::PrepareAsyncHealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq) { + return ::grpc::internal::ClientAsyncWriterFactory< ::stable::agones::dev::sdk::Empty>::Create(channel_.get(), cq, rpcmethod_Health_, context, response, false, nullptr); +} + +SDK::Service::Service() { + AddMethod(new ::grpc::internal::RpcServiceMethod( + SDK_method_names[0], + ::grpc::internal::RpcMethod::NORMAL_RPC, + new ::grpc::internal::RpcMethodHandler< SDK::Service, ::stable::agones::dev::sdk::Empty, ::stable::agones::dev::sdk::Empty>( + std::mem_fn(&SDK::Service::Ready), this))); + AddMethod(new ::grpc::internal::RpcServiceMethod( + SDK_method_names[1], + ::grpc::internal::RpcMethod::NORMAL_RPC, + new ::grpc::internal::RpcMethodHandler< SDK::Service, ::stable::agones::dev::sdk::Empty, ::stable::agones::dev::sdk::Empty>( + std::mem_fn(&SDK::Service::Shutdown), this))); + AddMethod(new ::grpc::internal::RpcServiceMethod( + SDK_method_names[2], + ::grpc::internal::RpcMethod::CLIENT_STREAMING, + new ::grpc::internal::ClientStreamingHandler< SDK::Service, ::stable::agones::dev::sdk::Empty, ::stable::agones::dev::sdk::Empty>( + std::mem_fn(&SDK::Service::Health), this))); +} + +SDK::Service::~Service() { +} + +::grpc::Status SDK::Service::Ready(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) { + (void) context; + (void) request; + (void) response; + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); +} + +::grpc::Status SDK::Service::Shutdown(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) { + (void) context; + (void) request; + (void) response; + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); +} + +::grpc::Status SDK::Service::Health(::grpc::ServerContext* context, ::grpc::ServerReader< ::stable::agones::dev::sdk::Empty>* reader, ::stable::agones::dev::sdk::Empty* response) { + (void) context; + (void) reader; + (void) response; + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); +} + + +} // namespace stable +} // namespace agones +} // namespace dev +} // namespace sdk + diff --git a/Agones/Source/Agones/Private/sdk.pb.cc b/Agones/Source/Agones/Private/sdk.pb.cc new file mode 100644 index 0000000..cf68357 --- /dev/null +++ b/Agones/Source/Agones/Private/sdk.pb.cc @@ -0,0 +1,342 @@ +// Copyright 2018 Google Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +// This code was autogenerated. Do not edit directly. +// Generated by the protocol buffer compiler. DO NOT EDIT! +// source: sdk.proto + +#include "sdk.pb.h" + +#include + +#include +#include +#include +#include +#include +#include +#include +#include +#include +// This is a temporary google only hack +#ifdef GOOGLE_PROTOBUF_ENFORCE_UNIQUENESS +#include "third_party/protobuf/version.h" +#endif +// @@protoc_insertion_point(includes) +namespace stable { +namespace agones { +namespace dev { +namespace sdk { +class EmptyDefaultTypeInternal { + public: + ::google::protobuf::internal::ExplicitlyConstructed + _instance; +} _Empty_default_instance_; +} // namespace sdk +} // namespace dev +} // namespace agones +} // namespace stable +namespace protobuf_sdk_2eproto { +void InitDefaultsEmptyImpl() { + GOOGLE_PROTOBUF_VERIFY_VERSION; + +#ifdef GOOGLE_PROTOBUF_ENFORCE_UNIQUENESS + ::google::protobuf::internal::InitProtobufDefaultsForceUnique(); +#else + ::google::protobuf::internal::InitProtobufDefaults(); +#endif // GOOGLE_PROTOBUF_ENFORCE_UNIQUENESS + { + void* ptr = &::stable::agones::dev::sdk::_Empty_default_instance_; + new (ptr) ::stable::agones::dev::sdk::Empty(); + ::google::protobuf::internal::OnShutdownDestroyMessage(ptr); + } + ::stable::agones::dev::sdk::Empty::InitAsDefaultInstance(); +} + +void InitDefaultsEmpty() { + static GOOGLE_PROTOBUF_DECLARE_ONCE(once); + ::google::protobuf::GoogleOnceInit(&once, &InitDefaultsEmptyImpl); +} + +::google::protobuf::Metadata file_level_metadata[1]; + +const ::google::protobuf::uint32 TableStruct::offsets[] GOOGLE_PROTOBUF_ATTRIBUTE_SECTION_VARIABLE(protodesc_cold) = { + ~0u, // no _has_bits_ + GOOGLE_PROTOBUF_GENERATED_MESSAGE_FIELD_OFFSET(::stable::agones::dev::sdk::Empty, _internal_metadata_), + ~0u, // no _extensions_ + ~0u, // no _oneof_case_ + ~0u, // no _weak_field_map_ +}; +static const ::google::protobuf::internal::MigrationSchema schemas[] GOOGLE_PROTOBUF_ATTRIBUTE_SECTION_VARIABLE(protodesc_cold) = { + { 0, -1, sizeof(::stable::agones::dev::sdk::Empty)}, +}; + +static ::google::protobuf::Message const * const file_default_instances[] = { + reinterpret_cast(&::stable::agones::dev::sdk::_Empty_default_instance_), +}; + +void protobuf_AssignDescriptors() { + AddDescriptors(); + ::google::protobuf::MessageFactory* factory = NULL; + AssignDescriptors( + "sdk.proto", schemas, file_default_instances, TableStruct::offsets, factory, + file_level_metadata, NULL, NULL); +} + +void protobuf_AssignDescriptorsOnce() { + static GOOGLE_PROTOBUF_DECLARE_ONCE(once); + ::google::protobuf::GoogleOnceInit(&once, &protobuf_AssignDescriptors); +} + +void protobuf_RegisterTypes(const ::std::string&) GOOGLE_PROTOBUF_ATTRIBUTE_COLD; +void protobuf_RegisterTypes(const ::std::string&) { + protobuf_AssignDescriptorsOnce(); + ::google::protobuf::internal::RegisterAllTypes(file_level_metadata, 1); +} + +void AddDescriptorsImpl() { + InitDefaults(); + static const char descriptor[] GOOGLE_PROTOBUF_ATTRIBUTE_SECTION_VARIABLE(protodesc_cold) = { + "\n\tsdk.proto\022\025stable.agones.dev.sdk\"\007\n\005Em" + "pty2\340\001\n\003SDK\022E\n\005Ready\022\034.stable.agones.dev" + ".sdk.Empty\032\034.stable.agones.dev.sdk.Empty" + "\"\000\022H\n\010Shutdown\022\034.stable.agones.dev.sdk.E" + "mpty\032\034.stable.agones.dev.sdk.Empty\"\000\022H\n\006" + "Health\022\034.stable.agones.dev.sdk.Empty\032\034.s" + "table.agones.dev.sdk.Empty\"\000(\001B\005Z\003sdkb\006p" + "roto3" + }; + ::google::protobuf::DescriptorPool::InternalAddGeneratedFile( + descriptor, 285); + ::google::protobuf::MessageFactory::InternalRegisterGeneratedFile( + "sdk.proto", &protobuf_RegisterTypes); +} + +void AddDescriptors() { + static GOOGLE_PROTOBUF_DECLARE_ONCE(once); + ::google::protobuf::GoogleOnceInit(&once, &AddDescriptorsImpl); +} +// Force AddDescriptors() to be called at dynamic initialization time. +struct StaticDescriptorInitializer { + StaticDescriptorInitializer() { + AddDescriptors(); + } +} static_descriptor_initializer; +} // namespace protobuf_sdk_2eproto +namespace stable { +namespace agones { +namespace dev { +namespace sdk { + +// =================================================================== + +void Empty::InitAsDefaultInstance() { +} +#if !defined(_MSC_VER) || _MSC_VER >= 1900 +#endif // !defined(_MSC_VER) || _MSC_VER >= 1900 + +Empty::Empty() + : ::google::protobuf::Message(), _internal_metadata_(NULL) { + if (GOOGLE_PREDICT_TRUE(this != internal_default_instance())) { + ::protobuf_sdk_2eproto::InitDefaultsEmpty(); + } + SharedCtor(); + // @@protoc_insertion_point(constructor:stable.agones.dev.sdk.Empty) +} +Empty::Empty(const Empty& from) + : ::google::protobuf::Message(), + _internal_metadata_(NULL), + _cached_size_(0) { + _internal_metadata_.MergeFrom(from._internal_metadata_); + // @@protoc_insertion_point(copy_constructor:stable.agones.dev.sdk.Empty) +} + +void Empty::SharedCtor() { + _cached_size_ = 0; +} + +Empty::~Empty() { + // @@protoc_insertion_point(destructor:stable.agones.dev.sdk.Empty) + SharedDtor(); +} + +void Empty::SharedDtor() { +} + +void Empty::SetCachedSize(int size) const { + GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN(); + _cached_size_ = size; + GOOGLE_SAFE_CONCURRENT_WRITES_END(); +} +const ::google::protobuf::Descriptor* Empty::descriptor() { + ::protobuf_sdk_2eproto::protobuf_AssignDescriptorsOnce(); + return ::protobuf_sdk_2eproto::file_level_metadata[kIndexInFileMessages].descriptor; +} + +const Empty& Empty::default_instance() { + ::protobuf_sdk_2eproto::InitDefaultsEmpty(); + return *internal_default_instance(); +} + +Empty* Empty::New(::google::protobuf::Arena* arena) const { + Empty* n = new Empty; + if (arena != NULL) { + arena->Own(n); + } + return n; +} + +void Empty::Clear() { +// @@protoc_insertion_point(message_clear_start:stable.agones.dev.sdk.Empty) + ::google::protobuf::uint32 cached_has_bits = 0; + // Prevent compiler warnings about cached_has_bits being unused + (void) cached_has_bits; + + _internal_metadata_.Clear(); +} + +bool Empty::MergePartialFromCodedStream( + ::google::protobuf::io::CodedInputStream* input) { +#define DO_(EXPRESSION) if (!GOOGLE_PREDICT_TRUE(EXPRESSION)) goto failure + ::google::protobuf::uint32 tag; + // @@protoc_insertion_point(parse_start:stable.agones.dev.sdk.Empty) + for (;;) { + ::std::pair< ::google::protobuf::uint32, bool> p = input->ReadTagWithCutoffNoLastTag(127u); + tag = p.first; + if (!p.second) goto handle_unusual; + handle_unusual: + if (tag == 0) { + goto success; + } + DO_(::google::protobuf::internal::WireFormat::SkipField( + input, tag, _internal_metadata_.mutable_unknown_fields())); + } +success: + // @@protoc_insertion_point(parse_success:stable.agones.dev.sdk.Empty) + return true; +failure: + // @@protoc_insertion_point(parse_failure:stable.agones.dev.sdk.Empty) + return false; +#undef DO_ +} + +void Empty::SerializeWithCachedSizes( + ::google::protobuf::io::CodedOutputStream* output) const { + // @@protoc_insertion_point(serialize_start:stable.agones.dev.sdk.Empty) + ::google::protobuf::uint32 cached_has_bits = 0; + (void) cached_has_bits; + + if ((_internal_metadata_.have_unknown_fields() && ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) { + ::google::protobuf::internal::WireFormat::SerializeUnknownFields( + (::google::protobuf::internal::GetProto3PreserveUnknownsDefault() ? _internal_metadata_.unknown_fields() : _internal_metadata_.default_instance()), output); + } + // @@protoc_insertion_point(serialize_end:stable.agones.dev.sdk.Empty) +} + +::google::protobuf::uint8* Empty::InternalSerializeWithCachedSizesToArray( + bool deterministic, ::google::protobuf::uint8* target) const { + (void)deterministic; // Unused + // @@protoc_insertion_point(serialize_to_array_start:stable.agones.dev.sdk.Empty) + ::google::protobuf::uint32 cached_has_bits = 0; + (void) cached_has_bits; + + if ((_internal_metadata_.have_unknown_fields() && ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) { + target = ::google::protobuf::internal::WireFormat::SerializeUnknownFieldsToArray( + (::google::protobuf::internal::GetProto3PreserveUnknownsDefault() ? _internal_metadata_.unknown_fields() : _internal_metadata_.default_instance()), target); + } + // @@protoc_insertion_point(serialize_to_array_end:stable.agones.dev.sdk.Empty) + return target; +} + +size_t Empty::ByteSizeLong() const { +// @@protoc_insertion_point(message_byte_size_start:stable.agones.dev.sdk.Empty) + size_t total_size = 0; + + if ((_internal_metadata_.have_unknown_fields() && ::google::protobuf::internal::GetProto3PreserveUnknownsDefault())) { + total_size += + ::google::protobuf::internal::WireFormat::ComputeUnknownFieldsSize( + (::google::protobuf::internal::GetProto3PreserveUnknownsDefault() ? _internal_metadata_.unknown_fields() : _internal_metadata_.default_instance())); + } + int cached_size = ::google::protobuf::internal::ToCachedSize(total_size); + GOOGLE_SAFE_CONCURRENT_WRITES_BEGIN(); + _cached_size_ = cached_size; + GOOGLE_SAFE_CONCURRENT_WRITES_END(); + return total_size; +} + +void Empty::MergeFrom(const ::google::protobuf::Message& from) { +// @@protoc_insertion_point(generalized_merge_from_start:stable.agones.dev.sdk.Empty) + GOOGLE_DCHECK_NE(&from, this); + const Empty* source = + ::google::protobuf::internal::DynamicCastToGenerated( + &from); + if (source == NULL) { + // @@protoc_insertion_point(generalized_merge_from_cast_fail:stable.agones.dev.sdk.Empty) + ::google::protobuf::internal::ReflectionOps::Merge(from, this); + } else { + // @@protoc_insertion_point(generalized_merge_from_cast_success:stable.agones.dev.sdk.Empty) + MergeFrom(*source); + } +} + +void Empty::MergeFrom(const Empty& from) { +// @@protoc_insertion_point(class_specific_merge_from_start:stable.agones.dev.sdk.Empty) + GOOGLE_DCHECK_NE(&from, this); + _internal_metadata_.MergeFrom(from._internal_metadata_); + ::google::protobuf::uint32 cached_has_bits = 0; + (void) cached_has_bits; + +} + +void Empty::CopyFrom(const ::google::protobuf::Message& from) { +// @@protoc_insertion_point(generalized_copy_from_start:stable.agones.dev.sdk.Empty) + if (&from == this) return; + Clear(); + MergeFrom(from); +} + +void Empty::CopyFrom(const Empty& from) { +// @@protoc_insertion_point(class_specific_copy_from_start:stable.agones.dev.sdk.Empty) + if (&from == this) return; + Clear(); + MergeFrom(from); +} + +bool Empty::IsInitialized() const { + return true; +} + +void Empty::Swap(Empty* other) { + if (other == this) return; + InternalSwap(other); +} +void Empty::InternalSwap(Empty* other) { + using std::swap; + _internal_metadata_.Swap(&other->_internal_metadata_); + swap(_cached_size_, other->_cached_size_); +} + +::google::protobuf::Metadata Empty::GetMetadata() const { + protobuf_sdk_2eproto::protobuf_AssignDescriptorsOnce(); + return ::protobuf_sdk_2eproto::file_level_metadata[kIndexInFileMessages]; +} + + +// @@protoc_insertion_point(namespace_scope) +} // namespace sdk +} // namespace dev +} // namespace agones +} // namespace stable + +// @@protoc_insertion_point(global_scope) diff --git a/Agones/Source/Agones/Public/IAgones.h b/Agones/Source/Agones/Public/IAgones.h new file mode 100644 index 0000000..f686a8e --- /dev/null +++ b/Agones/Source/Agones/Public/IAgones.h @@ -0,0 +1,38 @@ +// Copyright 1998-2015 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "ModuleManager.h" + + +/** + * The public interface to this module. In most cases, this interface is only public to sibling modules + * within this plugin. + */ +class IAgones : public IModuleInterface +{ + +public: + + /** + * Singleton-like access to this module's interface. This is just for convenience! + * Beware of calling this during the shutdown phase, though. Your module might have been unloaded already. + * + * @return Returns singleton instance, loading the module on demand if needed + */ + static inline IAgones& Get() + { + return FModuleManager::LoadModuleChecked< IAgones >( "Agones" ); + } + + /** + * Checks to see if this module is loaded and ready. It is only valid to call Get() if IsAvailable() returns true. + * + * @return True if the module is loaded and ready to use + */ + static inline bool IsAvailable() + { + return FModuleManager::Get().IsModuleLoaded( "Agones" ); + } +}; + diff --git a/Agones/Source/Agones/Public/sdk.grpc.pb.h b/Agones/Source/Agones/Public/sdk.grpc.pb.h new file mode 100644 index 0000000..0706399 --- /dev/null +++ b/Agones/Source/Agones/Public/sdk.grpc.pb.h @@ -0,0 +1,307 @@ +// Generated by the gRPC C++ plugin. +// If you make any local change, they will be lost. +// source: sdk.proto +// Original file comments: +// Copyright 2017 Google Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +// +#ifndef GRPC_sdk_2eproto__INCLUDED +#define GRPC_sdk_2eproto__INCLUDED +#define GPR_FORBID_UNREACHABLE_CODE 1 +#define GOOGLE_PROTOBUF_NO_RTTI 1 +#include "sdk.pb.h" + +#include +#include +#include +#include +#include +#include +#include +#include +#include + +namespace grpc { +class CompletionQueue; +class Channel; +class ServerCompletionQueue; +class ServerContext; +} // namespace grpc + +namespace stable { +namespace agones { +namespace dev { +namespace sdk { + +// SDK service to be used in the GameServer SDK to the Pod Sidecar +class SDK final { + public: + static constexpr char const* service_full_name() { + return "stable.agones.dev.sdk.SDK"; + } + class StubInterface { + public: + virtual ~StubInterface() {} + // Call when the GameServer is ready + virtual ::grpc::Status Ready(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::stable::agones::dev::sdk::Empty* response) = 0; + std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>> AsyncReady(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>>(AsyncReadyRaw(context, request, cq)); + } + std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>> PrepareAsyncReady(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>>(PrepareAsyncReadyRaw(context, request, cq)); + } + // Call when the GmaeServer is shutting down + virtual ::grpc::Status Shutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::stable::agones::dev::sdk::Empty* response) = 0; + std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>> AsyncShutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>>(AsyncShutdownRaw(context, request, cq)); + } + std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>> PrepareAsyncShutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>>(PrepareAsyncShutdownRaw(context, request, cq)); + } + // Send a Empty every d Duration to declare that this GameSever is healthy + std::unique_ptr< ::grpc::ClientWriterInterface< ::stable::agones::dev::sdk::Empty>> Health(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response) { + return std::unique_ptr< ::grpc::ClientWriterInterface< ::stable::agones::dev::sdk::Empty>>(HealthRaw(context, response)); + } + std::unique_ptr< ::grpc::ClientAsyncWriterInterface< ::stable::agones::dev::sdk::Empty>> AsyncHealth(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq, void* tag) { + return std::unique_ptr< ::grpc::ClientAsyncWriterInterface< ::stable::agones::dev::sdk::Empty>>(AsyncHealthRaw(context, response, cq, tag)); + } + std::unique_ptr< ::grpc::ClientAsyncWriterInterface< ::stable::agones::dev::sdk::Empty>> PrepareAsyncHealth(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncWriterInterface< ::stable::agones::dev::sdk::Empty>>(PrepareAsyncHealthRaw(context, response, cq)); + } + private: + virtual ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>* AsyncReadyRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) = 0; + virtual ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>* PrepareAsyncReadyRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) = 0; + virtual ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>* AsyncShutdownRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) = 0; + virtual ::grpc::ClientAsyncResponseReaderInterface< ::stable::agones::dev::sdk::Empty>* PrepareAsyncShutdownRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) = 0; + virtual ::grpc::ClientWriterInterface< ::stable::agones::dev::sdk::Empty>* HealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response) = 0; + virtual ::grpc::ClientAsyncWriterInterface< ::stable::agones::dev::sdk::Empty>* AsyncHealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq, void* tag) = 0; + virtual ::grpc::ClientAsyncWriterInterface< ::stable::agones::dev::sdk::Empty>* PrepareAsyncHealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq) = 0; + }; + class Stub final : public StubInterface { + public: + Stub(const std::shared_ptr< ::grpc::ChannelInterface>& channel); + ::grpc::Status Ready(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::stable::agones::dev::sdk::Empty* response) override; + std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>> AsyncReady(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>>(AsyncReadyRaw(context, request, cq)); + } + std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>> PrepareAsyncReady(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>>(PrepareAsyncReadyRaw(context, request, cq)); + } + ::grpc::Status Shutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::stable::agones::dev::sdk::Empty* response) override; + std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>> AsyncShutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>>(AsyncShutdownRaw(context, request, cq)); + } + std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>> PrepareAsyncShutdown(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>>(PrepareAsyncShutdownRaw(context, request, cq)); + } + std::unique_ptr< ::grpc::ClientWriter< ::stable::agones::dev::sdk::Empty>> Health(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response) { + return std::unique_ptr< ::grpc::ClientWriter< ::stable::agones::dev::sdk::Empty>>(HealthRaw(context, response)); + } + std::unique_ptr< ::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>> AsyncHealth(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq, void* tag) { + return std::unique_ptr< ::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>>(AsyncHealthRaw(context, response, cq, tag)); + } + std::unique_ptr< ::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>> PrepareAsyncHealth(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq) { + return std::unique_ptr< ::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>>(PrepareAsyncHealthRaw(context, response, cq)); + } + + private: + std::shared_ptr< ::grpc::ChannelInterface> channel_; + ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* AsyncReadyRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) override; + ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* PrepareAsyncReadyRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) override; + ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* AsyncShutdownRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) override; + ::grpc::ClientAsyncResponseReader< ::stable::agones::dev::sdk::Empty>* PrepareAsyncShutdownRaw(::grpc::ClientContext* context, const ::stable::agones::dev::sdk::Empty& request, ::grpc::CompletionQueue* cq) override; + ::grpc::ClientWriter< ::stable::agones::dev::sdk::Empty>* HealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response) override; + ::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>* AsyncHealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq, void* tag) override; + ::grpc::ClientAsyncWriter< ::stable::agones::dev::sdk::Empty>* PrepareAsyncHealthRaw(::grpc::ClientContext* context, ::stable::agones::dev::sdk::Empty* response, ::grpc::CompletionQueue* cq) override; + const ::grpc::internal::RpcMethod rpcmethod_Ready_; + const ::grpc::internal::RpcMethod rpcmethod_Shutdown_; + const ::grpc::internal::RpcMethod rpcmethod_Health_; + }; + static std::unique_ptr NewStub(const std::shared_ptr< ::grpc::ChannelInterface>& channel, const ::grpc::StubOptions& options = ::grpc::StubOptions()); + + class Service : public ::grpc::Service { + public: + Service(); + virtual ~Service(); + // Call when the GameServer is ready + virtual ::grpc::Status Ready(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response); + // Call when the GmaeServer is shutting down + virtual ::grpc::Status Shutdown(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response); + // Send a Empty every d Duration to declare that this GameSever is healthy + virtual ::grpc::Status Health(::grpc::ServerContext* context, ::grpc::ServerReader< ::stable::agones::dev::sdk::Empty>* reader, ::stable::agones::dev::sdk::Empty* response); + }; + template + class WithAsyncMethod_Ready : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithAsyncMethod_Ready() { + ::grpc::Service::MarkMethodAsync(0); + } + ~WithAsyncMethod_Ready() override { + BaseClassMustBeDerivedFromService(this); + } + // disable synchronous version of this method + ::grpc::Status Ready(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + void RequestReady(::grpc::ServerContext* context, ::stable::agones::dev::sdk::Empty* request, ::grpc::ServerAsyncResponseWriter< ::stable::agones::dev::sdk::Empty>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) { + ::grpc::Service::RequestAsyncUnary(0, context, request, response, new_call_cq, notification_cq, tag); + } + }; + template + class WithAsyncMethod_Shutdown : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithAsyncMethod_Shutdown() { + ::grpc::Service::MarkMethodAsync(1); + } + ~WithAsyncMethod_Shutdown() override { + BaseClassMustBeDerivedFromService(this); + } + // disable synchronous version of this method + ::grpc::Status Shutdown(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + void RequestShutdown(::grpc::ServerContext* context, ::stable::agones::dev::sdk::Empty* request, ::grpc::ServerAsyncResponseWriter< ::stable::agones::dev::sdk::Empty>* response, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) { + ::grpc::Service::RequestAsyncUnary(1, context, request, response, new_call_cq, notification_cq, tag); + } + }; + template + class WithAsyncMethod_Health : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithAsyncMethod_Health() { + ::grpc::Service::MarkMethodAsync(2); + } + ~WithAsyncMethod_Health() override { + BaseClassMustBeDerivedFromService(this); + } + // disable synchronous version of this method + ::grpc::Status Health(::grpc::ServerContext* context, ::grpc::ServerReader< ::stable::agones::dev::sdk::Empty>* reader, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + void RequestHealth(::grpc::ServerContext* context, ::grpc::ServerAsyncReader< ::stable::agones::dev::sdk::Empty, ::stable::agones::dev::sdk::Empty>* reader, ::grpc::CompletionQueue* new_call_cq, ::grpc::ServerCompletionQueue* notification_cq, void *tag) { + ::grpc::Service::RequestAsyncClientStreaming(2, context, reader, new_call_cq, notification_cq, tag); + } + }; + typedef WithAsyncMethod_Ready > > AsyncService; + template + class WithGenericMethod_Ready : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithGenericMethod_Ready() { + ::grpc::Service::MarkMethodGeneric(0); + } + ~WithGenericMethod_Ready() override { + BaseClassMustBeDerivedFromService(this); + } + // disable synchronous version of this method + ::grpc::Status Ready(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + }; + template + class WithGenericMethod_Shutdown : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithGenericMethod_Shutdown() { + ::grpc::Service::MarkMethodGeneric(1); + } + ~WithGenericMethod_Shutdown() override { + BaseClassMustBeDerivedFromService(this); + } + // disable synchronous version of this method + ::grpc::Status Shutdown(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + }; + template + class WithGenericMethod_Health : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithGenericMethod_Health() { + ::grpc::Service::MarkMethodGeneric(2); + } + ~WithGenericMethod_Health() override { + BaseClassMustBeDerivedFromService(this); + } + // disable synchronous version of this method + ::grpc::Status Health(::grpc::ServerContext* context, ::grpc::ServerReader< ::stable::agones::dev::sdk::Empty>* reader, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + }; + template + class WithStreamedUnaryMethod_Ready : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithStreamedUnaryMethod_Ready() { + ::grpc::Service::MarkMethodStreamed(0, + new ::grpc::internal::StreamedUnaryHandler< ::stable::agones::dev::sdk::Empty, ::stable::agones::dev::sdk::Empty>(std::bind(&WithStreamedUnaryMethod_Ready::StreamedReady, this, std::placeholders::_1, std::placeholders::_2))); + } + ~WithStreamedUnaryMethod_Ready() override { + BaseClassMustBeDerivedFromService(this); + } + // disable regular version of this method + ::grpc::Status Ready(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + // replace default version of method with streamed unary + virtual ::grpc::Status StreamedReady(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::stable::agones::dev::sdk::Empty,::stable::agones::dev::sdk::Empty>* server_unary_streamer) = 0; + }; + template + class WithStreamedUnaryMethod_Shutdown : public BaseClass { + private: + void BaseClassMustBeDerivedFromService(const Service *service) {} + public: + WithStreamedUnaryMethod_Shutdown() { + ::grpc::Service::MarkMethodStreamed(1, + new ::grpc::internal::StreamedUnaryHandler< ::stable::agones::dev::sdk::Empty, ::stable::agones::dev::sdk::Empty>(std::bind(&WithStreamedUnaryMethod_Shutdown::StreamedShutdown, this, std::placeholders::_1, std::placeholders::_2))); + } + ~WithStreamedUnaryMethod_Shutdown() override { + BaseClassMustBeDerivedFromService(this); + } + // disable regular version of this method + ::grpc::Status Shutdown(::grpc::ServerContext* context, const ::stable::agones::dev::sdk::Empty* request, ::stable::agones::dev::sdk::Empty* response) final override { + abort(); + return ::grpc::Status(::grpc::StatusCode::UNIMPLEMENTED, ""); + } + // replace default version of method with streamed unary + virtual ::grpc::Status StreamedShutdown(::grpc::ServerContext* context, ::grpc::ServerUnaryStreamer< ::stable::agones::dev::sdk::Empty,::stable::agones::dev::sdk::Empty>* server_unary_streamer) = 0; + }; + typedef WithStreamedUnaryMethod_Ready > StreamedUnaryService; + typedef Service SplitStreamedService; + typedef WithStreamedUnaryMethod_Ready > StreamedService; +}; + +} // namespace sdk +} // namespace dev +} // namespace agones +} // namespace stable + + +#endif // GRPC_sdk_2eproto__INCLUDED diff --git a/Agones/Source/Agones/Public/sdk.h b/Agones/Source/Agones/Public/sdk.h new file mode 100644 index 0000000..313120b --- /dev/null +++ b/Agones/Source/Agones/Public/sdk.h @@ -0,0 +1,50 @@ +// Copyright 2017 Google Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. +#define GPR_FORBID_UNREACHABLE_CODE 1 +#define GOOGLE_PROTOBUF_NO_RTTI 1 +#include +#include "sdk.grpc.pb.h" + +namespace agones { + + // The Agones SDK + class SDK { + public: + // Creates a new instance of the SDK. + // Does not connect to anything. + SDK(); + + // Must be called before any other functions on the SDK. + // This will attempt to do a handshake with the sdk server, timing out + // after 30 seconds. + // Returns true if the connection was successful, false if not. + bool Connect(); + + // Marks the Game Server as ready to receive connections + grpc::Status Ready(); + + // Send Health ping. This is a synchronous request. + bool Health(); + + // Marks the Game Server as ready to shutdown + grpc::Status Shutdown(); + + ~SDK(); + + private: + std::shared_ptr channel; + std::unique_ptr stub; + std::unique_ptr< ::grpc::ClientWriter< ::stable::agones::dev::sdk::Empty>> health; + }; +} diff --git a/Agones/Source/Agones/Public/sdk.pb.h b/Agones/Source/Agones/Public/sdk.pb.h new file mode 100644 index 0000000..812f0cd --- /dev/null +++ b/Agones/Source/Agones/Public/sdk.pb.h @@ -0,0 +1,202 @@ +// Copyright 2018 Google Inc. All Rights Reserved. +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +// This code was autogenerated. Do not edit directly. +// Generated by the protocol buffer compiler. DO NOT EDIT! +// source: sdk.proto + +#ifndef PROTOBUF_sdk_2eproto__INCLUDED +#define PROTOBUF_sdk_2eproto__INCLUDED + +#include + +#include + +#define GPR_FORBID_UNREACHABLE_CODE 1 +#define GOOGLE_PROTOBUF_NO_RTTI 1 + + +#if GOOGLE_PROTOBUF_VERSION < 3005000 +#error This file was generated by a newer version of protoc which is +#error incompatible with your Protocol Buffer headers. Please update +#error your headers. +#endif +#if 3005000 < GOOGLE_PROTOBUF_MIN_PROTOC_VERSION +#error This file was generated by an older version of protoc which is +#error incompatible with your Protocol Buffer headers. Please +#error regenerate this file with a newer version of protoc. +#endif + +#include +#include +#include +#include +#include +#include +#include +#include // IWYU pragma: export +#include // IWYU pragma: export +#include +// @@protoc_insertion_point(includes) + +namespace protobuf_sdk_2eproto { +// Internal implementation detail -- do not use these members. +struct TableStruct { + static const ::google::protobuf::internal::ParseTableField entries[]; + static const ::google::protobuf::internal::AuxillaryParseTableField aux[]; + static const ::google::protobuf::internal::ParseTable schema[1]; + static const ::google::protobuf::internal::FieldMetadata field_metadata[]; + static const ::google::protobuf::internal::SerializationTable serialization_table[]; + static const ::google::protobuf::uint32 offsets[]; +}; +void AddDescriptors(); +void InitDefaultsEmptyImpl(); +void InitDefaultsEmpty(); +inline void InitDefaults() { + InitDefaultsEmpty(); +} +} // namespace protobuf_sdk_2eproto +namespace stable { +namespace agones { +namespace dev { +namespace sdk { +class Empty; +class EmptyDefaultTypeInternal; +extern EmptyDefaultTypeInternal _Empty_default_instance_; +} // namespace sdk +} // namespace dev +} // namespace agones +} // namespace stable +namespace stable { +namespace agones { +namespace dev { +namespace sdk { + +// =================================================================== + +class Empty : public ::google::protobuf::Message /* @@protoc_insertion_point(class_definition:stable.agones.dev.sdk.Empty) */ { + public: + Empty(); + virtual ~Empty(); + + Empty(const Empty& from); + + inline Empty& operator=(const Empty& from) { + CopyFrom(from); + return *this; + } + #if LANG_CXX11 + Empty(Empty&& from) noexcept + : Empty() { + *this = ::std::move(from); + } + + inline Empty& operator=(Empty&& from) noexcept { + if (GetArenaNoVirtual() == from.GetArenaNoVirtual()) { + if (this != &from) InternalSwap(&from); + } else { + CopyFrom(from); + } + return *this; + } + #endif + static const ::google::protobuf::Descriptor* descriptor(); + static const Empty& default_instance(); + + static void InitAsDefaultInstance(); // FOR INTERNAL USE ONLY + static inline const Empty* internal_default_instance() { + return reinterpret_cast( + &_Empty_default_instance_); + } + static PROTOBUF_CONSTEXPR int const kIndexInFileMessages = + 0; + + void Swap(Empty* other); + friend void swap(Empty& a, Empty& b) { + a.Swap(&b); + } + + // implements Message ---------------------------------------------- + + inline Empty* New() const PROTOBUF_FINAL { return New(NULL); } + + Empty* New(::google::protobuf::Arena* arena) const PROTOBUF_FINAL; + void CopyFrom(const ::google::protobuf::Message& from) PROTOBUF_FINAL; + void MergeFrom(const ::google::protobuf::Message& from) PROTOBUF_FINAL; + void CopyFrom(const Empty& from); + void MergeFrom(const Empty& from); + void Clear() PROTOBUF_FINAL; + bool IsInitialized() const PROTOBUF_FINAL; + + size_t ByteSizeLong() const PROTOBUF_FINAL; + bool MergePartialFromCodedStream( + ::google::protobuf::io::CodedInputStream* input) PROTOBUF_FINAL; + void SerializeWithCachedSizes( + ::google::protobuf::io::CodedOutputStream* output) const PROTOBUF_FINAL; + ::google::protobuf::uint8* InternalSerializeWithCachedSizesToArray( + bool deterministic, ::google::protobuf::uint8* target) const PROTOBUF_FINAL; + int GetCachedSize() const PROTOBUF_FINAL { return _cached_size_; } + private: + void SharedCtor(); + void SharedDtor(); + void SetCachedSize(int size) const PROTOBUF_FINAL; + void InternalSwap(Empty* other); + private: + inline ::google::protobuf::Arena* GetArenaNoVirtual() const { + return NULL; + } + inline void* MaybeArenaPtr() const { + return NULL; + } + public: + + ::google::protobuf::Metadata GetMetadata() const PROTOBUF_FINAL; + + // nested types ---------------------------------------------------- + + // accessors ------------------------------------------------------- + + // @@protoc_insertion_point(class_scope:stable.agones.dev.sdk.Empty) + private: + + ::google::protobuf::internal::InternalMetadataWithArena _internal_metadata_; + mutable int _cached_size_; + friend struct ::protobuf_sdk_2eproto::TableStruct; + friend void ::protobuf_sdk_2eproto::InitDefaultsEmptyImpl(); +}; +// =================================================================== + + +// =================================================================== + +#ifdef __GNUC__ + #pragma GCC diagnostic push + #pragma GCC diagnostic ignored "-Wstrict-aliasing" +#endif // __GNUC__ +// Empty + +#ifdef __GNUC__ + #pragma GCC diagnostic pop +#endif // __GNUC__ + +// @@protoc_insertion_point(namespace_scope) + +} // namespace sdk +} // namespace dev +} // namespace agones +} // namespace stable + +// @@protoc_insertion_point(global_scope) + +#endif // PROTOBUF_sdk_2eproto__INCLUDED diff --git a/Config/DefaultEngine.ini b/Config/DefaultEngine.ini index 376bd43..dc8bea1 100644 --- a/Config/DefaultEngine.ini +++ b/Config/DefaultEngine.ini @@ -140,6 +140,22 @@ GlyphTextureSize=x4096 +CollisionChannelRedirects=(OldName="VehicleMovement",NewName="Vehicle") +CollisionChannelRedirects=(OldName="PawnMovement",NewName="Pawn") +[/Script/WindowsTargetPlatform.WindowsTargetSettings] +Compiler=Default +-TargetedRHIs=PCD3D_SM5 +-TargetedRHIs=PCD3D_SM4 ++TargetedRHIs=PCD3D_SM5 +MinimumOSVersion=MSOS_Vista +AudioDevice= +AudioSampleRate=48000 +AudioCallbackBufferFrameSize=1024 +AudioNumBuffersToEnqueue=1 +AudioMaxChannels=0 +AudioNumSourceWorkers=4 +SpatializationPlugin= +ReverbPlugin= +OcclusionPlugin= + [/Script/Engine.PhysicsSettings] DefaultGravityZ=-980.000000 DefaultTerminalVelocity=4000.000000 diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index 7c6d19a..c341163 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -5,11 +5,6 @@ ProjectName=Third Person Game Template [/Script/AbilityFramework.AFCueManager] DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet -[/Script/UnrealEd.ProjectPackagingSettings] -IncludeAppLocalPrerequisites=True -ApplocalPrerequisitesDirectory=(Path="$(EngineDir)/Binaries/ThirdParty/AppLocalDependencies") -bGenerateChunks=True - [/Script/Engine.AssetManagerSettings] -PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps"))) -PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game"))) @@ -23,4 +18,39 @@ bShouldGuessTypeAndNameInEditor=True bShouldAcquireMissingChunksOnLoad=False MetaDataTagsForAssetRegistry=() +[/Script/UnrealEd.ProjectPackagingSettings] +Build=IfProjectHasCode +BuildConfiguration=PPBC_Development +StagingDirectory=(Path="D:/Unreal/UE-Master/ActionRPGGame/Saved/StagedBuilds") +FullRebuild=False +ForDistribution=False +IncludeDebugFiles=False +BlueprintNativizationMethod=Disabled +bIncludeNativizedAssetsInProjectGeneration=False +bExcludeMonolithicEngineHeadersInNativizedCode=False +UsePakFile=True +bGenerateChunks=True +bGenerateNoChunks=False +bChunkHardReferencesOnly=False +bBuildHttpChunkInstallData=False +HttpChunkInstallDataDirectory=(Path="") +HttpChunkInstallDataVersion= +IncludePrerequisites=True +IncludeAppLocalPrerequisites=True +bShareMaterialShaderCode=False +bSharedMaterialNativeLibraries=False +ApplocalPrerequisitesDirectory=(Path="$(EngineDir)/Binaries/ThirdParty/AppLocalDependencies") +IncludeCrashReporter=False +InternationalizationPreset=English +-CulturesToStage=en ++CulturesToStage=en +bCookAll=False +bCookMapsOnly=False +bCompressed=False +bEncryptIniFiles=False +bEncryptPakIndex=False +bSkipEditorContent=False +bSkipMovies=False +bNativizeBlueprintAssets=False +bNativizeOnlySelectedBlueprints=False diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index a4810aa..0635653 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -37,17 +37,18 @@ bDefaultViewportMouseLock=False bAlwaysShowTouchInterface=False bShowConsoleOnFourFingerTap=True bEnableGestureRecognizer=False +bUseAutocorrect=False DefaultViewportMouseCaptureMode=CapturePermanently_IncludingInitialMouseDown DefaultViewportMouseLockMode=LockOnCapture FOVScale=0.011110 DoubleClickTime=0.200000 +ActionMappings=(ActionName="Jump",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=SpaceBar) +ActionMappings=(ActionName="Jump",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Gamepad_FaceButton_Bottom) -+ActionMappings=(ActionName="Input.Gun.Shoot",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=LeftMouseButton) -+ActionMappings=(ActionName="Input.Gun.Reload",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=R) ++ActionMappings=(ActionName="Shoot",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=LeftMouseButton) ++ActionMappings=(ActionName="Reload",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=R) +ActionMappings=(ActionName="SwitchAbilitySet",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=B) +ActionMappings=(ActionName="InputAbilityManager",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=K) -+ActionMappings=(ActionName="Input.UI.WeaponNext",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollUp) ++ActionMappings=(ActionName="NextWeapon",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollUp) +ActionMappings=(ActionName="Input.UI.WeaponPrevious",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollDown) +ActionMappings=(ActionName="InputInventory",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=I) +ActionMappings=(ActionName="Input.UI.Holster",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=O) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp index 6fa8fc5..efa7956 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -204,7 +204,7 @@ bool UAFAbilityComponent::ReplicateSubobjects(class UActorChannel *Channel, clas { WroteSomething |= Channel->ReplicateSubobject(const_cast(DefaultAttributes), *Bunch, *RepFlags); } - for (const FAFAbilityItem& Ability : AbilityContainer.AbilitiesItems) + for (const FAFAbilitySpec& Ability : AbilityContainer.ActivatableAbilities) { //if (Set.InputOverride) // WroteSomething |= Channel->ReplicateSubobject(const_cast(Set.InputOverride), *Bunch, *RepFlags); @@ -274,193 +274,106 @@ void UAFAbilityComponent::UninitializeComponent() //EffectTimerManager.Reset(); //GameEffectContainer } -void UAFAbilityComponent::BindInputs(class UInputComponent* InputComponent) +void UAFAbilityComponent::BindInputs(class UInputComponent* InputComponent, FString BindEnum) { - for (const FGameplayTag& Tag : AbilityInputs) - { - BindAbilityToAction(InputComponent, Tag); - } -} -void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) -{ - AbilityContainer.SetBlockedInput(InActionName, bBlock); -} -void UAFAbilityComponent::BP_BindAbilityToAction(FGameplayTag ActionName) -{ - UInputComponent* InputComponent = GetOwner()->FindComponentByClass(); - check(InputComponent); - - BindAbilityToAction(InputComponent, ActionName); -} -void UAFAbilityComponent::BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName) -{ - check(InputComponent); - - if (!InputComponent) + UEnum* bindEnum = FindObject(ANY_PACKAGE, *BindEnum); + if (!bindEnum) return; + int32 num = bindEnum->NumEnums(); + + for (uint8 Idx = 0; Idx < num; Idx++) { - FInputActionBinding AB(ActionName.GetTagName(), IE_Pressed); - AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputPressed, ActionName); - InputComponent->AddActionBinding(AB); - } - - // Released event - { - FInputActionBinding AB(ActionName.GetTagName(), IE_Released); - AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputReleased, ActionName); - InputComponent->AddActionBinding(AB); - } - SetBlockedInput(ActionName, false); -} -void UAFAbilityComponent::SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag - , const FAFOnAbilityReady& InputDelegate) -{ - AbilityContainer.SetAbilityToAction(InAbilityPtr, InInputTag); - ENetRole role = GetOwnerRole(); + FString Name = bindEnum->GetNameStringByIndex(Idx); + { + FInputActionBinding AB(FName(*Name), IE_Pressed); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputPressed, Idx); + InputComponent->AddActionBinding(AB); + } - if (GetOwner()->GetNetMode() == ENetMode::NM_Client - && role == ENetRole::ROLE_AutonomousProxy) - { - if (InputDelegate.IsBound()) + // Released event { - AddOnAbilityInputReadyDelegate(InAbilityPtr, InputDelegate); + FInputActionBinding AB(FName(*Name), IE_Released); + AB.ActionDelegate.GetDelegateForManualSet().BindUObject(this, &UAFAbilityComponent::NativeInputReleased, Idx); + InputComponent->AddActionBinding(AB); } - ServerSetAbilityToAction(InAbilityPtr, InInputTag); } } -TSoftClassPtr UAFAbilityComponent::IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) +void UAFAbilityComponent::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) { - for (const FGameplayTag& Tag : InInputTag) - { - return AbilityContainer.IsAbilityBoundToAction(Tag); - break; - } - return TSoftClassPtr(); } -void UAFAbilityComponent::ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) -{ - if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - SetAbilityToAction(InAbilityPtr, InInputTag, FAFOnAbilityReady()); - } -} -bool UAFAbilityComponent::ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) -{ - return true; -} -void UAFAbilityComponent::RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr) -{ - AbilityContainer.RemoveAbilityFromAction(InAbilityPtr); - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerRemoveAbilitiesFromActions(InAbilityPtr.ToSoftObjectPath()); - } -} -void UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr) -{ - AbilityContainer.RemoveAbilityFromAction(TSoftClassPtr(InAbilityPtr)); -} -bool UAFAbilityComponent::ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr) -{ - return true; -} -void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr) + + +TSoftClassPtr UAFAbilityComponent::IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag) { - NotifyOnAbilityInputReady(InAbilityPtr); - UGAAbilityBase* Ability = AbilityContainer.TagToAbility.FindRef(InAbilityPtr); - if (Ability) - { - Ability->OnAbilityInputReady(); - } + return TSoftClassPtr(); } -void UAFAbilityComponent::SetAbilitiesToActions(const TArray& InAbilitiesActions - , const TArray& InputDelegate) + +void UAFAbilityComponent::BindAbilityToInputIDs(const FAFAbilitySpecHandle Handle, TArray InputIDs) { - for (const FAFAbilityActionSet& Set : InAbilitiesActions) - { - AbilityContainer.SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs); - } + AbilityContainer.BindAbilityToInputIDs(Handle, InputIDs); ENetRole role = GetOwnerRole(); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client && role == ENetRole::ROLE_AutonomousProxy) { - for (int32 Idx = 0; Idx < InAbilitiesActions.Num(); Idx++) + /*for (int32 Idx = 0; Idx < InAbilitiesActions.Num(); Idx++) { if (InputDelegate[Idx].IsBound()) { AddOnAbilityInputReadyDelegate(InAbilitiesActions[Idx].AbilityTag, InputDelegate[Idx]); } - } - - ServerSetAbilitiesToActions(InAbilitiesActions); + }*/ + + ServerBindAbilityToInputIDs(Handle, InputIDs); } } -void UAFAbilityComponent::ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions) +void UAFAbilityComponent::ServerBindAbilityToInputIDs_Implementation(const FAFAbilitySpecHandle Handle, const TArray& InputIDs) { - if (GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - for (const FAFAbilityActionSet& Set : InAbilitiesActions) - { - SetAbilityToAction(Set.AbilityTag, Set.AbilityInputs, FAFOnAbilityReady()); - } - } + AbilityContainer.BindAbilityToInputIDs(Handle, InputIDs); } -bool UAFAbilityComponent::ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions) +bool UAFAbilityComponent::ServerBindAbilityToInputIDs_Validate(const FAFAbilitySpecHandle Handle, const TArray& InputIDs) { return true; } -void UAFAbilityComponent::BP_InputPressed(FGameplayTag ActionName) -{ - NativeInputPressed(ActionName); -} -void UAFAbilityComponent::NativeInputPressed(FGameplayTag ActionName) +void UAFAbilityComponent::NativeInputPressed(uint8 InputID) { FAFPredictionHandle PredHandle; if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { PredHandle = FAFPredictionHandle::GenerateClientHandle(this); - AbilityContainer.HandleInputPressed(ActionName, PredHandle); + AbilityContainer.HandleInputPressed(InputID, PredHandle); } - ServerNativeInputPressed(ActionName, PredHandle); - + ServerNativeInputPressed(InputID, PredHandle); } -void UAFAbilityComponent::ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) +void UAFAbilityComponent::ServerNativeInputPressed_Implementation(uint8 InputID, FAFPredictionHandle InPredictionHandle) { - AbilityContainer.HandleInputPressed(ActionName, InPredictionHandle); - //NativeInputPressed(ActionName); + AbilityContainer.HandleInputPressed(InputID, InPredictionHandle); } -bool UAFAbilityComponent::ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle) +bool UAFAbilityComponent::ServerNativeInputPressed_Validate(uint8 InputID, FAFPredictionHandle InPredictionHandle) { return true; } -void UAFAbilityComponent::BP_InputReleased(FGameplayTag ActionName) -{ - NativeInputReleased(ActionName); -} - -void UAFAbilityComponent::NativeInputReleased(FGameplayTag ActionName) +void UAFAbilityComponent::NativeInputReleased(uint8 InputID) { if (GetOwner()->GetNetMode() == ENetMode::NM_Client) { - AbilityContainer.HandleInputReleased(ActionName); + AbilityContainer.HandleInputReleased(InputID); } - ServerNativeInputReleased(ActionName); + ServerNativeInputReleased(InputID); } -void UAFAbilityComponent::ServerNativeInputReleased_Implementation(FGameplayTag ActionName) +void UAFAbilityComponent::ServerNativeInputReleased_Implementation(uint8 InputID) { - AbilityContainer.HandleInputReleased(ActionName); + AbilityContainer.HandleInputReleased(InputID); } -bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag ActionName) +bool UAFAbilityComponent::ServerNativeInputReleased_Validate(uint8 InputID) { return true; } @@ -468,79 +381,57 @@ bool UAFAbilityComponent::ServerNativeInputReleased_Validate(FGameplayTag Action void UAFAbilityComponent::BP_AddAbility(TSoftClassPtr InAbility, TArray InInputTag) { - NativeAddAbility(InAbility, InInputTag); } -void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbility, - const TArray& InInputTag) +void UAFAbilityComponent::NativeAddAbility(TSoftClassPtr InAbility, const FAFAbilitySpecHandle ClientHandle) { - //FGameplayTag AlreadyBound = IsAbilityBoundToAction(InAbilityTag, InInputTag); if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeAddAbility(InAbility.ToSoftObjectPath(), InInputTag); - /*if (AlreadyBound.IsValid()) - { - for (const FGameplayTag& Input : InInputTag) - { - AbilityContainer.RemoveAbilityFromAction(AlreadyBound); - } - }*/ - } - else - { - /*if (AlreadyBound.IsValid()) - { - AbilityContainer.RemoveAbilityFromAction(AlreadyBound); - }*/ - if (UAssetManager* Manager = UAssetManager::GetIfValid()) - { - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - FStreamableManager& StreamManager = UAssetManager::GetStreamableManager(); - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, InAbility); - - StreamManager.RequestAsyncLoad(InAbility.ToSoftObjectPath() - , del); - } - } + ServerNativeAddAbility(InAbility.ToSoftObjectPath(), ClientHandle); } } -void UAFAbilityComponent::NativeAddAbilityFromObject(UGAAbilityBase* InAbility, TSoftClassPtr AbilityPtr) +void UAFAbilityComponent::NativeAddAbilityFromObject(UGAAbilityBase* InAbility, const FAFAbilitySpecHandle ClientHandle) { - AbilityContainer.AddAbilityFromObject(InAbility, AbilityPtr); + } -void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, - const TArray& InInputTag) +void UAFAbilityComponent::ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, const FAFAbilitySpecHandle& ClientHandle) { - NativeAddAbility(TSoftClassPtr(InAbility), InInputTag); + FAFAbilitySpecHandle ServerHandle = FAFAbilitySpecHandle::GenerateHandle(); + + if (UAssetManager* Manager = UAssetManager::GetIfValid()) + { + FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); + IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); + FStreamableManager& StreamManager = UAssetManager::GetStreamableManager(); + { + TSoftClassPtr Ab(InAbility); + FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFAbilityComponent::OnFinishedLoad, Ab, ServerHandle, ClientHandle); + + StreamManager.RequestAsyncLoad(InAbility + , del); + } + } } -bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, - const TArray& InInputTag) +bool UAFAbilityComponent::ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, const FAFAbilitySpecHandle& ClientHandle) { return true; } -void UAFAbilityComponent::OnFinishedLoad(TSoftClassPtr InAbility) +void UAFAbilityComponent::OnFinishedLoad(TSoftClassPtr InAbility, const FAFAbilitySpecHandle Handle, const FAFAbilitySpecHandle ClientHandle) { - if (AbilityContainer.AbilityExists(InAbility)) - { - return; - } if (GetOwnerRole() < ENetRole::ROLE_Authority) { return; } - - FStreamableManager& Manager = UAssetManager::GetStreamableManager(); TSubclassOf cls = InAbility.Get(); if (cls) { - InstanceAbility(cls, InAbility); + UGAAbilityBase* ability = AbilityContainer.AddAbility(cls, Handle, ClientHandle); + AbilityContainer.MarkArrayDirty(); } { @@ -552,41 +443,30 @@ void UAFAbilityComponent::BP_RemoveAbility(TSoftClassPtr TagIn) { } -void UAFAbilityComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag) +void UAFAbilityComponent::NativeRemoveAbility(const FAFAbilitySpecHandle InHandle) { if (GetOwnerRole() < ENetRole::ROLE_Authority) { - ServerNativeRemoveAbility(InAbilityTag.ToSoftObjectPath()); + ServerNativeRemoveAbility(InHandle); } - AbilityContainer.RemoveAbility(InAbilityTag); + AbilityContainer.RemoveAbility(InHandle); } -void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag) +void UAFAbilityComponent::ServerNativeRemoveAbility_Implementation(const FAFAbilitySpecHandle& InHandle) { - AbilityContainer.RemoveAbility(TSoftClassPtr(InAbilityTag)); + AbilityContainer.RemoveAbility(InHandle); } -bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag) +bool UAFAbilityComponent::ServerNativeRemoveAbility_Validate(const FAFAbilitySpecHandle& InHandle) { return true; } -UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByTag(TSoftClassPtr TagIn) +UGAAbilityBase* UAFAbilityComponent::BP_GetAbilityByHandle(FAFAbilitySpecHandle TagIn) { - UGAAbilityBase* retVal = AbilityContainer.GetAbility(TagIn); - return retVal; -} -UGAAbilityBase* UAFAbilityComponent::InstanceAbility(TSubclassOf AbilityClass - , TSoftClassPtr InClassPtr) -{ - if (AbilityClass) - { - UGAAbilityBase* ability = AbilityContainer.AddAbility(AbilityClass, InClassPtr); - AbilityContainer.MarkArrayDirty(); - return ability; - } - return nullptr; + return AbilityContainer.GetAbility(TagIn); } + void UAFAbilityComponent::OnRep_InstancedAbilities() { } @@ -640,4 +520,8 @@ void UAFAbilityComponent::PlayMontage(UAnimMontage* MontageIn, FName SectionName void UAFAbilityComponent::MulticastPlayMontage_Implementation(UAnimMontage* MontageIn, FName SectionName, float Speed = 1) { +} +void UAFAbilityComponent::ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr) +{ + } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp index 740f0da..f6673d5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityTypes.cpp @@ -5,20 +5,18 @@ #include "Abilities/GAAbilityBase.h" #include "AFAbilityTypes.h" -void FAFAbilityItem::PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer) +void FAFAbilitySpec::PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer) { if (InArraySerializer.AbilitiesComp.IsValid()) { FAFAbilityContainer& InArraySerializerC = const_cast(InArraySerializer); + InArraySerializerC.SpecMap.Remove(Handle); //remove attributes //UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = nullptr; - InArraySerializerC.AbilityToAction.Remove(AbilityClass); - InArraySerializerC.AbilitiesInputs.Remove(AbilityClass); - InArraySerializerC.TagToAbility.Remove(AbilityClass); } } -void FAFAbilityItem::PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer) +void FAFAbilitySpec::PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer) { if (InArraySerializer.AbilitiesComp.IsValid()) { @@ -38,35 +36,21 @@ void FAFAbilityItem::PostReplicatedAdd(const struct FAFAbilityContainer& InArray //TODO - CHANGE ATTRIBUTE HANDLING UGAAttributesBase* attr = InArraySerializer.AbilitiesComp->RepAttributes.AttributeMap.FindRef(Ability->AbilityTag); Ability->Attributes = attr; - - InArraySerializerC.AbilitiesInputs.Add(AbilityClass, Ability); //.Add(Ability->AbilityTag, Ability); - InArraySerializerC.TagToAbility.Add(AbilityClass, Ability); - InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(AbilityClass); + InArraySerializerC.SpecMap.Add(Handle, *this); + InArraySerializerC.AbilitiesComp->NotifyOnAbilityReady(*this, Handle, ClientHandle); } } -void FAFAbilityItem::PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer) +void FAFAbilitySpec::PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer) { } - -void FAFAbilityContainer::SetBlockedInput(const FGameplayTag& InActionName, bool bBlock) -{ - if (BlockedInput.Contains(InActionName)) - { - BlockedInput[InActionName] = bBlock; - } - else - { - BlockedInput.Add(InActionName, bBlock); - } -} UGAAbilityBase* FAFAbilityContainer::AddAbility(TSubclassOf AbilityIn - , TSoftClassPtr InClassPtr) + , const FAFAbilitySpecHandle Handle, const FAFAbilitySpecHandle ClientHandle) { + ENetMode NetMode = AbilitiesComp->GetNetMode(); if (AbilityIn && AbilitiesComp.IsValid()) { - UGAAbilityBase* ability = NewObject(AbilitiesComp->GetOwner(), AbilityIn); ability->AbilityComponent = AbilitiesComp.Get(); if (AbilitiesComp.IsValid()) @@ -78,71 +62,45 @@ UGAAbilityBase* FAFAbilityContainer::AddAbility(TSubclassOfInitAbility(); FGameplayTag Tag = ability->AbilityTag; - - AbilitiesInputs.Add(InClassPtr, ability); - FAFAbilityItem AbilityItem(ability, InClassPtr); - MarkItemDirty(AbilityItem); - AbilityItem.Ability = ability; - AbilitiesItems.Add(AbilityItem); - TagToAbility.Add(InClassPtr, ability); + FAFAbilitySpec Spec; + Spec.Ability = ability; + Spec.Handle = Handle; + Spec.ClientHandle = ClientHandle; + MarkItemDirty(Spec); + ActivatableAbilities.Add(Spec); + SpecMap.Add(Handle, Spec); MarkArrayDirty(); if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) { - AbilitiesComp->NotifyOnAbilityReady(InClassPtr); + //AbilitiesComp->NotifyOnAbilityReady(InClassPtr); } - /* if (ActionName.IsValid()) - { - UInputComponent* InputComponent = AbilitiesComp->GetOwner()->FindComponentByClass(); - AbilitiesComp->BindAbilityToAction(InputComponent, ActionName, Tag); - }*/ + return ability; } return nullptr; } -void FAFAbilityContainer::AddAbilityFromObject(class UGAAbilityBase* AbilityIn, TSoftClassPtr InClassPtr) +void FAFAbilityContainer::RemoveAbility(const FAFAbilitySpecHandle AbilityIn) { - if (AbilityIn && AbilitiesComp.IsValid()) + auto pred = [AbilityIn](const FAFAbilitySpec& Item) -> bool { - - UGAAbilityBase* ability = AbilityIn;// NewObject(AbilitiesComp->GetOwner(), AbilityIn); - ability->AbilityComponent = AbilitiesComp.Get(); - if (AbilitiesComp.IsValid()) + if (Item.Handle == AbilityIn) { - APawn* POwner = Cast(AbilitiesComp->GetOwner()); - ability->POwner = POwner; - ability->PCOwner = Cast(POwner->Controller); - ability->OwnerCamera = nullptr; + return true; } - ability->InitAbility(); - FGameplayTag Tag = ability->AbilityTag; - - AbilitiesInputs.Add(InClassPtr, ability); - FAFAbilityItem AbilityItem(ability, InClassPtr); - MarkItemDirty(AbilityItem); - AbilityItem.Ability = ability; - AbilitiesItems.Add(AbilityItem); - TagToAbility.Add(InClassPtr, ability); - - MarkArrayDirty(); - if (AbilitiesComp->GetNetMode() == ENetMode::NM_Standalone - || AbilitiesComp->GetOwnerRole() == ENetRole::ROLE_Authority) + else { - AbilitiesComp->NotifyOnAbilityReady(InClassPtr); + return false; } - } -} - -void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& AbilityIn) -{ - int32 Index = AbilitiesItems.IndexOfByKey(AbilityIn); + }; + int32 Index = ActivatableAbilities.IndexOfByPredicate(pred); if (Index == INDEX_NONE) return; - UGAAbilityBase* Ability = TagToAbility.FindRef(AbilityIn); + UGAAbilityBase* Ability = SpecMap.FindRef(AbilityIn).Ability; for (auto It = Ability->AbilityTasks.CreateIterator(); It; ++It) @@ -151,110 +109,47 @@ void FAFAbilityContainer::RemoveAbility(const TSoftClassPtr& Abi } Ability->AbilityTasks.Reset(); - AbilityToAction.Remove(AbilityIn); - AbilitiesInputs.Remove(AbilityIn); - TagToAbility.Remove(AbilityIn); - MarkItemDirty(AbilitiesItems[Index]); - AbilitiesItems.RemoveAt(Index); + SpecMap.Remove(AbilityIn); + MarkItemDirty(ActivatableAbilities[Index]); + ActivatableAbilities.RemoveAt(Index); MarkArrayDirty(); } -TSoftClassPtr FAFAbilityContainer::IsAbilityBoundToAction(const FGameplayTag& InInputTag) -{ - TSoftClassPtr Ability; - TSoftClassPtr* AbilityTag = ActionToAbility.Find(InInputTag); - if (AbilityTag) - { - Ability = *AbilityTag; - } - - return Ability; -} - -void FAFAbilityContainer::SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag) -{ - for (const FGameplayTag& InputTag : InInputTag) - { - TSoftClassPtr& AbilityClassPtr = ActionToAbility.FindOrAdd(InputTag); - AbilityClassPtr = InAbiltyPtr; - TArray& ActionTag = AbilityToAction.FindOrAdd(InAbiltyPtr); - ActionTag.Add(InputTag); - } - if (!AbilitiesComp.IsValid()) - return; - UGAAbilityBase* Ability = TagToAbility.FindRef(InAbiltyPtr); - if (Ability) - { - Ability->OnAbilityInputReady(); - } - if (AbilitiesComp->GetOwner()->GetNetMode() == ENetMode::NM_DedicatedServer) - { - AbilitiesComp->ClientNotifyAbilityInputReady(InAbiltyPtr); - } -} -void FAFAbilityContainer::RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr) +UGAAbilityBase* FAFAbilityContainer::GetAbility(FAFAbilitySpecHandle InAbiltyPtr) { - TArray* Inputs = AbilityToAction.Find(InAbiltyPtr); - - if (Inputs) - { - for (const FGameplayTag& Input : *Inputs) - { - ActionToAbility.Remove(Input); - } - - AbilityToAction.Remove(InAbiltyPtr); - } -} -UGAAbilityBase* FAFAbilityContainer::GetAbility(TSoftClassPtr InAbiltyPtr) -{ - UGAAbilityBase* retAbility = AbilitiesInputs.FindRef(InAbiltyPtr); + UGAAbilityBase* retAbility = SpecMap.FindRef(InAbiltyPtr).Ability; return retAbility; } -void FAFAbilityContainer::HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) + +void FAFAbilityContainer::HandleInputPressed(const uint8 InputID, const FAFPredictionHandle& InPredictionHandle) { - if (BlockedInput.FindRef(ActionName)) - { - return; - } - TSoftClassPtr AbiltyPtr = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(AbiltyPtr); - if (ability) - { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - ability->OnNativeInputPressed(ActionName, InPredictionHandle); - } + FAFAbilitySpec Spec = InputToAbilitySpec.FindRef(InputID); + + + ENetMode NetMode = AbilitiesComp->GetNetMode(); + if(Spec.Ability) + Spec.Ability->OnNativeInputPressed(InputID, InPredictionHandle); } -void FAFAbilityContainer::HandleInputReleased(FGameplayTag ActionName) +void FAFAbilityContainer::HandleInputReleased(const uint8 InputID) { - if (BlockedInput.FindRef(ActionName)) - { - return; - } - TSoftClassPtr abilityTag = ActionToAbility.FindRef(ActionName); - UGAAbilityBase* ability = AbilitiesInputs.FindRef(abilityTag); - if (ability) - { - ability->OnNativeInputReleased(ActionName); - } + FAFAbilitySpec Spec = InputToAbilitySpec.FindRef(InputID); + + ENetMode NetMode = AbilitiesComp->GetNetMode(); + if(Spec.Ability) + Spec.Ability->OnNativeInputReleased(InputID); } -void FAFAbilityContainer::TriggerAbylityByTag(TSoftClassPtr InTag) +void FAFAbilityContainer::BindAbilityToInputIDs(const FAFAbilitySpecHandle Handle, TArray InputIDs) { - UGAAbilityBase* ability = AbilitiesInputs.FindRef(InTag); - if (ability) + ENetMode NetMode = AbilitiesComp->GetNetMode(); + + FAFAbilitySpec Spec = SpecMap[Handle]; + + for (uint8 ID : InputIDs) { - if (ability->IsWaitingForConfirm()) - { - ability->ConfirmAbility(); - return; - } - FAFPredictionHandle PredHandle = FAFPredictionHandle::GenerateClientHandle(AbilitiesComp.Get()); - ability->OnNativeInputPressed(FGameplayTag(), PredHandle); + FAFAbilitySpec& Ref = InputToAbilitySpec.FindOrAdd(ID); + Ref = Spec; } -} \ No newline at end of file + Spec.Ability->OnAbilityInputReady(); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp index 96bb5a8..6c0bc22 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFBlueprintFunctionLibrary.cpp @@ -24,7 +24,7 @@ void UAFBlueprintFunctionLibrary::TriggerAbilityPressedByTag(UObject* Target, return; } - Comp->NativeInputPressed(ActionTag); + //Comp->NativeInputPressed(ActionTag); } void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, const FGameplayTag& AbilityTag, FGameplayTag ActionTag) @@ -42,5 +42,5 @@ void UAFBlueprintFunctionLibrary::TriggerAbilityReleasedByTag(UObject* Target, return; } - Comp->NativeInputReleased(ActionTag); + //Comp->NativeInputReleased(ActionTag); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp index 47da901..fbc008a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp @@ -205,21 +205,21 @@ void UGAAbilityBase::OnAbilityInited() { } -void UGAAbilityBase::OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle) +void UGAAbilityBase::OnNativeInputPressed(uint8 InputID, const FAFPredictionHandle& InPredictionHandle) { { - UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); + //UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputPressed in ability %s"), *GetName()); PredictionHandle = InPredictionHandle; - OnInputPressed(ActionName); + OnInputPressed(InputID); OnInputPressedDelegate.Broadcast(); } } -void UGAAbilityBase::OnNativeInputReleased(FGameplayTag ActionName) +void UGAAbilityBase::OnNativeInputReleased(uint8 InputID) { { UE_LOG(AbilityFramework, Log, TEXT("OnNativeInputReleased in ability %s"), *GetName()); - OnInputReleased(ActionName); + OnInputReleased(InputID); OnInputReleasedDelegate.Broadcast(); } } @@ -731,11 +731,11 @@ bool UGAAbilityBase::CallRemoteFunction(UFunction* Function, void* Parameters, F void UGAAbilityBase::ExecuteAbilityInputPressedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) { - AbilityComponent->NativeInputPressed(ActionName); + //AbilityComponent->NativeInputPressed(ActionName); } void UGAAbilityBase::ExecuteAbilityInputReleasedFromTag(FGameplayTag AbilityTagIn, FGameplayTag ActionName) { - AbilityComponent->NativeInputReleased(ActionName); + //AbilityComponent->NativeInputReleased(ActionName); } bool UGAAbilityBase::HaveGameplayTag(AActor* Target, const FGameplayTag& Tag) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp index 97a3787..f62f9c2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -40,10 +40,8 @@ void FAFAttributeBase::InitializeAttribute(UAFAbilityComponent* InComponent, con Modifiers.Empty(); Modifiers.AddDefaulted(7);// static_cast(EGAAttributeMod::Invalid)); //Modifiers.AddDefaulted(static_cast(EGAAttributeMod::Invalid)); - if (ExtensionClass) - { - ExtensionClass.GetDefaultObject()->Initialize(InComponent, InAttributeName); - } + AbilityComp = InComponent; + SelfName = FGAAttribute(InAttributeName); } void FAFAttributeBase::CopyFromOther(FAFAttributeBase* Other) { @@ -165,7 +163,7 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& //FString name = GetTypeName(); if (ExtensionClass) { - ExtensionClass.GetDefaultObject()->OnPreAttributeModify(CurrentValue); + ExtensionClass.GetDefaultObject()->OnPreAttributeModify(AbilityComp, SelfName, CurrentValue); FGAEffectContext* Context = InContext.GetPtr(); if (InContext.IsValid()) { @@ -232,7 +230,7 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& } if (ExtensionClass) { - ExtensionClass.GetDefaultObject()->OnPostAttributeModify(returnValue); + ExtensionClass.GetDefaultObject()->OnPostAttributeModify(AbilityComp, SelfName, returnValue); if (InContext.IsValid()) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp index 6066955..f81bd71 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeExtension.cpp @@ -4,20 +4,11 @@ #include "../AFAbilityComponent.h" #include "GAAttributeExtension.h" - - - -void UGAAttributeExtension::Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName) -{ - AbilityComponent = InAbilityComponent; - Attribute = FGAAttribute(InAttributeName); -} - -void UGAAttributeExtension::OnPreAttributeModify(float InValue) +void UGAAttributeExtension::OnPreAttributeModify(class UAFAbilityComponent* InComp, const FGAAttribute& Attribute, float InValue) { - AbilityComponent->NotifyOnPreAttributeModified(Attribute); + InComp->NotifyOnPreAttributeModified(Attribute); } -void UGAAttributeExtension::OnPostAttributeModify(float InValue) +void UGAAttributeExtension::OnPostAttributeModify(class UAFAbilityComponent* InComp, const FGAAttribute& Attribute, float InValue) { - AbilityComponent->NotifyOnPostAttributeModified(Attribute); + InComp->NotifyOnPostAttributeModified(Attribute); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h index 5053109..ffe2bde 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -29,7 +29,7 @@ DECLARE_MULTICAST_DELEGATE_OneParam(FGAGenericEffectDelegate, FGAEffectHandle); DECLARE_MULTICAST_DELEGATE_OneParam(FAFAttributeChangedDelegate, FAFAttributeChangedData); -DECLARE_DELEGATE(FAFOnAbilityReady); +DECLARE_DELEGATE_ThreeParams(FAFOnAbilityReady, FAFAbilitySpec, FAFAbilitySpecHandle, FAFAbilitySpecHandle); DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAFOnAbilityAdded, const FGameplayTag&, AbilityTag); DECLARE_DELEGATE(FAFGenericAttributeDelegate); @@ -386,20 +386,20 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public bool bIsAnyAbilityActive; //AbilityTag, Delegate - TMap, FAFOnAbilityReady> OnAbilityReadyMap; + TMap OnAbilityReadyMap; - void AddOnAbilityReadyDelegate(const TSoftClassPtr& InAbilityPtr, FAFOnAbilityReady& InDelegate) + void AddOnAbilityReadyDelegate(const FAFAbilitySpecHandle InAbilityPtr, FAFOnAbilityReady& InDelegate) { if(InDelegate.IsBound()) OnAbilityReadyMap.Add(InAbilityPtr, InDelegate); } - void NotifyOnAbilityReady(const TSoftClassPtr& InAbilityPtr) + void NotifyOnAbilityReady(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) { - if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(InAbilityPtr)) + if (FAFOnAbilityReady* Ready = OnAbilityReadyMap.Find(ClientHandle)) { - Ready->ExecuteIfBound(); - OnAbilityReadyMap.Remove(InAbilityPtr); + Ready->ExecuteIfBound(Spec, ServerHandle, ClientHandle); + OnAbilityReadyMap.Remove(ClientHandle); } } @@ -411,11 +411,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public OnAbilityInputReadyMap.Add(InAbilityPtr, InDelegate); } - void NotifyOnAbilityInputReady(const TSoftClassPtr& InAbilityPtr) + void NotifyOnAbilityInputReady(const TSoftClassPtr& InAbilityPtr, FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) { if (FAFOnAbilityReady* Ready = OnAbilityInputReadyMap.Find(InAbilityPtr)) { - Ready->ExecuteIfBound(); + Ready->ExecuteIfBound(Spec, ServerHandle, ClientHandle); OnAbilityInputReadyMap.Remove(InAbilityPtr); } } @@ -499,22 +499,11 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - void BindInputs(class UInputComponent* InputComponent); - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Bind Ability To Action"), Category = "AbilityFramework|Abilities") - void BP_BindAbilityToAction(FGameplayTag ActionName); - void BindAbilityToAction(UInputComponent* InputComponent, FGameplayTag ActionName); - - //need to be called on both client and server. - //Change InInputTag To Array, clear previous binds on the same tag. - void SetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag, const FAFOnAbilityReady& InputDelegate); + void BindInputs(class UInputComponent* InputComponent, FString BindEnum); + TSoftClassPtr IsAbilityBoundToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); -protected: - UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilityToAction(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); - void ServerSetAbilityToAction_Implementation(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); - bool ServerSetAbilityToAction_Validate(const TSoftClassPtr& InAbilityPtr, const TArray& InInputTag); public: /* Called when ability action has been binded on server. */ UFUNCTION(Client, Reliable) @@ -522,39 +511,28 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void ClientNotifyAbilityInputReady_Implementation(const TSoftClassPtr& InAbilityPtr); - void SetAbilitiesToActions(const TArray& InAbilitiesActions, const TArray& InputDelegate); - UFUNCTION(Server, Reliable, WithValidation) - void ServerSetAbilitiesToActions(const TArray& InAbilitiesActions); - void ServerSetAbilitiesToActions_Implementation(const TArray& InAbilitiesActions); - bool ServerSetAbilitiesToActions_Validate(const TArray& InAbilitiesActions); - void RemoveAbilitiesFromActions(const TSoftClassPtr& InAbilityPtr); + void BindAbilityToInputIDs(const FAFAbilitySpecHandle Handle, TArray InputIDs); UFUNCTION(Server, Reliable, WithValidation) - void ServerRemoveAbilitiesFromActions(const FSoftObjectPath& InAbilityPtr); - void ServerRemoveAbilitiesFromActions_Implementation(const FSoftObjectPath& InAbilityPtr); - bool ServerRemoveAbilitiesFromActions_Validate(const FSoftObjectPath& InAbilityPtr); - - UFUNCTION(BlueprintCallable, meta=(DisplayName="Input Pressed"), Category = "AbilityFramework|Abilities") - void BP_InputPressed(FGameplayTag ActionName); + void ServerBindAbilityToInputIDs(const FAFAbilitySpecHandle Handle, const TArray& InputIDs); + void ServerBindAbilityToInputIDs_Implementation(const FAFAbilitySpecHandle Handle, const TArray& InputIDs); + bool ServerBindAbilityToInputIDs_Validate(const FAFAbilitySpecHandle Handle, const TArray& InputIDs); - void NativeInputPressed(FGameplayTag ActionName); + void NativeInputPressed(uint8 InputID); protected: UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputPressed(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - virtual void ServerNativeInputPressed_Implementation(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); - virtual bool ServerNativeInputPressed_Validate(FGameplayTag ActionName, FAFPredictionHandle InPredictionHandle); + void ServerNativeInputPressed(uint8 InputID, FAFPredictionHandle InPredictionHandle); + virtual void ServerNativeInputPressed_Implementation(uint8 InputID, FAFPredictionHandle InPredictionHandle); + virtual bool ServerNativeInputPressed_Validate(uint8 InputID, FAFPredictionHandle InPredictionHandle); public: - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Input Released"), Category = "AbilityFramework|Abilities") - void BP_InputReleased(FGameplayTag ActionName); - - void NativeInputReleased(FGameplayTag ActionName); + void NativeInputReleased(uint8 InputID); protected: UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeInputReleased(FGameplayTag ActionName); - virtual void ServerNativeInputReleased_Implementation(FGameplayTag ActionName); - virtual bool ServerNativeInputReleased_Validate(FGameplayTag ActionName); + void ServerNativeInputReleased(uint8 InputID); + virtual void ServerNativeInputReleased_Implementation(uint8 InputID); + virtual bool ServerNativeInputReleased_Validate(uint8 InputID); public: /* Finds ability using asset registry and then gives it to component. @@ -567,43 +545,44 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void BP_AddAbility(TSoftClassPtr InAbility, TArray InInputTag); - void NativeAddAbility(TSoftClassPtr InAbility, - const TArray& InInputTag); + /* + Adds new ability to this AbilityComponent. + Client handle is used to trigger ability related events on client which requested this function. + Please note that to find ability by handle you must refer to it trough server generated ability handle. + Which can be received by registering delegate trough: + @AddOnAbilityReadyDelegate + */ + void NativeAddAbility(TSoftClassPtr InAbility, const FAFAbilitySpecHandle ClientHandle); /* Adds ability using existing instance of object. Should only be called on authority or in standalone. */ - void NativeAddAbilityFromObject(UGAAbilityBase* InAbility, TSoftClassPtr AbilityPtr); + void NativeAddAbilityFromObject(UGAAbilityBase* InAbility, const FAFAbilitySpecHandle ClientHandle); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeAddAbility(const FSoftObjectPath& InAbility, - const TArray& InInputTag); - - void ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, - const TArray& InInputTag); - - bool ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, - const TArray& InInputTag); + void ServerNativeAddAbility(const FSoftObjectPath& InAbility, const FAFAbilitySpecHandle& ClientHandle); + void ServerNativeAddAbility_Implementation(const FSoftObjectPath& InAbility, const FAFAbilitySpecHandle& ClientHandle); + bool ServerNativeAddAbility_Validate(const FSoftObjectPath& InAbility, const FAFAbilitySpecHandle& ClientHandle); - void OnFinishedLoad(TSoftClassPtr InAbility); + void OnFinishedLoad(TSoftClassPtr InAbility, const FAFAbilitySpecHandle Handle, const FAFAbilitySpecHandle ClientHandle); UFUNCTION(BlueprintCallable, meta = (DisplayName = "Remove Ability"), Category = "AbilityFramework|Abilities") void BP_RemoveAbility(TSoftClassPtr TagIn); - void NativeRemoveAbility(TSoftClassPtr InAbilityTag); + void NativeRemoveAbility(const FAFAbilitySpecHandle InHandle); UFUNCTION(Server, Reliable, WithValidation) - void ServerNativeRemoveAbility(const FSoftObjectPath& InAbilityTag); + void ServerNativeRemoveAbility(const FAFAbilitySpecHandle& InHandle); - void ServerNativeRemoveAbility_Implementation(const FSoftObjectPath& InAbilityTag); + void ServerNativeRemoveAbility_Implementation(const FAFAbilitySpecHandle& InHandle); - bool ServerNativeRemoveAbility_Validate(const FSoftObjectPath& InAbilityTag); + bool ServerNativeRemoveAbility_Validate(const FAFAbilitySpecHandle& InHandle); //TODO: Make it procted - UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Tag"), Category = "AbilityFramework|Abilities") - UGAAbilityBase* BP_GetAbilityByTag(TSoftClassPtr TagIn); + UFUNCTION(BlueprintCallable, meta = (DisplayName = "Get Ability By Handle"), Category = "AbilityFramework|Abilities") + UGAAbilityBase* BP_GetAbilityByHandle(FAFAbilitySpecHandle TagIn); bool ReplicateSubobjects(class UActorChannel *Channel, class FOutBunch *Bunch, FReplicationFlags *RepFlags) override; @@ -612,8 +591,6 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void NotifyOnAbilityAdded(const FGameplayTag& InAbilityTag); protected: void InitializeInstancedAbilities(); - UGAAbilityBase* InstanceAbility(TSubclassOf AbilityClass - , TSoftClassPtr InClassPtr); public: diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h index 408caa2..3cbdfd8 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityTypes.h @@ -7,41 +7,75 @@ class UGAAbilityBase; -USTRUCT() -struct ABILITYFRAMEWORK_API FAFAbilityItem : public FFastArraySerializerItem +USTRUCT(BlueprintType) +struct FAFAbilitySpecHandle { GENERATED_BODY() + friend struct FAFAbilitySpec; +public: + UPROPERTY() + uint32 Handle; + static FAFAbilitySpecHandle GenerateHandle() + { + static uint32 HandleID = 0; + HandleID++; + FAFAbilitySpecHandle Handle; + Handle.Handle = HandleID; + return Handle; + } +public: + bool IsValid() const + { + return Handle != 0; + } + bool operator==(const FAFAbilitySpecHandle& ROther) const + { + return Handle == ROther.Handle; + } + friend uint32 GetTypeHash(const FAFAbilitySpecHandle& InHandle) + { + return InHandle.Handle; + } +}; + + +/* + Handle is created on calling client and then send to server. If/when server instance ability and send back it to client + it will use exactly the same handle. +*/ +USTRUCT() +struct ABILITYFRAMEWORK_API FAFAbilitySpec : public FFastArraySerializerItem +{ + GENERATED_BODY() public: + friend struct FAFAbilitySpecHandle; UPROPERTY() UGAAbilityBase* Ability; UPROPERTY() - TSoftClassPtr AbilityClass; - - FAFAbilityItem() - {}; - - FAFAbilityItem(UGAAbilityBase* InAbility, TSoftClassPtr InAbilityClass) - : Ability(InAbility) - , AbilityClass(InAbilityClass) - {} + uint8 InputID; + /* Server generated handle that is valid on both client and server. Use it to find ability */ + UPROPERTY() + FAFAbilitySpecHandle Handle; + /* Client generated handle that is only used temporarily to fire events on owning client. */ + UPROPERTY() + FAFAbilitySpecHandle ClientHandle; void PreReplicatedRemove(const struct FAFAbilityContainer& InArraySerializer); void PostReplicatedAdd(const struct FAFAbilityContainer& InArraySerializer); void PostReplicatedChange(const struct FAFAbilityContainer& InArraySerializer); - const bool operator==(const TSoftClassPtr& OtherAbility) const + bool operator==(const FAFAbilitySpec& ROther) const { - return AbilityClass == OtherAbility; + return Handle == ROther.Handle; } - - const bool operator==(UGAAbilityBase* OtherAbility) const + bool operator==(const FAFAbilitySpecHandle& ROther) const { - return Ability == OtherAbility; + return Handle == ROther; } - const bool operator==(const FAFAbilityItem& OtherItem) const + friend uint32 GetTypeHash(const FAFAbilitySpec& InSpec) { - return Ability == OtherItem.Ability; + return InSpec.Handle.Handle; } }; @@ -50,57 +84,33 @@ struct ABILITYFRAMEWORK_API FAFAbilityContainer : public FFastArraySerializer { GENERATED_BODY() public: - + TWeakObjectPtr AbilitiesComp; UPROPERTY() - TArray AbilitiesItems; - - TWeakObjectPtr AbilitiesComp; - TMap BlockedInput; - - TMap, FGameplayTag> AbilityToInput; - - //Custom binding, for server side validation. - - //ActionInput, AbilityClassPtr - TMap> ActionToAbility; - - //maybe.. replace SoftClassPtr with FObjectKey ? - - //AbilityTag, ActionInput - TMap, TArray> AbilityToAction; - - //abilityTag, Ability Ptr - TMap, UGAAbilityBase*> AbilitiesInputs; - - TMap, UGAAbilityBase*> TagToAbility; - - void SetBlockedInput(const FGameplayTag& InActionName, bool bBlock); - UGAAbilityBase* AddAbility(TSubclassOf AbilityIn - , TSoftClassPtr InClassPtr); - - void AddAbilityFromObject(class UGAAbilityBase* AbilityIn, TSoftClassPtr InClassPtr); + TArray ActivatableAbilities; - void RemoveAbility(const TSoftClassPtr& AbilityIn); + TMap SpecMap; - void SetAbilityToAction(const TSoftClassPtr& InAbiltyPtr, const TArray& InInputTag); - void RemoveAbilityFromAction(const TSoftClassPtr& InAbiltyPtr); - TSoftClassPtr IsAbilityBoundToAction(const FGameplayTag& InInputTag); + TMap InputToAbilitySpec; - UGAAbilityBase* GetAbility(TSoftClassPtr InAbiltyPtr); + UGAAbilityBase* AddAbility(TSubclassOf AbilityIn, const FAFAbilitySpecHandle Handle, const FAFAbilitySpecHandle ClientHandle); - void HandleInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); - void HandleInputReleased(FGameplayTag ActionName); - void TriggerAbylityByTag(TSoftClassPtr InTag); + void RemoveAbility(const FAFAbilitySpecHandle AbilityIn); + + UGAAbilityBase* GetAbility(FAFAbilitySpecHandle InAbiltyPtr); + + void HandleInputPressed(const uint8 InputID, const FAFPredictionHandle& InPredictionHandle); + void HandleInputReleased(const uint8 InputID); - bool AbilityExists(TSoftClassPtr InAbiltyPtr) const + bool AbilityExists(FAFAbilitySpecHandle InAbiltyPtr) const { - return AbilityToInput.Contains(InAbiltyPtr); + return SpecMap.Contains(InAbiltyPtr); } bool NetDeltaSerialize(FNetDeltaSerializeInfo & DeltaParms) { - return FFastArraySerializer::FastArrayDeltaSerialize(AbilitiesItems, DeltaParms, *this); + return FFastArraySerializer::FastArrayDeltaSerialize(ActivatableAbilities, DeltaParms, *this); } + void BindAbilityToInputIDs(const FAFAbilitySpecHandle Handle, TArray InputIDs); }; template<> diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h index 66daae9..b9ea1df 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h @@ -301,7 +301,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt * @param ActionName - Name of action which tirggered this ability * @param InPredictionHandle - Prediction Handle Generate By Client */ - void OnNativeInputPressed(FGameplayTag ActionName, const FAFPredictionHandle& InPredictionHandle); + void OnNativeInputPressed(uint8 InputID, const FAFPredictionHandle& InPredictionHandle); /* * @call Order: * Previous Function: UGAAbilityBase::OnNativeInputPressed @@ -316,11 +316,11 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt * @param ActionName - Name of action which tirggered this ability */ UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnInputPressed(FGameplayTag ActionName); + void OnInputPressed(uint8 InputID); - void OnNativeInputReleased(FGameplayTag ActionName); + void OnNativeInputReleased(uint8 InputID); UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnInputReleased(FGameplayTag ActionName); + void OnInputReleased(uint8 InputID); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index 3a4194c..181b0f3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -63,7 +63,12 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase { GENERATED_BODY() public: - + + UPROPERTY(NotReplicated) + class UAFAbilityComponent* AbilityComp; + UPROPERTY(NotReplicated) + FGAAttribute SelfName; + UPROPERTY(EditAnywhere, SaveGame) float BaseValue; /* diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h index cc748f5..69cd535 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeExtension.h @@ -14,14 +14,11 @@ class ABILITYFRAMEWORK_API UGAAttributeExtension : public UObject { GENERATED_BODY() public: - UPROPERTY() - class UAFAbilityComponent* AbilityComponent; UPROPERTY() FGAAttribute Attribute; - void Initialize(UAFAbilityComponent* InAbilityComponent, const FName& InAttributeName); - void OnPreAttributeModify(float InValue); - void OnPostAttributeModify(float InValue); + void OnPreAttributeModify(class UAFAbilityComponent* InComp, const FGAAttribute& Attribute, float InValue); + void OnPostAttributeModify(class UAFAbilityComponent* InComp, const FGAAttribute& Attribute, float InValue); virtual void PreAttributeModify(const FGAEffectContext& InContext, float PreValue) {}; virtual void PostAttributeModify(const FGAEffectContext& InContext, float PreValue, float PostValue) {}; diff --git a/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin b/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin deleted file mode 100644 index b3a3879..0000000 --- a/Plugins/AbilityFrameworkDebugger/AbilityFrameworkDebugger.uplugin +++ /dev/null @@ -1,37 +0,0 @@ -{ - "FileVersion": 3, - "Version": 1, - "VersionName": "1.0", - "FriendlyName": "AbilityFrameworkDebugger", - "Description": "", - "Category": "Other", - "CreatedBy": "", - "CreatedByURL": "", - "DocsURL": "", - "MarketplaceURL": "", - "SupportURL": "", - "CanContainContent": true, - "IsBetaVersion": false, - "Installed": false, - "Modules": [ - { - "Name": "AbilityFrameworkDebugger", - "Type": "Runtime", - "LoadingPhase": "Default" - } - ], - "Plugins": [ - { - "Name": "AbilityFramework", - "Enabled": true - }, - { - "Name": "AbilityManager", - "Enabled": true - }, - { - "Name": "DraggableWindow", - "Enabled": true - } - ] -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs deleted file mode 100644 index f0aa592..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/AbilityFrameworkDebugger.Build.cs +++ /dev/null @@ -1,58 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; - -public class AbilityFrameworkDebugger : ModuleRules -{ - public AbilityFrameworkDebugger(ReadOnlyTargetRules Target) : base(Target) - { - PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - - PrivateIncludePaths.AddRange( - new string[] { - "AbilityFrameworkDebugger/Private", - // ... add other private include paths required here ... - } - ); - - - PublicDependencyModuleNames.AddRange( - new string[] - { - "Core", - // ... add other public dependencies that you statically link with here ... - } - ); - - - PrivateDependencyModuleNames.AddRange( - new string[] - { - "CoreUObject", - "Engine", - "InputCore", - "UMG", - "Slate", - "SlateCore", - "GameplayTags", - "GameplayTasks", - "AbilityFramework", - "AbilityManager", - "DraggableWindow" - // ... add private dependencies that you statically link with here ... - } - ); - - - DynamicallyLoadedModuleNames.AddRange( - new string[] - { - // ... add any modules that your module loads dynamically here ... - } - ); - if (Target.Type == TargetRules.TargetType.Editor) - { - PublicDependencyModuleNames.AddRange(new string[] { "UnrealEd", "PropertyEditor" }); - } - } -} diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp deleted file mode 100644 index 705f984..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.cpp +++ /dev/null @@ -1,107 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDAbilityGiveTrigger.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" -#include "Abilities/GAAbilityBase.h" - -// Sets default values -AAFDAbilityGiveTrigger::AAFDAbilityGiveTrigger() -{ - // Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it. - PrimaryActorTick.bCanEverTick = true; - RootComp = CreateDefaultSubobject(RootCompName); - RootComponent = RootComp; - - Icon = CreateDefaultSubobject(IconName); - Icon->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); - Trigger = CreateDefaultSubobject(TriggerName); - Trigger->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); - - //Trigger2 = CreateDefaultSubobject(TriggerName); - //Trigger2->AttachToComponent(RootComp, FAttachmentTransformRules::KeepRelativeTransform); -} - -// Called when the game starts or when spawned -void AAFDAbilityGiveTrigger::BeginPlay() -{ - Super::BeginPlay(); - Trigger->OnComponentBeginOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::BeginOverlap); - Trigger->OnComponentEndOverlap.AddDynamic(this, &AAFDAbilityGiveTrigger::EndOverlap); -} - -// Called every frame -void AAFDAbilityGiveTrigger::Tick(float DeltaTime) -{ - Super::Tick(DeltaTime); - -} - -void AAFDAbilityGiveTrigger::BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, - int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult) -{ - if (!AbilityConfig.AbilityTag.IsValid()) - return; - - IAFAbilityInterface* AbilityInterface = Cast(OtherActor); - if (!AbilityInterface) - return; - - if(!CurrentComponent) - CurrentComponent = AbilityInterface->GetAbilityComp(); - - //FAFOnAbilityReady del = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityReady, AbilityConfig.AbilityTag, - // AbilityConfig.InputTag); - - APawn* pawn = Cast(OtherActor); - if(pawn) - { - AController* AC = pawn->GetController(); - if(AC) - { - TArray Comps = AC->GetComponentsByTag(UAMAbilityManagerComponent::StaticClass(), TEXT("AbilityManager")); - if(Comps.Num() == 1 && !AbilityManager) - { - AbilityManager = Cast(Comps[0]); - } - - if(AbilityManager) - AbilityManager->NativeEquipAbility(AbilityConfig.AbilityTag, AbilityConfig.Group, AbilityConfig.Slot); - } - } - - //if(AbilityManager) - //{ - // - //} - //CurrentComponent->AddOnAbilityReadyDelegate(AbilityConfig.AbilityTag, del); - //CurrentComponent->NativeAddAbilityFromTag(AbilityConfig.AbilityTag, nullptr);// , /*Input*/ ShootInput); -} - -void AAFDAbilityGiveTrigger::EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex) -{ - if (!AbilityConfig.AbilityTag.IsValid()) - return; -} - -void AAFDAbilityGiveTrigger::OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) -{ - UGAAbilityBase* Ability = Cast(CurrentComponent->BP_GetAbilityByTag(InAbilityTag)); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &AAFDAbilityGiveTrigger::OnAbilityInputReady, - InAbilityTag, InAbilityInput); - - CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - } - else - { - CurrentComponent->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); - } -} - - -void AAFDAbilityGiveTrigger::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput) -{ - -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h deleted file mode 100644 index 2df3625..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDAbilityGiveTrigger.h +++ /dev/null @@ -1,83 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "GameFramework/Actor.h" -#include "Components/BoxComponent.h" -#include "Components/ShapeComponent.h" -#include "GameplayTags.h" -#include "AMTypes.h" -#include "AMAbilityManagerComponent.h" -#include "AFDAbilityGiveTrigger.generated.h" - -USTRUCT(BlueprintType) -struct FAFDAbilityConfig -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - EAMGroup Group; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - EAMSlot Slot; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - TSoftClassPtr AbilityTag; - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - TArray InputTag; -}; - -static const FName RootCompName = TEXT("RootComp"); -static const FName TriggerName = TEXT("Trigger"); -static const FName IconName = TEXT("Icon"); -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API AAFDAbilityGiveTrigger : public AActor -{ - GENERATED_BODY() -protected: - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - USceneComponent* RootComp; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - UBillboardComponent* Icon; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - UBoxComponent* Trigger; - - UPROPERTY(VisibleAnywhere, BlueprintReadOnly) - UShapeComponent* Trigger2; - - UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Config") - FAFDAbilityConfig AbilityConfig; - - UPROPERTY() - class UAFAbilityComponent* CurrentComponent; - UPROPERTY() - class UAMAbilityManagerComponent* AbilityManager; - -public: - // Sets default values for this actor's properties - AAFDAbilityGiveTrigger(); - -protected: - // Called when the game starts or when spawned - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void Tick(float DeltaTime) override; -protected: - UFUNCTION() - void BeginOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, - int32 OtherBodyIndex, bool bFromSweep, const FHitResult& SweepResult); - /** Delegate for notification of end of overlap with a specific component */ - UFUNCTION() - void EndOverlap(UPrimitiveComponent* OverlappedComponent, AActor* OtherActor, UPrimitiveComponent* OtherComp, int32 OtherBodyIndex); - - UFUNCTION() - void OnAbilityReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); - - UFUNCTION() - void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput); - - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp deleted file mode 100644 index d33bda5..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.cpp +++ /dev/null @@ -1,11 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDBlueprintFunctionLibrary.h" -#include "AFDManager.h" - - - -//void UAFDBlueprintFunctionLibrary::OpenAbilityDebugger() -//{ -// FAFDManager::Get(); -//} diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h deleted file mode 100644 index 49d85b9..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDBlueprintFunctionLibrary.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Kismet/BlueprintFunctionLibrary.h" -#include "AFDBlueprintFunctionLibrary.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API UAFDBlueprintFunctionLibrary : public UBlueprintFunctionLibrary -{ - GENERATED_BODY() -public: - //UFUNCTION(Exec) - // static void OpenAbilityDebugger(); - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp deleted file mode 100644 index dc9608a..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.cpp +++ /dev/null @@ -1,41 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDManager.h" -#include "EngineGlobals.h" -#include "Engine/Engine.h" -#include "Engine/GameViewportClient.h" -#include "Slate.h" -#include "SlateCore.h" -#include "DWManager.h" - -FAFDManager* FAFDManager::Instance = nullptr; - -FAFDManager::FAFDManager() -{ -} - -FAFDManager::~FAFDManager() -{ -} - -void FAFDManager::Init() -{ - Dekstop = SNew(SAFDDesktopWidget).Visibility(EVisibility::SelfHitTestInvisible); - GEngine->GameViewport->AddViewportWidgetContent(Dekstop.ToSharedRef()); -} - -FDWWWindowHandle FAFDManager::AddDebugWindow(TSharedPtr InWindowContent) -{ - return FDWManager::Get().CreateWindow(InWindowContent, "Debug"); -} - -#if WITH_EDITORONLY_DATA -void FAFDManager::PIEDestroy() -{ - if (Instance) - { - delete Instance; - Instance = nullptr; - } -} -#endif \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h deleted file mode 100644 index c309907..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AFDManager.h +++ /dev/null @@ -1,38 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "SAFDDesktopWidget.h" -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API FAFDManager -{ -private: - static FAFDManager* Instance; - TSharedPtr Dekstop; -protected: - void Init(); -public: - - static FAFDManager& Get() - { - if(!Instance) - { - Instance = new FAFDManager(); - Instance->Init(); - } - return*Instance; - } - -#if WITH_EDITORONLY_DATA - static void PIEDestroy(); -#endif - - - FDWWWindowHandle AddDebugWindow(TSharedPtr InWindowContent); - - FAFDManager(); - ~FAFDManager(); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp deleted file mode 100644 index 83672d1..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.cpp +++ /dev/null @@ -1,7 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AFDAbilityBase.h" - - - - diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h deleted file mode 100644 index 40341a2..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/Abilities/AFDAbilityBase.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Abilities/GAAbilityBase.h" -#include "AFDAbilityBase.generated.h" - -/** - * - */ -UCLASS() -class ABILITYFRAMEWORKDEBUGGER_API UAFDAbilityBase : public UGAAbilityBase -{ - GENERATED_BODY() - - - - -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp deleted file mode 100644 index e0ac611..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.cpp +++ /dev/null @@ -1,45 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "AbilityFrameworkDebugger.h" -#include "HAL/IConsoleManager.h" -#include "AFDManager.h" -#if WITH_EDITORONLY_DATA -#include "Editor.H" -#endif -#define LOCTEXT_NAMESPACE "FAbilityFrameworkDebuggerModule" - -void FAbilityFrameworkDebuggerModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module - CommandOpenAbilityDebugger = IConsoleManager::Get().RegisterConsoleCommand( - TEXT("OpenAbilityDebugger"), - TEXT("Opens ability debugger"), - FConsoleCommandDelegate::CreateStatic(OpenAbilityDebugger), - ECVF_Default - ); - -#if WITH_EDITORONLY_DATA - FEditorDelegates::EndPIE.AddRaw(this, &FAbilityFrameworkDebuggerModule::HandlePIEEnd); -#endif //WITH_EDITORONLY_DATA -} - -void FAbilityFrameworkDebuggerModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. - IConsoleManager::Get().UnregisterConsoleObject(CommandOpenAbilityDebugger); -} - -void FAbilityFrameworkDebuggerModule::OpenAbilityDebugger() -{ - FAFDManager::Get(); -} -#if WITH_EDITORONLY_DATA -void FAbilityFrameworkDebuggerModule::HandlePIEEnd(bool InVal) -{ - FAFDManager::PIEDestroy(); -} -#endif -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FAbilityFrameworkDebuggerModule, AbilityFrameworkDebugger) \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h deleted file mode 100644 index d50fefe..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/AbilityFrameworkDebugger.h +++ /dev/null @@ -1,22 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FAbilityFrameworkDebuggerModule : public IModuleInterface -{ -private: - IConsoleObject* CommandOpenAbilityDebugger; - static void OpenAbilityDebugger(); -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; - -#if WITH_EDITORONLY_DATA - void HandlePIEEnd(bool InVal); -#endif -}; \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp deleted file mode 100644 index 48c1171..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.cpp +++ /dev/null @@ -1,74 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDAttributes.h" -#include "SlateOptMacros.h" -#include "SListView.h" -#include "SGridPanel.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDAttributes::Construct(const FArguments& InArgs) -{ - AFInterface = InArgs._AbilityInterface; - ChildSlot - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SOverlay) - +SOverlay::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SListView>) - .ListItemsSource(&Attributes) - .OnGenerateRow(this, &SAFDAttributes::GenerateListRow) - ] - ]; - GatherAttributes(); -} -void SAFDAttributes::GatherAttributes() -{ - if (!AFInterface) - return; - - UGAAttributesBase* AttributesObject = AFInterface->GetAttributes(); - if (!AttributesObject) - return; - - Attributes.Empty(); - for(TFieldIterator It(AttributesObject->GetClass(), EFieldIteratorFlags::IncludeSuper); It; ++It) - { - TSharedPtr AttributeRow = MakeShareable(new FAttributeRow); - UStructProperty* Prop = *It; - FAFAttributeBase* Attr = Prop->ContainerPtrToValuePtr(AttributesObject); - if (Attr) - { - AttributeRow->Attribute = Attr; - AttributeRow->Name = It->GetName(); - AttributeRow->Value = TAttribute::Create(TAttribute::FGetter::CreateSP(AttributeRow.Get(), &FAttributeRow::GetValue)); - } - Attributes.Add(AttributeRow); - } - -} -TSharedRef SAFDAttributes::GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable) -{ - return - SNew(STableRow< TSharedRef >, OwnerTable) - [ - SNew(SGridPanel) - .FillColumn(0, 1) - +SGridPanel::Slot(0,0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(FText::FromString(NotifyName->Name)) - ] - + SGridPanel::Slot(1, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(NotifyName->Value) - ] - ]; -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h deleted file mode 100644 index 57f937b..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDAttributes.h +++ /dev/null @@ -1,39 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" -#include "AFAbilityInterface.h" -#include "Attributes/GAAttributesBase.h" - -struct FAttributeRow : public TSharedFromThis -{ - FString Name; - FAFAttributeBase* Attribute; - TAttribute Value; - - FText GetValue() const - { - return FText::AsNumber(Attribute->GetCurrentValue()); - } -}; - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDAttributes : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDAttributes) - {} - SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) - SLATE_END_ARGS() - - IAFAbilityInterface* AFInterface; - TArray> Attributes; - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - void GatherAttributes(); - TSharedRef GenerateListRow(TSharedPtr NotifyName, const TSharedRef& OwnerTable); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp deleted file mode 100644 index d2091b4..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.cpp +++ /dev/null @@ -1,203 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDDesktopWidget.h" -#include "SlateCore.h" -#include "Slate.h" -#include "SlateOptMacros.h" -#include "SBoxPanel.h" -#include "SButton.h" -#include "STextBlock.h" -#include "AFDManager.h" -#include "Engine/Engine.h" -#include "Engine/GameViewportClient.h" -#include "GameFramework/PlayerController.h" -#include "SAFDViewportMouseCapture.h" -#include "SAFDEffects.h" -#include "SAFDAttributes.h" - -void SAFDMainWidget::Construct(const FArguments& InArgs) -{ - FWorldContext* WorldContext = GEngine->GetWorldContextFromGameViewport(GEngine->GameViewport); - UWorld* world = WorldContext->World(); - World = world; - FOnClicked OnPickActorClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnPickActorClicked); - - FOnClicked OnAttributesClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnAttributesClicked); - FOnClicked OnEffectsClickedDel = FOnClicked::CreateSP(this, &SAFDMainWidget::OnEffectsClicked); - - ChildSlot - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - .FillHeight(1.0f) - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SOverlay) - +SOverlay::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Top) - .AutoHeight() - [ - SNew(STextBlock) - .Text(this, &SAFDMainWidget::GetActorName) - ] - + SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Top) - .MaxHeight(24) - .AutoHeight() - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(OnAttributesClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("Attributes")) - ] - ] - + SHorizontalBox::Slot() - [ - SNew(SButton) - .OnClicked(OnEffectsClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("Effects")) - ] - ] - ] - + SVerticalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - .FillWidth(1.0f) - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SAssignNew(Content, SWidgetSwitcher) - ] - ] - ] - ] - +SVerticalBox::Slot() - .MaxHeight(32.0f) - .AutoHeight() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Bottom) - [ - SNew(SButton) - .OnClicked(OnPickActorClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("Pick Actor")) - ] - ] - ]; -} - -FText SAFDMainWidget::GetActorName() const -{ - if(SelectedActor.IsValid()) - { - return FText::FromString(SelectedActor->GetName()); - } - return FText::FromString("Select Actor from viewport."); -} -FReply SAFDMainWidget::OnPickActorClicked() -{ - CaptureWidget = SNew(SAFDViewportMouseCapture); - FSimpleDelegate del = FSimpleDelegate::CreateSP(this, &SAFDMainWidget::OnActorPicked); - CaptureWidget->OnMouseButtonDownDelegate = del; - GEngine->GameViewport->AddViewportWidgetContent(CaptureWidget.ToSharedRef(), 1001); - - return FReply::Handled(); -} - -FReply SAFDMainWidget::OnAttributesClicked() -{ - Content->SetActiveWidgetIndex(0); - return FReply::Handled(); -} -FReply SAFDMainWidget::OnEffectsClicked() -{ - Content->SetActiveWidgetIndex(1); - return FReply::Handled(); -} - -void SAFDMainWidget::OnActorPicked() -{ - APlayerController* PC = World->GetFirstPlayerController(); - FHitResult OutHit; - PC->GetHitResultUnderCursor(ECollisionChannel::ECC_Visibility, false, OutHit); - - if(OutHit.bBlockingHit) - { - AActor* actor = OutHit.GetActor(); - SelectedActor = OutHit.Actor; - if(IAFAbilityInterface* Interface = Cast(OutHit.GetActor())) - { - Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SAFDAttributes) - .AbilityInterface(Interface) - ]; - Content->AddSlot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SNew(SAFDEffects) - .AbilityInterface(Interface) - ]; - } - } - - GEngine->GameViewport->RemoveViewportWidgetContent(CaptureWidget.ToSharedRef()); -} -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDDesktopWidget::Construct(const FArguments& InArgs) -{ - FOnClicked OnNewDebugWindowClickedDel = FOnClicked::CreateSP(this, &SAFDDesktopWidget::OnNewDebugWindowClicked); - ChildSlot - [ - SNew(SHorizontalBox) - +SHorizontalBox::Slot() - .HAlign(EHorizontalAlignment::HAlign_Right) - .VAlign(EVerticalAlignment::VAlign_Top) - [ - SNew(SVerticalBox) - +SVerticalBox::Slot() - [ - SNew(SButton) - .OnClicked(OnNewDebugWindowClickedDel) - [ - SNew(STextBlock) - .Text(FText::FromString("New Debug Window")) - ] - ] - ] - // Populate the widget - ]; - -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -FReply SAFDDesktopWidget::OnNewDebugWindowClicked() -{ - TSharedPtr wid = SNew(SAFDMainWidget); - FDWWWindowHandle Handle = FAFDManager::Get().AddDebugWindow(wid); - wid->SetWindowHandle(Handle); - return FReply::Handled(); -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h deleted file mode 100644 index 73f612c..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDDesktopWidget.h +++ /dev/null @@ -1,54 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" -#include "SDraggableWindowWidget.h" -#include "SWidgetSwitcher.h" - -class ABILITYFRAMEWORKDEBUGGER_API SAFDMainWidget : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDMainWidget) - {} - SLATE_END_ARGS() -protected: - TWeakObjectPtr World; - TWeakObjectPtr SelectedActor; - TSharedPtr Content; - FDWWWindowHandle WindowHandle; - TSharedPtr CaptureWidget; - /** Constructs this widget with InArgs */ -public: - void Construct(const FArguments& InArgs); -protected: - FReply OnPickActorClicked(); - FReply OnAttributesClicked(); - FReply OnEffectsClicked(); - - void OnActorPicked(); - - FText GetActorName() const; -public: - void SetWindowHandle(const FDWWWindowHandle& InHandle) - { - WindowHandle = InHandle; - } -}; - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDDesktopWidget : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDDesktopWidget) - {} - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - - FReply OnNewDebugWindowClicked(); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp deleted file mode 100644 index babb94a..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.cpp +++ /dev/null @@ -1,16 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDEffectInspector.h" -#include "SlateOptMacros.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDEffectInspector::Construct(const FArguments& InArgs) -{ - /* - ChildSlot - [ - // Populate the widget - ]; - */ -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h deleted file mode 100644 index e9de984..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffectInspector.h +++ /dev/null @@ -1,20 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDEffectInspector : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDEffectInspector) - {} - SLATE_END_ARGS() - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp deleted file mode 100644 index 53bd36c..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.cpp +++ /dev/null @@ -1,105 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDEffects.h" -#include "SlateOptMacros.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDEffects::Construct(const FArguments& InArgs) -{ - AFInterface = InArgs._AbilityInterface; - AbilityComponent = AFInterface->GetAbilityComp(); - - InitializeEffects(); - ChildSlot - [ - SNew(SOverlay) - + SOverlay::Slot() - .HAlign(EHorizontalAlignment::HAlign_Fill) - .VAlign(EVerticalAlignment::VAlign_Fill) - [ - SAssignNew(ListView, SListView>) - .ListItemsSource(&Effects) - .OnGenerateRow(this, &SAFDEffects::GenerateListRow) - ] - ]; - -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION -SAFDEffects::~SAFDEffects() -{ - -} - -void SAFDEffects::InitializeEffects() -{ - if (!AbilityComponent.IsValid()) - return; - - //ListView->RebuildList(); -} - - -TSharedRef SAFDEffects::GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable) -{ - return - SNew(STableRow< TSharedRef >, OwnerTable) - [ - SNew(SGridPanel) - .FillColumn(0, 1) - /*.FillColumn(1,1) - .FillColumn(2,1)*/ - + SGridPanel::Slot(0, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(FText::FromString(EffectRow->EffectClassName)) - ] - + SGridPanel::Slot(1, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(EffectRow->TimeRemaining) - ] - + SGridPanel::Slot(2, 0) - .HAlign(EHorizontalAlignment::HAlign_Fill) - [ - SNew(STextBlock) - .Text(EffectRow->PeriodTime) - ] - ]; -} - -void SAFDEffects::OnEffectApplied(FGAEffectHandle InHandle) -{ - TSharedPtr Row = MakeShareable(new FAFDEffectRow); - UE_LOG(LogTemp, Warning, TEXT("SAFDEffects::OnEffectAppliede")); - Effects.Add(Row); - - ListView->RebuildList(); -} -void SAFDEffects::OnEffectRemoved(FGAEffectHandle InHandle) -{ - class Predicate - { - FGAEffectHandle HandleC; - public: - Predicate(const FGAEffectHandle& InH) - :HandleC(InH) - {} - bool operator()(const FAFDEffectRow& Other) const - { - return HandleC == Other.Handle; - } - bool operator()(TSharedPtr Other) const - { - return HandleC == Other->Handle; - } - }; - int32 Idx = Effects.IndexOfByPredicate(Predicate(InHandle)); //Effects.IndexOfByKey(InHandle); - if(Idx > -1) - { - Effects.RemoveAt(Idx); - } - - ListView->RebuildList(); -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h deleted file mode 100644 index 6d17270..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDEffects.h +++ /dev/null @@ -1,82 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" - -#include "GAGlobalTypes.h" -#include "Effects/GAGameEffect.h" -#include "AFAbilityInterface.h" -#include "AFAbilityComponent.h" - -struct FAFDEffectRow : public TSharedFromThis -{ - FString EffectClassName; - FGAEffectHandle Handle; - TAttribute TimeRemaining; - TAttribute PeriodTime; - TWeakObjectPtr AbilityComponent; - - FText GetTimeRemaining() const - { - return FText::AsNumber(0); - //return FText::AsNumber(AbilityComponent->GameEffectContainer.GetRemainingTime(Handle)); - } - - FText GetPeriodTime() const - { - return FText::AsNumber(0); - //return FText::AsNumber(RepInfo->GetPeriodTime(static_cast(FPlatformTime::Seconds()))); - } - - const bool operator==(const FAFDEffectRow& Other) const - { - return Handle == Other.Handle; - } - - const bool operator==(const FGAEffectHandle& InHandle) const - { - return Handle == InHandle; - } - const bool operator==(FGAEffectHandle InHandle) const - { - return Handle == InHandle; - } - const bool operator==(TSharedPtr InHandle) const - { - return Handle == InHandle->Handle; - } -}; - - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDEffects : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDEffects) - {} - SLATE_ARGUMENT(IAFAbilityInterface*, AbilityInterface) - SLATE_END_ARGS() -protected: - IAFAbilityInterface* AFInterface; - TWeakObjectPtr AbilityComponent; - TSharedPtr>> ListView; - FDelegateHandle OnEffectAppliedHandle; - FDelegateHandle OnEffectRemovedHandle; - FDelegateHandle OnEffectExpiredHandle; - - TArray> Effects; - -public: - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - ~SAFDEffects(); -protected: - TSharedRef GenerateListRow(TSharedPtr EffectRow, const TSharedRef& OwnerTable); - void InitializeEffects(); - void OnEffectApplied(FGAEffectHandle InHandle); - void OnEffectRemoved(FGAEffectHandle InHandle); -}; diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp deleted file mode 100644 index 5560253..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.cpp +++ /dev/null @@ -1,22 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "SAFDViewportMouseCapture.h" -#include "SlateOptMacros.h" - -BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -void SAFDViewportMouseCapture::Construct(const FArguments& InArgs) -{ - /* - ChildSlot - [ - // Populate the widget - ]; - */ -} -END_SLATE_FUNCTION_BUILD_OPTIMIZATION - -FReply SAFDViewportMouseCapture::OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) -{ - OnMouseButtonDownDelegate.ExecuteIfBound(); - return FReply::Handled(); -} \ No newline at end of file diff --git a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h b/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h deleted file mode 100644 index 30e79b2..0000000 --- a/Plugins/AbilityFrameworkDebugger/Source/AbilityFrameworkDebugger/Public/SAFDViewportMouseCapture.h +++ /dev/null @@ -1,24 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Widgets/SCompoundWidget.h" - -/** - * - */ -class ABILITYFRAMEWORKDEBUGGER_API SAFDViewportMouseCapture : public SCompoundWidget -{ -public: - SLATE_BEGIN_ARGS(SAFDViewportMouseCapture) - {} - SLATE_END_ARGS() - - FSimpleDelegate OnMouseButtonDownDelegate; - - /** Constructs this widget with InArgs */ - void Construct(const FArguments& InArgs); - - virtual FReply OnMouseButtonDown(const FGeometry& MyGeometry, const FPointerEvent& MouseEvent) override; -}; diff --git a/Plugins/AbilityManager/AbilityManager.uplugin b/Plugins/AbilityManager/AbilityManager.uplugin deleted file mode 100644 index bfa155d..0000000 --- a/Plugins/AbilityManager/AbilityManager.uplugin +++ /dev/null @@ -1,34 +0,0 @@ -{ - "FileVersion": 3, - "Version": 1, - "VersionName": "1.0", - "FriendlyName": "AbilityManager", - "Description": "Manages input and UI for abilities. Sample implementation with most common functionality.", - "Category": "Other", - "CreatedBy": "", - "CreatedByURL": "", - "DocsURL": "", - "MarketplaceURL": "", - "SupportURL": "", - "CanContainContent": true, - "IsBetaVersion": false, - "Installed": false, - "Modules": [ - { - "Name": "AbilityManager", - "Type": "Runtime", - "LoadingPhase": "Default" - }, - { - "Name": "AbilityManagerEditor", - "Type": "Editor", - "LoadingPhase": "Default" - } - ], - "Plugins": [ - { - "Name": "AbilityFramework", - "Enabled": true - } - ] -} \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs b/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs deleted file mode 100644 index ef559fa..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/AbilityManager.Build.cs +++ /dev/null @@ -1,49 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; - -public class AbilityManager : ModuleRules -{ - public AbilityManager(ReadOnlyTargetRules Target) : base(Target) - { - PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - - PrivateIncludePaths.AddRange( - new string[] { - // ... add other private include paths required here ... - } - ); - - - PublicDependencyModuleNames.AddRange( - new string[] - { - "Core", - // ... add other public dependencies that you statically link with here ... - } - ); - - - PrivateDependencyModuleNames.AddRange( - new string[] - { - "CoreUObject", - "Engine", - "Slate", - "SlateCore", - "GameplayTags", - "GameplayTasks", - "AbilityFramework" - // ... add private dependencies that you statically link with here ... - } - ); - - - DynamicallyLoadedModuleNames.AddRange( - new string[] - { - // ... add any modules that your module loads dynamically here ... - } - ); - } -} diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp b/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp deleted file mode 100644 index 38779ca..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.cpp +++ /dev/null @@ -1,451 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AMAbilityManagerComponent.h" -#include "AFAbilityComponent.h" -#include "AFAbilityInterface.h" - -// Sets default values for this component's properties -UAMAbilityManagerComponent::UAMAbilityManagerComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - bWantsInitializeComponent = true; - SetIsReplicated(true); - // ... -} - - -// Called when the game starts -void UAMAbilityManagerComponent::BeginPlay() -{ - Super::BeginPlay(); - //OnNextGroupDelegate = FGroupConfirmDelegate::(this, UAMAbilityManagerComponent::OnNextGroupConfirmed); - // ... - -} -void UAMAbilityManagerComponent::InitializeComponent() -{ - uint8 GroupNum = Groups.Num(); - - AbilitySet.SetNum(GroupNum); - AbilityTagsSet.SetNum(GroupNum); - for(int32 Idx = 0; Idx < GroupNum; Idx++) - { - AbilitySet[Idx].SetNum(Groups[Idx].SlotNum); - AbilityTagsSet[Idx].SetNum(Groups[Idx].SlotNum); - } -} - -// Called every frame -void UAMAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} -void UAMAbilityManagerComponent::BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent) -{ - if (!AbilityComponent) - return; - - for (const FGameplayTag& Input : InputsToBind) - { - AbilityComponent->BindAbilityToAction(InputComponent, Input); - } -} - -UGAAbilityBase* UAMAbilityManagerComponent::GetAbility(EAMGroup InGroup, EAMSlot InSlot) -{ - return AbilitySet.Num() >= Groups.Num() ? AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Get() : nullptr; -} -void UAMAbilityManagerComponent::SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility) -{ - if (AbilitySet.Num() < Groups.Num()) - return; - - AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbility; -} -void UAMAbilityManagerComponent::RemoveAbility(EAMGroup InGroup, EAMSlot InSlot) -{ - if (AbilitySet.Num() < Groups.Num()) - return; - - AbilitySet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset();; -} - -TArray UAMAbilityManagerComponent::GetInputTag(EAMGroup InGroup, EAMSlot InSlot) -{ - return InputSetup.GetInputs(InGroup, InSlot); -} -void UAMAbilityManagerComponent::SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag) -{ - -} - -TSoftClassPtr UAMAbilityManagerComponent::GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot) -{ - if (AbilityTagsSet.IsValidIndex(AMEnumToInt(InGroup)) - && AbilityTagsSet[AMEnumToInt(InGroup)].IsValidIndex(AMEnumToInt(InSlot))) - { - return AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)]; - } - return TSoftClassPtr(); -} -void UAMAbilityManagerComponent::SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag) -{ - AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)] = InAbilityTag; -} -void UAMAbilityManagerComponent::RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot) -{ - AbilityTagsSet[AMEnumToInt(InGroup)][AMEnumToInt(InSlot)].Reset(); -} - -void UAMAbilityManagerComponent::NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - TArray IAbilityInput; - - if(ActiveGroup == InGroup) - IAbilityInput = GetInputTag(InGroup, InSlot); - - FAFOnAbilityReady del; - //if (IsClient()) - { - del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, - IAbilityInput, InGroup, InSlot, bBindInput); - AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - } - - AbilityComp->NativeAddAbility(InAbilityTag, IAbilityInput);// , /*Input*/ ShootInput); -} -void UAMAbilityManagerComponent::NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - FAFOnAbilityReady del; - //if (IsClient()) - { - //del = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityReadyInternal, InAbilityTag, - // IAbilityInput, InGroup, InSlot); - //AbilityComp->AddOnAbilityReadyDelegate(InAbilityTag, del); - } - if (InAbilityTag.IsNull()) - InAbilityTag = GetAbilityTag(InGroup, InSlot); - - RemoveAbility(InGroup, InSlot); - RemoveAbilityTag(InGroup, InSlot); - - AbilityComp->NativeRemoveAbility(InAbilityTag); -} -void UAMAbilityManagerComponent::OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot, bool bBindInput) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - - - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - if (bBindInput) - { - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UAMAbilityManagerComponent::OnAbilityInputReady, - InAbilityTag, InAbilityInput, InGroup, InSlot); - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, ReadyDelegate); - - ExecuteAbilityReadyEvent(InAbilityTag); - } - - } - else - { - SetAbility(InGroup, InSlot, Ability); - SetAbilityTag(InGroup, InSlot, InAbilityTag); - SetInputTag(InGroup, InSlot, InAbilityInput); - if (bBindInput) - { - AbilityComp->SetAbilityToAction(InAbilityTag, InAbilityInput, FAFOnAbilityReady()); - ExecuteAbilityReadyEvent(InAbilityTag); - } - } - OnAbilityReady(InAbilityTag, InAbilityInput, InGroup, InSlot); -} - -void UAMAbilityManagerComponent::OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) -{ - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return; - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return; - - UAFAbilityComponent* AbilityComp = ABInt->GetAbilityComp(); - if (!AbilityComp) - return; - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - SetAbility(InGroup, InSlot, Ability); - SetAbilityTag(InGroup, InSlot, InAbilityTag); - SetInputTag(InGroup, InSlot, InAbilityInput); - //ExecuteAbilityReadyEvent(InAbilityTag); -} - -void UAMAbilityManagerComponent::NextGroup() -{ - ENetMode NetMode = GetOwner()->GetNetMode(); - if (NetMode == ENetMode::NM_Client - || NetMode == ENetMode::NM_Standalone) - { - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex++; - if(CurrentIndex > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - - if (ActiveGroup < AMIntToEnum(Groups.Num())) - { - } - else - { - ActiveGroup = EAMGroup::Group001; - } - } - - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerNextGroup(AMEnumToInt(ActiveGroup)); - } -} - -void UAMAbilityManagerComponent::PreviousGroup() -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex--; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex < 0) - { - ActiveGroup = AMIntToEnum(Groups.Num() - 1); - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerPreviousGroup(static_cast(ActiveGroup)); - } -} - -void UAMAbilityManagerComponent::ServerNextGroup_Implementation(int32 WeaponIndex) -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex++; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = AMIntToEnum(CurrentIndex); - } - if (ActiveGroup < AMIntToEnum(Groups.Num())) - { - } - else - { - ActiveGroup = EAMGroup::Group001; - } - //so Server index is different. Client might tried to cheat - //or sometrhing. We will override it. - //situation where client can chage multiple weapons within second - //should not have place, as there is animation and/or internal cooldown on weapon change. - //since it will be done trough ability. - if (ActiveGroup != AMIntToEnum(WeaponIndex)) - { - ClientNextGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientNextGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UAMAbilityManagerComponent::ServerNextGroup_Validate(int32 WeaponIndex) -{ - return true; -} -void UAMAbilityManagerComponent::ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) -{ - ActiveGroup = AMIntToEnum(WeaponIndex); - OnNextGroupConfirmed(ActiveGroup, bPredictionSuccess); -} - -void UAMAbilityManagerComponent::ServerPreviousGroup_Implementation(int32 WeaponIndex) -{ - int32 CurrentIndex = AMEnumToInt(ActiveGroup); - CurrentIndex--; - ActiveGroup = AMIntToEnum(CurrentIndex); - if (CurrentIndex < 0) - { - ActiveGroup = AMIntToEnum(Groups.Num() -1); - } - if (ActiveGroup != AMIntToEnum(WeaponIndex)) - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UAMAbilityManagerComponent::ServerPreviousGroup_Validate(int32 WeaponIndex) -{ - return true; -} -void UAMAbilityManagerComponent::ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess) -{ - ActiveGroup = AMIntToEnum(WeaponIndex); - OnPreviousGroupConfirmed(ActiveGroup, bPredictionSuccess); -} - -void UAMAbilityManagerComponent::SelectGroup(EAMGroup InGroup) -{ - if (AMEnumToInt(InGroup) > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = InGroup; - } - if (GetOwnerRole() < ENetRole::ROLE_Authority) - { - ServerSelectGroup(InGroup); - } - else - { - OnGroupSelectionConfirmed(InGroup, true); - } -} -void UAMAbilityManagerComponent::ServerSelectGroup_Implementation(EAMGroup InGroup) -{ - if (AMEnumToInt(InGroup) > Groups.Num()) - { - ActiveGroup = EAMGroup::Group001; - } - else - { - ActiveGroup = InGroup; - } - if (ActiveGroup != InGroup) - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), false); - } - else - { - ClientPreviousGroup(AMEnumToInt(ActiveGroup), true); - } -} -bool UAMAbilityManagerComponent::ServerSelectGroup_Validate(EAMGroup InGroup) -{ - return true; -} - - -void UAMAbilityManagerComponent::ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess) -{ - if (bPredictionSuccess) - { - OnGroupSelectionConfirmed(InGroup, true); - } - else - { - ActiveGroup = InGroup; - OnGroupSelectionConfirmed(InGroup, false); - } -} - - -class UAFAbilityComponent* UAMAbilityManagerComponent::GetAbilityComponent() -{ - UAFAbilityComponent* AbilityComponent = nullptr; - APlayerController* MyPC = Cast(GetOwner()); - if (!MyPC) - return AbilityComponent; - - IAFAbilityInterface* ABInt = Cast(MyPC->GetPawn()); - if (!ABInt) - return AbilityComponent; - - AbilityComponent = ABInt->GetAbilityComp(); - - return AbilityComponent; -} - -bool UAMAbilityManagerComponent::IsServerOrStandalone() const -{ - AActor* Owner = GetOwner(); - if (Owner->GetNetMode() == ENetMode::NM_DedicatedServer - || Owner->GetNetMode() == ENetMode::NM_Standalone) - { - return true; - } - return false; -} -bool UAMAbilityManagerComponent::IsClientOrStandalone() const -{ - AActor* Owner = GetOwner(); - if (Owner->GetNetMode() == ENetMode::NM_Client - || Owner->GetNetMode() == ENetMode::NM_Standalone) - { - return true; - } - return false; -} -bool UAMAbilityManagerComponent::IsClient() const -{ - AActor* Owner = GetOwner(); - if (Owner->GetNetMode() == ENetMode::NM_Client - || Owner->Role < ENetRole::ROLE_Authority) - { - return true; - } - return false; -} - -void UAMAbilityManagerComponent::BindOnAbilityReadDelegate(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) -{ - -} diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h b/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h deleted file mode 100644 index 08d1adf..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/Public/AMAbilityManagerComponent.h +++ /dev/null @@ -1,201 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "Net/UnrealNetwork.h" -#include "Engine/ActorChannel.h" - -#include "AMTypes.h" -#include "GameplayTags.h" -#include "Abilities/GAAbilityBase.h" -#include "AMAbilityManagerComponent.generated.h" - - - -/* -- Group -- Set -- Ability --Inputs (multiple); - -*/ - -//all the inputs assigned to SINGLE ability; - -USTRUCT() -struct FAMAbilityInputSlot -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Inputs; - - TArray operator()() - { - return Inputs; - } -}; - - -USTRUCT() -struct FAMAbilityInputGroup -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Slots; -}; - - -USTRUCT() -struct FAMAbilityInputContainer -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TArray Groups; - - - TArray GetInputs(EAMGroup InGroup, EAMSlot InSlot) - { - return Groups[AMEnumToInt(InGroup)].Slots[AMEnumToInt(InSlot)](); - } -}; - -USTRUCT() -struct FAMAbilitySlotConfig -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - uint8 SlotNum; -}; - -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ABILITYMANAGER_API UAMAbilityManagerComponent : public UActorComponent -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere) - TArray Groups; - - //Map input bindings to particular slot and group. - UPROPERTY(EditAnywhere) - FAMAbilityInputContainer InputSetup; - - UPROPERTY(EditAnywhere, Category = "Input Config") - TArray InputsToBind; - - EAMGroup ActiveGroup; - - TArray>> AbilityTagsSet; - TArray>> AbilitySet; - TArray> ValidGroups; - TMap, FSimpleDelegate> AbilityReadyEvents; - - DECLARE_DELEGATE_TwoParams(FGroupConfirmDelegate, int32, bool) - - FGroupConfirmDelegate OnNextGroupDelegate; - FGroupConfirmDelegate OnPreviousGroupDelegate; - -public: - // Sets default values for this component's properties - UAMAbilityManagerComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - virtual void InitializeComponent() override; -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - void BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent); - UGAAbilityBase* GetAbility(EAMGroup InGroup, EAMSlot InSlot); - void SetAbility(EAMGroup InGroup, EAMSlot InSlot, UGAAbilityBase* InAbility); - void RemoveAbility(EAMGroup InGroup, EAMSlot InSlot); - - TSoftClassPtr GetAbilityTag(EAMGroup InGroup, EAMSlot InSlot); - void SetAbilityTag(EAMGroup InGroup, EAMSlot InSlot, TSoftClassPtr InAbilityTag); - void RemoveAbilityTag(EAMGroup InGroup, EAMSlot InSlot); - - TArray GetInputTag(EAMGroup InGroup, EAMSlot InSlot); - void SetInputTag(EAMGroup InGroup, EAMSlot InSlot, TArray InAbilityTag); - - void NativeEquipAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot, bool bBindInput = true); - void NativeRemoveAbility(TSoftClassPtr InAbilityTag, EAMGroup InGroup, EAMSlot InSlot); -protected: - virtual void OnAbilityReady(TSoftClassPtr InAbilityTag, const TArray& InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot) {}; -private: - UFUNCTION() - void OnAbilityReadyInternal(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot, bool bBindInput); - -public: - UFUNCTION() - void OnAbilityInputReady(TSoftClassPtr InAbilityTag, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot); - - UFUNCTION(BlueprintCallable) - virtual void NextGroup(); - UFUNCTION(BlueprintCallable) - virtual void PreviousGroup(); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerNextGroup(int32 WeaponIndex); - void ServerNextGroup_Implementation(int32 WeaponIndex); - bool ServerNextGroup_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientNextGroup(int32 WeaponIndex, bool bPredictionSuccess); - void ClientNextGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); - - UFUNCTION(Server, Reliable, WithValidation) - void ServerPreviousGroup(int32 WeaponIndex); - void ServerPreviousGroup_Implementation(int32 WeaponIndex); - bool ServerPreviousGroup_Validate(int32 WeaponIndex); - UFUNCTION(Client, Reliable) - void ClientPreviousGroup(int32 WeaponIndex, bool bPredictionSuccess); - void ClientPreviousGroup_Implementation(int32 WeaponIndex, bool bPredictionSuccess); - - - virtual void OnNextGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; - virtual void OnPreviousGroupConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; - virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) {}; - - UFUNCTION(BlueprintCallable) - void SelectGroup(EAMGroup InGroup); - UFUNCTION(Server, Reliable, WithValidation) - void ServerSelectGroup(EAMGroup InGroup); - void ServerSelectGroup_Implementation(EAMGroup InGroup); - bool ServerSelectGroup_Validate(EAMGroup InGroup); - UFUNCTION(Client, Reliable) - void ClientSelectGroup(EAMGroup InGroup, bool bPredictionSuccess); - void ClientSelectGroup_Implementation(EAMGroup InGroup, bool bPredictionSuccess); - - - void AddOnAbilityReadyEvent(const TSoftClassPtr& Ability, const FSimpleDelegate& Delegate) - { - if (!AbilityReadyEvents.Contains(Ability)) - { - AbilityReadyEvents.Add(Ability, Delegate); - } - } - - void ExecuteAbilityReadyEvent(const TSoftClassPtr& Ability) - { - if (FSimpleDelegate* Event = AbilityReadyEvents.Find(Ability)) - { - Event->ExecuteIfBound(); - AbilityReadyEvents.Remove(Ability); - } - } -protected: - class UAFAbilityComponent* GetAbilityComponent(); - void BindOnAbilityReadDelegate(TSoftClassPtr, TArray InAbilityInput, - EAMGroup InGroup, EAMSlot InSlot); - bool IsServerOrStandalone() const; - bool IsClientOrStandalone() const; - bool IsClient() const; -}; diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp b/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp deleted file mode 100644 index d34aeaf..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.cpp +++ /dev/null @@ -1,3 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "AMTypes.h" \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h b/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h deleted file mode 100644 index 90b017d..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/Public/AMTypes.h +++ /dev/null @@ -1,95 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "AMTypes.generated.h" - -UENUM(BlueprintType) -enum class EAMSlot : uint8 -{ - Slot001 = 0, - Slot002 = 1, - Slot003 = 2, - Slot004 = 3, - Slot005 = 4, - Slot006 = 5, - Slot007 = 6, - Slot008 = 7, - Slot009 = 8, - Slot010 = 9, - Slot011 = 10, - Slot012 = 11, - Slot013 = 12, - Slot014 = 13, - Slot015 = 14, - Slot016 = 15, - Slot017 = 16, - Slot018 = 17, - Slot019 = 18, - Slot020 = 19, - Slot021 = 20, - Slot022 = 21, - Slot023 = 22, - Slot024 = 23, - Slot025 = 24, - Slot026 = 25, - Slot027 = 26, - Slot028 = 27, - Slot029 = 28, - Slot030 = 29, - Slot031 = 30, - Slot032 = 31, - MAX -}; - -UENUM(BlueprintType) -enum class EAMGroup : uint8 -{ - Group001 = 0, - Group002 = 1, - Group003 = 2, - Group004 = 3, - Group005 = 4, - Group006 = 5, - Group007 = 6, - Group008 = 7, - Group009 = 8, - Group010 = 9, - Group011 = 10, - Group012 = 11, - Group013 = 12, - Group014 = 13, - Group015 = 14, - Group016 = 15, - Group017 = 16, - Group018 = 17, - Group019 = 18, - Group020 = 19, - Group021 = 20, - Group022 = 21, - Group023 = 22, - Group024 = 23, - Group025 = 24, - Group026 = 25, - Group027 = 26, - Group028 = 27, - Group029 = 28, - Group030 = 29, - Group031 = 30, - Group032 = 31, - - MAX -}; - -template -int32 AMEnumToInt(T InVal) -{ - return static_cast(InVal); -} - -template -T AMIntToEnum(int32 InVal) -{ - return static_cast(InVal); -} \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp b/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp deleted file mode 100644 index 3f142ff..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "AbilityManager.h" - -#define LOCTEXT_NAMESPACE "FAbilityManagerModule" - -void FAbilityManagerModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FAbilityManagerModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FAbilityManagerModule, AbilityManager) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h b/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h deleted file mode 100644 index 677d67e..0000000 --- a/Plugins/AbilityManager/Source/AbilityManager/Public/AbilityManager.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FAbilityManagerModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs b/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs deleted file mode 100644 index abec3a8..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/AbilityManagerEditor.Build.cs +++ /dev/null @@ -1,52 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -using UnrealBuildTool; - -public class AbilityManagerEditor : ModuleRules -{ - public AbilityManagerEditor(ReadOnlyTargetRules Target) : base(Target) - { - PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - - PrivateIncludePaths.AddRange( - new string[] { - "AbilityManagerEditor/Private", - // ... add other private include paths required here ... - } - ); - - - PublicDependencyModuleNames.AddRange( - new string[] - { - "Core", - // ... add other public dependencies that you statically link with here ... - } - ); - - - PrivateDependencyModuleNames.AddRange( - new string[] - { - "CoreUObject", - "Engine", - "Slate", - "SlateCore", - "UnrealEd", - "PropertyEditor", - "GameplayTags", - "GameplayTasks", - "AbilityFramework", - "AbilityManager" - // ... add private dependencies that you statically link with here ... - } - ); - - DynamicallyLoadedModuleNames.AddRange( - new string[] - { - // ... add any modules that your module loads dynamically here ... - } - ); - } -} diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp deleted file mode 100644 index f87f7b0..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.cpp +++ /dev/null @@ -1,36 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "AMAbilityInputProperty.h" -#include "AbilityManagerEditor.h" -#include "IDetailsView.h" -#include "PropertyEditorModule.h" -#include "Editor/PropertyEditor/Public/PropertyEditing.h" -#include "Editor/PropertyEditor/Private/IDetailsViewPrivate.h" -#include "Editor/PropertyEditor/Private/SDetailsViewBase.h" -#include "Editor/PropertyEditor/Private/SDetailsView.h" -//D:\Unreal\UnrealEngine-Master\Engine\Source\Editor\PropertyEditor\Private\SDetailsView.h -#include "STextCombobox.h" -#include "STreeView.h" -#include "SButton.h" -#include "STextBlock.h" - -#include "EditorClassUtils.h" - - -TSharedRef FAMAbilityInputProperty::MakeInstance() -{ - return MakeShareable(new FAMAbilityInputProperty); -} - -FAMAbilityInputProperty::~FAMAbilityInputProperty() -{ - -} - -void FAMAbilityInputProperty::CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} -void FAMAbilityInputProperty::CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) -{ - -} diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h deleted file mode 100644 index c31729d..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AMAbilityInputProperty.h +++ /dev/null @@ -1,18 +0,0 @@ -// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#pragma once -#include "IPropertyTypeCustomization.h" -#include "PropertyHandle.h" - -class FAMAbilityInputProperty : public IPropertyTypeCustomization -{ -public: - static TSharedRef MakeInstance(); - /** - * Destructor - */ - virtual ~FAMAbilityInputProperty(); - - /** IPropertyTypeCustomization interface */ - virtual void CustomizeHeader(TSharedRef InStructPropertyHandle, FDetailWidgetRow& HeaderRow, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; - virtual void CustomizeChildren(TSharedRef InStructPropertyHandle, IDetailChildrenBuilder& StructBuilder, IPropertyTypeCustomizationUtils& StructCustomizationUtils) override; -}; \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp deleted file mode 100644 index 06b8d0e..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#include "AbilityManagerEditor.h" - -#define LOCTEXT_NAMESPACE "FAbilityManagerEditor" - -void FAbilityManagerEditorModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FAbilityManagerEditorModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FAbilityManagerEditorModule, AbilityManagerEditor) \ No newline at end of file diff --git a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h b/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h deleted file mode 100644 index 0879ce8..0000000 --- a/Plugins/AbilityManager/Source/AbilityManagerEditor/Public/AbilityManagerEditor.h +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. - -#pragma once - -#include "CoreMinimal.h" -#include "ModuleManager.h" - -class FAbilityManagerEditorModule : public IModuleInterface -{ -public: - - /** IModuleInterface implementation */ - virtual void StartupModule() override; - virtual void ShutdownModule() override; -}; \ No newline at end of file diff --git a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h index 86a3610..f16fb4a 100644 --- a/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h +++ b/Plugins/InventoryFramework/Source/InventoryFramework/Public/IFEquipmentComponent.h @@ -51,7 +51,14 @@ class INVENTORYFRAMEWORK_API UIFEquipmentComponent : public UActorComponent template T* GetItem(uint8 InLocalIndex) { - return Cast(EquipmentItems[InLocalIndex].Item); + if (EquipmentItems.IsValidIndex(InLocalIndex)) + { + return Cast(EquipmentItems[InLocalIndex].Item); + } + else + { + return nullptr; + } //return Cast(Inventory.Items[InLocalIndex].Item); } diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp deleted file mode 100644 index 68006cf..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/AnimNode_BlendLocomotionFour.cpp +++ /dev/null @@ -1,548 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#include "AnimNode_BlendLocomotionFour.h" -#include "AnimationRuntime.h" -#include "GameFramework/CharacterMovementComponent.h" -#include "GameFramework/Character.h" -#include "Animation/AnimClassInterface.h" -#include "Animation/AnimInstanceProxy.h" -#include "Animation/BlendProfile.h" -#include "DrawDebugHelpers.h" - -#include "Engine.h" -///////////////////////////////////////////////////// -// FAnimNode_BlendLocomotionFour -FString FDirToString(EFCardinalDirection Dir) -{ - switch (Dir) - { - case EFCardinalDirection::N: - return "N"; - case EFCardinalDirection::E: - return "E"; - case EFCardinalDirection::S: - return "S"; - case EFCardinalDirection::W: - return "W"; - default: - break; - } - return "Invalid"; -} -void FAnimNode_BlendLocomotionFour::Initialize_AnyThread(const FAnimationInitializeContext& Context) -{ - FAnimNode_Base::Initialize_AnyThread(Context); - - UAnimInstance* AnimInst = Cast(Context.AnimInstanceProxy->GetAnimInstanceObject()); - Character = Cast(AnimInst->TryGetPawnOwner()); - if (!Character) - return; - - CMC = Character->GetCharacterMovement(); - - if (!CMC) - return; - - const int NumPoses = BlendPose.Num(); - checkSlow(BlendTime.Num() == NumPoses); - - BlendWeights.Reset(NumPoses); - PosesToEvaluate.Reset(NumPoses); - if (NumPoses > 0) - { - // If we have at least 1 pose we initialize to full weight on - // the first pose - BlendWeights.AddZeroed(NumPoses); - BlendWeights[0] = 1.0f; - - PosesToEvaluate.Add(0); - - for (int32 ChildIndex = 0; ChildIndex < NumPoses; ++ChildIndex) - { - BlendPose[ChildIndex].Initialize(Context); - } - } - - RemainingBlendTimes.Empty(NumPoses); - RemainingBlendTimes.AddZeroed(NumPoses); - Blends.Empty(NumPoses); - Blends.AddZeroed(NumPoses); - - LastActiveChildIndex = INDEX_NONE; - - for (int32 i = 0; i < Blends.Num(); ++i) - { - FAlphaBlend& Blend = Blends[i]; - - Blend.SetBlendTime(0.0f); - Blend.SetBlendOption(BlendType); - Blend.SetCustomCurve(CustomBlendCurve); - } - Blends[0].SetAlpha(1.0f); - - if (BlendProfile) - { - // Initialise per-bone data - PerBoneSampleData.Empty(NumPoses); - PerBoneSampleData.AddZeroed(NumPoses); - - for (int32 Idx = 0; Idx < NumPoses; ++Idx) - { - FBlendSampleData& SampleData = PerBoneSampleData[Idx]; - SampleData.SampleDataIndex = Idx; - SampleData.PerBoneBlendData.AddZeroed(BlendProfile->GetNumBlendEntries()); - } - } -} - -void FAnimNode_BlendLocomotionFour::CacheBones_AnyThread(const FAnimationCacheBonesContext& Context) -{ - for (int32 ChildIndex = 0; ChildIndexGetActorRightVector(); - FVector Forward = Character->GetActorForwardVector(); - - FTransform Transform = Character->GetTransform(); - FVector CurrentAcceleration = CMC->GetCurrentAcceleration(); - FVector CurrentVelocity = CMC->Velocity; - - FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal2D(); - FVector VelocityDirection = CurrentVelocity.GetSafeNormal2D(); - - FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); - FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); - - float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); - int32 LocalDir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; - DotBlendTime = FMath::Abs(FVector::DotProduct(LocalVelocity, LocalAcceleration)); - BlendTime[0] = DotBlendTime; - BlendTime[1] = DotBlendTime; - BlendTime[2] = DotBlendTime; - BlendTime[3] = DotBlendTime; - - NDot = FMath::RoundToInt(FVector::DotProduct(Forward, VelocityDirection)); - EDot = FMath::RoundToInt(FVector::DotProduct(Right, VelocityDirection)); - - const int NumPoses = BlendPose.Num(); - checkSlow((BlendTime.Num() == NumPoses) && (BlendWeights.Num() == NumPoses)); - - PosesToEvaluate.Empty(NumPoses); - - if (NumPoses > 0) - { - // Handle a change in the active child index; adjusting the target weights - const int32 ChildIndex = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4;; - - if (ChildIndex != LastActiveChildIndex) - { - bool LastChildIndexIsInvalid = (LastActiveChildIndex == INDEX_NONE); - - const float CurrentWeight = BlendWeights[ChildIndex]; - const float DesiredWeight = 1.0f; - const float WeightDifference = FMath::Clamp(FMath::Abs(DesiredWeight - CurrentWeight), 0.0f, 1.0f); - - // scale by the weight difference since we want always consistency: - // - if you're moving from 0 to full weight 1, it will use the normal blend time - // - if you're moving from 0.5 to full weight 1, it will get there in half the time - const float LocalRemainingBlendTime = LastChildIndexIsInvalid ? 0.0f : (BlendTime[ChildIndex] * WeightDifference); - - for (int32 i = 0; i < RemainingBlendTimes.Num(); ++i) - { - RemainingBlendTimes[i] = LocalRemainingBlendTime; - } - - // If we have a valid previous child and we're instantly blending - update that pose with zero weight - if (LocalRemainingBlendTime == 0.0f && !LastChildIndexIsInvalid) - { - BlendPose[LastActiveChildIndex].Update(Context.FractionalWeight(0.0f)); - } - - for (int32 i = 0; i < Blends.Num(); ++i) - { - FAlphaBlend& Blend = Blends[i]; - - Blend.SetBlendTime(LocalRemainingBlendTime); - - if (i == ChildIndex) - { - Blend.SetValueRange(BlendWeights[i], 1.0f); - } - else - { - Blend.SetValueRange(BlendWeights[i], 0.0f); - } - } - - // when this flag is true, we'll reinitialize the children - if (bResetChildOnActivation) - { - FAnimationInitializeContext ReinitializeContext(Context.AnimInstanceProxy); - - // reinitialize - BlendPose[ChildIndex].Initialize(ReinitializeContext); - } - - LastActiveChildIndex = ChildIndex; - } - - // Advance the weights - //@TODO: This means we advance even in a frame where the target weights/times just got modified; is that desirable? - float SumWeight = 0.0f; - for (int32 i = 0; i < Blends.Num(); ++i) - { - float& BlendWeight = BlendWeights[i]; - - FAlphaBlend& Blend = Blends[i]; - Blend.Update(Context.GetDeltaTime()); - BlendWeight = Blend.GetBlendedValue(); - - SumWeight += BlendWeight; - } - - // Renormalize the weights - if ((SumWeight > ZERO_ANIMWEIGHT_THRESH) && (FMath::Abs(SumWeight - 1.0f) > ZERO_ANIMWEIGHT_THRESH)) - { - float ReciprocalSum = 1.0f / SumWeight; - for (int32 i = 0; i < BlendWeights.Num(); ++i) - { - BlendWeights[i] *= ReciprocalSum; - } - } - - // Update our active children - for (int32 i = 0; i < BlendPose.Num(); ++i) - { - const float BlendWeight = BlendWeights[i]; - if (BlendWeight > ZERO_ANIMWEIGHT_THRESH) - { - BlendPose[i].Update(Context.FractionalWeight(BlendWeight)); - PosesToEvaluate.Add(i); - } - } - - // If we're using a blend profile, extract the scales and build blend sample data - if (BlendProfile) - { - for (int32 i = 0; i < BlendPose.Num(); ++i) - { - // Update Per-Bone Info - const float BlendWeight = BlendWeights[i]; - FBlendSampleData& PoseSampleData = PerBoneSampleData[i]; - PoseSampleData.TotalWeight = BlendWeight; - - for (int32 j = 0; j < PoseSampleData.PerBoneBlendData.Num(); ++j) - { - float& BoneBlend = PoseSampleData.PerBoneBlendData[j]; - float WeightScale = BlendProfile->GetEntryBlendScale(j); - - if (ChildIndex != i) - { - WeightScale = 1.0f / WeightScale; - } - - BoneBlend = BlendWeight * WeightScale; - } - } - - FBlendSampleData::NormalizeDataWeight(PerBoneSampleData); - } - } - - - switch (static_cast(LocalDir)) - { - case EFCardinalDirection::N: - { - FQuat ForwardQuat = FQuat::FindBetween(Forward, CurrentVelocity); - OrientN = FRotator(ForwardQuat).Yaw; - CurrentOrient = OrientN;// - //if (NDot == EDot) - /*{ - NorthPose.Update(Context.FractionalWeight(DotBlendTime)); - EastPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); - }*/ - /*else - { - NorthPose.Update(Context); - }*/ - - break; - } - case EFCardinalDirection::E: - { - FQuat LeftQuat = FQuat::FindBetween(Right, CurrentVelocity); - OrientE = FRotator(LeftQuat).Yaw; - CurrentOrient = OrientE; - //if (NDot == EDot) - /*{ - NorthPose.Update(Context.FractionalWeight(1.0f - DotBlendTime)); - EastPose.Update(Context.FractionalWeight(DotBlendTime)); - }*/ - /*else - { - EastPose.Update(Context); - }*/ - - // FMath::FInterpConstantTo(OldOrient, OrientE, DeltaTime, 300.0f); - break; - } - case EFCardinalDirection::S: - { - FQuat BackQuat = FQuat::FindBetween(Forward*(-1), CurrentVelocity); - OrientS = FRotator(BackQuat).Yaw; - CurrentOrient = OrientS; - break; - } - case EFCardinalDirection::W: - { - FQuat RightQuat = FQuat::FindBetween(Right*(-1), CurrentVelocity); - OrientW = FRotator(RightQuat).Yaw; - CurrentOrient = OrientW;// FMath::FInterpConstantTo(OldOrient, OrientW, DeltaTime, 300.0f); - break; - } - default: - break; - } - -} - -void FAnimNode_BlendLocomotionFour::Evaluate_AnyThread(FPoseContext& Output) -{ - ANIM_MT_SCOPE_CYCLE_COUNTER(BlendPosesInGraph, !IsInGameThread()); - { - //BlendPose[CurrentPose].Evaluate(Output); - } - const int32 NumPoses = PosesToEvaluate.Num(); - if ((NDot == EDot) && (NumPoses > 0) && (BlendPose.Num() == BlendWeights.Num())) - { - // Scratch arrays for evaluation, stack allocated - TArray> FilteredPoses; - TArray> FilteredCurve; - FilteredPoses.SetNum(NumPoses, false); - FilteredCurve.SetNum(NumPoses, false); - - int32 NumActivePoses = 0; - for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) - { - int32 PoseIndex = PosesToEvaluate[i]; - - FPoseContext EvaluateContext(Output); - - FPoseLink& LocalCurrentPose = BlendPose[PoseIndex]; - LocalCurrentPose.Evaluate(EvaluateContext); - - FilteredPoses[i].CopyBonesFrom(EvaluateContext.Pose); - FilteredCurve[i] = EvaluateContext.Curve; - } - - // Use the calculated blend sample data if we're blending per-bone - if (BlendProfile) - { - FAnimationRuntime::BlendPosesTogetherPerBone(FilteredPoses, FilteredCurve, BlendProfile, PerBoneSampleData, PosesToEvaluate, Output.Pose, Output.Curve); - } - else - { - FAnimationRuntime::BlendPosesTogether(FilteredPoses, FilteredCurve, BlendWeights, PosesToEvaluate, Output.Pose, Output.Curve); - } - - } - else - { - for (int32 i = 0; i < PosesToEvaluate.Num(); ++i) - { - int32 PoseIndex = PosesToEvaluate[i]; - - FPoseLink& LocalCurrentPose = BlendPose[PoseIndex]; - LocalCurrentPose.Evaluate(Output); - - } - //Output.ResetToRefPose(); - } - - //FPoseContext EvaluateContext(Output); - //const FBoneContainer& BoneContainer = Output.AnimInstanceProxy->GetRequiredBones(); - //FComponentSpacePoseContext CSOutput(Output.AnimInstanceProxy); - //EFCardinalDirection ghf = Cast(Character)->GetCardianlDirection(); - //switch (Dir) - //{ - //case EFCardinalDirection::N: - //{ - // //if (OldDirection != Dir) - // { - // //if (NDot == EDot) - // { - // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); - - // FPoseContext Pose1(Output); - // FPoseContext Pose2(Output); - - // NorthPose.Evaluate(Pose1); - // EastPose.Evaluate(Pose2); - // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); - // - // } - // /*else - // { - // NorthPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); - // }*/ - // } - // /*else - // { - // NorthPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientN); - // }*/ - // break; - //} - //case EFCardinalDirection::E: - //{ - // - // //if (OldDirection != Dir) - // { - // //if (NDot == EDot) - // { - // //Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); - - // FPoseContext Pose1(Output); - // FPoseContext Pose2(Output); - - // NorthPose.Evaluate(Pose2); - // EastPose.Evaluate(Pose1); - // - // FAnimationRuntime::BlendTwoPosesTogether(Pose1.Pose, Pose2.Pose, Pose1.Curve, Pose2.Curve, (DotBlendTime), Output.Pose, Output.Curve); - // - // - // } - // /*else - // { - // EastPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); - // }*/ - - // } - // /*else - // { - // EastPose.Evaluate(Output); - // Reorient(Output.Pose, CSOutput, BoneContainer, OrientE); - // }*/ - // break; - //} - //case EFCardinalDirection::S: - //{ - // break; - //} - //case EFCardinalDirection::W: - //{ - // break; - //} - //{ - //default: - // break; - //} - //} - -} - -void FAnimNode_BlendLocomotionFour::GatherDebugData(FNodeDebugData& DebugData) -{ - //const int32 ChildIndex = GetActiveChildIndex(); - - //FString DebugLine = GetNodeName(DebugData); - //DebugLine += FString::Printf(TEXT("(BlendTime: %f "), DotBlendTime); - - //DebugData.AddDebugItem(DebugLine); - - //NorthPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); - //EastPose.GatherDebugData(DebugData.BranchFlow(DotBlendTime)); -} - - -void FAnimNode_BlendLocomotionFour::Reorient(FCompactPose& CompactPose, FComponentSpacePoseContext& CSOutput, const FBoneContainer& BoneContainer, float Orient) -{ - if (!FMath::IsNearlyZero(Orient, KINDA_SMALL_NUMBER)) - { - const FRotator DeltaRotation(0.0f, Orient, 0.f); - const FQuat DeltaQuat(DeltaRotation); - const FQuat MeshToComponentQuat(FRotator::ZeroRotator); - - // Convert our rotation from Component Space to Mesh Space. - const FQuat MeshSpaceDeltaQuat = MeshToComponentQuat.Inverse() * DeltaQuat * MeshToComponentQuat; - - // Apply rotation to root bone. - FCompactPoseBoneIndex RootBoneIndex(0); - CompactPose[RootBoneIndex].SetRotation(CompactPose[RootBoneIndex].GetRotation() * DeltaQuat); - CompactPose[RootBoneIndex].NormalizeRotation(); - } - // if (IKFootRootBone.IsValidToEvaluate(BoneContainer)) - // { - // // Prepare convert Quat and BoneContainer. - // const FQuat MeshToComponentQuat(FRotator(0.f, 0.f, 0.f)); - - // CSOutput.Pose.InitPose(CompactPose); - - // //Build our desired rotation for IK root bone. - // FRotator DeltaRotation(0.0f, 0.0f, 0.f); - // switch (Settings.YawRotationAxis) - // { - // case EAxis::X: - // DeltaRotation.Roll = Orient; - // case EAxis::Y: - // DeltaRotation.Pitch = Orient; - // case EAxis::Z: - // DeltaRotation.Yaw = Orient; - // default: - // break; - // } - // const FQuat DeltaQuat(DeltaRotation); - // // Convert our rotation from Component Space to Mesh Space. - // const FQuat MeshSpaceDeltaQuat = DeltaQuat; - // // Apply rotation to IK root bone. - // FCompactPoseBoneIndex RotateBoneIndex = IKFootRootBone.GetCompactPoseIndex(BoneContainer); - // CompactPose[RotateBoneIndex].SetRotation(CompactPose[RotateBoneIndex].GetRotation() * MeshSpaceDeltaQuat); - // CompactPose[RotateBoneIndex].NormalizeRotation(); - - - // // Do the same things like IK foot root bone to pelvis, but in the reversed orientation. - // FCompactPoseBoneIndex PelvisBoneIndex(1); - // FTransform PelvisBoneTM = CSOutput.Pose.GetComponentSpaceTransform(PelvisBoneIndex); - - // const FRotator PelvisDeltaRotation(DeltaRotation.Pitch * Settings.BodyOrientationAlpha, DeltaRotation.Yaw * Settings.BodyOrientationAlpha, DeltaRotation.Roll * Settings.BodyOrientationAlpha); - // FQuat PelvisDeltaQuat(PelvisDeltaRotation); - - // //const FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse() *PelvisDeltaQuat * PelvisBoneTM.GetRotation(); - // FQuat MeshSpacePelvisDeltaQuat = PelvisBoneTM.GetRotation().Inverse()*PelvisDeltaQuat * PelvisBoneTM.GetRotation(); - - // CompactPose[PelvisBoneIndex].ConcatenateRotation(MeshSpacePelvisDeltaQuat); - // CompactPose[PelvisBoneIndex].NormalizeRotation(); - - // // Apply rotation to spine - // if (SpineBones.Num()) - // { - // for (int32 j = 0; j < SpineBones.Num(); j++) - // { - // if (SpineBones[j].Bone.IsValidToEvaluate(BoneContainer)) - // { - // FCompactPoseBoneIndex SpineBoneIndex = SpineBones[j].Bone.GetCompactPoseIndex(BoneContainer); - // FTransform SpineBoneTM = CSOutput.Pose.GetComponentSpaceTransform(SpineBoneIndex); - // const FRotator SpineDeltaRotation((-PelvisDeltaRotation.Pitch / SpineBones.Num()), (-PelvisDeltaRotation.Yaw / SpineBones.Num()), (-PelvisDeltaRotation.Roll / SpineBones.Num())); - // const FQuat SpineDeltaQuat(SpineDeltaRotation); - // const FQuat MeshSpaceSpineDeltaQuat = SpineBoneTM.GetRotation().Inverse() * SpineDeltaQuat * SpineBoneTM.GetRotation(); - // CompactPose[SpineBoneIndex].ConcatenateRotation(MeshSpaceSpineDeltaQuat); - // CompactPose[SpineBoneIndex].NormalizeRotation(); - // //GEngine->AddOnScreenDebugMessage(-1, DeltaTime, FColor::Yellow, (FString::Printf(TEXT(" SpineDeltaQuat: %s, MeshSpaceSpineDeltaQuat: %s PelvisDeltaQuat: %s"), *SpineDeltaQuat.ToString(), *MeshSpaceSpineDeltaQuat.ToString(), *PelvisDeltaQuat.ToString()))); - // } - // } - // } - // } - //} -} diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp deleted file mode 100644 index 1cf28be..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.cpp +++ /dev/null @@ -1,34 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "OrionAnimComponent.h" - - -// Sets default values for this component's properties -UOrionAnimComponent::UOrionAnimComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - - // ... -} - - -// Called when the game starts -void UOrionAnimComponent::BeginPlay() -{ - Super::BeginPlay(); - - // ... - -} - - -// Called every frame -void UOrionAnimComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} - diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h index 93b3c69..16e0c65 100644 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h +++ b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimComponent.h @@ -4,6 +4,9 @@ #include "CoreMinimal.h" #include "Components/ActorComponent.h" + +#include "OrionTypes.h" + #include "OrionAnimComponent.generated.h" @@ -11,6 +14,11 @@ UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ORIONANIMATION_API UOrionAnimComponent : public UActorComponent { GENERATED_BODY() +protected: + EOrionCardinalDirection CardinalDirection; + + UPROPERTY() + class ACharacter* CharacterOwner; public: // Sets default values for this component's properties @@ -24,6 +32,7 @@ class ORIONANIMATION_API UOrionAnimComponent : public UActorComponent // Called every frame virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - + void InitializeAnim(ACharacter* InCharacter); + + void CalculateCardinalDirection(); }; diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp deleted file mode 100644 index 835b245..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionAnimation.cpp +++ /dev/null @@ -1,20 +0,0 @@ -// Copyright 1998-2018 Epic Games, Inc. All Rights Reserved. - -#include "OrionAnimation.h" - -#define LOCTEXT_NAMESPACE "FOrionAnimationModule" - -void FOrionAnimationModule::StartupModule() -{ - // This code will execute after your module is loaded into memory; the exact timing is specified in the .uplugin file per-module -} - -void FOrionAnimationModule::ShutdownModule() -{ - // This function may be called during shutdown to clean up your module. For modules that support dynamic reloading, - // we call this function before unloading the module. -} - -#undef LOCTEXT_NAMESPACE - -IMPLEMENT_MODULE(FOrionAnimationModule, OrionAnimation) \ No newline at end of file diff --git a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp b/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp deleted file mode 100644 index da8cfef..0000000 --- a/Plugins/OrionAnimation/Source/OrionAnimation/Public/OrionInterface.cpp +++ /dev/null @@ -1,6 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "OrionInterface.h" - - -// Add default functionality here for any IOrionInterface functions that are not pure virtual. diff --git a/Plugins/uFire/Source/uFire/uFire.Build.cs b/Plugins/uFire/Source/uFire/uFire.Build.cs index 544ed10..fba39a0 100644 --- a/Plugins/uFire/Source/uFire/uFire.Build.cs +++ b/Plugins/uFire/Source/uFire/uFire.Build.cs @@ -8,12 +8,7 @@ public uFire(ReadOnlyTargetRules Target) : base(Target) { PCHUsage = ModuleRules.PCHUsageMode.UseExplicitOrSharedPCHs; - PublicIncludePaths.AddRange( - new string[] { - "uFire/Public" - // ... add public include paths required here ... - } - ); + //PublicIncludePaths.AddRange(); PrivateIncludePaths.AddRange( diff --git a/Source/ActionRPGGame/ActionRPGGame.Build.cs b/Source/ActionRPGGame/ActionRPGGame.Build.cs index b80eea2..7df1898 100644 --- a/Source/ActionRPGGame/ActionRPGGame.Build.cs +++ b/Source/ActionRPGGame/ActionRPGGame.Build.cs @@ -27,11 +27,9 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) "AssetRegistry", "OrionAnimation", "ActorSequence", - "AbilityManager", "JsonUObject", "InventoryFramework", - "OnlineSubsystem", - "OnlineSubsystemGameSparks" + "OnlineSubsystem" }); if (Target.Type == TargetRules.TargetType.Editor) @@ -79,12 +77,6 @@ public ActionRPGGame(ReadOnlyTargetRules Target) : base(Target) bEnableExceptions = true; } } - else - { - } - } - else - { } } } diff --git a/Source/ActionRPGGame/Private/ARCharacter.cpp b/Source/ActionRPGGame/Private/ARCharacter.cpp index 275cc9e..e2fb0fa 100644 --- a/Source/ActionRPGGame/Private/ARCharacter.cpp +++ b/Source/ActionRPGGame/Private/ARCharacter.cpp @@ -33,7 +33,6 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) // set our turn rates for input BaseTurnRate = 5.f; BaseLookUpRate = 25.f; - bStopDistancePredicted = false; // Don't rotate when the controller rotates. Let that just affect the camera. bUseControllerRotationPitch = false; bUseControllerRotationYaw = false; @@ -54,7 +53,9 @@ AARCharacter::AARCharacter(const FObjectInitializer& ObjectInitializer) GetCharacterMovement()->MaxWalkSpeed = 270.0f; GetCharacterMovement()->MaxWalkSpeedCrouched = 150.0f; GetCharacterMovement()->BrakingDecelerationWalking = 150.0f; - + + OrionAnimComp = CreateDefaultSubobject(TEXT("OrionAnimComp")); + // Create a camera boom (pulls in towards the player if there is a collision) CameraBoom = CreateDefaultSubobject(TEXT("CameraBoom")); //CameraBoom->SetupAttachment(GetMesh()); @@ -190,245 +191,9 @@ void AARCharacter::BeginPlay() WeaponInventory->InitializeWeapons(this); } -FString DirToString(EFourCardinalDirection dir) -{ - switch (dir) - { - case EFourCardinalDirection::N: - return "N"; - case EFourCardinalDirection::E: - return "E"; - case EFourCardinalDirection::S: - return "S"; - case EFourCardinalDirection::W: - return "W"; - default: - break; - } - return "Invalid"; -} - -float AARCharacter::GetAnimOrient() -{ - return CurrentOrient; -} -float AARCharacter::GetAnimOrientN() { return OrientN; }; -float AARCharacter::GetAnimOrientE() { return OrientE; }; -float AARCharacter::GetAnimOrientS() { return OrientS; }; -float AARCharacter::GetAnimOrientW() { return OrientW; }; - -EFCardinalDirection AARCharacter::GetCardianlDirection() -{ - int32 dir = static_cast(FourDirections); - - return static_cast(dir); -} void AARCharacter::Tick(float DeltaSeconds) { Super::Tick(DeltaSeconds); - - UCharacterMovementComponent* CMC = GetCharacterMovement(); - - if (!CMC) - return; - FVector CharLocation = GetActorLocation(); - - FVector CurrentAcceleration = CMC->GetCurrentAcceleration(); - FVector CurrentVelocity = CMC->Velocity; - - FVector AccelerationDirection = CurrentAcceleration.GetSafeNormal(); - FVector LineEnd = (AccelerationDirection * 80.0f) + GetActorLocation(); - - //::DrawDebugLine(GetWorld(), GetActorLocation(), LineEnd, FColor::Red, false, -1.0f, 0, 10); - - FVector VelocityDirection = CurrentVelocity.GetSafeNormal(); - - float Vel = (CurrentVelocity.Size() / CMC->GetMaxSpeed()) * 100; - - FVector VelocityEnd = (VelocityDirection * Vel) + GetActorLocation(); - - //::DrawDebugLine(GetWorld(), GetActorLocation()+FVector(0,0,10), VelocityEnd + FVector(0, 0, 10), FColor::Blue, false, -1.0f, 0, 10); - - FTransform Transform = GetTransform(); - FVector LocalAcceleration = Transform.InverseTransformVectorNoScale(AccelerationDirection); - FVector LocalVelocity = Transform.InverseTransformVectorNoScale(VelocityDirection); - - FQuat QRot = LocalAcceleration.ToOrientationQuat(); - FRotator Rot = FRotator(QRot); - float Angle = Rot.Yaw;// FMath::RadiansToDegrees(FMath::Atan2(LocalVelocity.Y, LocalVelocity.X)); - float Angle2 = (FMath::RoundToInt(Angle) + 360) % 360; - FVector Right = GetActorRightVector(); - FVector Forward = GetActorForwardVector(); - - - FQuat QAngle = FQuat::FindBetweenNormals(Forward, LocalVelocity); - - FRotator RAngle(QAngle); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 145), "RAngle: " + FString::FormatAsNumber(RAngle.Yaw), nullptr, FColor::Red, 0, true); - - - FVector V1 = (Forward + Right).GetSafeNormal2D(); - FVector V2 = (Forward + (Right * (-1))).GetSafeNormal2D(); - - - int32 Octant = FMath::RoundToInt((Angle2)) % 8; - EigthDirections = static_cast(Octant); - float Atan2Angle = FMath::Atan2(LocalVelocity.Y, LocalVelocity.X); - int32 Dir = FMath::RoundToInt((Atan2Angle * 2 / PI) + 4) % 4; - - EFourCardinalDirection NewDir = static_cast(Dir); - - - switch (EigthDirections) - { - case EEightCardinalDirection::S: - break; - case EEightCardinalDirection::NE: - break; - case EEightCardinalDirection::W: - break; - case EEightCardinalDirection::SE: - break; - case EEightCardinalDirection::N: - break; - case EEightCardinalDirection::SW: - break; - case EEightCardinalDirection::E: - break; - case EEightCardinalDirection::NW: - { - /*if(OldFourDirections == EFourCardinalDirection::W) - NewDir = EFourCardinalDirection::N;*/ - break; - } - default: - break; - } - - if (NewDir != FourDirections) - { - OldFourDirections = FourDirections; - } - FourDirections = NewDir; - - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 135), "OldFourDirections: " + DirToString(OldFourDirections), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 140), "FourDirections: " + DirToString(FourDirections), nullptr, FColor::Red, 0, true); - - float VelAccelDot = FVector::DotProduct(LocalVelocity, LocalAcceleration); - int32 intDot = FMath::RoundToInt(VelAccelDot); - OrientationDOT = VelAccelDot; - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 150), "VelAccelDot: " + FString::FormatAsNumber(intDot), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 155), "FVelAccelDot: " + FString::Printf(TEXT("%f"), VelAccelDot), nullptr, FColor::Red, 0, true); - - - float TargetForward = FVector::DotProduct(CurrentVelocity, Forward); - ForwardDirection = FMath::FInterpConstantTo(ForwardDirection, TargetForward, DeltaSeconds, 100.0f); - - float LateralForward = FVector::DotProduct(CurrentVelocity, Right); - LateralDirection = FMath::FInterpConstantTo(LateralDirection, LateralForward, DeltaSeconds, 100.0f); - - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 165), "ForwardDirection: " + FString::Printf(TEXT("%f"), ForwardDirection), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 170), "LateralDirection: " + FString::Printf(TEXT("%f"), LateralDirection), nullptr, FColor::Red, 0, true); - - FString SVelocity = "V: " + FString::Printf(TEXT("%d"), FMath::RoundToInt(CurrentVelocity.Size())) + " LV: " + FString::Printf(TEXT("%f"), LocalVelocity.Size()); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 90), SVelocity, nullptr, FColor::Red, 0, true); - - FString SAcceleration = "A: " + FString::Printf(TEXT("%d"), FMath::RoundToInt(CurrentAcceleration.Size())) + " LA: " + FString::Printf(TEXT("%f"), LocalAcceleration.Size()); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 95), SAcceleration, nullptr, FColor::Red, 0, true); - - FVector LocalVel = Transform.InverseTransformVector(CurrentVelocity); - - OldOrient = CurrentOrient; - FQuat VelQuat = LocalVelocity.ToOrientationQuat(); - //FRotator VelRot = VelQuat.GetAngle(); - float VelAngle = FMath::RadiansToDegrees(VelQuat.GetAngle()); - switch (FourDirections) - { - case EFourCardinalDirection::E: - { - FQuat LeftQuat = FQuat::FindBetween(Right, CurrentVelocity); - OrientE = FRotator(LeftQuat).Yaw; - CurrentOrient = OrientE; - - break; - } - case EFourCardinalDirection::N: - { - FQuat ForwardQuat = FQuat::FindBetween(Forward, CurrentVelocity); - OrientN = FRotator(ForwardQuat).Yaw; - float sign = FMath::Sign(OldOrient); - CurrentOrient = OrientN; - break; - } - case EFourCardinalDirection::W: - { - FQuat RightQuat = FQuat::FindBetween(Right*(-1), CurrentVelocity); - OrientW = FRotator(RightQuat).Yaw; - CurrentOrient = OrientW; - break; - } - case EFourCardinalDirection::S: - { - FQuat BackQuat = FQuat::FindBetween(Forward*(-1), CurrentVelocity); - OrientS = FRotator(BackQuat).Yaw; - - CurrentOrient = OrientW; - break; - } - default: - break; - } - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 105), "OrientN: " + FString::FormatAsNumber(OrientN) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 110), "OrientS: " + FString::FormatAsNumber(OrientS) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct((-1)*Forward, VelocityDirection)), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 115), "OrientE: " + FString::FormatAsNumber(OrientE) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right, VelocityDirection)), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 120), "OrientW: " + FString::FormatAsNumber(OrientW) + FString::Printf(TEXT(" DOT: %f"), FVector::DotProduct(Right*(-1), VelocityDirection)), nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 125), "CurrentOrient: " + FString::FormatAsNumber(CurrentOrient), nullptr, FColor::Red, 0, true); - -// FMath::RadiansToDegrees(FMath::Atan2(LocalVelocity.Y, LocalVelocity.X)); - float VelAngle2 = (FMath::RoundToInt(VelAngle) + 360) / 360; - - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 130), "VelAngle2: " + FString::FormatAsNumber(VelAngle2), nullptr, FColor::Red, 0, true); - - float DeltaVelocity = CurrentVelocity.Size()* DeltaSeconds; - if (!CurrentAcceleration.IsZero()) - { - bStopDistancePredicted = false; - } - if (CurrentAcceleration.Size() <= 0 - && CurrentVelocity.Size() < CMC->MaxWalkSpeed*0.75) - { - bStartedLocomotion = false; - } - - if (CurrentAcceleration.Size() > 0 - && CurrentVelocity.Size() > 0) - { - bStartedLocomotion = true; - } - - FVector FinalDestination = (AccelerationDirection * 400) + CharLocation; - float AccelSpeed = CurrentAcceleration.Size(); - if (!bStopDistancePredicted && CurrentAcceleration.IsZero()) - { - bStopDistancePredicted = true; - float CurVel = CurrentVelocity.SizeSquared(); - float StopDistance = (CurVel / (4*CMC->GroundFriction *CMC->BrakingFrictionFactor * CMC->BrakingDecelerationWalking)); - FVector Forward2 = VelocityDirection; - FVector StopLocation = (Forward2*StopDistance) + CharLocation; - //DrawDebugSphere(GetWorld(), StopLocation, 6, 8, FColor::Green, false, 2, 0, 2); - } - - //DrawDebugSphere(GetWorld(), FinalDestination, 6, 8, FColor::Red, false, -1, 0, 2); - float Offset = 20; - for (float Idx = 1; Idx < 20; Idx++) - { - FVector BetweenDestination = (AccelerationDirection * Offset) + CharLocation; - Offset += 20; - //DrawDebugSphere(GetWorld(), BetweenDestination, 6, 8, FColor::Red, false, -1, 0, 2); - } - FString SAngle = FString("Angle: ") + FString::FormatAsNumber(Angle2); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 80), SAngle, nullptr, FColor::Red, 0, true); - //DrawDebugString(GetWorld(), GetActorLocation() + FVector(0, 0, 60), "4: Fourtant : " + FString::FormatAsNumber(Fourtant), nullptr, FColor::Red, 0, true); } ////////////////////////////////////////////////////////////////////////// // Input @@ -451,7 +216,7 @@ void AARCharacter::SetupPlayerInputComponent(class UInputComponent* PlayerInputC PlayerInputComponent->BindAxis("LookUp", this, &APawn::AddControllerPitchInput); PlayerInputComponent->BindAxis("LookUpRate", this, &AARCharacter::LookUpAtRate); - Abilities->BindInputs(PlayerInputComponent); + Abilities->BindInputs(PlayerInputComponent, "AbilityInput"); } diff --git a/Source/ActionRPGGame/Private/ARCharacterMovementComponent.cpp b/Source/ActionRPGGame/Private/ARCharacterMovementComponent.cpp index f07a2ee..d812da6 100644 --- a/Source/ActionRPGGame/Private/ARCharacterMovementComponent.cpp +++ b/Source/ActionRPGGame/Private/ARCharacterMovementComponent.cpp @@ -3,5 +3,3 @@ #include "ARCharacterMovementComponent.h" - - diff --git a/Source/ActionRPGGame/Private/ARPlayerController.cpp b/Source/ActionRPGGame/Private/ARPlayerController.cpp index 3788048..6466968 100644 --- a/Source/ActionRPGGame/Private/ARPlayerController.cpp +++ b/Source/ActionRPGGame/Private/ARPlayerController.cpp @@ -11,7 +11,6 @@ #include "Engine/LocalPlayer.h" #include "Components/CapsuleComponent.h" -#include "Abilities/ARAbilityManagerComponent.h" #include "UI/ARHUD.h" @@ -19,11 +18,9 @@ AARPlayerController::AARPlayerController(const FObjectInitializer& ObjectInitial : Super(ObjectInitializer) { UIComponent = ObjectInitializer.CreateDefaultSubobject(this, "UIComponent"); - AbilityManager = ObjectInitializer.CreateDefaultSubobject(this, "AbilityManager"); MainInventory = ObjectInitializer.CreateDefaultSubobject(this, "MainInventory"); MainInventory->SetIsReplicated(true); - AbilityManager->ComponentTags.Add(TEXT("AbilityManager")); bInputBount = false; } void AARPlayerController::BeginPlay() @@ -44,36 +41,26 @@ void AARPlayerController::BeginPlay() if (!bInputBount) { - AbilityComp->BindAbilityToAction(InputComponent, InputNextWeapon); - AbilityComp->BindAbilityToAction(InputComponent, InputPreviousWeapon); - AbilityComp->BindAbilityToAction(InputComponent, InputHolsterWeapon); - AbilityComp->BindAbilityToAction(InputComponent, InputSetAbilityGroup01); - AbilityComp->BindAbilityToAction(InputComponent, InputSetAbilityGroup02); - - - AbilityManager->BindInputs(InputComponent, AbilityComp); AARCharacter* Character = Cast(GetPawn()); - - Character->WeaponInventory->BindInputs(InputComponent, AbilityComp); - + bInputBount = true; } //doesn't matter. Internally ability component make sure abilities are instanced on server and replicated back. if (!AbilitytNextWeapon.IsNull()) { - FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytNextWeapon, InputNextWeapon); - AbilityComp->AddOnAbilityReadyDelegate(AbilitytNextWeapon, del1); - TArray NextWeap; - NextWeap.Add(InputNextWeapon); - AbilityComp->NativeAddAbility(AbilitytNextWeapon, NextWeap); + InputNextWeaponSpecHandle = FAFAbilitySpecHandle::GenerateHandle(); + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady); + AbilityComp->AddOnAbilityReadyDelegate(InputNextWeaponSpecHandle, del1); + + AbilityComp->NativeAddAbility(AbilitytNextWeapon, InputNextWeaponSpecHandle); } - if (!AbilitytPreviousWeapon.IsNull()) + /*if (!AbilitytPreviousWeapon.IsNull()) { FAFOnAbilityReady del2 = FAFOnAbilityReady::CreateUObject(this, &AARPlayerController::OnInputAbilityReady, AbilitytPreviousWeapon, InputPreviousWeapon); AbilityComp->AddOnAbilityReadyDelegate(AbilitytPreviousWeapon, del2); TArray PrevWeap; PrevWeap.Add(InputPreviousWeapon); - AbilityComp->NativeAddAbility(AbilitytPreviousWeapon, PrevWeap); + AbilityComp->NativeAddAbility(AbilitytPreviousWeapon); } if (!AbilitytHolstersWeapon.IsNull()) { @@ -81,7 +68,7 @@ void AARPlayerController::BeginPlay() AbilityComp->AddOnAbilityReadyDelegate(AbilitytHolstersWeapon, del3); TArray HolsterInput; HolsterInput.Add(InputHolsterWeapon); - AbilityComp->NativeAddAbility(AbilitytHolstersWeapon, HolsterInput); + AbilityComp->NativeAddAbility(AbilitytHolstersWeapon); } if (!SetAbilityGroup01.IsNull()) @@ -90,7 +77,7 @@ void AARPlayerController::BeginPlay() AbilityComp->AddOnAbilityReadyDelegate(SetAbilityGroup01, del3); TArray HolsterInput; HolsterInput.Add(InputSetAbilityGroup01); - AbilityComp->NativeAddAbility(SetAbilityGroup01, HolsterInput); + AbilityComp->NativeAddAbility(SetAbilityGroup01); } if (!SetAbilityGroup02.IsNull()) { @@ -98,8 +85,8 @@ void AARPlayerController::BeginPlay() AbilityComp->AddOnAbilityReadyDelegate(SetAbilityGroup02, del3); TArray HolsterInput; HolsterInput.Add(InputSetAbilityGroup02); - AbilityComp->NativeAddAbility(SetAbilityGroup02, HolsterInput); - } + AbilityComp->NativeAddAbility(SetAbilityGroup02); + }*/ } } @@ -141,7 +128,6 @@ void AARPlayerController::InputSwitchAbilitySet() } void AARPlayerController::InputShowHideAbilityManager() { - AbilityManager->ShowHideAbilityManager(); } void AARPlayerController::InputShowHideInventory() { @@ -150,7 +136,7 @@ void AARPlayerController::InputShowHideInventory() MyHUD->ShowHideInventory(); } } -void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag) +void AARPlayerController::OnInputAbilityReady(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) { IAFAbilityInterface* ABInt = Cast(GetPawn()); if (!ABInt) @@ -160,10 +146,11 @@ void AARPlayerController::OnInputAbilityReady(TSoftClassPtr InAb if (!AbilityComp) return; - UARAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); - TArray Inputs; - Inputs.Add(InInputTag); - AbilityComp->SetAbilityToAction(InAbilityTag, Inputs, FAFOnAbilityReady()); + InputNextWeaponSpecHandle = ServerHandle; + + TArray InputIds; + InputIds.Add(static_cast(AbilityInput::NextWeapon)); + AbilityComp->BindAbilityToInputIDs(ServerHandle, InputIds); } diff --git a/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp b/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp deleted file mode 100644 index ea3f337..0000000 --- a/Source/ActionRPGGame/Private/Abilities/ARAbilityManagerComponent.cpp +++ /dev/null @@ -1,109 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#include "ARAbilityManagerComponent.h" -#include "GameFramework/PlayerController.h" - -#include "ARPlayerController.h" - -// Sets default values for this component's properties -UARAbilityManagerComponent::UARAbilityManagerComponent() -{ - // Set this component to be initialized when the game starts, and to be ticked every frame. You can turn these features - // off to improve performance if you don't need them. - PrimaryComponentTick.bCanEverTick = true; - - // ... -} - - -// Called when the game starts -void UARAbilityManagerComponent::BeginPlay() -{ - Super::BeginPlay(); - if (GetOwner()->GetNetMode() == ENetMode::NM_Client - || GetOwner()->GetNetMode() == ENetMode::NM_Standalone) - { - APlayerController* OwnerPC = Cast(GetOwner()); - // ... - } -} - - -// Called every frame -void UARAbilityManagerComponent::TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) -{ - Super::TickComponent(DeltaTime, TickType, ThisTickFunction); - - // ... -} - -void UARAbilityManagerComponent::ShowHideAbilityManager() -{ -} - -void UARAbilityManagerComponent::SetCurrentSet(int32 SetIndex) -{ - //add server/client checks. - SelectGroup(AMIntToEnum(SetIndex)); - -} - -void UARAbilityManagerComponent::OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) -{ - EAMGroup Group = ValidGroup; //ActiveGroup - - UAFAbilityComponent* AbilityComp = GetAbilityComponent(); - if (!AbilityComp) - return; - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - TArray AbilityActionSet; - TArray InputReadyDelegates; - for (int32 Idx = 0; Idx < AbilityTagsSet[AMEnumToInt(ValidGroup)].Num(); Idx++) - { - TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); - TSoftClassPtr NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); - - FAFAbilityActionSet Set; - Set.AbilityInputs = WeaponInput; - Set.AbilityTag = NextWeaponAbility; - - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARAbilityManagerComponent::OnInputReady, - NextWeaponAbility, WeaponInput); - - AbilityActionSet.Add(Set); - InputReadyDelegates.Add(ReadyDelegate); - } - - AbilityComp->SetAbilitiesToActions(AbilityActionSet, InputReadyDelegates); - } - else - { - TArray AbilityActionSet; - TArray InputReadyDelegates; - - for (int32 Idx = 0; Idx < AbilityTagsSet[AMEnumToInt(ValidGroup)].Num(); Idx++) - { - TArray WeaponInput = GetInputTag(Group, AMIntToEnum(Idx)); - TSoftClassPtr NextWeaponAbility = GetAbilityTag(Group, AMIntToEnum(Idx)); - - FAFAbilityActionSet Set; - Set.AbilityInputs = WeaponInput; - Set.AbilityTag = NextWeaponAbility; - - FAFOnAbilityReady ReadyDelegate = FAFOnAbilityReady::CreateUObject(this, &UARAbilityManagerComponent::OnInputReady, - NextWeaponAbility, WeaponInput); - - AbilityActionSet.Add(Set); - InputReadyDelegates.Add(ReadyDelegate); - } - AbilityComp->SetAbilitiesToActions(AbilityActionSet, InputReadyDelegates); - OnAbilitySetChanged.Broadcast(ValidGroup); - } -} - -void UARAbilityManagerComponent::OnInputReady(TSoftClassPtr WeaponAbilityTag, TArray InInputTags) -{ - OnAbilitySetChanged.Broadcast(ActiveGroup); -} \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/UI/HUD/ARHUDPlayerInfo.cpp b/Source/ActionRPGGame/Private/UI/HUD/ARHUDPlayerInfo.cpp index 28eb3fe..2f9fcd5 100644 --- a/Source/ActionRPGGame/Private/UI/HUD/ARHUDPlayerInfo.cpp +++ b/Source/ActionRPGGame/Private/UI/HUD/ARHUDPlayerInfo.cpp @@ -3,7 +3,6 @@ #include "ARHUDPlayerInfo.h" #include "ARPlayerController.h" -#include "Abilities/ARAbilityManagerComponent.h" void UARHUDPlayerInfo::NativePreConstruct() { @@ -12,8 +11,4 @@ void UARHUDPlayerInfo::NativePreConstruct() void UARHUDPlayerInfo::NativeConstruct() { Super::NativeConstruct(); - if (AARPlayerController* MyPC = Cast(GetOwningPlayer())) - { - MyPC->AbilityManager->OnAbilitySetChanged.AddDynamic(this, &UARHUDPlayerInfo::OnAbilityGroupChanged); - } } \ No newline at end of file diff --git a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp index 41990b8..2867376 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARItemWeapon.cpp @@ -18,6 +18,11 @@ #include "Weapons/ARWeaponInventoryComponent.h" #include "Weapons/ARMagazineUpgradeEffect.h" +UARItemWeapon::UARItemWeapon() +{ + AbilityHandle = FAFAbilitySpecHandle::GenerateHandle(); +} + void UARItemWeapon::SetAbility(class UARWeaponAbilityBase* InAbility) { AbilityInstance = InAbility; diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp index 729553d..08c9a37 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponInventoryComponent.cpp @@ -18,7 +18,8 @@ UARWeaponInventoryComponent::UARWeaponInventoryComponent() MaxSlots = 4; AvailableSlots = 4; - WeaponAbilities.SetNum(4); + ClientWeaponAbilities.SetNum(4); + ServerWeaponAbilities.SetNum(4); CurrentWeaponIndex = -1; // ... } @@ -34,13 +35,6 @@ void UARWeaponInventoryComponent::BeginPlay() } void UARWeaponInventoryComponent::BindInputs(UInputComponent* InputComponent, class UAFAbilityComponent* AbilityComponent) { - if (!AbilityComponent) - return; - - for (const FGameplayTag& Input : WeaponInput) - { - AbilityComponent->BindAbilityToAction(InputComponent, Input); - } } void UARWeaponInventoryComponent::InitializeWeapons(APawn* Pawn) { @@ -72,73 +66,43 @@ void UARWeaponInventoryComponent::SetWeapon(const FARWeaponRPC& InWeapon, UChild Component->SetRelativeLocation(InWeapon.Position); Component->SetRelativeRotation(InWeapon.Rotation); } - /*else - { - FStreamableDelegate LoadFinished = FStreamableDelegate::CreateUObject(this, &UARWeaponInventoryComponent::AsynWeaponLoaded, Component, InWeapon); - UAssetManager::Get().GetStreamableManager().RequestAsyncLoad(InWeapon.Weapon.ToSoftObjectPath(), LoadFinished); - }*/ } void UARWeaponInventoryComponent::OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) { - UARItemWeapon* InWeapon = Cast(Item); - if (AARCharacter* Character = Cast(POwner)) + if (UARItemWeapon* ItemWeapon = Cast(Item)) { - FAFOnAbilityReady del; - { - del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(Index)); - Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); - } + } } void UARWeaponInventoryComponent::OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) { - UARItemWeapon* InWeapon = Cast(Item); - FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon.ToString(); - //Data.SocketName = InWeapon->Socket; - Data.Position = InWeapon->HolsteredPosition; - Data.Rotation = InWeapon->HolsteredRotation; - Data.AttachSlot = static_cast(LocalIndex); - SetWeapon(Data, GroupToComponent[LocalIndex]); - if (AARCharacter* Character = Cast(POwner)) + if (UARItemWeapon* ItemWeapon = Cast(Item)) { - TArray NoInput; - /*FAFOnAbilityReady del; - { - del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(LocalIndex)); - Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); - }*/ - if (!InWeapon->AbilityInstance) + if (AARCharacter* Character = Cast(POwner)) { - Character->GetAbilityComp()->NativeAddAbility(InWeapon->Ability, NoInput); + UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); + if (!AbilityComp) + return; + FAFOnAbilityReady Del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnAbilityAdded); + AbilityComp->AddOnAbilityReadyDelegate(ItemWeapon->AbilityHandle, Del); + + ClientWeaponAbilities[LocalIndex] = ItemWeapon->AbilityHandle; + //handle case of Client/Server ability handle. + AbilityComp->NativeAddAbility(ItemWeapon->Ability, ItemWeapon->AbilityHandle); } - WeaponAbilities[LocalIndex] = InWeapon->Ability; } } +void UARWeaponInventoryComponent::OnAbilityAdded(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) +{ + int32 Idx = ClientWeaponAbilities.IndexOfByKey(ClientHandle); + ServerWeaponAbilities[Idx] = ServerHandle; +} void UARWeaponInventoryComponent::OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) { - UARItemWeapon* InWeapon = Cast(Item); - FARWeaponRPC Data; - Data.Weapon = InWeapon->Weapon.ToString(); - //Data.SocketName = InWeapon->Socket; - Data.Position = InWeapon->HolsteredPosition; - Data.Rotation = InWeapon->HolsteredRotation; - Data.AttachSlot = static_cast(LocalIndex); - if (AARCharacter* Character = Cast(POwner)) + if (UARItemWeapon* ItemWeapon = Cast(Item)) { - TArray NoInput; - FAFOnAbilityReady del; - { - del = FAFOnAbilityReady::CreateUObject(this, &UARWeaponInventoryComponent::OnWeaponReady, InWeapon->Ability, static_cast(LocalIndex)); - Character->GetAbilityComp()->AddOnAbilityReadyDelegate(InWeapon->Ability, del); - } - WeaponAbilities[LocalIndex] = InWeapon->Ability; - if (InWeapon->AbilityInstance) - { - Character->GetAbilityComp()->NativeAddAbilityFromObject(InWeapon->AbilityInstance, InWeapon->Ability); - } + ServerWeaponAbilities[LocalIndex] = ItemWeapon->AbilityHandle; } - MulticastAddWeapon(Data); } void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtr InAbilityTag, int8 LocalIndex) { @@ -148,7 +112,7 @@ void UARWeaponInventoryComponent::OnWeaponReady(TSoftClassPtrGetAbilityComp(); - UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByTag(InAbilityTag)); + UGAAbilityBase* Ability = Cast(AbilityComp->BP_GetAbilityByHandle(ServerWeaponAbilities[LocalIndex])); SetAbilityToItem(LocalIndex, Ability); } void UARWeaponInventoryComponent::SetAbilityToItem(int8 InLocalIndex, class UGAAbilityBase* InAbility) @@ -164,7 +128,7 @@ void UARWeaponInventoryComponent::OnItemRemoved(uint8 LocalIndex) { AARCharacter* Character = Cast(POwner); - Character->GetAbilityComp()->NativeRemoveAbility(WeaponAbilities[LocalIndex]); + //Character->GetAbilityComp()->NativeRemoveAbility(WeaponAbilities[LocalIndex]); FARWeaponRPC Data; Data.Weapon.Reset(); @@ -301,7 +265,6 @@ void UARWeaponInventoryComponent::Unequip(int8 WeaponIndex) { return; } - Character->GetAbilityComp()->RemoveAbilitiesFromActions(EquipedWeapon->Ability); Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); } FARWeaponRPC Data; @@ -321,7 +284,6 @@ void UARWeaponInventoryComponent::Holster() return; if (AARCharacter* Character = Cast(POwner)) { - Character->GetAbilityComp()->RemoveAbilitiesFromActions(EquipedWeapon->Ability); Character->GetEquipedMainWeapon()->SetChildActorClass(nullptr); } FARWeaponRPC Data; @@ -400,6 +362,11 @@ void UARWeaponInventoryComponent::NextWeapon() { InWeapon = FindNextValid(); } + if (!InWeapon) + { + //we don't have any weapon. + return; + } FARWeaponRPC Data; Data.Weapon = InWeapon->Weapon.ToString(); //Data.SocketName = InWeapon->Socket; @@ -597,15 +564,11 @@ void UARWeaponInventoryComponent::HandleClientPrediction(int8 WeaponIndex, bool UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); if (!AbilityComp) return; - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); - } - else - { - AbilityComp->SetAbilityToAction(Item->Ability, WeaponInput, FAFOnAbilityReady()); - } + //TODO + TArray InputIDs; + InputIDs.Add(static_cast(AbilityInput::Shoot)); + InputIDs.Add(static_cast(AbilityInput::Reload)); + AbilityComp->BindAbilityToInputIDs(ServerWeaponAbilities[WeaponIndex], InputIDs); } return; } @@ -631,15 +594,11 @@ void UARWeaponInventoryComponent::HandleClientPrediction(int8 WeaponIndex, bool UAFAbilityComponent* AbilityComp = Character->GetAbilityComp(); if (!AbilityComp) return; - - if (GetOwner()->GetNetMode() == ENetMode::NM_Client) - { - AbilityComp->SetAbilityToAction(InWeapon->Ability, WeaponInput, FAFOnAbilityReady()); - } - else - { - AbilityComp->SetAbilityToAction(InWeapon->Ability, WeaponInput, FAFOnAbilityReady()); - } + //TODO + TArray InputIDs; + InputIDs.Add(static_cast(AbilityInput::Shoot)); + InputIDs.Add(static_cast(AbilityInput::Reload)); + AbilityComp->BindAbilityToInputIDs(ServerWeaponAbilities[WeaponIndex], InputIDs); } } } diff --git a/Source/ActionRPGGame/Public/ARCharacter.h b/Source/ActionRPGGame/Public/ARCharacter.h index 80c563b..f059441 100644 --- a/Source/ActionRPGGame/Public/ARCharacter.h +++ b/Source/ActionRPGGame/Public/ARCharacter.h @@ -13,49 +13,10 @@ #include "OrionAnimComponent.h" #include "IFInventoryInterface.h" #include "Weapons/ARWeaponInventoryComponent.h" -#include "ARCharacter.generated.h" - -UENUM(BlueprintType) -enum class EEightCardinalDirection : uint8 -{ - N = 0, - SW = 1, - E = 2, - NW = 3, - S = 4, - NE = 5, - W = 6, - SE = 7 -}; - -UENUM(BlueprintType) -enum class EFourCardinalDirection : uint8 -{ - N = 0, - E = 1, - S = 2, - W = 3 -}; - -UENUM(BlueprintType) -enum class EPivotDirectionChange : uint8 -{ - NtoE = 0, - NtoW = 1, - NToS = 2, -}; - -USTRUCT(BlueprintType) -struct FCardinalDirection -{ - GENERATED_BODY() - UPROPERTY(BlueprintReadOnly) - EFourCardinalDirection CaridnalDirections; - - EEightCardinalDirection HelperDirections; -}; +#include "OrionAnimComponent.h" +#include "ARCharacter.generated.h" USTRUCT(BlueprintType) struct FARCameraTransform { @@ -73,6 +34,22 @@ struct WeaponSocket static const FName EquipedMainWeapon; }; + +UENUM(BlueprintType) +enum class AbilityInput : uint8 +{ + Shoot = 0, + Reload = 1, + NextWeapon = 2, + PreviousWeapon = 3, + NextAbilitySet = 4, + PreviousAbilitySet = 5, + Ability01 = 6, + Ability02 = 7, + Ability03 = 8, + Ability04 = 9 +}; + UCLASS(config=Game) class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrionInterface, public IIFInventoryInterface { @@ -90,6 +67,9 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio class UAFAbilityComponent* Abilities; UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UAFEffectsComponent* EffectsComponent; + + UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) + UOrionAnimComponent* OrionAnimComp; public: UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = Camera, meta = (AllowPrivateAccess = "true")) class UARWeaponInventoryComponent* WeaponInventory; @@ -142,53 +122,11 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") FARCameraTransform CameraTransform; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - bool bStopDistancePredicted; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - bool bStartedLocomotion; - - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - EEightCardinalDirection EigthDirections; - - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - EFourCardinalDirection OldFourDirections; - - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - EFourCardinalDirection FourDirections; - - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - float MovingAngle; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - float OrientN; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - float OrientS; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - float OrientE; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - float OrientW; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Character Animation") - float OrientInterpolationSpeed; - - UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Character Animation") - float OrientationDOT; - - float ForwardDirection; - float LateralDirection; - UPROPERTY(BlueprintReadOnly, Category = "Character Animation") - float CurrentOrient; - float OldOrient; public: AARCharacter(const FObjectInitializer& ObjectInitializer); virtual void OnConstruction(const FTransform& Transform) override; virtual void PostInitializeComponents() override; - float GetAnimOrient() final; - EFCardinalDirection GetCardianlDirection() final; - float GetAnimOrientN() final; - float GetAnimOrientE() final; - float GetAnimOrientS() final; - float GetAnimOrientW() final; - + virtual void BeginPlay() override; virtual void Tick(float DeltaSeconds) override; /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ diff --git a/Source/ActionRPGGame/Public/ARCharacterMovementComponent.h b/Source/ActionRPGGame/Public/ARCharacterMovementComponent.h index 5b3d714..e6f4c3f 100644 --- a/Source/ActionRPGGame/Public/ARCharacterMovementComponent.h +++ b/Source/ActionRPGGame/Public/ARCharacterMovementComponent.h @@ -14,7 +14,4 @@ class ACTIONRPGGAME_API UARCharacterMovementComponent : public UCharacterMovemen { GENERATED_BODY() - - - }; diff --git a/Source/ActionRPGGame/Public/ARPlayerController.h b/Source/ActionRPGGame/Public/ARPlayerController.h index a26ee10..2b1267f 100644 --- a/Source/ActionRPGGame/Public/ARPlayerController.h +++ b/Source/ActionRPGGame/Public/ARPlayerController.h @@ -7,6 +7,7 @@ #include "GameplayTags.h" #include "IFInventoryComponent.h" #include "IFInventoryInterface.h" +#include "AFAbilityTypes.h" #include "ARPlayerController.generated.h" /** @@ -20,9 +21,6 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UARUIComponent* UIComponent; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") - class UARAbilityManagerComponent* AbilityManager; - UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category = "Components|UI") class UIFInventoryComponent* MainInventory; @@ -30,6 +28,8 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I FGameplayTag InputNextWeapon; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") TSoftClassPtr AbilitytNextWeapon; + UPROPERTY(Transient) + FAFAbilitySpecHandle InputNextWeaponSpecHandle; UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Ability Input") FGameplayTag InputPreviousWeapon; @@ -65,7 +65,7 @@ class ACTIONRPGGAME_API AARPlayerController : public APlayerController, public I void InputSwitchAbilitySet(); void InputShowHideAbilityManager(); void InputShowHideInventory(); - void OnInputAbilityReady(TSoftClassPtr InAbilityTag, FGameplayTag InInputTag); + void OnInputAbilityReady(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle); UFUNCTION(Client, Reliable) void ClientPossesed(APawn* InPawn); diff --git a/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h b/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h deleted file mode 100644 index eb790bd..0000000 --- a/Source/ActionRPGGame/Public/Abilities/ARAbilityManagerComponent.h +++ /dev/null @@ -1,54 +0,0 @@ -// Fill out your copyright notice in the Description page of Project Settings. - -#pragma once - -#include "CoreMinimal.h" -#include "Components/ActorComponent.h" -#include "GameplayTags.h" - -#include "Abilities/GAAbilityBase.h" -#include "AMAbilityManagerComponent.h" - -#include "ARAbilityManagerComponent.generated.h" - -DECLARE_DYNAMIC_MULTICAST_DELEGATE_OneParam(FAROnAbilitySetChanged, EAMGroup, Group); - -USTRUCT(BlueprintType) -struct FARAbilityItem -{ - GENERATED_BODY() -public: - UPROPERTY(EditAnywhere) - TSoftClassPtr Ability; -}; -UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) -class ACTIONRPGGAME_API UARAbilityManagerComponent : public UAMAbilityManagerComponent -{ - GENERATED_BODY() -protected: - UPROPERTY(EditAnywhere) - TArray AvailableAbilities; -public: - UPROPERTY(BlueprintAssignable) - FAROnAbilitySetChanged OnAbilitySetChanged; -public: - // Sets default values for this component's properties - UARAbilityManagerComponent(); - -protected: - // Called when the game starts - virtual void BeginPlay() override; - -public: - // Called every frame - virtual void TickComponent(float DeltaTime, ELevelTick TickType, FActorComponentTickFunction* ThisTickFunction) override; - - void ShowHideAbilityManager(); - - UFUNCTION(BlueprintCallable, Category = "ActionRPGGame|Ability Manager") - void SetCurrentSet(int32 SetIndex); - - virtual void OnGroupSelectionConfirmed(EAMGroup ValidGroup, bool bPredictionSuccess) override; - - void OnInputReady(TSoftClassPtr WeaponAbilityTag, TArray InInputTags); -}; diff --git a/Source/ActionRPGGame/Public/ActionRPGGame.h b/Source/ActionRPGGame/Public/ActionRPGGame.h index a467361..2986d44 100644 --- a/Source/ActionRPGGame/Public/ActionRPGGame.h +++ b/Source/ActionRPGGame/Public/ActionRPGGame.h @@ -3,6 +3,8 @@ #pragma once #include "CoreMinimal.h" +#include "Modules/ModuleManager.h" + class FActionRPGGameModule : public FDefaultGameModuleImpl { virtual void StartupModule() override; diff --git a/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.h b/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.h index 016e84c..3a28112 100644 --- a/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.h +++ b/Source/ActionRPGGame/Public/UI/HUD/ARHUDPlayerInfo.h @@ -49,8 +49,4 @@ class ACTIONRPGGAME_API UARHUDPlayerInfo : public UARUMGWidgetBase virtual void NativePreConstruct() override; virtual void NativeConstruct() override; - - UFUNCTION(BlueprintImplementableEvent, Category = "ActionRPGGame|UI") - void OnAbilityGroupChanged(EAMGroup CurrentGroup); - }; diff --git a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h index 450c99e..8525dfa 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h +++ b/Source/ActionRPGGame/Public/Weapons/ARItemWeapon.h @@ -32,9 +32,6 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(EditAnywhere, Category = "Visual") TSoftClassPtr Weapon; - - - UPROPERTY(EditAnywhere, Category = "Transforms") FVector HolsteredPosition; UPROPERTY(EditAnywhere, Category = "Transforms") @@ -56,6 +53,11 @@ class ACTIONRPGGAME_API UARItemWeapon : public UARItemBase UPROPERTY(Transient) float MagazineUpgradeValue; + UPROPERTY(Transient) + FAFAbilitySpecHandle AbilityHandle; + + UARItemWeapon(); + void SetAbility(class UARWeaponAbilityBase* InAbility); void AddMagazineUpgrade(class UARMagazineUpgradeItem* InMagazineUpgrade); diff --git a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h index d903047..2f1e385 100644 --- a/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h +++ b/Source/ActionRPGGame/Public/Weapons/ARWeaponInventoryComponent.h @@ -9,7 +9,6 @@ #include "Engine/ActorChannel.h" #include "IFInventoryComponent.h" #include "IFEquipmentComponent.h" -#include "AMTypes.h" #include "Weapons/ARWeaponAbilityBase.h" #include "ARWeaponInventoryComponent.generated.h" @@ -85,9 +84,9 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone TArray WeaponInput; TMap GroupToComponent; - TMap GroupToItem; - TArray> WeaponAbilities; + TArray ClientWeaponAbilities; + TArray ServerWeaponAbilities; int8 CurrentWeaponIndex; @@ -117,6 +116,8 @@ class ACTIONRPGGAME_API UARWeaponInventoryComponent : public UIFEquipmentCompone } virtual void OnClientPreItemAdded(UIFItemBase* Item, uint8 Index) override; virtual void OnItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; + UFUNCTION() + void OnAbilityAdded(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle); virtual void OnItemRemoved(uint8 LocalIndex) override; virtual void OnServerItemAdded(UIFItemBase* Item, uint8 LocalIndex) override; From 71eafc21f86b7b542e4b2583cb1535d63e85ddd0 Mon Sep 17 00:00:00 2001 From: Lukasz 'iniside' Baran Date: Tue, 10 Jul 2018 23:37:17 +0200 Subject: [PATCH 187/187] Syncing changed with P4. Reworked how cues work. Thy are now split into instanced and non instanced cues. Also reworking how EffectSpec and Context are created and passed around various systems, to minimize heap allocations, and as few as copies as possible --- .gitignore | 12 +- Config/DefaultGame.ini | 28 +- Config/DefaultInput.ini | 9 +- .../Private/AFAbilityComponent.cpp | 11 +- .../Private/AFAbilityInterface.cpp | 3 +- .../AbilityFramework/Private/AFCueManager.cpp | 363 ++++------------- .../Private/AFEffectsComponent.cpp | 69 ++-- .../Private/Abilities/GAAbilityBase.cpp | 122 +++--- .../Private/AbilityFramework.cpp | 11 +- .../Private/Attributes/GAAttributeBase.cpp | 22 +- .../Private/Attributes/GAAttributesBase.cpp | 2 +- .../GAAttributesBlueprintFunctionLibrary.cpp | 4 +- .../Private/Cues/AFCueStaticBlueprint.cpp | 8 + .../Cues/AFCueStaticGeneratedClass.cpp | 8 + .../{GAEffectCue.cpp => AFCueActor.cpp} | 38 +- ...eBlueprint.cpp => AFCueActorBlueprint.cpp} | 10 +- ...Class.cpp => AFCueActorGeneratedClass.cpp} | 6 +- .../Private/Effects/AFCueStatic.cpp | 131 ++++++ .../AFAttributeStongerOverride.cpp | 4 +- .../AFAtributeDurationUnique.cpp | 2 +- .../AFAttributeDurationOverride.cpp | 2 +- .../AFPeriodApplicationExtend.cpp | 2 +- .../AFPeriodApplicationOverride.cpp | 2 +- .../AFEffectTask_EffectAppliedToSelf.cpp | 4 +- .../AFEffectTask_EffectAppliedToTarget.cpp | 4 +- .../Private/Effects/GABlueprintLibrary.cpp | 384 +++++++----------- .../Private/Effects/GAEffectCueSequence.cpp | 6 +- .../Private/Effects/GAEffectExecution.cpp | 16 +- .../Private/Effects/GAEffectExtension.cpp | 34 ++ .../Private/Effects/GAGameEffect.cpp | 136 ++++--- .../Private/GAGlobalTypes.cpp | 22 +- .../Public/AFAbilityComponent.h | 2 +- .../Public/AFAbilityInterface.h | 3 +- .../AbilityFramework/Public/AFCueManager.h | 105 ++++- .../Public/AFEffectsComponent.h | 8 +- .../Public/Abilities/GAAbilityBase.h | 18 +- .../Public/AbilityFramework.h | 2 + .../Public/Attributes/GAAttributeBase.h | 2 +- .../Public/Attributes/GAAttributesBase.h | 2 +- .../Public/Cues/AFCueStaticBlueprint.h | 20 + .../Public/Cues/AFCueStaticGeneratedClass.h | 20 + .../Effects/{GAEffectCue.h => AFCueActor.h} | 6 +- ...ctCueBlueprint.h => AFCueActorBlueprint.h} | 6 +- ...atedClass.h => AFCueActorGeneratedClass.h} | 4 +- .../Public/Effects/AFCueStatic.h | 61 +++ .../AFEffectTask_EffectAppliedToSelf.h | 6 +- .../AFEffectTask_EffectAppliedToTarget.h | 6 +- .../Public/Effects/GABlueprintLibrary.h | 74 ++-- .../Public/Effects/GAEffectExecution.h | 2 +- .../Public/Effects/GAEffectExtension.h | 38 +- .../Public/Effects/GAGameEffect.h | 383 ++++++----------- .../AbilityFramework/Public/GAGlobalTypes.h | 4 +- .../Public/IAbilityFramework.h | 2 +- .../Public/LatentActions/AFTaskBase.h | 3 +- .../Public/AbilityFrameworkEditor.cpp | 13 +- .../CueStatic/AFCueStaticBlueprintFactory.cpp | 334 +++++++++++++++ .../AFCueStaticBlueprintFactory.h} | 6 +- .../AssetTypeActions_AFCueStaticBlueprint.cpp | 59 +++ .../AssetTypeActions_AFCueStaticBlueprint.h} | 3 +- ...ory.cpp => AFCueActorBlueprintFactory.cpp} | 48 +-- .../AFCueActorBlueprintFactory.h | 32 ++ .../EffectCueEditor/AFEffectCueDetails.cpp | 14 +- ... AssetTypeActions_AFCueActorBlueprint.cpp} | 28 +- .../AssetTypeActions_AFCueActorBlueprint.h | 27 ++ .../EffectCueEditor/GAEffectCueEditor.cpp | 10 +- .../EffectCueEditor/GAEffectCueEditor.h | 4 +- .../Private/AI/ARAICharacter.cpp | 2 +- Source/ActionRPGGame/Private/ARCharacter.cpp | 72 +++- .../ActionRPGGame/Private/ARGameInstance.cpp | 4 +- .../Private/Weapons/ARWeaponAbilityBase.cpp | 21 +- .../ActionRPGGame/Public/AI/ARAICharacter.h | 2 +- Source/ActionRPGGame/Public/ARCharacter.h | 27 +- 72 files changed, 1776 insertions(+), 1182 deletions(-) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticBlueprint.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticGeneratedClass.cpp rename Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/{GAEffectCue.cpp => AFCueActor.cpp} (76%) rename Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/{GAEffectCueBlueprint.cpp => AFCueActorBlueprint.cpp} (66%) rename Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/{GAEffectCueBlueprintGeneratedClass.cpp => AFCueActorGeneratedClass.cpp} (50%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueStatic.cpp create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticBlueprint.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticGeneratedClass.h rename Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/{GAEffectCue.h => AFCueActor.h} (93%) rename Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/{GAEffectCueBlueprint.h => AFCueActorBlueprint.h} (75%) rename Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/{GAEffectCueBlueprintGeneratedClass.h => AFCueActorGeneratedClass.h} (63%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueStatic.h create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.cpp rename Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/{EffectCueEditor/GAEffectCueBlueprintFactory.h => CueStatic/AFCueStaticBlueprintFactory.h} (87%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.cpp rename Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/{EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h => CueStatic/AssetTypeActions_AFCueStaticBlueprint.h} (86%) rename Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/{GAEffectCueBlueprintFactory.cpp => AFCueActorBlueprintFactory.cpp} (82%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.h rename Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/{AssetTypeActions_GAEffectCueBlueprint.cpp => AssetTypeActions_AFCueActorBlueprint.cpp} (53%) create mode 100644 Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.h diff --git a/.gitignore b/.gitignore index 42f855e..010cf74 100644 --- a/.gitignore +++ b/.gitignore @@ -243,14 +243,11 @@ pip-log.txt .vs/ .vs/* Binaries/ -Plugins/ -Plugins/* + Content/* Substance/ Substance/* !Content/Blueprints/ -!Plugins/AbilityFramework/Source -!Plugins/AbilityFrameworkEditor/Source DerivedDataCache/ Intermediate/ Saved/ @@ -266,4 +263,9 @@ Saved/ CodeBackup/States/GASAbilityStateCooldown.h *.bin *.pak -Config/DefaultARGame.ini \ No newline at end of file +Config/DefaultARGame.ini +Plugins/* +!Plugins/AbilityFramework/ +!Plugins/AbilityFramework/Source/ +!!Plugins/AbilityFrameworkEditor/ +!Plugins/AbilityFrameworkEditor/Source/ \ No newline at end of file diff --git a/Config/DefaultGame.ini b/Config/DefaultGame.ini index c341163..6c6fd12 100644 --- a/Config/DefaultGame.ini +++ b/Config/DefaultGame.ini @@ -5,19 +5,6 @@ ProjectName=Third Person Game Template [/Script/AbilityFramework.AFCueManager] DefaultCueSet=/Game/Prototypes/ProtCueSet.ProtCueSet -[/Script/Engine.AssetManagerSettings] --PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps"))) --PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game"))) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) -+PrimaryAssetTypesToScan=(PrimaryAssetType="EffectCue",AssetBaseClass=/Script/AbilityFramework.GAEffectCue,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) -bOnlyCookProductionAssets=False -bShouldManagerDetermineTypeAndName=False -bShouldGuessTypeAndNameInEditor=True -bShouldAcquireMissingChunksOnLoad=False -MetaDataTagsForAssetRegistry=() - [/Script/UnrealEd.ProjectPackagingSettings] Build=IfProjectHasCode BuildConfiguration=PPBC_Development @@ -54,3 +41,18 @@ bSkipMovies=False bNativizeBlueprintAssets=False bNativizeOnlySelectedBlueprints=False +[/Script/Engine.AssetManagerSettings] +-PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps"))) +-PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game"))) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Map",AssetBaseClass=/Script/Engine.World,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game/Maps")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="PrimaryAssetLabel",AssetBaseClass=/Script/Engine.PrimaryAssetLabel,bHasBlueprintClasses=False,bIsEditorOnly=True,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=Unknown)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="Ability",AssetBaseClass=/Script/AbilityFramework.GAAbilityBase,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="ActorCue",AssetBaseClass=/Script/AbilityFramework.AFCueActor,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) ++PrimaryAssetTypesToScan=(PrimaryAssetType="StaticCue",AssetBaseClass=/Script/AbilityFramework.AFCueStatic,bHasBlueprintClasses=True,bIsEditorOnly=False,Directories=((Path="/Game")),SpecificAssets=,Rules=(Priority=-1,bApplyRecursively=True,ChunkId=-1,CookRule=AlwaysCook)) +bOnlyCookProductionAssets=False +bShouldManagerDetermineTypeAndName=False +bShouldGuessTypeAndNameInEditor=True +bShouldAcquireMissingChunksOnLoad=False +MetaDataTagsForAssetRegistry=() + + diff --git a/Config/DefaultInput.ini b/Config/DefaultInput.ini index 0635653..8dd4a35 100644 --- a/Config/DefaultInput.ini +++ b/Config/DefaultInput.ini @@ -52,11 +52,10 @@ DoubleClickTime=0.200000 +ActionMappings=(ActionName="Input.UI.WeaponPrevious",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=MouseScrollDown) +ActionMappings=(ActionName="InputInventory",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=I) +ActionMappings=(ActionName="Input.UI.Holster",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=O) -+ActionMappings=(ActionName="Input.Ability01.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=One) -+ActionMappings=(ActionName="Input.Ability02.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Two) -+ActionMappings=(ActionName="Input.Ability03.Activate",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Three) -+ActionMappings=(ActionName="Input.UI.SetAbilityGroup01",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Zero) -+ActionMappings=(ActionName="Input.UI.SetAbilityGroup02",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Nine) ++ActionMappings=(ActionName="Ability01",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=One) ++ActionMappings=(ActionName="Ability02",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Two) ++ActionMappings=(ActionName="Ability03",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Three) ++ActionMappings=(ActionName="Ability04",bShift=False,bCtrl=False,bAlt=False,bCmd=False,Key=Four) +AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=W) +AxisMappings=(AxisName="MoveForward",Scale=-1.000000,Key=S) +AxisMappings=(AxisName="MoveForward",Scale=1.000000,Key=Up) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp index efa7956..2b1665d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityComponent.cpp @@ -16,7 +16,7 @@ #include "Effects/GAGameEffect.h" #include "Effects/GAEffectExtension.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #include "AFCueManager.h" #include "Effects/GABlueprintLibrary.h" #include "Async.h" @@ -86,7 +86,7 @@ void UAFAbilityComponent::BroadcastAttributeChange(const FGAAttribute& InAttribu void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn , const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty - , const FAFContextHandle& InContext) + , const FGAEffectContext& InContext) { //OnAttributePreModifed.Broadcast(ModIn, 0); //Add log. @@ -96,12 +96,11 @@ void UAFAbilityComponent::ModifyAttribute(FGAEffectMod& ModIn } float NewValue = DefaultAttributes->ModifyAttribute(ModIn, HandleIn, InProperty, InContext); FAFAttributeChangedData Data; - FGAEffectContext& Context = InProperty.GetContext(HandleIn).GetRef(); Data.Mod = ModIn; - Data.Target = Context.Target; - Data.Location = Context.HitResult.Location; + Data.Target = InContext.Target; + Data.Location = InContext.HitResult.Location; OnAttributeModifed.Broadcast(Data); - Context.InstigatorComp->NotifyInstigatorTargetAttributeChanged(Data, Context); + InContext.InstigatorComp->NotifyInstigatorTargetAttributeChanged(Data, InContext); //add default replication (PropertyRep) that attribute changed. }; void UAFAbilityComponent::NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp index 134412e..b3b15e7 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFAbilityInterface.cpp @@ -17,9 +17,8 @@ UAFAbilityInterface::UAFAbilityInterface(const FObjectInitializer& ObjectInitial FGAEffectHandle IAFAbilityInterface::ApplyEffectToTarget( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { - return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, InHandle, Params, Modifier); + return GetEffectsComponent()->ApplyEffectToTarget(EffectIn, Params, Modifier); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp index 795be8d..d812d46 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFCueManager.cpp @@ -1,8 +1,13 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "AbilityFramework.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" +#include "Effects/AFCueStatic.h" #include "AFCueManager.h" +#include "GameplayTagsManager.h" + +#include "Engine/ObjectLibrary.h" + #if WITH_EDITOR #include "Editor.h" #endif @@ -30,108 +35,56 @@ void UAFCueManager::Initialize() #endif //WITH_EDITORONLY_DATA FCoreUObjectDelegates::PreLoadMap.AddUObject(this, &UAFCueManager::HandlePreLoadMap); FCoreUObjectDelegates::PostLoadMapWithWorld.AddUObject(this, &UAFCueManager::HandlePostLoadMap); -} -#if WITH_EDITOR -void UAFCueManager::HandleOnPIEEnd(bool InVal) -{ - CurrentWorld = nullptr; - for (auto It = InstancedCues.CreateIterator(); It; ++It) + + StaticCues = UObjectLibrary::CreateLibrary(UAFCueStatic::StaticClass(), true, GIsEditor); + if (GIsEditor) { - if (It->Value.IsValid()) - { - while (!It->Value->IsEmpty()) - { - AGAEffectCue* ToDestroy = nullptr; - It->Value->Dequeue(ToDestroy); - if (ToDestroy) - { - ToDestroy->Destroy(); - } - } - } + StaticCues->bIncludeOnlyOnDiskAssets = true; } - for (auto It = UsedCues.CreateIterator(); It; ++It) + + TArray Paths; + Paths.Add("/Game"); + StaticCues->LoadBlueprintAssetDataFromPaths(Paths, true); + + TArray StaticCueAssets; + StaticCues->GetAssetDataList(StaticCueAssets); + + FName TagProperty = GET_MEMBER_NAME_CHECKED(UAFCueStatic, EffectCueTagSearch); + UGameplayTagsManager& TagManager = UGameplayTagsManager::Get(); + + for (const FAssetData& CueAsset : StaticCueAssets) { - if (It->Value.Num() <= 0) - { - UsedCues.Remove(It->Key); - } - for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) + const FName Tag = CueAsset.GetTagValueRef(TagProperty); + + if (!Tag.IsNone()) { - if (QIt->Value.IsValid()) - { - while (!QIt->Value->IsEmpty()) - { - AGAEffectCue* ToDestroy = nullptr; - QIt->Value->Dequeue(ToDestroy); - if (ToDestroy) - { - ToDestroy->Destroy(); - } - } - } - if (It->Value.Num() <= 0) - { - UsedCues.Remove(It->Key); - } + const FString GeneratedClassTag = CueAsset.GetTagValueRef(FBlueprintTags::GeneratedClassPath); + + FGameplayTag ReqTag = TagManager.RequestGameplayTag(Tag); + FSoftObjectPath AssetPath; + AssetPath.SetPath(FPackageName::ExportTextPathToObjectPath(*GeneratedClassTag)); + FAFCueData CueData; + CueData.CueTag = ReqTag; + CueData.AssetId = CueAsset.GetPrimaryAssetId(); + Cues.Add(CueData); } + } + for (int32 Idx = 0; Idx < Cues.Num(); Idx++) + { + int32& i = CuesMap.FindOrAdd(Cues[Idx].CueTag); + i = Idx; } - ActiveCues.Empty(); - InstancedCues.Empty(); - UsedCues.Empty(); +} +#if WITH_EDITOR +void UAFCueManager::HandleOnPIEEnd(bool InVal) +{ + CurrentWorld = nullptr; } #endif //WITH_EDITOR void UAFCueManager::HandlePreLoadMap(const FString& InMapName) { CurrentWorld = nullptr; - - InstancedCues.Reset(); - InstancedCues.Compact(); - UsedCues.Reset(); - UsedCues.Compact(); - //for (auto It = InstancedCues.CreateIterator(); It; ++It) - //{ - // if (It->Value.IsValid()) - // { - // while (!It->Value->IsEmpty()) - // { - // AGAEffectCue* ToDestroy = nullptr; - // It->Value->Dequeue(ToDestroy); - // if (ToDestroy) - // { - // ToDestroy->Destroy(); - // } - // } - // } - //} - //for (auto It = UsedCues.CreateIterator(); It; ++It) - //{ - // if (It->Value.Num() <= 0) - // { - // UsedCues.Remove(It->Key); - // } - // for (auto QIt = It->Value.CreateIterator(); QIt; ++QIt) - // { - // if (QIt->Value.IsValid()) - // { - // while (!QIt->Value->IsEmpty()) - // { - // AGAEffectCue* ToDestroy = nullptr; - // QIt->Value->Dequeue(ToDestroy); - // if (ToDestroy) - // { - // ToDestroy->Destroy(); - // } - // } - // } - // if (It->Value.Num() <= 0) - // { - // UsedCues.Remove(It->Key); - // } - // } - - //} } void UAFCueManager::HandlePostLoadMap(UWorld* InWorld) { @@ -139,8 +92,9 @@ void UAFCueManager::HandlePostLoadMap(UWorld* InWorld) } -void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) +void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags + , const FGAEffectCueParams& CueParams + , EAFCueEvent CueEvent) { if (!CurrentWorld) CurrentWorld = CueParams.Instigator->GetWorld(); @@ -150,212 +104,73 @@ void UAFCueManager::HandleCue(const FGameplayTagContainer& Tags, { for (const FGameplayTag& CueTag : Tags) { + int32 Idx = CuesMap[CueTag]; + FAFCueData Data = Cues[Idx]; - AGAEffectCue* actor = nullptr; - ENetRole mode = CueParams.Instigator->GetRemoteRole(); - TUniquePtr>& Cues = InstancedCues.FindOrAdd(CueTag); - if (Cues.IsValid()) + if (Data.CueClass) { - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(CueTag); - - if (!UseCuesQueue.IsValid()) - { - UseCuesQueue = MakeUnique>(); - } - { - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); - } - if (actor) - { - ActiveCues.Add(InHandle, actor); - actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.GetActor(), CueParams.Causer.Get(), CueParams.HitResult, CueParams); - } - else - { - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - - TArray AssetData; - FARFilter Filter; - Filter.TagsAndValues.Add("EffectCueTagSearch", CueTag.ToString()); - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("EffectCue"), AssetData[0].AssetName); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) - { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams, InHandle); - - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); - } - } - return;//don't try to load asset, we already have pooled instance. + HandleCueEvent(Cues[Idx].CueClass, CueParams, CueEvent); } - - - FAssetRegistryModule& AssetRegistryModule = FModuleManager::LoadModuleChecked("AssetRegistry"); - IAssetRegistry& AssetRegistry = AssetRegistryModule.Get(); - - TArray AssetData; - FARFilter Filter; - Filter.TagsAndValues.Add("EffectCueTagSearch", CueTag.ToString()); - AssetRegistryModule.Get().GetAssets(Filter, AssetData); - FPrimaryAssetId PrimaryAssetId = FPrimaryAssetId(FPrimaryAssetType("EffectCue"), AssetData[0].AssetName); - FPrimaryAssetTypeInfo Info; - if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + else //load cue asynchronously { - FStreamableDelegate del = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, CueTag, PrimaryAssetId, CueParams, InHandle); - - Manager->LoadPrimaryAsset(PrimaryAssetId, - TArray(), - del); + FPrimaryAssetId PrimaryAssetId = Data.AssetId; + FPrimaryAssetTypeInfo Info; + if (Manager->GetPrimaryAssetTypeInfo(PrimaryAssetId.PrimaryAssetType, Info)) + { + FStreamableDelegate StreamDelegate = FStreamableDelegate::CreateUObject(this, &UAFCueManager::OnFinishedLoad, Idx, Data.AssetId, CueParams, CueEvent); + TSharedPtr Handle = Manager->LoadPrimaryAsset(PrimaryAssetId, TArray(), StreamDelegate); + } } } } } -void UAFCueManager::HandleExecuteCue(FAFCueHandle InHandle) -{ - AGAEffectCue** Cue = ActiveCues.Find(InHandle); - if (Cue) - { - AGAEffectCue* cue = *Cue; - cue->NativeOnExecuted(); - } -} -void UAFCueManager::OnFinishedLoad(FGameplayTag InCueTag +void UAFCueManager::OnFinishedLoad(int32 Idx , FPrimaryAssetId InPrimaryAssetId , FGAEffectCueParams CueParams - , FAFCueHandle InHandle) + , EAFCueEvent CueEvent) { if (UAssetManager* Manager = UAssetManager::GetIfValid()) { - UObject* loaded = Manager->GetPrimaryAssetObject(InPrimaryAssetId); - TSubclassOf cls = Cast(loaded); - if (cls) - { - TSubclassOf CueClass = cls; - if (!CueClass) - return; - - ENetRole mode = CueParams.Instigator->GetRemoteRole(); - FString role; - switch (mode) - { - case ROLE_None: - role = "ROLE_None"; - break; - case ROLE_SimulatedProxy: - role = "ROLE_SimulatedProxy"; - break; - case ROLE_AutonomousProxy: - role = "ROLE_AutonomousProxy"; - break; - case ROLE_Authority: - role = "ROLE_Authority"; - break; - case ROLE_MAX: - role = "ROLE_MAX"; - break; - default: - break; - } - - FString prefix = ""; - //if (mode == ENetMode::NM_Client) - //{ - // prefix = FString::Printf(TEXT("Client %d: "), GPlayInEditorID - 1); - //} - - UE_LOG(AbilityFramework, Log, TEXT("%s : CueManager HandleCue: %s, Instigator: %s, Location: %s, World: %s, Role: %s"), - *prefix, - *InCueTag.ToString(), - CueParams.Instigator.IsValid() ? *CueParams.Instigator->GetName() : TEXT("Invalid Instigator"), - *CueParams.HitResult.Location.ToString(), - *CurrentWorld->GetName(), - *role - ); - - FActorSpawnParameters SpawnParams; - FVector Location = CueParams.HitResult.Location; - FRotator Rotation = FRotator::ZeroRotator; - AGAEffectCue* actor = nullptr; - - TUniquePtr>& Cues = InstancedCues.FindOrAdd(InCueTag); - if (!Cues.IsValid()) - { - Cues = MakeUnique>(); - } - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(InCueTag); - - if (!UseCuesQueue.IsValid()) - { - UseCuesQueue = MakeUnique>(); - } + UObject* CueClass = Manager->GetPrimaryAssetObject(InPrimaryAssetId); + size_t classSize = sizeof(*CueClass); - if (Cues->IsEmpty()) - { - actor = CurrentWorld->SpawnActor(CueClass, Location, Rotation, SpawnParams); - Cues->Enqueue(actor); - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); - } - else - { - Cues->Dequeue(actor); - UseCuesQueue->Enqueue(actor); - } - - if (actor) - { - ActiveCues.Add(InHandle, actor); - actor->NativeBeginCue(CueParams.Instigator.Get(), CueParams.HitResult.Actor.Get(), - CueParams.Causer.Get(), CueParams.HitResult, CueParams); - } - } - - /*{ - Manager->UnloadPrimaryAsset(InPrimaryAssetId); - }*/ + Cues[Idx].CueClass = Cast(CueClass); + HandleCueEvent(Cues[Idx].CueClass, CueParams, CueEvent); } } void UAFCueManager::HandleRemoveCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams, FAFCueHandle InHandle) { - if (!CurrentWorld) - CurrentWorld = CueParams.Instigator->GetWorld(); - for (const FGameplayTag& Tag : CueParams.CueTags) - { - AGAEffectCue* actor = nullptr; - TUniquePtr>& Cues = InstancedCues.FindOrAdd(Tag); - if (!Cues.IsValid()) - { - Cues = MakeUnique>(); - } - FObjectKey InstigatorKey(CueParams.Instigator.Get()); - TMap>>& UsedCuesMap = UsedCues.FindOrAdd(InstigatorKey); - TUniquePtr>& UseCuesQueue = UsedCuesMap.FindOrAdd(Tag); - if (!UseCuesQueue.IsValid()) +} + +void UAFCueManager::HandleCueEvent(UClass* InCueClass, const FGAEffectCueParams& InCueParams, EAFCueEvent CueEvent) +{ + if (UAFCueStatic* StaticCue = Cast(InCueClass->ClassDefaultObject)) + { + switch (CueEvent) { - UseCuesQueue = MakeUnique>(); + case Activated: + StaticCue->OnActivate(InCueParams); + break; + case Executed: + StaticCue->OnExecuted(InCueParams); + break; + case Expire: + StaticCue->OnExpire(InCueParams); + break; + case Removed: + StaticCue->OnRemoved(InCueParams); + break; + default: + break; } - - UseCuesQueue->Dequeue(actor); + } + else if (AAFCueActor* ActorCue = Cast(InCueClass->ClassDefaultObject)) + { - if (actor) - { - ActiveCues.Remove(InHandle); - Cues->Enqueue(actor); - actor->NativeOnRemoved(); - } } } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp index 87b6110..72e906c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AFEffectsComponent.cpp @@ -10,7 +10,7 @@ #include "Effects/GAEffectExecution.h" #include "Effects/GAGameEffect.h" #include "Effects/GAEffectExtension.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #include "AFCueManager.h" #include "Effects/GABlueprintLibrary.h" @@ -51,12 +51,11 @@ void UAFEffectsComponent::TickComponent(float DeltaTime, ELevelTick TickType, FA FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { FGAEffectProperty& InProperty = Params.GetProperty(); - const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpec()->AppliedEventTags; + const FGameplayTagContainer& AppliedEventTags = InProperty.GetSpecData()->AppliedEventTags; FAFEventData Data; @@ -71,25 +70,24 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToSelf( } OnAppliedToSelf.Broadcast(Params.Context, Params.Property, Params.EffectSpec); - if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpec()->EffectTag)) + if (FAFEffectEvent* Delegate = OnEffectApplyToSelf.Find(InProperty.GetSpecData()->EffectTag)) { Delegate->ExecuteIfBound(); } - FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, InHandle, Params, Modifier); + FGAEffectHandle Handle = GameEffectContainer.ApplyEffect(EffectIn, Params, Modifier); GameEffectContainer.MarkArrayDirty(); return Handle; } FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { - FGAEffectProperty& InProperty = Params.GetProperty(); - FGAEffectContext& InContext = Params.GetContext(); - if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpec()->EffectTag)) + const FGAEffectProperty& InProperty = Params.GetProperty(); + const FGAEffectContext& InContext = Params.GetContext(); + if (FAFEffectEvent* Delegate = OnEffectApplyToTarget.Find(InProperty.GetSpecData()->EffectTag)) { Delegate->ExecuteIfBound(); } @@ -98,7 +96,7 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( FAFCueHandle CueHandle = FAFCueHandle::GenerateHandle(); - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + if (InProperty.GetSpecData()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams(InContext, InProperty); MulticastApplyEffectCue(CueParams, CueHandle); @@ -109,7 +107,7 @@ FGAEffectHandle UAFEffectsComponent::ApplyEffectToTarget( if (InContext.TargetComp.IsValid()) { FGAEffectHandle Handle; - Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, InHandle, Params, Modifier); + Handle = InContext.GetTargetEffectsComponent()->ApplyEffectToSelf(EffectIn, Params, Modifier); //if (!PropertyByHandle.Contains(Handle)) // PropertyByHandle.Add(Handle, &InProperty); @@ -126,26 +124,26 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn , FAFEffectParams Params , FAFFunctionModifier Modifier) { - FGAEffectContext& Context = Params.Context.GetRef(); + const FGAEffectContext& Context = Params.Context; FGAEffectProperty& Property = Params.Property.GetRef(); - FAFEffectSpec& EffectSpec = Params.GetSpec(); + const FAFEffectSpec& EffectSpec = Params.GetSpec(); /* this patth will give effects chance to do any replicated events, like applying cues. WE do not make any replication at the ApplyEffect because some effect might want to apply cues on periods on expiration etc, and all those will go trouch ExecuteEffect path. */ - const FGameplayTagContainer& RequiredTags = Property.GetSpec()->RequiredTags; - if (RequiredTags.Num() > 0) + const FGameplayTagContainer& ExecutionDenyTags = Property.GetSpecData()->ExecutionDenyTags; + if (ExecutionDenyTags.Num() > 0) { - if (!HasAll(RequiredTags)) + if (HasAny(ExecutionDenyTags)) { - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s not executed, require tags: %s"), *Property.GetSpec()->GetName(), *RequiredTags.ToString()); + UE_LOG(GameAttributesEffects, Log, TEXT("UAFEffectsComponent:: Effect %s not executed, execution denyied by tags: %s"), *Property.GetSpecData()->GetName(), *ExecutionDenyTags.ToString()); return; } } //apply execution events: - const FGameplayTagContainer& ExecuteEventTags = Property.GetSpec()->ExecuteEventTags; + const FGameplayTagContainer& ExecuteEventTags = Property.GetSpecData()->ExecuteEventTags; FAFEventData Data(Params); for (const FGameplayTag& Tag : ExecuteEventTags) { @@ -153,19 +151,20 @@ void UAFEffectsComponent::ExecuteEffect(FGAEffectHandle HandleIn } //OnEffectExecuted.Broadcast(HandleIn, HandleIn.GetEffectSpec()->OwnedTags); - UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *Property.GetSpec()->GetName()); + UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Effect %s executed"), *Property.GetSpecData()->GetName()); FGAEffectMod Mod = FAFStatics::GetAttributeModifier(Property.GetAttributeModifier() - , Property.GetSpec() + , Property.GetSpecData() , Context , HandleIn); EffectSpec.OnExecuted(); - ExecuteEffectEvent(Property.GetSpec()->OnPeriodEvent); + ExecuteEffectEvent(Property.GetSpecData()->OnPeriodEvent); FAFCueHandle* CueHandle = EffectToCue.Find(HandleIn); + FGAEffectCueParams CueParams(Context, Property); if (CueHandle) - MulticastExecuteEffectCue(*CueHandle); + MulticastExecuteEffectCue(Params.GetProperty().GetSpecData()->StaticClass(), CueParams); Property.ExecuteEffect(HandleIn, Mod, Params, Modifier); PostExecuteEffect(); @@ -181,20 +180,20 @@ void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn { //call effect internal delegate: FGAEffectProperty& InProperty = Params.GetProperty(); - FGAEffectContext& InContext = Params.GetContext(); - FAFEffectSpec& EffectSpec = Params.GetSpec(); + const FGAEffectContext& InContext = Params.GetContext(); + const FAFEffectSpec& EffectSpec = Params.GetSpec(); FGAEffect* Effect = GameEffectContainer.GetEffect(HandleIn); EffectSpec.OnExpired(); ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); - ExecuteEffectEvent(InProperty.GetSpec()->OnExpiredEvent); + ExecuteEffectEvent(InProperty.GetSpecData()->OnExpiredEvent); if (mode == ENetMode::NM_DedicatedServer || mode == ENetMode::NM_ListenServer) { ClientExpireEffect(InProperty.GetPredictionHandle()); } - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + if (InProperty.GetSpecData()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams(InContext, InProperty); @@ -205,7 +204,7 @@ void UAFEffectsComponent::ExpireEffect(FGAEffectHandle HandleIn } } - TArray handles = GameEffectContainer.RemoveEffect(Params.Property); + TArray handles = GameEffectContainer.RemoveEffect(Params.Property, InContext); } void UAFEffectsComponent::ClientExpireEffect_Implementation(FAFPredictionHandle PredictionHandle) @@ -227,7 +226,7 @@ void UAFEffectsComponent::RemoveEffect(const FAFPropertytHandle& InProperty { InternalRemoveEffect(InProperty, InContext); } - ExecuteEffectEvent(InProperty.GetSpec()->OnRemovedEvent); + ExecuteEffectEvent(InProperty.GetSpecData()->OnRemovedEvent); FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); FAFCueHandle* CueHandle = EffectToCue.Find(InHandle); @@ -241,7 +240,7 @@ void UAFEffectsComponent::InternalRemoveEffect(const FAFPropertytHandle& InPrope UE_LOG(GameAttributesEffects, Log, TEXT("UAFAbilityComponent:: Reset Timers and Remove Effect")); //MulticastRemoveEffectCue(HandleIn); - if (InProperty.GetSpec()->Cues.CueTags.Num() > 0) + if (InProperty.GetSpecData()->Cues.CueTags.Num() > 0) { FGAEffectCueParams CueParams(InContext, InProperty.GetRef()); ENetRole role = GetOwnerRole(); @@ -253,7 +252,7 @@ void UAFEffectsComponent::InternalRemoveEffect(const FAFPropertytHandle& InPrope } } - TArray handles = GameEffectContainer.RemoveEffect(InProperty); + TArray handles = GameEffectContainer.RemoveEffect(InProperty, InContext); } void UAFEffectsComponent::AddEffectEvent(const FGameplayTag& InEventTag, const FSimpleDelegate& InEvent) @@ -403,7 +402,7 @@ bool UAFEffectsComponent::DenyEffectApplication(const FGameplayTagContainer& InT bool bDenyApplication = false; if (InTags.Num() > 0) { - bDenyApplication = HasAll(InTags); + bDenyApplication = HasAny(InTags); } return bDenyApplication; } @@ -437,17 +436,17 @@ void UAFEffectsComponent::MulticastApplyEffectCue_Implementation(FGAEffectCuePar if (mode == ENetMode::NM_Standalone || role != ENetRole::ROLE_Authority) { - UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, InHandle); + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, EAFCueEvent::Activated); } } -void UAFEffectsComponent::MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle) +void UAFEffectsComponent::MulticastExecuteEffectCue_Implementation(TSubclassOf EffectSpec, FGAEffectCueParams CueParams) { ENetRole role = GetOwnerRole(); ENetMode mode = GetOwner()->GetNetMode(); if (mode == ENetMode::NM_Standalone || role != ENetRole::ROLE_Authority) { - UAFCueManager::Get()->HandleExecuteCue(InHandle); + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, EAFCueEvent::Executed); } } @@ -458,7 +457,7 @@ void UAFEffectsComponent::MulticastRemoveEffectCue_Implementation(FGAEffectCuePa if (mode == ENetMode::NM_Standalone || role != ENetRole::ROLE_Authority) { - UAFCueManager::Get()->HandleRemoveCue(CueParams.CueTags, CueParams, InHandle); + UAFCueManager::Get()->HandleCue(CueParams.CueTags, CueParams, EAFCueEvent::Removed); } } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp index fbc008a..57cb4a6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Abilities/GAAbilityBase.cpp @@ -135,17 +135,17 @@ void UGAAbilityBase::InitAbility() { //still want to initialize, as Spec is used in multiple places. DefaultContext = UGABlueprintLibrary::MakeContext(this, POwner, AvatarActor, this, FHitResult(ForceInit)).GetRef(); - ActivationEffect.InitializeIfNotInitialized(DefaultContext); - CooldownEffect.InitializeIfNotInitialized(DefaultContext); + ActivationEffect.InitializeIfNotInitialized(POwner, this); + CooldownEffect.InitializeIfNotInitialized(POwner, this); for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) { - AttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + AttributeCost[Idx].InitializeIfNotInitialized(POwner, this); } AttributeCostHandle.AddZeroed(AttributeCost.Num()); for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) { - AbilityAttributeCost[Idx].InitializeIfNotInitialized(DefaultContext); + AbilityAttributeCost[Idx].InitializeIfNotInitialized(POwner, this); } AbilityAttributeCostHandle.AddZeroed(AbilityAttributeCost.Num()); if (AbilityComponent) @@ -255,14 +255,9 @@ void UGAAbilityBase::NativeOnBeginAbilityActivation(bool bApplyActivationEffect) void UGAAbilityBase::OnCooldownEffectExpired() { UE_LOG(AFAbilities, Log, TEXT("Cooldown expired In Ability: %s"), *GetName()); - - if (CooldownEffectHandle.IsValid()) - { - //CooldownEffectHandle.GetContextRef().InstigatorComp->RemoveEffect(CooldownEffect, DefaultContext); - } } /* Functions for activation effect delegates */ -void UGAAbilityBase::NativeOnAbilityActivationFinish(FGAEffectHandle InHandle) +void UGAAbilityBase::NativeOnAbilityActivationFinish() { UE_LOG(AbilityFramework, Log, TEXT("Ability Activation Effect Expired In Ability: %s"), *GetName()); OnActivationFinished(); @@ -280,7 +275,7 @@ void UGAAbilityBase::NativeOnAbilityActivationCancel() OnActivationCancel(); //AbilityActivatedCounter++; } -void UGAAbilityBase::OnActivationEffectPeriod(FGAEffectHandle InHandle) +void UGAAbilityBase::OnActivationEffectPeriod() { UE_LOG(AFAbilities, Log, TEXT("Ability Activation Effect Period In Ability: %s"), *GetName()); @@ -300,9 +295,9 @@ void UGAAbilityBase::NativeFinishAbility() AbilityComponent->ExecutingAbility = nullptr; OnConfirmDelegate.Clear(); OnConfirmDelegate.RemoveAll(this); - if (!ActivationEffectHandle.IsValid()) + if (ActivationEffectHandle.Num() > 0 && !ActivationEffectHandle[0].IsValid()) { - GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle[0]); ActivationEffectHandle.Reset(); } //remove effect. @@ -314,7 +309,7 @@ void UGAAbilityBase::CancelActivation() } void UGAAbilityBase::NativeCancelActivation() { - if (!ActivationEffectHandle.IsValid()) + if (ActivationEffectHandle.Num() > 0 && !ActivationEffectHandle[0].IsValid()) return; UAFAbilityComponent* AttrComp = DefaultContext.InstigatorComp.Get(); @@ -323,7 +318,7 @@ void UGAAbilityBase::NativeCancelActivation() OnConfirmDelegate.RemoveAll(this); if (GetEffectsComponent()) { - GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle); + GetEffectsComponent()->RemoveEffect(ActivationEffect, DefaultContext, ActivationEffectHandle[0]); AbilityState = EAFAbilityState::Waiting; ActivationEffectHandle.Reset(); } @@ -347,18 +342,17 @@ void UGAAbilityBase::ConfirmAbility() bool UGAAbilityBase::ApplyCooldownEffect() { - if (!CooldownEffect.GetSpec()) + if (!CooldownEffect.GetSpecData()) { return false; } FAFFunctionModifier Modifier; - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd, CooldownEffectHandle); - GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpec()->OnExpiredEvent, PeriodDel); + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnCooldownEnd); + GetEffectsComponent()->AddEffectEvent(CooldownEffect.GetSpecData()->OnExpiredEvent, PeriodDel); CooldownEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( CooldownEffect - , CooldownEffectHandle , this , POwner , this @@ -368,17 +362,17 @@ bool UGAAbilityBase::ApplyCooldownEffect() if (role >= ENetRole::ROLE_Authority) { - ClientSetCooldownHandle(CooldownEffectHandle); + ClientSetCooldownHandle(CooldownEffectHandle[0]); } OnCooldownStart(); //CooldownEffectHandle.GetEffectRef().OnEffectExpired.AddUObject(this, &UGAAbilityBase::OnCooldownEnd); return false; } -void UGAAbilityBase::NativeOnCooldownEnd(FGAEffectHandle InHandle) +void UGAAbilityBase::NativeOnCooldownEnd() { //AbilityComponent->RemoveEffect(CooldownEffect, DefaultContext); - OnCooldownEnd(InHandle); + OnCooldownEnd(); CooldownEffectHandle.Reset(); } void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCooldownHandle) @@ -387,7 +381,7 @@ void UGAAbilityBase::ClientSetCooldownHandle_Implementation(FGAEffectHandle InCo } bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) { - if (!ActivationEffect.GetSpec()) + if (!ActivationEffect.GetSpecData()) return false; FHitResult Hit(ForceInit); @@ -402,16 +396,13 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) if (bApplyActivationEffect) { FHitResult HitIn; - if (ActivationEffectHandle.IsValid()) - ActivationEffectHandle.Reset(); - FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish, ActivationEffectHandle); - GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnExpiredEvent, AppliedDel); + FSimpleDelegate AppliedDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::NativeOnAbilityActivationFinish); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpecData()->OnExpiredEvent, AppliedDel); FAFFunctionModifier Modifier; ActivationEffectHandle = UGABlueprintLibrary::ApplyGameEffectToObject( ActivationEffect - , ActivationEffectHandle , this , POwner , this @@ -423,15 +414,15 @@ bool UGAAbilityBase::ApplyActivationEffect(bool bApplyActivationEffect) if (PeriodCheck > 0) { - FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod, ActivationEffectHandle); - GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpec()->OnPeriodEvent, PeriodDel); + FSimpleDelegate PeriodDel = FSimpleDelegate::CreateUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); + GetEffectsComponent()->AddEffectEvent(ActivationEffect.GetSpecData()->OnPeriodEvent, PeriodDel); //if (!ActivationEffectHandle.GetEffectRef().OnEffectPeriod.IsBound()) // ActivationEffectHandle.GetEffectRef().OnEffectPeriod.AddUObject(this, &UGAAbilityBase::OnActivationEffectPeriod); } } else { - NativeOnAbilityActivationFinish(FGAEffectHandle()); + NativeOnAbilityActivationFinish(); } return false; } @@ -535,7 +526,6 @@ bool UGAAbilityBase::ApplyAttributeCost() { AttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( AttributeCost[Idx] - , AttributeCostHandle[Idx] , POwner , POwner , this @@ -557,7 +547,6 @@ bool UGAAbilityBase::ApplyAbilityAttributeCost() { AbilityAttributeCostHandle[Idx] = UGABlueprintLibrary::ApplyGameEffectToObject( AbilityAttributeCost[Idx] - , AbilityAttributeCostHandle[Idx] , this , POwner , this @@ -588,8 +577,8 @@ bool UGAAbilityBase::CheckAbilityAttributeCost() { for (int32 Idx = 0; Idx < AbilityAttributeCost.Num(); Idx++) { - float ModValue = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float ModValue = AbilityAttributeCost[Idx].GetSpecData()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AbilityAttributeCost[Idx].GetSpecData()->AtributeModifier.Attribute; float AttributeVal = GetAttributes()->GetFloatValue(Attribute); if (ModValue > AttributeVal) return false; @@ -602,8 +591,8 @@ bool UGAAbilityBase::CheckAttributeCost() for (int32 Idx = 0; Idx < AttributeCost.Num(); Idx++) { - float ModValue = AttributeCost[Idx].GetSpec()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); - FGAAttribute Attribute = AttributeCost[Idx].GetSpec()->AtributeModifier.Attribute; + float ModValue = AttributeCost[Idx].GetSpecData()->AtributeModifier.Magnitude.GetFloatValue(DefaultContext); + FGAAttribute Attribute = AttributeCost[Idx].GetSpecData()->AtributeModifier.Attribute; float AttributeVal = Interface->GetAttributes()->GetFloatValue(Attribute); if (ModValue > AttributeVal) return false; @@ -612,8 +601,11 @@ bool UGAAbilityBase::CheckAttributeCost() } bool UGAAbilityBase::IsOnCooldown() { + if (CooldownEffectHandle.Num() <= 0) + return false; + bool bOnCooldown = false; - bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle); + bOnCooldown = GetEffectsComponent()->IsEffectActive(CooldownEffectHandle[0]); if (bOnCooldown) { OnNotifyOnCooldown.Broadcast(); @@ -622,8 +614,11 @@ bool UGAAbilityBase::IsOnCooldown() } bool UGAAbilityBase::IsActivating() { + if (ActivationEffectHandle.Num() <= 0) + return false; + bool bAbilityActivating = false; - bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffect.GetHandle(this)); + bool bHaveEffect = GetEffectsComponent()->IsEffectActive(ActivationEffectHandle[0]); bool bInActivatingState = AbilityState == EAFAbilityState::Activating; UE_LOG(AbilityFramework, Log, TEXT("IsActivating Ability, Effect: %s, State: %s \n"), bHaveEffect ? TEXT("true") : TEXT("false"), bInActivatingState ? TEXT("true") : TEXT("false")); bAbilityActivating = bHaveEffect || bInActivatingState; @@ -641,11 +636,16 @@ void UGAAbilityBase::BP_ApplyCooldown() float UGAAbilityBase::GetCurrentActivationTime() { - if (ActivationEffectHandle.IsValid()) + if (ActivationEffectHandle.Num() <= 0) + { + return 0; + } + + if (ActivationEffectHandle[0].IsValid()) { if (IAFAbilityInterface* Interface = DefaultContext.TargetInterface) { - FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle); + FGAEffect* Effect = Interface->GetEffectsComponent()->GetEffect(ActivationEffectHandle[0]); if (Effect) { return Effect->GetCurrentDuration(); @@ -834,23 +834,33 @@ bool UGAAbilityBase::LineTraceSingleByChannelCorrected(FName SocketName, float R //Helpers float UGAAbilityBase::GetActivationRemainingTime() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle); + if (ActivationEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(ActivationEffectHandle[0]); } float UGAAbilityBase::GetActivationRemainingTimeNormalized() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle); + if (ActivationEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(ActivationEffectHandle[0]); } float UGAAbilityBase::GetActivationCurrentTime() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle); + if (ActivationEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(ActivationEffectHandle[0]); } float UGAAbilityBase::GetActivationCurrentTimeNormalized() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle); + if (ActivationEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(ActivationEffectHandle[0]); } float UGAAbilityBase::GetActivationEndTime() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle); + if (ActivationEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(ActivationEffectHandle[0]); } float UGAAbilityBase::BP_GetActivationRemainingTime() { @@ -876,23 +886,33 @@ float UGAAbilityBase::BP_GetActivationEndTime() float UGAAbilityBase::GetCooldownRemainingTime() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle); + if (CooldownEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTime(CooldownEffectHandle[0]); } float UGAAbilityBase::GetCooldownRemainingTimeNormalized() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle); + if (CooldownEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetRemainingTimeNormalized(CooldownEffectHandle[0]); } float UGAAbilityBase::GetCooldownCurrentTime() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle); + if (CooldownEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTime(CooldownEffectHandle[0]); } float UGAAbilityBase::GetCooldownCurrentTimeNormalized() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle); + if (CooldownEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetCurrentTimeNormalized(CooldownEffectHandle[0]); } float UGAAbilityBase::GetCooldownEndTime() const { - return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle); + if (CooldownEffectHandle.Num() <= 0) + return 0; + return NativeGetEffectsComponent()->GameEffectContainer.GetEndTime(CooldownEffectHandle[0]); } float UGAAbilityBase::BP_GetCooldownRemainingTime() { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp index 25f3d4f..a2e5e3e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/AbilityFramework.cpp @@ -1,7 +1,8 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. #pragma once #include "AbilityFramework.h" - +#include "AFCueManager.h" +#include "Misc/CoreDelegates.h" DEFINE_LOG_CATEGORY(AbilityFramework); DEFINE_LOG_CATEGORY(GameAttributesGeneral); DEFINE_LOG_CATEGORY(GameAttributes); @@ -199,6 +200,9 @@ void FAbilityFramework::StartupModule() #endif //WITH_EDITOR //FAFEffectTimerManager::Get(); // This code will execute after your module is loaded into memory (but after global variables are initialized, of course.) + + //initialize existing cues. + FCoreDelegates::OnFEngineLoopInitComplete.AddRaw(this, &FAbilityFramework::InitCues); } @@ -208,6 +212,9 @@ void FAbilityFramework::ShutdownModule() // we call this function before unloading the module. } - +void FAbilityFramework::InitCues() +{ + UAFCueManager::Get(); +} IMPLEMENT_MODULE(FAbilityFramework, AbilityFramework) \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp index f62f9c2..5f2aef1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributeBase.cpp @@ -158,18 +158,16 @@ bool FAFAttributeBase::CheckIfStronger(const FGAEffectMod& InMod) return false; } float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - FGAEffectProperty& InProperty, const FAFContextHandle& InContext) + FGAEffectProperty& InProperty, const FGAEffectContext& InContext) { //FString name = GetTypeName(); if (ExtensionClass) { ExtensionClass.GetDefaultObject()->OnPreAttributeModify(AbilityComp, SelfName, CurrentValue); - FGAEffectContext* Context = InContext.GetPtr(); - if (InContext.IsValid()) - { - ExtensionClass.GetDefaultObject()->PreAttributeModify(InContext.GetRef() - , CurrentValue); - } + + ExtensionClass.GetDefaultObject()->PreAttributeModify(InContext + , CurrentValue); + } float returnValue = -1; @@ -181,7 +179,7 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& if ( !InProperty.GetIsInstant()) { FGAModifier AttrMod(ModIn.AttributeMod, ModIn.Value, HandleIn); - AttrMod.Tags.AppendTags(InProperty.GetSpec()->AttributeTags); + AttrMod.Tags.AppendTags(InProperty.GetSpecData()->AttributeTags); AddBonus(ModIn, HandleIn); return ModIn.Value; } @@ -232,13 +230,11 @@ float FAFAttributeBase::Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& { ExtensionClass.GetDefaultObject()->OnPostAttributeModify(AbilityComp, SelfName, returnValue); - if (InContext.IsValid()) - { - ExtensionClass.GetDefaultObject()->PostAttributeModify( - InContext.GetRef() + ExtensionClass.GetDefaultObject()->PostAttributeModify( + InContext , PreValue , returnValue); - } + } return returnValue; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp index 10c7d3d..fe29ab0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBase.cpp @@ -294,7 +294,7 @@ void UGAAttributesBase::ModifyAttribute(const FGAEffect& EffectIn) float UGAAttributesBase::ModifyAttribute(const FGAEffectMod& ModIn , const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty - , const FAFContextHandle& InContext) + , const FGAEffectContext& InContext) { FAFAttributeBase* attr = nullptr; UGAAttributesBase* atrObj = this; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp index 3a194a8..a4fc7f1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Attributes/GAAttributesBlueprintFunctionLibrary.cpp @@ -67,6 +67,6 @@ void UGAAttributesBlueprintFunctionLibrary::ExchangeAttributesValues( return; FAFFunctionModifier ModF; - UGABlueprintLibrary::ApplyGameEffectToObject(From, FromHandle, FromTarget, Instigator, Causer, ModF); - UGABlueprintLibrary::ApplyGameEffectToObject(To, ToHandle, ToTarget, Instigator, Causer, ModF); + UGABlueprintLibrary::ApplyGameEffectToObject(From, FromTarget, Instigator, Causer, ModF); + UGABlueprintLibrary::ApplyGameEffectToObject(To, ToTarget, Instigator, Causer, ModF); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticBlueprint.cpp new file mode 100644 index 0000000..ee34def --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticBlueprint.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFCueStaticBlueprint.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticGeneratedClass.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticGeneratedClass.cpp new file mode 100644 index 0000000..13b398a --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Cues/AFCueStaticGeneratedClass.cpp @@ -0,0 +1,8 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" +#include "AFCueStaticGeneratedClass.h" + + + + diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActor.cpp similarity index 76% rename from Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp rename to Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActor.cpp index 0564782..2814c05 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCue.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActor.cpp @@ -1,32 +1,32 @@ // Fill out your copyright notice in the Description page of Project Settings. -#include "../AbilityFramework.h" +#include "AbilityFramework.h" #include "MovieScene.h" #include "GAEffectCueSequence.h" #include "ActorSequencePlayer.h" -#include "GAEffectCue.h" +#include "AFCueActor.h" -AGAEffectCue::AGAEffectCue(const FObjectInitializer& ObjectInitializer) +AAFCueActor::AAFCueActor(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { PrimaryActorTick.bCanEverTick = true; PrimaryActorTick.bStartWithTickEnabled = true; StartTime = 0; EndTime = 5; - if (HasAnyFlags(RF_ClassDefaultObject) || GetArchetype() == GetDefault()) + if (HasAnyFlags(RF_ClassDefaultObject) || GetArchetype() == GetDefault()) { Sequence = ObjectInitializer.CreateDefaultSubobject(this, "Sequence"); Sequence->SetFlags(RF_Public | RF_Transactional); SequencePlayer = ObjectInitializer.CreateDefaultSubobject(this, "SequencePlayer"); } } -void AGAEffectCue::PostInitProperties() +void AAFCueActor::PostInitProperties() { UpdateAssetRegistryInfo(); Super::PostInitProperties(); } -void AGAEffectCue::Serialize(FArchive& Ar) +void AAFCueActor::Serialize(FArchive& Ar) { if (Ar.IsSaving()) { @@ -41,7 +41,7 @@ void AGAEffectCue::Serialize(FArchive& Ar) } } #if WITH_EDITORONLY_DATA -void AGAEffectCue::UpdateAssetBundleData() +void AAFCueActor::UpdateAssetBundleData() { AssetBundleData.Reset(); UpdateAssetRegistryInfo(); @@ -53,7 +53,7 @@ void AGAEffectCue::UpdateAssetBundleData() } } -void AGAEffectCue::PreSave(const class ITargetPlatform* TargetPlatform) +void AAFCueActor::PreSave(const class ITargetPlatform* TargetPlatform) { Super::PreSave(TargetPlatform); @@ -66,7 +66,7 @@ void AGAEffectCue::PreSave(const class ITargetPlatform* TargetPlatform) } } #endif -void AGAEffectCue::PostLoad() +void AAFCueActor::PostLoad() { Super::PostLoad(); @@ -82,12 +82,12 @@ void AGAEffectCue::PostLoad() } #endif } -FPrimaryAssetId AGAEffectCue::GetPrimaryAssetId() const +FPrimaryAssetId AAFCueActor::GetPrimaryAssetId() const { FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); - const AGAEffectCue* A = this; - return FPrimaryAssetId(FPrimaryAssetType("EffectCue"), dupa1); + const AAFCueActor* A = this; + return FPrimaryAssetId(FPrimaryAssetType("ActorCue"), dupa1); //if (HasAnyFlags(RF_ClassDefaultObject)) { UClass* SearchNativeClass = GetClass(); @@ -111,12 +111,12 @@ FPrimaryAssetId AGAEffectCue::GetPrimaryAssetId() const //return FPrimaryAssetId(GetClass()->GetFName(), GetFName()); } -void AGAEffectCue::SetAnimation(class UGAEffectCueSequence* InSequence) +void AAFCueActor::SetAnimation(class UGAEffectCueSequence* InSequence) { Sequence = InSequence; } // Called when the game starts or when spawned -void AGAEffectCue::BeginPlay() +void AAFCueActor::BeginPlay() { if (!SequencePlayer) { @@ -129,7 +129,7 @@ void AGAEffectCue::BeginPlay() } // Called every frame -void AGAEffectCue::Tick( float DeltaTime ) +void AAFCueActor::Tick( float DeltaTime ) { Super::Tick( DeltaTime ); if (SequencePlayer) @@ -137,7 +137,7 @@ void AGAEffectCue::Tick( float DeltaTime ) SequencePlayer->Update(DeltaTime); } } -void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, +void AAFCueActor::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObject* Causer, const FHitResult& HitInfo, const FGAEffectCueParams& CueParams) { BeginCue(InstigatorOut, TargetOut, Causer, HitInfo); @@ -147,16 +147,16 @@ void AGAEffectCue::NativeBeginCue(AActor* InstigatorOut, AActor* TargetOut, UObj } } -void AGAEffectCue::NativeOnExecuted() +void AAFCueActor::NativeOnExecuted() { OnExecuted(); } -void AGAEffectCue::NativeOnRemoved() +void AAFCueActor::NativeOnRemoved() { OnRemoved(); } -void AGAEffectCue::UpdateAssetRegistryInfo() +void AAFCueActor::UpdateAssetRegistryInfo() { EffectCueTagSearch = CueTag.GetTagName(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActorBlueprint.cpp similarity index 66% rename from Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp rename to Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActorBlueprint.cpp index a9f021e..b16fef9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprint.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActorBlueprint.cpp @@ -1,12 +1,12 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. #include "AbilityFramework.h" -#include "GAEffectCueBlueprint.h" +#include "AFCueActorBlueprint.h" ////////////////////////////////////////////////////////////////////////// // UGameplayAbilityBlueprint -UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectInitializer) +UAFCueActorBlueprint::UAFCueActorBlueprint(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { } @@ -14,14 +14,14 @@ UGAEffectCueBlueprint::UGAEffectCueBlueprint(const FObjectInitializer& ObjectIni #if WITH_EDITOR /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ -UGAEffectCueBlueprint* UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint) +UAFCueActorBlueprint* UAFCueActorBlueprint::FindRootGameplayAbilityBlueprint(UAFCueActorBlueprint* DerivedBlueprint) { - UGAEffectCueBlueprint* ParentBP = NULL; + UAFCueActorBlueprint* ParentBP = NULL; // Determine if there is a gameplay ability blueprint in the ancestry of this class for (UClass* ParentClass = DerivedBlueprint->ParentClass; ParentClass != UObject::StaticClass(); ParentClass = ParentClass->GetSuperClass()) { - if (UGAEffectCueBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) + if (UAFCueActorBlueprint* TestBP = Cast(ParentClass->ClassGeneratedBy)) { ParentBP = TestBP; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActorGeneratedClass.cpp similarity index 50% rename from Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp rename to Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActorGeneratedClass.cpp index 580daab..f04cbf6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueBlueprintGeneratedClass.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueActorGeneratedClass.cpp @@ -1,12 +1,12 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" -#include "GAEffectCueBlueprintGeneratedClass.h" +#include "AbilityFramework.h" +#include "AFCueActorGeneratedClass.h" ////////////////////////////////////////////////////////////////////////// // UGameplayAbilityBlueprint -UGAEffectCueBlueprintGeneratedClass::UGAEffectCueBlueprintGeneratedClass(const FObjectInitializer& ObjectInitializer) +UAFCueActorGeneratedClass::UAFCueActorGeneratedClass(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueStatic.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueStatic.cpp new file mode 100644 index 0000000..f6bc2d4 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/AFCueStatic.cpp @@ -0,0 +1,131 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#include "AbilityFramework.h" + +#include "Engine/AssetManager.h" + +#include "AFCueStatic.h" + + +UAFCueStatic::UAFCueStatic(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + +} + +void UAFCueStatic::PostInitProperties() +{ + UpdateAssetRegistryInfo(); + Super::PostInitProperties(); +} + +void UAFCueStatic::Serialize(FArchive& Ar) +{ + if (Ar.IsSaving()) + { + UpdateAssetRegistryInfo(); + } + + Super::Serialize(Ar); + + if (Ar.IsLoading()) + { + UpdateAssetRegistryInfo(); + } +} +#if WITH_EDITORONLY_DATA +void UAFCueStatic::UpdateAssetBundleData() +{ + AssetBundleData.Reset(); + UpdateAssetRegistryInfo(); + + // By default parse the metadata + if (UAssetManager::IsValid()) + { + UAssetManager::Get().InitializeAssetBundlesFromMetadata(this, AssetBundleData); + } +} + +void UAFCueStatic::PreSave(const class ITargetPlatform* TargetPlatform) +{ + Super::PreSave(TargetPlatform); + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid()) + { + // Bundles may have changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +} +#endif +void UAFCueStatic::PostLoad() +{ + Super::PostLoad(); + +#if WITH_EDITORONLY_DATA + FAssetBundleData OldData = AssetBundleData; + + UpdateAssetBundleData(); + + if (UAssetManager::IsValid() && OldData != AssetBundleData) + { + // Bundles changed, refresh + UAssetManager::Get().RefreshAssetData(this); + } +#endif +} +FPrimaryAssetId UAFCueStatic::GetPrimaryAssetId() const +{ + FName dupa1 = FPackageName::GetShortFName(GetOutermost()->GetFName()); + + const UAFCueStatic* A = this; + return FPrimaryAssetId(FPrimaryAssetType("StaticCue"), dupa1); + //if (HasAnyFlags(RF_ClassDefaultObject)) + { + UClass* SearchNativeClass = GetClass(); + + while (SearchNativeClass && !SearchNativeClass->HasAnyClassFlags(CLASS_Native | CLASS_Intrinsic)) + { + SearchNativeClass = SearchNativeClass->GetSuperClass(); + } + + if (SearchNativeClass && SearchNativeClass != GetClass()) + { + // If blueprint, return native class and asset name + + } + + // Native CDO, return nothing + return FPrimaryAssetId(); + } +} +void UAFCueStatic::UpdateAssetRegistryInfo() +{ + EffectCueTagSearch = CueTag.GetTagName(); +} + +bool UAFCueStatic::OnExecuted_Implementation(const FGAEffectCueParams& Hit) const +{ + return true; +} +void UAFCueStatic::OnActivate_Implementation(const FGAEffectCueParams& Hit) const +{ +} +void UAFCueStatic::OnExpire_Implementation(const FGAEffectCueParams& Hit) const +{ +} +void UAFCueStatic::OnRemoved_Implementation(const FGAEffectCueParams& Hit) const +{ +} + +UWorld* UAFCueStatic::GetWorld() const +{ + /*TIndirectArray WorldContexts = GEngine->GetWorldContexts(); + UWorld* World = nullptr; + for (const FWorldContext& Ctx : WorldContexts) + { + World = Ctx.World(); + }*/ + return nullptr; +} \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp index 46e7ee3..95a6008 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/ApplicationRequirement/AFAttributeStongerOverride.cpp @@ -15,14 +15,14 @@ bool UAFAttributeStongerOverride::CanApply( , struct FGAEffectContainer* InContainer) { bool bCanApply = true; - FGAAttribute Attribute = Params.GetProperty().GetSpec()->AtributeModifier.Attribute; + FGAAttribute Attribute = Params.GetProperty().GetSpecData()->AtributeModifier.Attribute; FAFAttributeBase* AttributePtr = Params.GetContext().TargetInterface->GetAttribute(Attribute); FGAEffectProperty& InProperty = Params.GetProperty(); if (AttributePtr) { FGAEffectMod mod = FAFStatics::GetAttributeModifier(InProperty.GetAttributeModifier() - , InProperty.GetSpec() + , InProperty.GetSpecData() , Params.GetContext() , InHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp index d38c4e1..d043d7a 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAtributeDurationUnique.cpp @@ -16,7 +16,7 @@ bool UAFAtributeDurationUnique::ApplyEffect( , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { - if (InContainer->IsEffectActive(Params.GetSpec().GetEffectClass())) + if (InContainer->IsEffectActive(Params.Property.SpecClass.SpecClass.Get())) { return false; } diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp index 145e7bf..02e6f6c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFAttributeDurationOverride.cpp @@ -15,7 +15,7 @@ bool UAFAttributeDurationOverride::ApplyEffect( , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { - InContainer->RemoveEffect(Params.Property); + InContainer->RemoveEffect(Params.Property, Params.GetContext()); FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp index c6b461d..3d47b88 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationExtend.cpp @@ -22,7 +22,7 @@ bool UAFPeriodApplicationExtend::ApplyEffect( FGAEffect& ExtEffect = *InContainer->GetEffect(handle); FGAEffect& Effect = const_cast(EffectIn); - FGAEffectContext& ExtContext = const_cast(Params).GetProperty().GetContext(handle).GetRef(); + FGAEffectContext& ExtContext = const_cast(Params).GetContext(); FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp index db10dbe..255e753 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/CustomApplications/AFPeriodApplicationOverride.cpp @@ -16,7 +16,7 @@ bool UAFPeriodApplicationOverride::ApplyEffect( , const FAFFunctionModifier& Modifier) { - InContainer->RemoveEffect(Params.Property); + InContainer->RemoveEffect(Params.Property, Params.GetContext()); FTimerManager& DurationTimer = const_cast(Params).GetTargetTimerManager(); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp index 584eaed..79bf78f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.cpp @@ -34,9 +34,9 @@ void UAFEffectTask_EffectAppliedToSelf::Activate() Super::Activate(); } -void UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback(FAFContextHandle Context +void UAFEffectTask_EffectAppliedToSelf::GameplayEventCallback(FGAEffectContext Context , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec) + , FAFEffectSpec Spec) { //if (ShouldBroadcastAbilityTaskDelegates()) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp index 9c8b566..b81e9f6 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.cpp @@ -37,9 +37,9 @@ void UAFEffectTask_EffectAppliedToTarget::Activate() Super::Activate(); } -void UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback(FAFContextHandle Context +void UAFEffectTask_EffectAppliedToTarget::GameplayEventCallback(FGAEffectContext Context , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec) + , FAFEffectSpec Spec) { //if (ShouldBroadcastAbilityTaskDelegates()) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp index be0a89d..be06b10 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GABlueprintLibrary.cpp @@ -14,47 +14,82 @@ #include "Engine/Engine.h" #include "AFSimpleInterface.h" #include "AFAttributeInterface.h" +#include "AFEffectsComponent.h" UGABlueprintLibrary::UGABlueprintLibrary(const FObjectInitializer& ObjectInitializer) -: Super(ObjectInitializer) + : Super(ObjectInitializer) { } -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToObject( +TArray UGABlueprintLibrary::ApplyGameEffectToObject( UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle , class UObject* Target , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier) { - return ApplyEffectToObject(InEffect, Handle, Target, Instigator, Causer, Modifier); + TArray Targets; + Targets.Add(Target); + return ApplyEffectToObject(InEffect, Targets, Instigator, Causer, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToActor( +TArray UGABlueprintLibrary::ApplyGameEffectToActor( UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle , class AActor* Target , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier) { - return ApplyEffectToActor(InEffect, Handle, Target, Instigator, Causer, Modifier); + TArray Targets; + Targets.Add(Target); + return ApplyEffectToActor(InEffect, Targets, Instigator, Causer, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyGameEffectToLocation( +TArray UGABlueprintLibrary::ApplyGameEffectToLocation( UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle , const FHitResult& Target , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier) { - return ApplyEffectFromHit(InEffect, Handle, Target, Instigator, Causer, Modifier); + TArray Targets; + Targets.Add(Target); + return ApplyEffectFromHit(InEffect, Targets, Instigator, Causer, Modifier); } + +TArray UGABlueprintLibrary::ApplyGameEffectToObjects( + UPARAM(Ref) FAFPropertytHandle& InEffect + , TArray Targets + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffectToObject(InEffect, Targets, Instigator, Causer, Modifier); +} +TArray UGABlueprintLibrary::ApplyGameEffectToActors( + UPARAM(Ref) FAFPropertytHandle& InEffect + , TArray Targets + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffectToActor(InEffect, Targets, Instigator, Causer, Modifier); +} + +TArray UGABlueprintLibrary::ApplyGameEffectToTargets( + UPARAM(Ref) FAFPropertytHandle& InEffect + , const TArray& Targets + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier) +{ + return ApplyEffectFromHit(InEffect, Targets, Instigator, Causer, Modifier); +} + + FString NetModeToString(ENetMode NetMode) { switch (NetMode) @@ -72,269 +107,152 @@ FString NetModeToString(ENetMode NetMode) return FString("Invalid"); } -FGAEffectHandle UGABlueprintLibrary::ApplyEffect( +TArray UGABlueprintLibrary::ApplyEffect( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target + , TArray Targets , class APawn* Instigator , UObject* Causer - , const FHitResult& HitIn + , const TArray& HitsIn , const FAFFunctionModifier& Modifier) { - ENetMode NetMode = GEngine->GetNetMode(Instigator->GetWorld()); - - UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect START, NetMode %s"), *NetModeToString(NetMode)); - UE_LOG(GameAttributesEffects, Error, TEXT("-----")); - IAFAbilityInterface* Ability = Cast(Causer); - if (!Ability) + bool bCheckHits = Targets.Num() == HitsIn.Num(); + TArray Handles; + for (int32 Idx = 0; Idx < Targets.Num(); Idx++) { - UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); - return FGAEffectHandle(); - } - - IAFAbilityInterface* TargetInterface = Cast(Target); - if (!InEffect.GetClass().GetDefaultObject()->Application.GetDefaultObject()->CanApply(TargetInterface, InEffect.GetClass())) - { - return FGAEffectHandle(); - } - bool bReusedParams = false; - bool bPeriodicEffect = false; - bool bReusedSpec = false; - if (Handle.IsValid() && (InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) - { - bPeriodicEffect = true; - } + UObject* Target = Targets[Idx]; + FHitResult HitIn; + if (bCheckHits) + { + HitIn = HitsIn[Idx]; + } + - FAFContextHandle Context; - FAFEffectSpecHandle EffectSpecHandle; - - //only reused Spec and Context if effect is instant ? - if (Handle.IsValid() && !bPeriodicEffect) - { - Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); + ENetMode NetMode = GEngine->GetNetMode(Instigator->GetWorld()); - FAFContextHandle ExistingContext = InEffect.GetContext(Handle); - /*if (ExistingContext.IsValid()) + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect START, NetMode %s"), *NetModeToString(NetMode)); + UE_LOG(GameAttributesEffects, Error, TEXT("-----")); + IAFAbilityInterface* Ability = Cast(Causer); + if (!Ability) { - Context = ExistingContext; - Context.SetTarget(Target); - bReusedParams = true; - }*/ - /*FAFEffectSpecHandle SpecHandle = InEffect.GetEffectSpec(Handle); - EffectSpecHandle = SpecHandle; - bReusedParams = true; - bReusedSpec = true;*/ - } - else - { - Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - } - - InEffect.InitializeIfNotInitialized(Context.GetRef()); - UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); - + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); + return Handles; + } - if ((InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) - { - bPeriodicEffect = true; - } + IAFAbilityInterface* TargetInterface = Cast(Target); - if (!InEffect.IsInitialized()) - { - UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); - return FGAEffectHandle(); - } - - - if (!Target2->HaveEffectRquiredTags(InEffect.GetSpec()->RequiredTags)) - { - return FGAEffectHandle(); - } - if (Target2->DenyEffectApplication(InEffect.GetSpec()->DenyTags)) - { - return FGAEffectHandle(); - } - UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); - FGAEffect effect; - effect.World = Instigator->GetWorld(); - if (Ability) - { - //InEffect.SetPredictionHandle(Ability->GetPredictionHandle()); + if (!InEffect.GetClass().GetDefaultObject()->Application.GetDefaultObject()->CanApply(TargetInterface, InEffect.GetClass())) + { + return Handles; + } + bool bReusedParams = false; + bool bPeriodicEffect = false; - effect.PredictionHandle = Ability->GetPredictionHandle(); - } - IAFAbilityInterface* InstigatorInterface = Cast(Instigator); - - FAFEffectParams Params(InEffect); - if (Params.EffectSpec.GetPtr()) - { - if (Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target.IsValid()) + FAFEffectSpecHandle EffectSpecHandle; + FAFEffectParams Params(InEffect); + InEffect.InitializeIfNotInitialized(Instigator, Causer); + Params.Context = InEffect.GetPtr()->GetContextCopy(Target, HitIn); + + UAFEffectsComponent* Target2 = Params.Context.GetTargetEffectsComponent(); + + UGAGameEffectSpec* Spec = InEffect.GetSpecData(); + + if (!Target2->HaveEffectRquiredTags(Spec->ApplicationRequiredTags)) { - UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + return Handles; } - } - if (!bReusedSpec) - { - FAFEffectSpec* EffectSpec = new FAFEffectSpec(Context, InEffect.GetClass()); - AddTagsToEffect(EffectSpec); - Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); - if (EffectSpec->GetContext().GetPtr()->Target.IsValid()) + if (Target2->DenyEffectApplication(Spec->DenyTags)) { - UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *EffectSpec->GetContext().GetPtr()->Target->GetName()); + return Handles; } - } - else - { - Params.EffectSpec = EffectSpecHandle; - Params.EffectSpec.SetContext(Context); - } - if (Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target.IsValid()) - { - UE_LOG(GameAttributesEffects, Log, TEXT(" Post Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); - } - Params.bRecreated = bReusedParams; - Params.bPeriodicEffect = bPeriodicEffect; - Params.Context = Context; - FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); + if ((InEffect.GetDuration() > 0 || InEffect.GetPeriod() > 0)) + { + bPeriodicEffect = true; + } - UE_LOG(GameAttributesEffects, Error, TEXT("-----")); - UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect END")); - + if (!InEffect.IsInitialized()) + { + UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); + return Handles; + } - return NewHandle; -} -FGAEffectHandle UGABlueprintLibrary::ApplyEffect( - FGAEffectProperty* InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FHitResult& HitIn - , const FAFFunctionModifier& Modifier) -{ - //IAFAbilityInterface* Ability = Cast(Causer); - //if (!Ability) - //{ - // UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect Effects must be applied trough Ability")); - // return FGAEffectHandle(); - //} - //bool bReusedParams = false; - //bool bPeriodicEffect = false; - //bool bReusedSpec = false; - //if (Handle.IsValid() && (InEffect->GetDuration() > 0 || InEffect->GetPeriod() > 0)) - //{ - // bPeriodicEffect = true; - //} - - //FAFContextHandle Context; - //FAFEffectSpecHandle EffectSpecHandle; - - //if (Handle.IsValid()) - //{ - // if (bPeriodicEffect) - // { - // FAFContextHandle* ExistingContext = InEffect->GetContext(Handle); - // if (ExistingContext) - // { - // Context = *ExistingContext; - // Context.SetTarget(Target); - // bReusedParams = true; - // } - // FAFEffectSpecHandle* SpecHandle = InEffect->GetEffectSpec(Handle); - // EffectSpecHandle = *SpecHandle; - // bReusedSpec = true; - // } - // else - // { - // Context = InEffect->GetInstantContext(); - // Context.SetTarget(Target); - - // EffectSpecHandle = InEffect->GetInstantEffectSpec(); - // bReusedParams = true; - // bReusedSpec = true; - // } - //} - //else - //{ - // Context = MakeContext(Target, Instigator, nullptr, Causer, HitIn); - //} - - //InEffect->InitializeIfNotInitialized(Context.GetRef()); - - //if (!InEffect->IsInitialized()) - //{ - // UE_LOG(GameAttributesEffects, Error, TEXT("Invalid Effect Spec")); - // return FGAEffectHandle(); - //} - - //UAFEffectsComponent* Target2 = Context.GetRef().GetTargetEffectsComponent(); - //if (!Target2->HaveEffectRquiredTags(InEffect->GetSpec()->RequiredTags)) - //{ - // return FGAEffectHandle(); - //} - //if (Target2->DenyEffectApplication(InEffect->GetSpec()->DenyTags)) - //{ - // return FGAEffectHandle(); - //} - //UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Context.GetRef().ToString()); - - //FGAEffect effect; - //effect.World = Instigator->GetWorld(); - //if (Ability) - //{ - // InEffect->SetPredictionHandle(Ability->GetPredictionHandle()); - // effect.PredictionHandle = Ability->GetPredictionHandle(); - // - //} - // - //FAFPropertytHandle Property = FAFPropertytHandle::Generate(*InEffect); - //FAFEffectParams Params(Property); - //FAFEffectSpec* EffectSpec = new FAFEffectSpec(); - ////AddTagsToEffect(EffectSpec); - //Params.Context = Context; - // - //Params.EffectSpec = FAFEffectSpecHandle::Generate(EffectSpec); - - //IAFAbilityInterface* InstigatorInterface = Cast(Instigator); - //FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Handle, Params, Modifier); - FGAEffectHandle NewHandle; - return NewHandle; + + + UE_LOG(GameAttributesEffects, Log, TEXT("MakeOutgoingSpecObj: Created new Context: %s"), *Params.Context.ToString()); + + FGAEffect effect; + effect.World = Instigator->GetWorld(); + if (Ability) + { + effect.PredictionHandle = Ability->GetPredictionHandle(); + } + IAFAbilityInterface* InstigatorInterface = Cast(Instigator); + + + /*if (Params.EffectSpec.GetPtr()) + { + if (Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target.IsValid()) + { + UE_LOG(GameAttributesEffects, Log, TEXT(" Pre Spec Target: %s"), *Params.EffectSpec.GetPtr()->GetContext().GetPtr()->Target->GetName()); + } + }*/ + + Params.EffectSpec = InEffect.GetPtr()->GetSpecCopy(); + AddTagsToEffect(&Params.EffectSpec); + + Params.bRecreated = bReusedParams; + Params.bPeriodicEffect = bPeriodicEffect; + + FGAEffectHandle NewHandle = InstigatorInterface->ApplyEffectToTarget(effect, Params, Modifier); + Handles.Add(NewHandle); + UE_LOG(GameAttributesEffects, Error, TEXT("-----")); + UE_LOG(GameAttributesEffects, Error, TEXT("UGABlueprintLibrary::ApplyEffect END")); + + } + return Handles; } -FGAEffectHandle UGABlueprintLibrary::ApplyEffectFromHit( + +TArray UGABlueprintLibrary::ApplyEffectFromHit( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , const FHitResult& Target + , const TArray& Targets , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier) { - return ApplyEffect(InEffect, Handle, Target.GetActor(), Instigator, Causer, Target, Modifier); + TArray ActorTargets; + for (const FHitResult& Hit : Targets) + { + ActorTargets.Add(Hit.GetActor()); + } + return ApplyEffect(InEffect, ActorTargets, Instigator, Causer, Targets, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyEffectToActor( +TArray UGABlueprintLibrary::ApplyEffectToActor( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class AActor* Target + , TArray Target , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier) { - FHitResult Hit(ForceInit); - return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); + TArray Hits; + TArray ObjTargets; + for (AActor* A : Target) + { + ObjTargets.Add(A); + } + return ApplyEffect(InEffect, ObjTargets, Instigator, Causer, Hits, Modifier); } -FGAEffectHandle UGABlueprintLibrary::ApplyEffectToObject( +TArray UGABlueprintLibrary::ApplyEffectToObject( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target + , TArray Target , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier) { - FHitResult Hit(ForceInit); - return ApplyEffect(InEffect, Handle, Target, Instigator, Causer, Hit, Modifier); + TArray Hits; + return ApplyEffect(InEffect, Target, Instigator, Causer, Hits, Modifier); } FAFContextHandle UGABlueprintLibrary::MakeContext(class UObject* Target, class APawn* Instigator, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp index b373f14..1fc2476 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectCueSequence.cpp @@ -1,7 +1,7 @@ // Fill out your copyright notice in the Description page of Project Settings. #include "../AbilityFramework.h" -#include "GAEffectCue.h" +#include "AFCueActor.h" #include "MovieScene.h" #include "MovieSceneCommonHelpers.h" #include "Modules/ModuleManager.h" @@ -36,10 +36,10 @@ UGAEffectCueSequence::UGAEffectCueSequence(const FObjectInitializer& ObjectIniti void UGAEffectCueSequence::PostInitProperties() { #if WITH_EDITOR && WITH_EDITORONLY_DATA - AGAEffectCue* OwnerCue = Cast(GetOuter()); + AAFCueActor* OwnerCue = Cast(GetOuter()); if (!bHasBeenInitialized && !HasAnyFlags(RF_ClassDefaultObject) && OwnerCue && !OwnerCue->HasAnyFlags(RF_ClassDefaultObject)) { - FGuid BindingID = MovieScene->AddPossessable(OwnerCue ? OwnerCue->GetActorLabel() : TEXT("Owner"), OwnerCue ? OwnerCue->GetClass() : AGAEffectCue::StaticClass()); + FGuid BindingID = MovieScene->AddPossessable(OwnerCue ? OwnerCue->GetActorLabel() : TEXT("Owner"), OwnerCue ? OwnerCue->GetClass() : AAFCueActor::StaticClass()); //ObjectReferences.CreateBinding(BindingID, FActorSequenceObjectReference::CreateForContextActor()); OnInitializeSequenceEvent.Broadcast(this); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp index 0a782b8..a28d5f9 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExecution.cpp @@ -1,9 +1,11 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFramework.h" -#include "../GAGlobalTypes.h" -#include "../Attributes/GAAttributeBase.h" -#include "../AFAbilityComponent.h" +#include "AbilityFramework.h" +#include "GAGlobalTypes.h" +#include "Attributes/GAAttributeBase.h" +#include "AFAbilityComponent.h" +#include "Effects/GAGameEffect.h" +#include "AFAbilityInterface.h" #include "GAEffectExecution.h" UGAEffectExecution::UGAEffectExecution(const FObjectInitializer& ObjectInitializer) @@ -11,7 +13,7 @@ UGAEffectExecution::UGAEffectExecution(const FObjectInitializer& ObjectInitializ { } -void UGAEffectExecution::PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context) +void UGAEffectExecution::PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, const FGAEffectContext& Context) { UE_LOG(GameAttributesEffects, Log, TEXT("Sample execution class implementation")); } @@ -20,6 +22,6 @@ void UGAEffectExecution::ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffec const FAFFunctionModifier& Modifier) { PreModifyAttribute(HandleIn, ModIn, Params.GetContext()); - FAFContextHandle ContextHandle = Params.GetContextHandle(); - Params.GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty(), ContextHandle); + const FGAEffectContext& Context = Params.GetContext(); + const_cast(Params).GetContext().TargetInterface->ModifyAttribute(ModIn, HandleIn, Params.GetProperty(), Context); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp index 8bd4fac..3e82610 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAEffectExtension.cpp @@ -28,10 +28,29 @@ void UGAEffectExtension::NativeOnEffectExecuted() void UGAEffectExtension::NativeOnEffectExpired() { OnEffectExpired(); + CleanupTasks(); } void UGAEffectExtension::NativeOnEffectRemoved() { OnEffectRemoved(); + CleanupTasks(); +} + +void UGAEffectExtension::NativeOnEffectAppliedCDO() +{ + OnEffectAppliedCDO(); +} +void UGAEffectExtension::NativeOnEffectExecutedCDO() +{ + OnEffectExecutedCOD(); +} +void UGAEffectExtension::NativeOnEffectExpiredCDO() +{ + OnEffectExpiredCDO(); +} +void UGAEffectExtension::NativeOnEffectRemovedCDO() +{ + OnEffectRemovedCDO(); } UWorld* UGAEffectExtension::GetWorld() const @@ -44,6 +63,7 @@ UWorld* UGAEffectExtension::GetWorld() const void UGAEffectExtension::OnLatentTaskAdded(FName InstanceName, class UAFTaskBase* TaskIn) { + ActiveTasks.Add(TaskIn); if (!InstanceName.IsNone()) { Tasks.Add(InstanceName, TaskIn); @@ -67,4 +87,18 @@ void UGAEffectExtension::OnLatentTaskDeactivated(class UAFTaskBase* TaskIn) class UAFTaskBase* UGAEffectExtension::GetCachedLatentAction(FName TaskName) { return Tasks.FindRef(TaskName); +} + +void UGAEffectExtension::CleanupTasks() +{ + for (UAFTaskBase* Task : ActiveTasks) + { + Task->EndTask(); + } + + ActiveTasks.Reset(); + ActiveTasks.Shrink(); + + Tasks.Reset(); + Tasks.Shrink(); } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp index 3657146..9c31b1f 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/Effects/GAGameEffect.cpp @@ -18,30 +18,30 @@ DEFINE_STAT(STAT_GatherModifiers); -void FAFEffectSpec::OnApplied() +void FAFEffectSpec::OnApplied() const { - if (Extension) + if (Extension.IsValid()) { Extension->NativeOnEffectApplied(); } } -void FAFEffectSpec::OnExpired() +void FAFEffectSpec::OnExpired() const { - if (Extension) + if (Extension.IsValid()) { Extension->NativeOnEffectExpired(); } } -void FAFEffectSpec::OnRemoved() +void FAFEffectSpec::OnRemoved() const { - if (Extension) + if (Extension.IsValid()) { Extension->NativeOnEffectRemoved(); } } -void FAFEffectSpec::OnExecuted() +void FAFEffectSpec::OnExecuted() const { - if (Extension) + if (Extension.IsValid()) { Extension->NativeOnEffectExecuted(); } @@ -51,14 +51,18 @@ FAFEffectSpec::FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOfExtension) + SpecClass = InSpecClass; + OwnedTags.AppendTags(InSpecClass.GetDefaultObject()->OwnedTags); +} +void FAFEffectSpec::Instance() +{ + if (SpecClass.GetDefaultObject()->Extension) { - Extension = NewObject(Context.GetPtr()->Target.Get(), InSpecClass.GetDefaultObject()->Extension); + Extension = NewObject(Context.GetPtr()->Target.Get(), SpecClass.GetDefaultObject()->Extension); Extension->OwningComponent = Context.GetPtr()->TargetInterface->GetEffectsComponent(); + Extension->SourceComponent = Context.GetPtr()->InstigatorInterface->GetEffectsComponent(); } - OwnedTags.AppendTags(InSpecClass.GetDefaultObject()->OwnedTags); } - float FAFEffectSpec::GetFloatFromAttributeMagnitude( const FGAMagnitude& AttributeIn , const FGAEffectContext& InContext) const @@ -110,6 +114,15 @@ float FAFEffectSpec::GetPeriod(const FGAEffectContext& InContext) return GetFloatFromAttributeMagnitude(GetSpec()->Period, InContext); } +float FAFEffectSpec::GetDuration(const FGAEffectContext& InContext) const +{ + return GetFloatFromAttributeMagnitude(GetSpec()->Duration, InContext); +} +float FAFEffectSpec::GetPeriod(const FGAEffectContext& InContext) const +{ + return GetFloatFromAttributeMagnitude(GetSpec()->Period, InContext); +} + FGAEffectProperty::FGAEffectProperty() : ApplicationRequirement(nullptr) , Application(nullptr) @@ -150,22 +163,30 @@ void FGAEffectProperty::Initialize(TSubclassOf EffectClass) if (EffectClass) { Spec = EffectClass->GetDefaultObject(); - ApplicationRequirement = GetSpec()->ApplicationRequirement.GetDefaultObject(); - Application = GetSpec()->Application.GetDefaultObject(); - Execution = GetSpec()->ExecutionType.GetDefaultObject(); + ApplicationRequirement = GetSpecData()->ApplicationRequirement.GetDefaultObject(); + Application = GetSpecData()->Application.GetDefaultObject(); + Execution = GetSpecData()->ExecutionType.GetDefaultObject(); } } -void FGAEffectProperty::InitializeIfNotInitialized(const FGAEffectContext& InContext - , TSubclassOf EffectClass) +void FGAEffectProperty::InitializeIfNotInitialized( + class APawn* Instigator + , UObject* Causer + , TSubclassOf EffectClass + ) { if (!IsInitialized()) { + SpecClass = EffectClass; + + FGAEffectContext* Context = new FGAEffectContext(Instigator, Causer); + + EffectContext = FAFContextHandle::Generate(Context); Initialize(EffectClass); } if (Spec.IsValid()) { - Duration = GetSpec()->Duration.GetFloatValue(InContext); - Period = GetSpec()->Period.GetFloatValue(InContext); + Duration = GetSpecData()->Duration.GetFloatValue(EffectContext.GetRef()); + Period = GetSpecData()->Period.GetFloatValue(EffectContext.GetRef()); if ((Duration > 0) || (Period > 0)) { @@ -350,15 +371,15 @@ float FGAEffect::GetCurrentDuration() const } FTimerManager& FAFEffectParams::GetTargetTimerManager() { - return Context.GetPtr()->TargetComp->GetWorld()->GetTimerManager(); + return Context.TargetComp->GetWorld()->GetTimerManager(); } UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() { - return Context.GetPtr()->GetTargetEffectsComponent(); + return Context.GetTargetEffectsComponent(); } UAFEffectsComponent* FAFEffectParams::GetTargetEffectsComponent() const { - return Context.GetPtr()->GetTargetEffectsComponent(); + return Context.GetTargetEffectsComponent(); } void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams CueParams) { @@ -378,7 +399,6 @@ void FGameCueContainer::AddCue(FGAEffectHandle EffectHandle, FGAEffectCueParams FGAEffectHandle FGAEffectContainer::ApplyEffect( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier) { @@ -392,14 +412,9 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( ENetRole role = OwningComponent->GetOwnerRole(); ENetMode mode = OwningComponent->GetOwner()->GetNetMode(); - if (!Params.bRecreated) - { - Handle = FGAEffectHandle::GenerateHandle(); - } - else - { - Handle = InHandle; - } + + Handle = FGAEffectHandle::GenerateHandle(); + if (InProperty.CanApply(EffectIn, this, Params, Handle)) { if(!Params.bPeriodicEffect) //instatnt effect. @@ -408,11 +423,6 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( if (InProperty.ApplyEffect(Handle, EffectIn, this, Params)) { - Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() - , Handle - , Params.Context - , Params.EffectSpec); - InProperty.ApplyExecute(Handle, Params, Modifier); // UE_LOG(GameAttributes, Log, TEXT("FGAEffectContainer::EffectApplied %s"), *HandleIn.GetEffectSpec()->GetName() ); @@ -424,14 +434,9 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( if (InProperty.ApplyEffect(Handle, EffectIn, this, Params)) { - FAFEffectSpec& Spec = Params.GetSpec(); - FGAEffectContext& Context = Params.GetContext(); - - Params.Property.GetRef().RegisterHandle(Params.GetContext().Target.Get() - , Handle - , Params.Context - , Params.EffectSpec); - + const FAFEffectSpec& Spec = Params.GetSpec(); + const FGAEffectContext& Context = Params.GetContext(); + const_cast(EffectIn).AppliedTime = OwningComponent->GetWorld()->TimeSeconds; const_cast(EffectIn).LastTickTime = OwningComponent->GetWorld()->TimeSeconds; const_cast(EffectIn).Duration = Spec.GetDuration(Context); @@ -439,7 +444,7 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( MarkItemDirty(const_cast(EffectIn)); int32 newItem = ActiveEffectInfos.Add(EffectIn); MarkArrayDirty(); - AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &ActiveEffectInfos[newItem], InProperty); + AddEffect(Handle, const_cast(EffectIn).PredictionHandle, &ActiveEffectInfos[newItem], InProperty, Params); //InProperty.ApplyExecute(Handle, Params, Modifier); //generate it only on client, and apply prediction key from client. @@ -457,12 +462,12 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( Params.GetSpec().OnApplied(); FAFEventData EventData; - const FGameplayTagContainer& AppliedEvents = InProperty.GetSpec()->AppliedEventTags; + const FGameplayTagContainer& AppliedEvents = InProperty.GetSpecData()->AppliedEventTags; for(const FGameplayTag& Event : AppliedEvents) OwningComponent->TriggerAppliedEvent(Event, EventData); - FGAEffectContext& InContext = Params.GetContext(); - TArray& Effects = InProperty.GetSpec()->IfHaveTagEffect.Effects; + const FGAEffectContext& InContext = Params.GetContext(); + TArray& Effects = InProperty.GetSpecData()->IfHaveTagEffect.Effects; for (FAFConditionalEffect& Effect : Effects) { if (Effect.RequiredTag.IsValid() @@ -471,12 +476,12 @@ FGAEffectHandle FGAEffectContainer::ApplyEffect( //Hack. We need a way store handles for conditional effects. FAFPropertytHandle PropertyNew(Effect.Effect); FGAEffectHandle OtherHandle; - OtherHandle = UGABlueprintLibrary::ApplyEffect(PropertyNew + /*OtherHandle = UGABlueprintLibrary::ApplyEffect(PropertyNew , OtherHandle , InContext.Target.Get() , InContext.Instigator.Get() , InContext.Causer.Get() - , InContext.HitResult); + , InContext.HitResult);*/ } } @@ -489,7 +494,7 @@ TSet FGAEffectContainer::GetHandlesByClass(const FGAEffectPrope , const FGAEffectContext& InContext) { TSet Handles; - UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UGAGameEffectSpec* Spec = InProperty.GetSpecData(); EGAEffectAggregation Aggregation = Spec->EffectAggregation; UClass* EffectClass = Spec->GetClass(); @@ -528,14 +533,15 @@ void FGAEffectContainer::AddEffect( , const FAFPredictionHandle& InPredHandle , FGAEffect* InEffect , const FGAEffectProperty& InProperty + , const FAFEffectParams& Params , bool bInfinite) { HandleByPrediction.Add(InPredHandle, InHandle); PredictionByHandle.Add(InHandle, InPredHandle); PredictedEffectInfos.Add(InPredHandle, InEffect); - UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UGAGameEffectSpec* Spec = InProperty.GetSpecData(); UClass* SpecClass = Spec->GetClass(); - FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); + const FGAEffectContext& Context = Params.GetContext(); TSet& Effects = EffectByAttribute.FindOrAdd(Spec->AtributeModifier.Attribute); Effects.Add(InHandle); @@ -566,14 +572,14 @@ void FGAEffectContainer::AddEffect( int dbg = 0; } -void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty) +void FGAEffectContainer::RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectContext& InContext, const FAFPropertytHandle& InProperty) { - RemoveEffectInternal(InProperty, InHandle); + RemoveEffectInternal(InProperty, InContext, InHandle); } -TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num) +TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandle& HandleIn, const FGAEffectContext& InContext, int32 Num) { - UGAGameEffectSpec* Spec = HandleIn.GetSpec(); + UGAGameEffectSpec* Spec = HandleIn.GetSpecData(); EGAEffectAggregation Aggregation = Spec->EffectAggregation; FObjectKey key(HandleIn.GetClass()); TArray* handles = EffectByClass.Find(key);//GetHandlesByClass(HandleIn, InContext); @@ -587,8 +593,7 @@ TArray FGAEffectContainer::RemoveEffect(const FAFPropertytHandl if (handles->IsValidIndex(0)) { FGAEffectHandle OutHandle = (*handles)[idx]; - RemoveEffectInternal(HandleIn, OutHandle); - const_cast(HandleIn).CleanUp(OutHandle); + RemoveEffectInternal(HandleIn, InContext, OutHandle); } } @@ -768,19 +773,18 @@ float FGAEffectContainer::GetEndTime(const FGAEffectHandle& InHandle) const return 0; } -void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle) +void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle) { FGAEffect* Effect = ActiveEffects[InHandle]; - UGAGameEffectSpec* Spec = InProperty.GetSpec(); + UGAGameEffectSpec* Spec = InProperty.GetSpecData(); UClass* SpecClass = Spec->GetClass(); - FGAEffectContext& Context = InProperty.GetContext(InHandle).GetRef(); - FTimerManager& DurationTimer = Context.TargetComp->GetWorld()->GetTimerManager(); + FTimerManager& DurationTimer = InContext.TargetComp->GetWorld()->GetTimerManager(); DurationTimer.ClearTimer(Effect->DurationTimerHandle); DurationTimer.ClearTimer(Effect->PeriodTimerHandle); - APawn* Instigator = Context.Instigator.Get(); - UObject* ObjectTarget = Context.Target.Get(); + APawn* Instigator = InContext.Instigator.Get(); + UObject* ObjectTarget = InContext.Target.Get(); FAFPredictionHandle PredHandle = PredictionByHandle[InHandle]; HandleByPrediction.Remove(PredHandle); @@ -793,7 +797,7 @@ void FGAEffectContainer::RemoveEffectInternal(const FAFPropertytHandle& InProper TSet* Effects = EffectByAttribute.Find(Spec->AtributeModifier.Attribute); if (Effects) { - IAFAbilityInterface* IntTarget = Context.TargetInterface; + IAFAbilityInterface* IntTarget = InContext.TargetInterface; IntTarget->RemoveBonus(Attribute, InHandle, AttributeMod); Effects->Remove(InHandle); if (Effects->Num() == 0) diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp index ff8bdb1..71cd769 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Private/GAGlobalTypes.cpp @@ -35,11 +35,29 @@ FGAEffectContext::FGAEffectContext(TWeakObjectPtr Targe InstigatorInterface = Cast(Instigator.Get()); IAFAbilityInterface* CauserInterface = Cast(Causer.Get()); } -void FGAEffectContext::SetTarget(UObject* NewTarget) + + +FGAEffectContext::FGAEffectContext(APawn* InInstigator, UObject* InCauser) +{ + Instigator = InInstigator; + Causer = InCauser; + + IAFAbilityInterface* ABI = Cast(InInstigator); + InstigatorAttributes = ABI->GetAttributes(); + InstigatorComp = ABI->GetAbilityComp(); + InstigatorInterface = ABI; +} + +void FGAEffectContext::SetTarget(UObject* NewTarget, const FHitResult& InHit) { + HitResult = InHit; IAFAbilityInterface* ATI = Cast(NewTarget); if (!ATI) { + TargetComp.Reset(); + Target.Reset(); + TargetInterface = nullptr; + TargetAttributes.Reset(); return; } @@ -349,5 +367,5 @@ FGAEffectCueParams::FGAEffectCueParams(const FGAEffectContext& InContext, const : HitResult(InContext.HitResult) , Instigator(InContext.Instigator) , Causer(InContext.Causer) - , CueTags(InProperty.GetSpec()->Cues.CueTags) + , CueTags(InProperty.GetSpecData()->Cues.CueTags) {}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h index ffe2bde..4c128f5 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityComponent.h @@ -340,7 +340,7 @@ class ABILITYFRAMEWORK_API UAFAbilityComponent : public UActorComponent, public void ModifyAttribute(FGAEffectMod& ModIn , const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty - , const FAFContextHandle& InContext);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; + , const FGAEffectContext& InContext);// { DefaultAttributes->ModifyAttribute(ModIn, HandleIn); }; void NotifyInstigatorTargetAttributeChanged(const FAFAttributeChangedData& InData, const FGAEffectContext& InContext); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h index 497cdb4..c60eeda 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFAbilityInterface.h @@ -35,7 +35,7 @@ class IAFAbilityInterface virtual float GetAttributeValue(FGAAttribute AttributeIn) const { return 0; }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) {}; + struct FGAEffectProperty& InProperty, const FGAEffectContext& InContext) {}; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) { return nullptr; }; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) {}; @@ -51,7 +51,6 @@ class IAFAbilityInterface FGAEffectHandle ApplyEffectToTarget( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h index 86bb9c7..4d4052d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFCueManager.h @@ -6,9 +6,84 @@ #include "UObject/NoExportTypes.h" #include "GameplayTags.h" #include "GAGlobalTypes.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #include "AFCueManager.generated.h" + +USTRUCT() +struct FAFCueData +{ + GENERATED_BODY() +public: + UPROPERTY() + FGameplayTag CueTag; + UPROPERTY() + FPrimaryAssetId AssetId; + UPROPERTY(Transient) + UClass* CueClass; + + FAFCueData() + : CueClass(nullptr) + {} +}; + +UENUM() +enum EAFCueEvent +{ + Activated, + Executed, + Expire, + Removed +}; + +struct FAFCueActorKey +{ + FObjectKey InstigatorKey; + FObjectKey TargetKey; + FGameplayTag CueTag; + struct Target {}; + struct Instigator {}; + + FAFCueActorKey(Instigator, UObject* InInstigator) + : InstigatorKey(FObjectKey(InInstigator)) + , TargetKey(FObjectKey()) + , CueTag(FGameplayTag()) + {} + + FAFCueActorKey(Target, UObject* InTarget) + : InstigatorKey(FObjectKey()) + , TargetKey(FObjectKey(InTarget)) + , CueTag(FGameplayTag()) + {} + + FAFCueActorKey(const FGameplayTag& Tag) + : InstigatorKey(FObjectKey()) + , TargetKey(FObjectKey()) + , CueTag(Tag) + {} + + FAFCueActorKey(UObject* InInstigator, UObject* InTarget, const FGameplayTag& Tag) + : InstigatorKey(FObjectKey(InInstigator)) + , TargetKey(FObjectKey(InTarget)) + , CueTag(Tag) + {} + + inline bool operator==(const FAFCueActorKey& Other) const + { + return InstigatorKey == Other.InstigatorKey + && TargetKey == Other.TargetKey + && CueTag == Other.CueTag; + } + +}; + +inline uint32 GetTypeHash(const FAFCueActorKey& Key) +{ + return GetTypeHash(Key.InstigatorKey) ^ + GetTypeHash(Key.TargetKey) ^ + GetTypeHash(Key.CueTag); +} + /** * */ @@ -20,16 +95,15 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject //UPROPERTY() static UAFCueManager* ManagerInstance; UWorld* CurrentWorld; - - //store per instigator ? Causer ? or global pool ? - //stores unused instanced cues. - TMap>> InstancedCues; - //store per instigator ? Causer ? - //stores used cues. - TMap>>> UsedCues; - TMap ActiveCues; + UPROPERTY() + UObjectLibrary* StaticCues; + + TArray Cues; + TMap CuesMap; + //Cues = Instigator+Target (optional) since Actor Cue might not have target (ie. Fire storm effect). + TMap InstancedCues; public: void Initialize(); #if WITH_EDITOR @@ -40,14 +114,17 @@ class ABILITYFRAMEWORK_API UAFCueManager : public UObject void HandlePostLoadMap(UWorld* InWorld); public: static UAFCueManager* Get(); - void HandleCue(const FGameplayTagContainer& Tags, - const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); - void HandleExecuteCue(FAFCueHandle InHandle); + void HandleCue(const FGameplayTagContainer& Tags + , const FGAEffectCueParams& CueParams + , EAFCueEvent CueEvent); + void HandleRemoveCue(const FGameplayTagContainer& Tags, const FGAEffectCueParams& CueParams, FAFCueHandle InHandle); protected: - void OnFinishedLoad(FGameplayTag InCueTag + void OnFinishedLoad(int32 Idx , FPrimaryAssetId InPrimaryAssetId , FGAEffectCueParams CueParams - , FAFCueHandle InHandle); + , EAFCueEvent CueEvent); + + void HandleCueEvent(UClass* InCueClass, const FGAEffectCueParams& InCueParams, EAFCueEvent CueEvent); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h index 0a5c7b1..6a63c3d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AFEffectsComponent.h @@ -18,7 +18,7 @@ DECLARE_DELEGATE(FAFEffectEvent); DECLARE_DELEGATE_OneParam(FAFEventDelegate, FAFEventData); -DECLARE_MULTICAST_DELEGATE_ThreeParams(FAFApplicationDelegate, FAFContextHandle, FAFPropertytHandle, FAFEffectSpecHandle); +DECLARE_MULTICAST_DELEGATE_ThreeParams(FAFApplicationDelegate, FGAEffectContext, FAFPropertytHandle, FAFEffectSpec); UCLASS( ClassGroup=(Custom), meta=(BlueprintSpawnableComponent) ) class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent @@ -91,7 +91,6 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent */ FGAEffectHandle ApplyEffectToSelf( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); @@ -111,7 +110,6 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent */ FGAEffectHandle ApplyEffectToTarget( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); @@ -170,8 +168,8 @@ class ABILITYFRAMEWORK_API UAFEffectsComponent : public UActorComponent virtual void MulticastApplyEffectCue_Implementation(FGAEffectCueParams CueParams, FAFCueHandle InHandle); UFUNCTION(NetMulticast, Unreliable) - void MulticastExecuteEffectCue(FAFCueHandle InHandle); - void MulticastExecuteEffectCue_Implementation(FAFCueHandle InHandle); + void MulticastExecuteEffectCue(TSubclassOf EffectSpec, FGAEffectCueParams CueParams); + void MulticastExecuteEffectCue_Implementation(TSubclassOf EffectSpec, FGAEffectCueParams CueParams); UFUNCTION(NetMulticast, Unreliable) void MulticastRemoveEffectCue(FGAEffectCueParams CueParams, FAFCueHandle InHandle); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h index b9ea1df..0bf50a4 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Abilities/GAAbilityBase.h @@ -168,7 +168,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt */ UPROPERTY(EditAnywhere, meta=(AllowedClass="AFAbilityCooldownSpec"), Category = "Config") FAFPropertytHandle CooldownEffect; - FGAEffectHandle CooldownEffectHandle; + TArray CooldownEffectHandle; /* Tags applied to the time of activation ability. Only applies to abilities, which are not instant (for now). @@ -182,7 +182,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt */ UPROPERTY(EditAnywhere, meta = (AllowedClass = "AFAbilityActivationSpec,AFAbilityPeriodSpec,AFAbilityInfiniteDurationSpec,AFAbilityPeriodicInfiniteSpec"), Category = "Config") FAFPropertytHandle ActivationEffect; - FGAEffectHandle ActivationEffectHandle; + TArray ActivationEffectHandle; /* These attributes will be reduced by specified amount when ability is activated. @@ -190,13 +190,13 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt */ UPROPERTY(EditAnywhere, Category = "Config") TArray AttributeCost; - TArray AttributeCostHandle; + TArray> AttributeCostHandle; /* Attribute cost from ability own attributes */ UPROPERTY(EditAnywhere, Category = "Config") TArray AbilityAttributeCost; - TArray AbilityAttributeCostHandle; + TArray> AbilityAttributeCostHandle; UPROPERTY(AssetRegistrySearchable) FName AbilityTagSearch; @@ -224,7 +224,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt public: //because I'm to lazy to write all those friend states.. UFUNCTION() - void OnActivationEffectPeriod(FGAEffectHandle InHandle); + void OnActivationEffectPeriod(); /* Replication counters for above events. */ @@ -395,14 +395,14 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") void OnCooldownStart(); UFUNCTION(BlueprintImplementableEvent, Category = "AbilityFramework|Abilities") - void OnCooldownEnd(FGAEffectHandle InHandle); + void OnCooldownEnd(); - void NativeOnCooldownEnd(FGAEffectHandle InHandle); + void NativeOnCooldownEnd(); UFUNCTION() void OnCooldownEffectExpired(); UFUNCTION() - void NativeOnAbilityActivationFinish(FGAEffectHandle InHandle); + void NativeOnAbilityActivationFinish(); UFUNCTION() void NativeOnAbilityActivationCancel(); @@ -472,7 +472,7 @@ class ABILITYFRAMEWORK_API UGAAbilityBase : public UObject, public IAFAbilityInt virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override { Attributes->RemoveBonus(AttributeIn, HandleIn, InMod); }; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty - , const FAFContextHandle& InContext) override + , const FGAEffectContext& InContext) override { if (!Attributes) { diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h index eca4711..888d139 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/AbilityFramework.h @@ -134,6 +134,8 @@ class FAbilityFramework : public IAbilityFramework /** IModuleInterface implementation */ virtual void StartupModule() override; virtual void ShutdownModule() override; + + void InitCues(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h index 181b0f3..274dbde 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributeBase.h @@ -120,7 +120,7 @@ struct ABILITYFRAMEWORK_API FAFAttributeBase inline float GetCurrentValue() { return CurrentValue; }; void CalculateBonus(); bool CheckIfStronger(const FGAEffectMod& InMod); - float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty, const FAFContextHandle& InContext); + float Modify(const FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, FGAEffectProperty& InProperty, const FGAEffectContext& InContext); void AddBonus(const FGAEffectMod& ModIn, const FGAEffectHandle& Handle); void RemoveBonus(const FGAEffectHandle& Handle, EGAAttributeMod InMod); void SetExtensionClass(TSubclassOf InExtensionClass) { ExtensionClass = InExtensionClass; }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h index bcf6ad5..6181b02 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Attributes/GAAttributesBase.h @@ -125,7 +125,7 @@ class ABILITYFRAMEWORK_API UGAAttributesBase : public UObject float ModifyAttribute(const FGAEffectMod& ModIn , const FGAEffectHandle& HandleIn , FGAEffectProperty& InProperty - , const FAFContextHandle& InContext); + , const FGAEffectContext& InContext); void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod); protected: bool bNetAddressable; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticBlueprint.h new file mode 100644 index 0000000..8c4107b --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticBlueprint.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Engine/Blueprint.h" +#include "AFCueStaticBlueprint.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFCueStaticBlueprint : public UBlueprint +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticGeneratedClass.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticGeneratedClass.h new file mode 100644 index 0000000..acf4b4d --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Cues/AFCueStaticGeneratedClass.h @@ -0,0 +1,20 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "AFCueStaticGeneratedClass.generated.h" + +/** + * + */ +UCLASS() +class ABILITYFRAMEWORK_API UAFCueStaticGeneratedClass : public UBlueprintGeneratedClass +{ + GENERATED_BODY() + + + + +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActor.h similarity index 93% rename from Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h rename to Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActor.h index 0301b04..8ca29c0 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCue.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActor.h @@ -8,10 +8,10 @@ #include "GameplayTags.h" #include "AssetBundleData.h" #include "Engine/AssetManager.h" -#include "GAEffectCue.generated.h" +#include "AFCueActor.generated.h" class UActorSequencePlayer; UCLASS() -class ABILITYFRAMEWORK_API AGAEffectCue : public AActor +class ABILITYFRAMEWORK_API AAFCueActor : public AActor { GENERATED_BODY() protected: @@ -23,7 +23,7 @@ class ABILITYFRAMEWORK_API AGAEffectCue : public AActor FAssetBundleData AssetBundleData; public: // Sets default values for this actor's properties - AGAEffectCue(const FObjectInitializer& ObjectInitializer); + AAFCueActor(const FObjectInitializer& ObjectInitializer); void PostInitProperties() override; void Serialize(FArchive& Ar) override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActorBlueprint.h similarity index 75% rename from Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h rename to Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActorBlueprint.h index 7bc9807..e850f2c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprint.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActorBlueprint.h @@ -4,14 +4,14 @@ #include "CoreMinimal.h" #include "UObject/ObjectMacros.h" #include "Engine/Blueprint.h" -#include "GAEffectCueBlueprint.generated.h" +#include "AFCueActorBlueprint.generated.h" /** * Game Effect Blueprint */ UCLASS(BlueprintType) -class ABILITYFRAMEWORK_API UGAEffectCueBlueprint : public UBlueprint +class ABILITYFRAMEWORK_API UAFCueActorBlueprint : public UBlueprint { GENERATED_UCLASS_BODY() UPROPERTY() @@ -26,7 +26,7 @@ UPROPERTY() // End of UBlueprint interface /** Returns the most base gameplay ability blueprint for a given blueprint (if it is inherited from another ability blueprint, returning null if only native / non-ability BP classes are it's parent) */ - static UGAEffectCueBlueprint* FindRootGameplayAbilityBlueprint(UGAEffectCueBlueprint* DerivedBlueprint); + static UAFCueActorBlueprint* FindRootGameplayAbilityBlueprint(UAFCueActorBlueprint* DerivedBlueprint); #endif }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActorGeneratedClass.h similarity index 63% rename from Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h rename to Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActorGeneratedClass.h index d6af270..4ae2d26 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectCueBlueprintGeneratedClass.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueActorGeneratedClass.h @@ -4,14 +4,14 @@ #include "CoreMinimal.h" #include "UObject/ObjectMacros.h" #include "Engine/BlueprintGeneratedClass.h" -#include "GAEffectCueBlueprintGeneratedClass.generated.h" +#include "AFCueActorGeneratedClass.generated.h" /** * Game Effect Blueprint */ UCLASS(BlueprintType) -class ABILITYFRAMEWORK_API UGAEffectCueBlueprintGeneratedClass : public UBlueprintGeneratedClass +class ABILITYFRAMEWORK_API UAFCueActorGeneratedClass : public UBlueprintGeneratedClass { GENERATED_UCLASS_BODY() }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueStatic.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueStatic.h new file mode 100644 index 0000000..8fbd33f --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/AFCueStatic.h @@ -0,0 +1,61 @@ +// Fill out your copyright notice in the Description page of Project Settings. + +#pragma once + +#include "CoreMinimal.h" +#include "GameplayTags.h" +#include "AssetBundleData.h" +#include "UObject/NoExportTypes.h" +#include "GAGlobalTypes.h" +#include "AFCueStatic.generated.h" + +/** + * An Non instanced Cue, where only CDO is used to execute it. + * They cannot have state or modify any external state. + */ +UCLASS(BlueprintType, Blueprintable, meta=(ShowWorldContextPin)) +class ABILITYFRAMEWORK_API UAFCueStatic : public UObject +{ + GENERATED_BODY() +public: + UPROPERTY(EditAnywhere, Category = "Cue") + FGameplayTag CueTag; + UPROPERTY(AssetRegistrySearchable) + FName EffectCueTagSearch; + UPROPERTY() + FAssetBundleData AssetBundleData; +public: + // Sets default values for this actor's properties + UAFCueStatic(const FObjectInitializer& ObjectInitializer); + void PostInitProperties() override; + + void Serialize(FArchive& Ar) override; + +#if WITH_EDITORONLY_DATA + void UpdateAssetBundleData(); + void PreSave(const class ITargetPlatform* TargetPlatform) override; +#endif //WITH_EDITORONLY_DATA + void PostLoad() override; + FPrimaryAssetId GetPrimaryAssetId() const override; +protected: + void UpdateAssetRegistryInfo(); + +public: + UFUNCTION(BlueprintNativeEvent, Category = "Ability Framework|Cues") + bool OnExecuted(const FGAEffectCueParams& Hit); + virtual bool OnExecuted_Implementation(const FGAEffectCueParams& Hit) const; + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Framework|Cues") + void OnActivate(const FGAEffectCueParams& Hit) const; + virtual void OnActivate_Implementation(const FGAEffectCueParams& Hit) const; + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Framework|Cues") + void OnExpire(const FGAEffectCueParams& Hit) const; + virtual void OnExpire_Implementation(const FGAEffectCueParams& Hit) const; + + UFUNCTION(BlueprintNativeEvent, Category = "Ability Framework|Cues") + void OnRemoved(const FGAEffectCueParams& Hit) const; + virtual void OnRemoved_Implementation(const FGAEffectCueParams& Hit) const; + + UWorld* GetWorld() const override; +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h index 81ac081..8cb571e 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToSelf.h @@ -18,7 +18,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectT { GENERATED_BODY() public: - DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); + DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FGAEffectContext, Context, FAFPropertytHandle, Property, FAFEffectSpec, Spec); UPROPERTY(BlueprintAssignable) FAFEffectEventDelegate OnEvent; @@ -33,9 +33,9 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToSelf : public UAFEffectT virtual void Activate() override; - virtual void GameplayEventCallback(FAFContextHandle Context + virtual void GameplayEventCallback(FGAEffectContext Context , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec); + , FAFEffectSpec Spec); virtual void OnTaskEnded() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h index 665f5a4..31fb999 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/EffectTasks/AFEffectTask_EffectAppliedToTarget.h @@ -18,7 +18,7 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffec { GENERATED_BODY() public: - DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FAFContextHandle, Context, FAFPropertytHandle, Property, FAFEffectSpecHandle, Spec); + DECLARE_DYNAMIC_MULTICAST_DELEGATE_ThreeParams(FAFEffectEventDelegate, FGAEffectContext, Context, FAFPropertytHandle, Property, FAFEffectSpec, Spec); UPROPERTY(BlueprintAssignable) FAFEffectEventDelegate OnEvent; @@ -33,9 +33,9 @@ class ABILITYFRAMEWORK_API UAFEffectTask_EffectAppliedToTarget : public UAFEffec virtual void Activate() override; - virtual void GameplayEventCallback(FAFContextHandle Context + virtual void GameplayEventCallback(FGAEffectContext Context , FAFPropertytHandle Property - , FAFEffectSpecHandle Spec); + , FAFEffectSpec Spec); virtual void OnTaskEnded() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h index 79d2fe8..8285465 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GABlueprintLibrary.h @@ -11,9 +11,8 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar GENERATED_UCLASS_BODY() public: UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToObject( + static TArray ApplyGameEffectToObject( UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle , class UObject* Target , class APawn* Instigator , UObject* Causer @@ -25,9 +24,8 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar and just change context of effect. */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToActor( + static TArray ApplyGameEffectToActor( UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle , class AActor* Target , class APawn* Instigator , UObject* Causer @@ -40,52 +38,70 @@ class ABILITYFRAMEWORK_API UGABlueprintLibrary : public UBlueprintFunctionLibrar */ UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") - static FGAEffectHandle ApplyGameEffectToLocation( + static TArray ApplyGameEffectToLocation( UPARAM(Ref) FAFPropertytHandle& InEffect - , FGAEffectHandle Handle , const FHitResult& Target , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier); - static FGAEffectHandle ApplyEffect( - FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target - , class APawn* Instigator - , UObject* Causer - , const FHitResult& HitIn - , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - static FGAEffectHandle ApplyEffect( - FGAEffectProperty* InEffect - , const FGAEffectHandle& Handle - , class UObject* Target + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static TArray ApplyGameEffectToObjects( + UPARAM(Ref) FAFPropertytHandle& InEffect + , TArray Targets + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static TArray ApplyGameEffectToActors( + UPARAM(Ref) FAFPropertytHandle& InEffect + , TArray Targets + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + /* + Makes outgoing effect spec and assign handle to it. + If valid handle is provided it will instead reuse existing effect spec from handle, + and just change context of effect. + */ + + UFUNCTION(BlueprintCallable, Category = "AbilityFramework|Effects") + static TArray ApplyGameEffectToTargets( + UPARAM(Ref) FAFPropertytHandle& InEffect + , const TArray& Targets + , class APawn* Instigator + , UObject* Causer + , const FAFFunctionModifier& Modifier); + + + static TArray ApplyEffect( + FAFPropertytHandle& InEffect + , TArray Targets , class APawn* Instigator , UObject* Causer - , const FHitResult& HitIn + , const TArray& HitsIn , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - - static FGAEffectHandle ApplyEffectFromHit( + + static TArray ApplyEffectFromHit( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , const FHitResult& Target + , const TArray& Targets , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier); - static FGAEffectHandle ApplyEffectToActor( + static TArray ApplyEffectToActor( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class AActor* Target + , TArray Targets , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier); - static FGAEffectHandle ApplyEffectToObject( + static TArray ApplyEffectToObject( FAFPropertytHandle& InEffect - , const FGAEffectHandle& Handle - , class UObject* Target + , TArray Targets , class APawn* Instigator , UObject* Causer , const FAFFunctionModifier& Modifier); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h index 2236b08..6b94d56 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExecution.h @@ -15,7 +15,7 @@ class ABILITYFRAMEWORK_API UGAEffectExecution : public UObject public: UGAEffectExecution(const FObjectInitializer& ObjectInitializer); - virtual void PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, FGAEffectContext& Context); + virtual void PreModifyAttribute(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, const FGAEffectContext& Context); virtual void ExecuteEffect(const FGAEffectHandle& HandleIn, FGAEffectMod& ModIn, const FAFEffectParams& Params, const FAFFunctionModifier& Modifier = FAFFunctionModifier()); diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h index 342e234..65a33bd 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAEffectExtension.h @@ -1,22 +1,13 @@ #pragma once #include "GameplayTagContainer.h" -#include "../GAGlobalTypes.h" +#include "GAGlobalTypes.h" #include "GAGameEffect.h" -#include "GameplayTaskOwnerInterface.h" +#include "LatentActions/AFLatentInterface.h" #include "GAEffectExtension.generated.h" /* Instanced effect with active event graph, where you can bind events on application. - - One instance per ability is applied per actor. (ie, one ability can apply only one instanced - effect to each actor). - So this is not suitable for effects which should have ability to be applied multiple times the same - actor to stack in intensity and still have different durations. - - When the same type of instanced effect from the same instigator will be applied to the same actor - old effect will be terminated and new one will be applied. - Or, old one will be refreshed (reset duration, reinitialize etc, but not destroyed). */ UCLASS(BlueprintType, Blueprintable, EditInLineNew) class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatentInterface //this interface is not needed, but NewTask is expting those functions. @@ -25,8 +16,15 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatent public: UPROPERTY(BlueprintReadOnly, Category = "Context") FGAEffectContext Context; + + /*Component which actually owns this Effect (Effect Target) */ UPROPERTY() class UAFEffectsComponent* OwningComponent; + + /* Component from this effect has originated (Effect Instigator) */ + UPROPERTY() + class UAFEffectsComponent* SourceComponent; + UPROPERTY() class AActor* Avatar; @@ -64,6 +62,21 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatent void NativeOnEffectExpired(); void NativeOnEffectRemoved(); + void NativeOnEffectAppliedCDO(); + void NativeOnEffectExecutedCDO(); + void NativeOnEffectExpiredCDO(); + void NativeOnEffectRemovedCDO(); + + + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectAppliedCDO() const; + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectExecutedCOD() const; + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectExpiredCDO() const; + UFUNCTION(BlueprintImplementableEvent, Category = "Event Graph") + void OnEffectRemovedCDO() const; + virtual UWorld* GetWorld() const override; /* IAFLatentInterface */ @@ -76,4 +89,7 @@ class ABILITYFRAMEWORK_API UGAEffectExtension : public UObject, public IAFLatent virtual class UAFTaskBase* GetCachedLatentAction(FName TaskName); /* IAFLatentInterface */ + +protected: + void CleanupTasks(); }; diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h index 5d4d5c2..52a95e1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/Effects/GAGameEffect.h @@ -113,6 +113,13 @@ struct FAFConditionalEffectContainer TArray Effects; }; +UENUM(BlueprintType) +enum class EAFExtensionType : uint8 +{ + NonInstanced UMETA(ToolTip = "Effect CDO will be used. Canno carry any state. You usually should use this if effect is instant or applied very often"), + Instanced UMETA(ToolTip = "Effect Extension will be instanced per effect application, these can have state and Tasks") + +}; /* Base effect class. You can derive your own specialized classes from it @@ -183,7 +190,10 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject UPROPERTY(EditAnywhere, Category = "Execution Type") TSubclassOf ExecutionType; - UPROPERTY(EditAnywhere, Category = "Modifiers") + + UPROPERTY(EditAnywhere, Category = "Extension") + EAFExtensionType ExtensionInstancingPolicy; + UPROPERTY(EditAnywhere, Category = "Extension") TSubclassOf Extension; /* Cues to apply by this effect. */ @@ -236,6 +246,7 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject /* Tags I own and I don't apply. New tags can be added here as the effect is applied. */ UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer OwnedTags; + /* Tags owned by this effect and not applied. Describe the type of this effect. */ UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer EffectTags; @@ -264,10 +275,14 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer AttributeTags; - /* If Target have these tags I will not be applied to it. */ + /* If Target have any of these tags, effect will not be applied. */ UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer DenyTags; - + + /* Tags, required for this effect to be applied. If these tags are not present, effect will be ignored. */ + UPROPERTY(EditAnywhere, Category = "Tags") + FGameplayTagContainer ApplicationRequiredTags; + /* Applied immunity tags. */ UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer AppliedImmunityTags; @@ -276,13 +291,9 @@ class ABILITYFRAMEWORK_API UGAGameEffectSpec : public UObject UPROPERTY(EditAnywhere, Category = "Tags") FGameplayTagContainer ApplyTags; - /* Tags, required for this effect to be applied. If these tags are not present, effect will be ignored. */ + /* If any of these tags are present on Effect Target, it will not be executed */ UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer RequiredTags; - - /* Tags, required for this effect to be executed. If these tags are not present, effect will be ignored. */ - UPROPERTY(EditAnywhere, Category = "Tags") - FGameplayTagContainer ExecutionRequiredTags; + FGameplayTagContainer ExecutionDenyTags; public: UGAGameEffectSpec(); }; @@ -390,9 +401,9 @@ struct ABILITYFRAMEWORK_API FAFContextHandle return DataPtr.Get(); } - void SetTarget(UObject* NewTarget) + void SetTarget(UObject* NewTarget, const FHitResult& InHit) { - DataPtr->SetTarget(NewTarget); + DataPtr->SetTarget(NewTarget, InHit); } bool operator==(const FAFContextHandle& Other) const @@ -428,11 +439,14 @@ struct TStructOpsTypeTraits< FAFContextHandle > : public TStructOpsTypeTraitsBas Dervied from GCObject because Extension property has been garbage collected. Even with UPROPERTY() and non-GC outer. */ -struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject +USTRUCT(BlueprintType) +struct ABILITYFRAMEWORK_API FAFEffectSpec // : public FGCObject { + GENERATED_BODY() private: FAFContextHandle Context; - UGAEffectExtension* Extension; //week ptr ? + UPROPERTY() + TWeakObjectPtr Extension; //week ptr ? TSubclassOf SpecClass; @@ -450,10 +464,10 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject FAFEffectSpec(const FAFContextHandle& InContext, TSubclassOf InSpecClass); - void OnApplied(); - void OnExpired(); - void OnRemoved(); - void OnExecuted(); + void OnApplied() const; + void OnExpired() const; + void OnRemoved() const; + void OnExecuted() const; FAFContextHandle GetContext() { return Context; @@ -478,6 +492,10 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject { return SpecClass.GetDefaultObject(); } + UGAGameEffectSpec* GetSpec() const + { + return SpecClass.GetDefaultObject(); + } float GetFloatFromAttributeMagnitude( const FGAMagnitude& AttributeIn @@ -489,16 +507,20 @@ struct ABILITYFRAMEWORK_API FAFEffectSpec : public FGCObject float GetDuration(const FGAEffectContext& InContext); float GetPeriod(const FGAEffectContext& InContext); + float GetDuration(const FGAEffectContext& InContext) const; + float GetPeriod(const FGAEffectContext& InContext) const; const TSubclassOf& GetEffectClass() { return SpecClass; } - virtual void AddReferencedObjects(FReferenceCollector& Collector) override - { - Collector.AddReferencedObject(Extension, Context.GetPtr()->Target.Get()); - } + void Instance(); + + //virtual void AddReferencedObjects(FReferenceCollector& Collector) override + //{ + // Collector.AddReferencedObject(Extension, Context.GetPtr()->Target.Get()); + //} }; USTRUCT(BlueprintType) @@ -594,6 +616,7 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty TWeakObjectPtr Application; TWeakObjectPtr Execution; TWeakObjectPtr Spec; + TSubclassOf SpecClass; FAFPredictionHandle PredictionHandle; float Duration; @@ -610,24 +633,26 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty */ - FAFContextHandle InstantContext; - FAFEffectSpecHandle InstantEffectSpec; + FAFContextHandle EffectContext; + FAFEffectSpecHandle EffectSpec; + //add chaing or not ? + //struct Aggregator + //{ + // FAFContextHandle InstantContext; + // FAFEffectSpecHandle InstantEffectSpec; + // FGAEffectHandle Handle; + //}; + + //TArray AppliedEffects; - TMap EffectSpecs; - //Cached context per created effect. - TMap Contexts; - //possibly multiple handles per target ? - TMap Handles; - TMap HandleToTarget; - TMap EffectCues; public: FGAEffectProperty(); FGAEffectProperty(TSubclassOf InClass); void PostScriptConstruct(); - UGAGameEffectSpec* GetSpec() { return Spec.Get(); } - UGAGameEffectSpec* GetSpec() const { return Spec.Get(); } + UGAGameEffectSpec* GetSpecData() { return Spec.Get(); } + UGAGameEffectSpec* GetSpecData() const { return Spec.Get(); } bool CanApply( const struct FGAEffect& EffectIn @@ -650,198 +675,72 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty , const FAFEffectParams& InParams , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); - //intentionally non const. - //FGAEffectHandle& GetHandleRef() { return Handle; } - //void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; - void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} - - void Initialize(TSubclassOf EffectClass); - void InitializeIfNotInitialized(const FGAEffectContext& InContext - , TSubclassOf EffectClass); - bool GetIsInstant() const - { - return bInstant; - } - inline float GetPeriod() const + /* Get or create Effect Spec. The Effect spec is created once per EffectProperty and then returned by value. */ + FAFEffectSpec GetSpecCopy() { - return Period; - } - inline float GetDuration() const - { - return Duration; - } - - void RegisterHandle( - UObject* Target - , const FGAEffectHandle& InHandle - , const FAFContextHandle& Context - , const FAFEffectSpecHandle& InSpec) - { - if (bInstant) + if (EffectSpec.IsValid()) { - InstantContext = Context; - InstantEffectSpec = InSpec; - return; + FAFEffectSpec* Ptr = EffectSpec.GetPtr().Get(); + Ptr->Instance(); + return *Ptr; } - if (HandleToTarget.Contains(InHandle)) + else { - UE_LOG(GameAttributes, Log, TEXT("FGAEffectProperty::RegisterHandle Handle already registered \n")); - return; + FAFEffectSpec* LocalSpec = new FAFEffectSpec(EffectContext, SpecClass); + LocalSpec->Instance(); + EffectSpec = FAFEffectSpecHandle::Generate(LocalSpec); + return *LocalSpec; } - - AddHandle(Target, InHandle); - AddContext(InHandle, Context); - AddEffectSpec(InHandle, InSpec); } - void AddHandle(UObject* Target, const FGAEffectHandle& InHandle) + FGAEffectContext GetContextCopy(UObject* Target, const FHitResult& InHit) { - FObjectKey key(Target); - Handles.Add(key, InHandle); - HandleToTarget.Add(InHandle, Target); - } - - FGAEffectHandle GetHandle(UObject* From) - { - FObjectKey key(From); - if (FGAEffectHandle* handle = Handles.Find(key)) - return *handle; - - return FGAEffectHandle(); - } - FGAEffectHandle GetHandle(UObject* From) const - { - FObjectKey key(From); - if (const FGAEffectHandle* handle = Handles.Find(key)) - return *handle; - - return FGAEffectHandle(); - } - - FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) - { - if (bInstant) + if (EffectContext.IsValid()) { - return InstantContext; + EffectContext.SetTarget(Target, InHit); + return *EffectContext.GetPtr(); } - FAFContextHandle* Ctx = Contexts.Find(InHandle); - if (Ctx) + else { - return *Ctx; + return FGAEffectContext(); } - return InstantContext; - } - const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const - { - if (bInstant) - { - return InstantContext; - } - const FAFContextHandle* Ctx = Contexts.Find(InHandle); - if (Ctx) - { - return *Ctx; - } - return InstantContext; } - void AddContext(const FGAEffectHandle& InHandle, const FAFContextHandle& ContextHandle) - { - Contexts.Add(InHandle, ContextHandle); - } + //intentionally non const. + //FGAEffectHandle& GetHandleRef() { return Handle; } + //void SetHandle(const FGAEffectHandle& InHandle) { Handle = InHandle; }; + void OnEffectRemoved(UObject* InTarget, const FGAEffectHandle& InHandle) {} - void RemoveContext(const FGAEffectHandle& InHandle) - { - Contexts.Remove(InHandle); - } + void Initialize(TSubclassOf EffectClass); + void InitializeIfNotInitialized( + class APawn* Instigator + , UObject* Causer + , TSubclassOf EffectClass); - FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) + bool GetIsInstant() const { - if (bInstant) - { - return InstantEffectSpec; - } - FAFEffectSpecHandle* SpecLocal = EffectSpecs.Find(InHandle); - if (SpecLocal) - { - return *SpecLocal; - } - return InstantEffectSpec; + return bInstant; } - const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const + inline float GetPeriod() const { - if (bInstant) - { - return InstantEffectSpec; - } - const FAFEffectSpecHandle* SpecLocal = EffectSpecs.Find(InHandle); - if (SpecLocal) - { - return *SpecLocal; - } - return InstantEffectSpec; + return Period; } - - void AddEffectSpec(const FGAEffectHandle& InHandle, const FAFEffectSpecHandle& ContextHandle) + inline float GetDuration() const { - EffectSpecs.Add(InHandle, ContextHandle); + return Duration; } - void RemoveEffectSpec(const FGAEffectHandle& InHandle) + void SetPredictionHandle(const FAFPredictionHandle& InHandle) { - EffectSpecs.Remove(InHandle); + PredictionHandle = InHandle; } - inline FAFPredictionHandle GetPredictionHandle() const + FAFPredictionHandle GetPredictionHandle() { return PredictionHandle; } - bool IsHandleValid(UObject* For) - { - FObjectKey Key(For); - FGAEffectHandle* Handle = Handles.Find(Key); - if (Handle) - { - return Handle->IsValid(); - } - return false; - } - bool IsHandleValid(UObject* For) const - { - FObjectKey Key(For); - const FGAEffectHandle* Handle = Handles.Find(Key); - if (Handle) - { - return Handle->IsValid(); - } - return false; - } - void RemoveHandle(const FGAEffectHandle& InHandle) - { - UObject* Target = nullptr; - HandleToTarget.RemoveAndCopyValue(InHandle, Target); - if(Target) - { - FObjectKey key(Target); - Handles.Remove(key); - } - } - - void CleanUp(const FGAEffectHandle& InHandle) - { - RemoveContext(InHandle); - EffectCues.Remove(InHandle); - RemoveHandle(InHandle); - RemoveEffectSpec(InHandle); - } - - void SetPredictionHandle(const FAFPredictionHandle& InHandle) - { - PredictionHandle = InHandle; - } - FGAAttributeModifier& GetAttributeModifier() { return Spec->AtributeModifier; @@ -852,10 +751,6 @@ struct ABILITYFRAMEWORK_API FGAEffectProperty { return ApplicationRequirement.IsValid() && Application.IsValid() && Execution.IsValid() && Spec.IsValid(); } - /*const bool IsValidHandle() const - { - return Handle.IsValid(); - }*/ }; template<> @@ -917,20 +812,28 @@ struct ABILITYFRAMEWORK_API FAFPropertytHandle void PostScriptConstruct() { + if (SpecClass.SpecClass) + { + + } } - /*FAFPropertytHandle(TSharedRef InPtr, uint32 InID) - : Test(InPtr) - , ID(InID) - {}*/ TSubclassOf GetClass() const { return SpecClass.SpecClass; } const TSubclassOf& GetClassRef() { return SpecClass.SpecClass; } public: - void InitializeIfNotInitialized(const FGAEffectContext& InContext) + void InitializeIfNotInitialized( + class APawn* Instigator + , UObject* Causer) + { + DataPtr->InitializeIfNotInitialized(Instigator, Causer, SpecClass.SpecClass); + } + + FAFEffectSpec GetSpecCopy() { - DataPtr->InitializeIfNotInitialized(InContext, SpecClass.SpecClass); + return DataPtr->GetSpecCopy(); } + FGAEffectProperty & GetRef() { return DataPtr.ToSharedRef().Get(); @@ -957,38 +860,15 @@ struct ABILITYFRAMEWORK_API FAFPropertytHandle return DataPtr->GetDuration(); } - UGAGameEffectSpec* GetSpec() - { - return DataPtr->GetSpec(); - } - UGAGameEffectSpec* GetSpec() const - { - return DataPtr->GetSpec(); - } - FGAEffectHandle GetHandle(UObject* From) - { - return DataPtr->GetHandle(From); - } - FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) + UGAGameEffectSpec* GetSpecData() { - return DataPtr->GetContext(InHandle); + return DataPtr->GetSpecData(); } - const FAFContextHandle& GetContext(const FGAEffectHandle& InHandle) const + UGAGameEffectSpec* GetSpecData() const { - return DataPtr->GetContext(InHandle); - } - FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) - { - return DataPtr->GetEffectSpec(InHandle); - } - const FAFEffectSpecHandle& GetEffectSpec(const FGAEffectHandle& InHandle) const - { - return DataPtr->GetEffectSpec(InHandle); - } - void CleanUp(const FGAEffectHandle& InHandle) - { - DataPtr->CleanUp(InHandle); + return DataPtr->GetSpecData(); } + const bool IsInitialized() const { return DataPtr->IsInitialized(); @@ -1033,14 +913,14 @@ struct TStructOpsTypeTraits< FAFPropertytHandle > : public TStructOpsTypeTraitsB }; }; -USTRUCT() +USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FAFEffectParams { GENERATED_BODY() //make this private and allow assign only trough constructr. - FAFContextHandle Context; + FGAEffectContext Context; FAFPropertytHandle Property; - FAFEffectSpecHandle EffectSpec; + FAFEffectSpec EffectSpec; bool bRecreated; bool bPeriodicEffect; public: @@ -1051,22 +931,14 @@ struct ABILITYFRAMEWORK_API FAFEffectParams , bRecreated(false) {}; - FAFContextHandle& GetContextHandle() + FGAEffectContext& GetContext() { return Context; } - const FAFContextHandle& GetContextHandle() const + const FGAEffectContext& GetContext() const { return Context; } - FGAEffectContext & GetContext() - { - return Context.GetRef(); - } - FGAEffectContext& GetContext() const - { - return Context.GetRef(); - } FGAEffectProperty& GetProperty() const { @@ -1075,11 +947,11 @@ struct ABILITYFRAMEWORK_API FAFEffectParams FAFEffectSpec& GetSpec() { - return EffectSpec.SpecPtr.ToSharedRef().Get(); + return EffectSpec; } - FAFEffectSpec& GetSpec() const + const FAFEffectSpec& GetSpec() const { - return EffectSpec.SpecPtr.ToSharedRef().Get(); + return EffectSpec; } FTimerManager& GetTargetTimerManager(); @@ -1088,23 +960,24 @@ struct ABILITYFRAMEWORK_API FAFEffectParams }; + USTRUCT(BlueprintType) struct ABILITYFRAMEWORK_API FAFEventData { GENERATED_BODY() public: UPROPERTY(BlueprintReadOnly) - FAFContextHandle ContextHandle; + FGAEffectContext ContextHandle; UPROPERTY(BlueprintReadOnly) - FAFEffectSpecHandle SpecHandle; + FAFEffectSpec SpecHandle; UPROPERTY(BlueprintReadOnly) FAFPropertytHandle PropertyHandle; FAFEventData() {}; - FAFEventData(FAFContextHandle InContextHandle - , FAFEffectSpecHandle InSpecHandle + FAFEventData(FGAEffectContext InContextHandle + , FAFEffectSpec InSpecHandle , FAFPropertytHandle InPropertyHandle ) : ContextHandle(InContextHandle) @@ -1338,14 +1211,13 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer */ FGAEffectHandle ApplyEffect( const FGAEffect& EffectIn - , const FGAEffectHandle& InHandle , const FAFEffectParams& Params , const FAFFunctionModifier& Modifier = FAFFunctionModifier()); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - TArray RemoveEffect(const FAFPropertytHandle& HandleIn, int32 Num = 1); + TArray RemoveEffect(const FAFPropertytHandle& HandleIn, const FGAEffectContext& InContext, int32 Num = 1); /* Removesgiven number of effects of the same type. If Num == 0 Removes all effects */ - void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FAFPropertytHandle& InProperty); + void RemoveEffectByHandle(const FGAEffectHandle& InHandle, const FGAEffectContext& InContext, const FAFPropertytHandle& InProperty); inline int32 GetEffectsNum() const { return ActiveEffectInfos.Num(); }; @@ -1357,6 +1229,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer , const FAFPredictionHandle& InPredHandle , FGAEffect* InEffect , const FGAEffectProperty& InProperty + , const FAFEffectParams& Params , bool bInfinite = false); //modifiers @@ -1391,7 +1264,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContainer : public FFastArraySerializer } bool IsEffectActive(TSubclassOf EffectClass); private: - void RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectHandle& InHandle); + void RemoveEffectInternal(const FAFPropertytHandle& InProperty, const FGAEffectContext& InContext, const FGAEffectHandle& InHandle); }; template<> struct TStructOpsTypeTraits< FGAEffectContainer > : public TStructOpsTypeTraitsBase2 diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h index e54a0ff..21e20a3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/GAGlobalTypes.h @@ -225,7 +225,7 @@ struct ABILITYFRAMEWORK_API FGAEffectContext class IAFAbilityInterface* TargetInterface; class IAFAbilityInterface* InstigatorInterface; - void SetTarget(UObject* NewTarget); + void SetTarget(UObject* NewTarget, const FHitResult& InHit); template inline T* GetTarget() { @@ -294,6 +294,8 @@ struct ABILITYFRAMEWORK_API FGAEffectContext FGAEffectContext(const FGAEffectContext& Other); + FGAEffectContext(APawn* InInstigator, UObject* InCauser); + FGAEffectContext(TWeakObjectPtr TargetAttributesIn, TWeakObjectPtr InstigatorAttributesIn, const FVector& TargetHitLocationIn, TWeakObjectPtr TargetIn, TWeakObjectPtr CauserIn, TWeakObjectPtr InstigatorIn, diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h index 3b4bce0..8ff3a17 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/IAbilityFramework.h @@ -2,7 +2,7 @@ #pragma once -#include "ModuleManager.h" +#include "Modules/ModuleManager.h" /** diff --git a/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h index 2db8241..ab9d327 100644 --- a/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h +++ b/Plugins/AbilityFramework/Source/AbilityFramework/Public/LatentActions/AFTaskBase.h @@ -52,9 +52,10 @@ class ABILITYFRAMEWORK_API UAFTaskBase : public UObject public: UFUNCTION(BlueprintCallable, meta = (BlueprintInternalUseOnly = "true"), Category = "Latent Action") virtual void ReadyForActivation(); + virtual void EndTask(); protected: virtual void Activate() {}; - virtual void EndTask(); + virtual void BeginDestroy() override; virtual void OnTaskEnded() {}; public: diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp index 342153e..fade3e1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/AbilityFrameworkEditor.cpp @@ -3,7 +3,7 @@ #include "AbilityFrameworkEditor.h" #include "GAAttributePin.h" #include "Attributes/GAAttributeGlobals.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #include "GAAttributePanelGraphPinFactory.h" #include "GAAttributeDetailCustomization.h" @@ -18,7 +18,8 @@ #include "EffectEditor/AssetTypeActions_GAEffectBlueprint.h" #include "AbilityEditor/AssetTypeActions_GAAbilityBlueprint.h" -#include "EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h" +#include "EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.h" +#include "CueStatic/AssetTypeActions_AFCueStaticBlueprint.h" #include "EffectCueEditor/AFEffectCueDetails.h" @@ -63,7 +64,7 @@ void FAbilityFrameworkEditor::RegisterAssetTypeAction(IAssetTools& AssetTools, T void FAbilityFrameworkEditor::OnInitializeSequence(UGAEffectCueSequence* Sequence) { auto* ProjectSettings = GetDefault(); - AGAEffectCue* Cue = Cast(Sequence->GetOuter()); + AAFCueActor* Cue = Cast(Sequence->GetOuter()); if (Cue) @@ -107,9 +108,11 @@ void FAbilityFrameworkEditor::StartupModule() RegisterAssetTypeAction(AssetTools, GABAction); TSharedRef GAAbilityAction = MakeShareable(new FAssetTypeActions_GAAbilityBlueprint()); RegisterAssetTypeAction(AssetTools, GAAbilityAction); - TSharedRef GAEffectCueAction = MakeShareable(new FAssetTypeActions_GAEffectCueBlueprint()); + TSharedRef GAEffectCueAction = MakeShareable(new FAssetTypeActions_AFCueActorBlueprint()); RegisterAssetTypeAction(AssetTools, GAEffectCueAction); - + //AssetTypeActions_AFCueStaticBlueprint + TSharedRef AFStaticCueAction = MakeShareable(new FAssetTypeActions_AFCueStaticBlueprint()); + RegisterAssetTypeAction(AssetTools, AFStaticCueAction); //BlueprintEditorTabBinding = MakeShared(); OnInitializeSequenceHandle = UGAEffectCueSequence::OnInitializeSequence().AddStatic(FAbilityFrameworkEditor::OnInitializeSequence); } diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.cpp new file mode 100644 index 0000000..2e308bc --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.cpp @@ -0,0 +1,334 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. +#include "AbilityFrameworkEditor.h" +#include "AFCueStaticBlueprintFactory.h" + +#include "InputCoreTypes.h" +#include "UObject/Interface.h" +#include "Layout/Visibility.h" +#include "Input/Reply.h" +#include "Widgets/SWidget.h" +#include "Widgets/DeclarativeSyntaxSupport.h" +#include "Misc/MessageDialog.h" +#include "Modules/ModuleManager.h" +#include "Widgets/SCompoundWidget.h" +#include "Widgets/SBoxPanel.h" +#include "Widgets/SWindow.h" +#include "Widgets/Layout/SBorder.h" +#include "Widgets/Text/STextBlock.h" +#include "Widgets/Layout/SBox.h" +#include "Widgets/Layout/SUniformGridPanel.h" +#include "Widgets/Input/SButton.h" +#include "EditorStyleSet.h" +#include "Editor.h" +#include "EdGraphSchema_K2.h" + +#include "ClassViewerModule.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "Engine/BlueprintGeneratedClass.h" +#include "Kismet2/KismetEditorUtilities.h" +#include "BlueprintEditorSettings.h" + +#include "Cues/AFCueStaticBlueprint.h" +#include "Cues/AFCueStaticGeneratedClass.h" + +#include "ClassViewerFilter.h" + +#include "Effects/AFCueStatic.h" + +#include "SlateOptMacros.h" + +// ------------------------------------------------------------------------------ +// Dialog to configure creation properties +// ------------------------------------------------------------------------------ +BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION + +class SEffectCueBlueprintCreateDialog : public SCompoundWidget +{ +public: + SLATE_BEGIN_ARGS(SEffectCueBlueprintCreateDialog){} + + SLATE_END_ARGS() + + /** Constructs this widget with InArgs */ + void Construct(const FArguments& InArgs) + { + bOkClicked = false; + ParentClass = UAFCueStatic::StaticClass(); + + ChildSlot + [ + SNew(SBorder) + .Visibility(EVisibility::Visible) + .BorderImage(FEditorStyle::GetBrush("Menu.Background")) + [ + SNew(SBox) + .Visibility(EVisibility::Visible) + .WidthOverride(500.0f) + [ + SNew(SVerticalBox) + + SVerticalBox::Slot() + .FillHeight(1) + [ + SNew(SBorder) + .BorderImage(FEditorStyle::GetBrush("ToolPanel.GroupBorder")) + .Content() + [ + SAssignNew(ParentClassContainer, SVerticalBox) + ] + ] + + // Ok/Cancel buttons + + SVerticalBox::Slot() + .AutoHeight() + .HAlign(HAlign_Right) + .VAlign(VAlign_Bottom) + .Padding(8) + [ + SNew(SUniformGridPanel) + .SlotPadding(FEditorStyle::GetMargin("StandardDialog.SlotPadding")) + .MinDesiredSlotWidth(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotWidth")) + .MinDesiredSlotHeight(FEditorStyle::GetFloat("StandardDialog.MinDesiredSlotHeight")) + + SUniformGridPanel::Slot(0, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCueBlueprintCreateDialog::OkClicked) + .Text(FText::FromString("OK")) + ] + + SUniformGridPanel::Slot(1, 0) + [ + SNew(SButton) + .HAlign(HAlign_Center) + .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) + .OnClicked(this, &SEffectCueBlueprintCreateDialog::CancelClicked) + .Text(FText::FromString("Cancel")) + ] + ] + ] + ] + ]; + + MakeParentClassPicker(); + } + + /** Sets properties for the supplied AbilitiesBlueprintFactory */ + bool ConfigureProperties(TWeakObjectPtr InEffectCueBlueprintFactory) + { + EffectCueBlueprintFactory = InEffectCueBlueprintFactory; + + TSharedRef Window = SNew(SWindow) + .Title(FText::FromString("Create Ability Blueprint")) + .ClientSize(FVector2D(400, 700)) + .SupportsMinimize(false).SupportsMaximize(false) + [ + AsShared() + ]; + + PickerWindow = Window; + + GEditor->EditorAddModalWindow(Window); + EffectCueBlueprintFactory.Reset(); + + return bOkClicked; + } + +private: + class FEffectCueBlueprintParentFilter : public IClassViewerFilter + { + public: + /** All children of these classes will be included unless filtered out by another setting. */ + TSet< const UClass* > AllowedChildrenOfClasses; + + FEffectCueBlueprintParentFilter() {} + + virtual bool IsClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const UClass* InClass, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InClass) != EFilterReturn::Failed; + } + + virtual bool IsUnloadedClassAllowed(const FClassViewerInitializationOptions& InInitOptions, const TSharedRef< const IUnloadedBlueprintData > InUnloadedClassData, TSharedRef< FClassViewerFilterFuncs > InFilterFuncs) override + { + // If it appears on the allowed child-of classes list (or there is nothing on that list) + return InFilterFuncs->IfInChildOfClassesSet(AllowedChildrenOfClasses, InUnloadedClassData) != EFilterReturn::Failed; + } + }; + + /** Creates the combo menu for the parent class */ + void MakeParentClassPicker() + { + // Load the classviewer module to display a class picker + FClassViewerModule& ClassViewerModule = FModuleManager::LoadModuleChecked("ClassViewer"); + + // Fill in options + FClassViewerInitializationOptions Options; + Options.Mode = EClassViewerMode::ClassPicker; + + // Only allow parenting to base blueprints. + Options.bIsBlueprintBaseOnly = true; + + TSharedPtr Filter = MakeShareable(new FEffectCueBlueprintParentFilter); + + // All child child classes of UGameplayAbility are valid. + Filter->AllowedChildrenOfClasses.Add(AAFCueActor::StaticClass()); + Options.ClassFilter = Filter; + + ParentClassContainer->ClearChildren(); + ParentClassContainer->AddSlot() + .AutoHeight() + [ + SNew(STextBlock) + .Text(FText::FromString("Parent Class:")) + .ShadowOffset(FVector2D(1.0f, 1.0f)) + ]; + + ParentClassContainer->AddSlot() + [ + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCueBlueprintCreateDialog::OnClassPicked)) + ]; + } + + /** Handler for when a parent class is selected */ + void OnClassPicked(UClass* ChosenClass) + { + ParentClass = ChosenClass; + } + + /** Handler for when ok is clicked */ + FReply OkClicked() + { + if (EffectCueBlueprintFactory.IsValid()) + { + EffectCueBlueprintFactory->BlueprintType = BPTYPE_Normal; + EffectCueBlueprintFactory->ParentClass = ParentClass.Get(); + } + + CloseDialog(true); + + return FReply::Handled(); + } + + void CloseDialog(bool bWasPicked = false) + { + bOkClicked = bWasPicked; + if (PickerWindow.IsValid()) + { + PickerWindow.Pin()->RequestDestroyWindow(); + } + } + + /** Handler for when cancel is clicked */ + FReply CancelClicked() + { + CloseDialog(); + return FReply::Handled(); + } + + FReply OnKeyDown(const FGeometry& MyGeometry, const FKeyEvent& InKeyEvent) + { + if (InKeyEvent.GetKey() == EKeys::Escape) + { + CloseDialog(); + return FReply::Handled(); + } + return SWidget::OnKeyDown(MyGeometry, InKeyEvent); + } + +private: + /** The factory for which we are setting up properties */ + TWeakObjectPtr EffectCueBlueprintFactory; + + /** A pointer to the window that is asking the user to select a parent class */ + TWeakPtr PickerWindow; + + /** The container for the Parent Class picker */ + TSharedPtr ParentClassContainer; + + /** The selected class */ + TWeakObjectPtr ParentClass; + + /** True if Ok was clicked */ + bool bOkClicked; +}; + +END_SLATE_FUNCTION_BUILD_OPTIMIZATION + +/*------------------------------------------------------------------------------ + UAbilitiesBlueprintFactory implementation. +------------------------------------------------------------------------------*/ + +UAFCueStaticBlueprintFactory::UAFCueStaticBlueprintFactory(const FObjectInitializer& ObjectInitializer) + : Super(ObjectInitializer) +{ + bCreateNew = true; + bEditAfterNew = true; + SupportedClass = UAFCueStaticBlueprint::StaticClass(); + ParentClass = UAFCueStatic::StaticClass(); +} + +bool UAFCueStaticBlueprintFactory::ConfigureProperties() +{ + TSharedRef Dialog = SNew(SEffectCueBlueprintCreateDialog); + return Dialog->ConfigureProperties(this); +}; + +UObject* UAFCueStaticBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +{ + // Make sure we are trying to factory a gameplay ability blueprint, then create and init one + check(Class->IsChildOf(UAFCueStaticBlueprint::StaticClass())); + + // If they selected an interface, force the parent class to be UInterface + if (BlueprintType == BPTYPE_Interface) + { + ParentClass = UInterface::StaticClass(); + } + + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(AAFCueActor::StaticClass()) ) + { + FFormatNamedArguments Args; + Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); + FMessageDialog::Open( EAppMsgType::Ok, FText::Format( FText::FromString("Cannot create a Ability Blueprint based on the class '{ClassName}'."), Args ) ); + return NULL; + } + else + { + UAFCueStaticBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UAFCueStaticBlueprint::StaticClass(), UAFCueStaticGeneratedClass::StaticClass(), CallingContext)); + + if (NewBP) + { +// UAFCueStaticBlueprint* AbilityBP = UAFCueActorBlueprint::FindRootGameplayAbilityBlueprint(NewBP); +// if (AbilityBP == NULL) +// { +// const UEdGraphSchema_K2* K2Schema = GetDefault(); +// +// // Only allow a gameplay ability graph if there isn't one in a parent blueprint +// UEdGraph* NewGraph = FBlueprintEditorUtils::CreateNewGraph(NewBP, TEXT("Ability Graph"), UGAEffectCueGraph::StaticClass(), UGAEffectCueGraphSchema::StaticClass()); +//#if WITH_EDITORONLY_DATA +// if (NewBP->UbergraphPages.Num()) +// { +// FBlueprintEditorUtils::RemoveGraphs(NewBP, NewBP->UbergraphPages); +// } +//#endif +// FBlueprintEditorUtils::AddUbergraphPage(NewBP, NewGraph); +// NewBP->LastEditedDocuments.Add(NewGraph); +// NewGraph->bAllowDeletion = false; +// +// UBlueprintEditorSettings* Settings = GetMutableDefault(); +// if(Settings && Settings->bSpawnDefaultBlueprintNodes) +// { +// int32 NodePositionY = 0; +// //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_ActivateAbility")), UGAAbilityBase::StaticClass(), NodePositionY); +// //FKismetEditorUtilities::AddDefaultEventNode(NewBP, NewGraph, FName(TEXT("K2_OnEndAbility")), UGAAbilityBase::StaticClass(), NodePositionY); +// } +// } + } + + return NewBP; + } +} + +UObject* UAFCueStaticBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +{ + return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); +} diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.h similarity index 87% rename from Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h rename to Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.h index 1c78872..4150463 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AFCueStaticBlueprintFactory.h @@ -8,10 +8,10 @@ #include "Engine/Blueprint.h" #include "Factories/Factory.h" #include "AssetTypeCategories.h" -#include "GAEffectCueBlueprintFactory.generated.h" +#include "AFCueStaticBlueprintFactory.generated.h" UCLASS(HideCategories=Object, MinimalAPI) -class UGAEffectCueBlueprintFactory : public UFactory +class UAFCueStaticBlueprintFactory : public UFactory { GENERATED_UCLASS_BODY() @@ -21,7 +21,7 @@ class UGAEffectCueBlueprintFactory : public UFactory // The parent class of the created blueprint UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) - TSubclassOf ParentClass; + TSubclassOf ParentClass; //~ Begin UFactory Interface virtual bool ConfigureProperties() override; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.cpp new file mode 100644 index 0000000..65f7cb7 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.cpp @@ -0,0 +1,59 @@ +// Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. +#include "AbilityFrameworkEditor.h" +#include "AssetTypeActions_AFCueStaticBlueprint.h" +#include "Misc/MessageDialog.h" +#include "Kismet2/BlueprintEditorUtils.h" +#include "BlueprintEditor.h" +//#include "GAEffectCueEditor.h" +#include "Cues/AFCueStaticBlueprint.h" + +#include "Effects/AFCueStatic.h" +#include "CueStatic/AFCueStaticBlueprintFactory.h" + +#define LOCTEXT_NAMESPACE "AssetTypeActions" + +FText FAssetTypeActions_AFCueStaticBlueprint::GetName() const +{ + return FText::FromString("Cue Static"); +} +UClass* FAssetTypeActions_AFCueStaticBlueprint::GetSupportedClass() const +{ + return UAFCueStaticBlueprint::StaticClass(); +} + +void FAssetTypeActions_AFCueStaticBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +{ + EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; + + for (auto ObjIt = InObjects.CreateConstIterator(); ObjIt; ++ObjIt) + { + auto Blueprint = Cast(*ObjIt); + if (Blueprint && Blueprint->SkeletonGeneratedClass && Blueprint->GeneratedClass) + { + TSharedRef< FBlueprintEditor > NewEditor(new FBlueprintEditor()); + + TArray Blueprints; + Blueprints.Add(Blueprint); + + NewEditor->InitBlueprintEditor(Mode, EditWithinLevelEditor, Blueprints, false); + } + else + { + FMessageDialog::Open(EAppMsgType::Ok, FText::FromString("Ability Blueprint could not be loaded because it derives from an invalid class. Check to make sure the parent class for this blueprint hasn't been removed!")); + } + } +} + +bool FAssetTypeActions_AFCueStaticBlueprint::ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const +{ + return false; +} + +UFactory* FAssetTypeActions_AFCueStaticBlueprint::GetFactoryForBlueprintType(UBlueprint* InBlueprint) const +{ + UAFCueStaticBlueprintFactory* EffectCueBlueprintFactory = NewObject(); + EffectCueBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + return EffectCueBlueprintFactory; +} + +#undef LOCTEXT_NAMESPACE \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.h similarity index 86% rename from Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h rename to Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.h index 55a06ad..40ef9ae 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/CueStatic/AssetTypeActions_AFCueStaticBlueprint.h @@ -2,12 +2,11 @@ #include "CoreMinimal.h" #include "Toolkits/IToolkitHost.h" #include "AssetTypeCategories.h" -//#include "Developer/AssetTools/Private/AssetTypeActions/AssetTypeActions_ClassTypeBase.h" #include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" class UFactory; -class FAssetTypeActions_GAEffectCueBlueprint : public FAssetTypeActions_Blueprint +class FAssetTypeActions_AFCueStaticBlueprint : public FAssetTypeActions_Blueprint { public: // IAssetTypeActions Implementation diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.cpp similarity index 82% rename from Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp rename to Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.cpp index d548866..2951ef1 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueBlueprintFactory.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.cpp @@ -1,6 +1,6 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "GAEffectCueBlueprintFactory.h" +#include "AbilityFrameworkEditor.h" +#include "AFCueActorBlueprintFactory.h" #include "InputCoreTypes.h" #include "UObject/Interface.h" #include "Layout/Visibility.h" @@ -28,8 +28,8 @@ #include "Kismet2/KismetEditorUtilities.h" #include "BlueprintEditorSettings.h" -#include "Effects/GAEffectCueBlueprint.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActorBlueprint.h" +#include "Effects/AFCueActor.h" #include "GAEffectCueGraph.h" #include "GAEffectCueGraphSchema.h" @@ -42,10 +42,10 @@ // ------------------------------------------------------------------------------ BEGIN_SLATE_FUNCTION_BUILD_OPTIMIZATION -class SEffectCueBlueprintCreateDialog : public SCompoundWidget +class SCueStaticBlueprintCreateDialog : public SCompoundWidget { public: - SLATE_BEGIN_ARGS(SEffectCueBlueprintCreateDialog){} + SLATE_BEGIN_ARGS(SCueStaticBlueprintCreateDialog){} SLATE_END_ARGS() @@ -53,7 +53,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget void Construct(const FArguments& InArgs) { bOkClicked = false; - ParentClass = AGAEffectCue::StaticClass(); + ParentClass = AAFCueActor::StaticClass(); ChildSlot [ @@ -93,7 +93,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget SNew(SButton) .HAlign(HAlign_Center) .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectCueBlueprintCreateDialog::OkClicked) + .OnClicked(this, &SCueStaticBlueprintCreateDialog::OkClicked) .Text(FText::FromString("OK")) ] + SUniformGridPanel::Slot(1, 0) @@ -101,7 +101,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget SNew(SButton) .HAlign(HAlign_Center) .ContentPadding(FEditorStyle::GetMargin("StandardDialog.ContentPadding")) - .OnClicked(this, &SEffectCueBlueprintCreateDialog::CancelClicked) + .OnClicked(this, &SCueStaticBlueprintCreateDialog::CancelClicked) .Text(FText::FromString("Cancel")) ] ] @@ -113,7 +113,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget } /** Sets properties for the supplied AbilitiesBlueprintFactory */ - bool ConfigureProperties(TWeakObjectPtr InEffectCueBlueprintFactory) + bool ConfigureProperties(TWeakObjectPtr InEffectCueBlueprintFactory) { EffectCueBlueprintFactory = InEffectCueBlueprintFactory; @@ -171,7 +171,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget TSharedPtr Filter = MakeShareable(new FEffectCueBlueprintParentFilter); // All child child classes of UGameplayAbility are valid. - Filter->AllowedChildrenOfClasses.Add(AGAEffectCue::StaticClass()); + Filter->AllowedChildrenOfClasses.Add(AAFCueActor::StaticClass()); Options.ClassFilter = Filter; ParentClassContainer->ClearChildren(); @@ -185,7 +185,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget ParentClassContainer->AddSlot() [ - ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SEffectCueBlueprintCreateDialog::OnClassPicked)) + ClassViewerModule.CreateClassViewer(Options, FOnClassPicked::CreateSP(this, &SCueStaticBlueprintCreateDialog::OnClassPicked)) ]; } @@ -237,7 +237,7 @@ class SEffectCueBlueprintCreateDialog : public SCompoundWidget private: /** The factory for which we are setting up properties */ - TWeakObjectPtr EffectCueBlueprintFactory; + TWeakObjectPtr EffectCueBlueprintFactory; /** A pointer to the window that is asking the user to select a parent class */ TWeakPtr PickerWindow; @@ -258,25 +258,25 @@ END_SLATE_FUNCTION_BUILD_OPTIMIZATION UAbilitiesBlueprintFactory implementation. ------------------------------------------------------------------------------*/ -UGAEffectCueBlueprintFactory::UGAEffectCueBlueprintFactory(const FObjectInitializer& ObjectInitializer) +UAFCueActorBlueprintFactory::UAFCueActorBlueprintFactory(const FObjectInitializer& ObjectInitializer) : Super(ObjectInitializer) { bCreateNew = true; bEditAfterNew = true; - SupportedClass = UGAEffectCueBlueprint::StaticClass(); - ParentClass = AGAEffectCue::StaticClass(); + SupportedClass = UAFCueActorBlueprint::StaticClass(); + ParentClass = AAFCueActor::StaticClass(); } -bool UGAEffectCueBlueprintFactory::ConfigureProperties() +bool UAFCueActorBlueprintFactory::ConfigureProperties() { - TSharedRef Dialog = SNew(SEffectCueBlueprintCreateDialog); + TSharedRef Dialog = SNew(SCueStaticBlueprintCreateDialog); return Dialog->ConfigureProperties(this); }; -UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) +UObject* UAFCueActorBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) { // Make sure we are trying to factory a gameplay ability blueprint, then create and init one - check(Class->IsChildOf(UGAEffectCueBlueprint::StaticClass())); + check(Class->IsChildOf(UAFCueActorBlueprint::StaticClass())); // If they selected an interface, force the parent class to be UInterface if (BlueprintType == BPTYPE_Interface) @@ -284,7 +284,7 @@ UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* ParentClass = UInterface::StaticClass(); } - if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(AGAEffectCue::StaticClass()) ) + if ( ( ParentClass == NULL ) || !FKismetEditorUtilities::CanCreateBlueprintOfClass(ParentClass) || !ParentClass->IsChildOf(AAFCueActor::StaticClass()) ) { FFormatNamedArguments Args; Args.Add( TEXT("ClassName"), (ParentClass != NULL) ? FText::FromString( ParentClass->GetName() ) : FText::FromString("Null") ); @@ -293,11 +293,11 @@ UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* } else { - UGAEffectCueBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UGAEffectCueBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); + UAFCueActorBlueprint* NewBP = CastChecked(FKismetEditorUtilities::CreateBlueprint(ParentClass, InParent, Name, BlueprintType, UAFCueActorBlueprint::StaticClass(), UBlueprintGeneratedClass::StaticClass(), CallingContext)); if (NewBP) { - UGAEffectCueBlueprint* AbilityBP = UGAEffectCueBlueprint::FindRootGameplayAbilityBlueprint(NewBP); + UAFCueActorBlueprint* AbilityBP = UAFCueActorBlueprint::FindRootGameplayAbilityBlueprint(NewBP); if (AbilityBP == NULL) { const UEdGraphSchema_K2* K2Schema = GetDefault(); @@ -328,7 +328,7 @@ UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* } } -UObject* UGAEffectCueBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) +UObject* UAFCueActorBlueprintFactory::FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) { return FactoryCreateNew(Class, InParent, Name, Flags, Context, Warn, NAME_None); } diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.h new file mode 100644 index 0000000..a8b46d3 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFCueActorBlueprintFactory.h @@ -0,0 +1,32 @@ +// Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. + +#pragma once + +#include "CoreMinimal.h" +#include "UObject/ObjectMacros.h" +#include "Templates/SubclassOf.h" +#include "Engine/Blueprint.h" +#include "Factories/Factory.h" +#include "AssetTypeCategories.h" +#include "AFCueActorBlueprintFactory.generated.h" + +UCLASS(HideCategories=Object, MinimalAPI) +class UAFCueActorBlueprintFactory : public UFactory +{ + GENERATED_UCLASS_BODY() + + // The type of blueprint that will be created + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TEnumAsByte BlueprintType; + + // The parent class of the created blueprint + UPROPERTY(EditAnywhere, Category=GameplayAbilitiesBlueprintFactory) + TSubclassOf ParentClass; + + //~ Begin UFactory Interface + virtual bool ConfigureProperties() override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn, FName CallingContext) override; + virtual UObject* FactoryCreateNew(UClass* Class, UObject* InParent, FName Name, EObjectFlags Flags, UObject* Context, FFeedbackContext* Warn) override; + + //~ Begin UFactory Interface +}; diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp index f301611..fcb61a3 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AFEffectCueDetails.cpp @@ -6,7 +6,7 @@ #include "STextCombobox.h" #include "STreeView.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #include "Effects/GAEffectCueSequence.h" #include "EditorReimportHandler.h" #include "MovieScene.h" @@ -29,7 +29,7 @@ class SEffectCueSequenceEditorWidget { private: TWeakObjectPtr WeakSequence; - AGAEffectCue* EffectCue; + AAFCueActor* EffectCue; TWeakPtr WeakBlueprintEditor; TSharedPtr Content; @@ -229,7 +229,7 @@ class SEffectCueSequenceEditorWidget , FText(), !bIdent );*/ } - void SetActorSequence(UGAEffectCueSequence* NewSequence, AGAEffectCue* InEffectCue) + void SetActorSequence(UGAEffectCueSequence* NewSequence, AAFCueActor* InEffectCue) { if (UGAEffectCueSequence* OldSequence = WeakSequence.Get()) { @@ -329,17 +329,17 @@ void FAFEffectCueDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) TSharedPtr HostTabManager = DetailsView->GetHostTabManager(); TArray> Objects; DetailLayout.GetObjectsBeingCustomized(Objects); - AGAEffectCue* EffectCue = Cast(Objects[0].Get()); + AAFCueActor* EffectCue = Cast(Objects[0].Get()); if (HostTabManager.IsValid() && HostTabManager->CanSpawnTab("EmbeddedEffectCueSequenceID")) { TSharedPtr ExistingTab = HostTabManager->FindExistingLiveTab(FName("EmbeddedEffectCueSequenceID")); if (ExistingTab.IsValid()) { - //EffectCue->StaticClass()->GetDefaultObject()->Sequence + //EffectCue->StaticClass()->GetDefaultObject()->Sequence //auto SequencerWidget = StaticCastSharedRef(ExistingTab->GetContent()); - StaticCastSharedRef(ExistingTab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); + StaticCastSharedRef(ExistingTab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); //bIsExternalTabAlreadyOpened = ThisSequence && SequencerWidget->GetSequence() == ThisSequence; return; } @@ -347,7 +347,7 @@ void FAFEffectCueDetails::CustomizeDetails(IDetailLayoutBuilder& DetailLayout) if (!Tab.IsValid()) Tab = HostTabManager->InvokeTab(FName("EmbeddedEffectCueSequenceID")); //Tab->SetContent(Sequencer->GetSequencerWidget()); - StaticCastSharedRef(Tab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); + StaticCastSharedRef(Tab->GetContent())->SetActorSequence(EffectCue->StaticClass()->GetDefaultObject()->Sequence, EffectCue); } } } \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.cpp similarity index 53% rename from Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp rename to Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.cpp index 326f96c..8df946c 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_GAEffectCueBlueprint.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.cpp @@ -1,25 +1,25 @@ // Copyright 1998-2014 Epic Games, Inc. All Rights Reserved. -#include "../AbilityFrameworkEditor.h" -#include "AssetTypeActions_GAEffectCueBlueprint.h" +#include "AbilityFrameworkEditor.h" +#include "AssetTypeActions_AFCueStaticBlueprint.h" #include "Misc/MessageDialog.h" #include "Kismet2/BlueprintEditorUtils.h" #include "GAEffectCueEditor.h" -#include "GAEffectCueBlueprint.h" -#include "Effects/GAEffectCue.h" -#include "GAEffectCueBlueprintFactory.h" +#include "AFCueActorBlueprint.h" +#include "Effects/AFCueActor.h" +#include "AFCueActorBlueprintFactory.h" #define LOCTEXT_NAMESPACE "AssetTypeActions" -FText FAssetTypeActions_GAEffectCueBlueprint::GetName() const +FText FAssetTypeActions_AFCueActorBlueprint::GetName() const { - return FText::FromString("Effect Cue"); + return FText::FromString("Cue Actor"); } -UClass* FAssetTypeActions_GAEffectCueBlueprint::GetSupportedClass() const +UClass* FAssetTypeActions_AFCueActorBlueprint::GetSupportedClass() const { - return UGAEffectCueBlueprint::StaticClass(); + return UAFCueActorBlueprint::StaticClass(); } -void FAssetTypeActions_GAEffectCueBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) +void FAssetTypeActions_AFCueActorBlueprint::OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor) { EToolkitMode::Type Mode = EditWithinLevelEditor.IsValid() ? EToolkitMode::WorldCentric : EToolkitMode::Standalone; @@ -42,15 +42,15 @@ void FAssetTypeActions_GAEffectCueBlueprint::OpenAssetEditor(const TArray(); - EffectCueBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); + UAFCueActorBlueprintFactory* EffectCueBlueprintFactory = NewObject(); + EffectCueBlueprintFactory->ParentClass = TSubclassOf(*InBlueprint->GeneratedClass); return EffectCueBlueprintFactory; } diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.h new file mode 100644 index 0000000..d4d1445 --- /dev/null +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/AssetTypeActions_AFCueActorBlueprint.h @@ -0,0 +1,27 @@ +#pragma once +#include "CoreMinimal.h" +#include "Toolkits/IToolkitHost.h" +#include "AssetTypeCategories.h" + +#include "Developer/AssetTools/Public/AssetTypeActions/AssetTypeActions_Blueprint.h" + +class UFactory; + +class FAssetTypeActions_AFCueActorBlueprint : public FAssetTypeActions_Blueprint +{ +public: + // IAssetTypeActions Implementation + virtual FText GetName() const override; + virtual FColor GetTypeColor() const override { return FColor(0, 96, 128); } + virtual UClass* GetSupportedClass() const override; + virtual void OpenAssetEditor(const TArray& InObjects, TSharedPtr EditWithinLevelEditor = TSharedPtr()) override; + virtual uint32 GetCategories() override { return EAssetTypeCategories::Gameplay; } + // End IAssetTypeActions Implementation + + // FAssetTypeActions_Blueprint interface + virtual UFactory* GetFactoryForBlueprintType(UBlueprint* InBlueprint) const override; + +private: + /** Returns true if the blueprint is data only */ + bool ShouldUseDataOnlyEditor(const UBlueprint* Blueprint) const; +}; \ No newline at end of file diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp index 4c50866..18496a2 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.cpp @@ -1,6 +1,6 @@ // Copyright 1998-2017 Epic Games, Inc. All Rights Reserved. #include "../AbilityFrameworkEditor.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #include "GAEffectCueEditor.h" #include "Effects/GAEffectCueSequence.h" #include "EditorReimportHandler.h" @@ -14,8 +14,8 @@ #include "Toolkits/ToolkitManager.h" #include "Toolkits/GlobalEditorCommonCommands.h" -#include "GAEffectCueBlueprint.h" -#include "GAEffectCueBlueprintFactory.h" +#include "AFCueActorBlueprint.h" +#include "AFCueActorBlueprintFactory.h" #include "GAEffectCueGraphSchema.h" #include "Kismet2/BlueprintEditorUtils.h" #include "SDockTab.h" @@ -112,7 +112,7 @@ void FGAEffectCueEditor::InitEffectCueEditor(const EToolkitMode::Type Mode, cons { InitBlueprintEditor(Mode, InitToolkitHost, InBlueprints, bShouldOpenInDefaultsMode); UBlueprint* BP = InBlueprints[0]; - EditedCue = BP->GeneratedClass->GetDefaultObject(); + EditedCue = BP->GeneratedClass->GetDefaultObject(); CueClass = BP->GeneratedClass; for (auto Blueprint : InBlueprints) @@ -193,7 +193,7 @@ UBlueprint* FGAEffectCueEditor::GetBlueprintObj() const const TArray& EditingObjs = GetEditingObjects(); for (int32 i = 0; i < EditingObjs.Num(); ++i) { - if (EditingObjs[i]->IsA()) + if (EditingObjs[i]->IsA()) { return (UBlueprint*)EditingObjs[i]; } diff --git a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h index 9094f6b..1babf1d 100644 --- a/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h +++ b/Plugins/AbilityFramework/Source/AbilityFrameworkEditor/Public/EffectCueEditor/GAEffectCueEditor.h @@ -24,8 +24,8 @@ class FGAEffectCueEditor : public FBlueprintEditor TArray GetAnimationEventContexts() const; FDelegateHandle BlueprintEditorTabSpawnerHandle, BlueprintEditorLayoutExtensionHandle; - class AGAEffectCue* EditedCue; - TSubclassOf CueClass; + class AAFCueActor* EditedCue; + TSubclassOf CueClass; TWeakObjectPtr EditedSequence; void ChangeViewedAnimation(UGAEffectCueSequence& InAnimationToView); void OnMovieSceneDataChanged(); diff --git a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp index 6db016c..395d992 100644 --- a/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp +++ b/Source/ActionRPGGame/Private/AI/ARAICharacter.cpp @@ -63,7 +63,7 @@ float AARAICharacter::GetAttributeValue(FGAAttribute AttributeIn) const } void AARAICharacter::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty, const FAFContextHandle& InContex) + struct FGAEffectProperty& InProperty, const FGAEffectContext& InContex) { Abilities->ModifyAttribute(ModIn, HandleIn, InProperty, InContex); } diff --git a/Source/ActionRPGGame/Private/ARCharacter.cpp b/Source/ActionRPGGame/Private/ARCharacter.cpp index e2fb0fa..855e75b 100644 --- a/Source/ActionRPGGame/Private/ARCharacter.cpp +++ b/Source/ActionRPGGame/Private/ARCharacter.cpp @@ -16,6 +16,7 @@ #include "Weapons/ARWeaponInventoryComponent.h" #include "ARCharacterMovementComponent.h" #include "ARPlayerController.h" +#include "ARAbilityBase.h" ////////////////////////////////////////////////////////////////////////// // AARCharacter @@ -185,6 +186,41 @@ void AARCharacter::BeginPlay() { Super::BeginPlay(); + if (!TestAbility01.IsNull()) + { + TestAbility01Handle = FAFAbilitySpecHandle::GenerateHandle(); + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARCharacter::OnAbility01Ready); + Abilities->AddOnAbilityReadyDelegate(TestAbility01Handle, del1); + + Abilities->NativeAddAbility(TestAbility01, TestAbility01Handle); + } + + if (!TestAbility02.IsNull()) + { + TestAbility02Handle = FAFAbilitySpecHandle::GenerateHandle(); + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARCharacter::OnAbility02Ready); + Abilities->AddOnAbilityReadyDelegate(TestAbility02Handle, del1); + + Abilities->NativeAddAbility(TestAbility02, TestAbility02Handle); + } + + if (!TestAbility03.IsNull()) + { + TestAbility03Handle = FAFAbilitySpecHandle::GenerateHandle(); + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARCharacter::OnAbility03Ready); + Abilities->AddOnAbilityReadyDelegate(TestAbility03Handle, del1); + + Abilities->NativeAddAbility(TestAbility03, TestAbility03Handle); + } + + if (!TestAbility04.IsNull()) + { + TestAbility04Handle = FAFAbilitySpecHandle::GenerateHandle(); + FAFOnAbilityReady del1 = FAFOnAbilityReady::CreateUObject(this, &AARCharacter::OnAbility04Ready); + Abilities->AddOnAbilityReadyDelegate(TestAbility04Handle, del1); + + Abilities->NativeAddAbility(TestAbility04, TestAbility04Handle); + } //LegsCloth->SetMasterPoseComponent(GetMesh()); WeaponInventory->SetIsReplicated(true); @@ -195,6 +231,40 @@ void AARCharacter::Tick(float DeltaSeconds) { Super::Tick(DeltaSeconds); } + +void AARCharacter::OnAbility01Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) +{ + TestAbility01Handle = ServerHandle; + + TArray InputIds; + InputIds.Add(static_cast(AbilityInput::Ability01)); + Abilities->BindAbilityToInputIDs(ServerHandle, InputIds); +} +void AARCharacter::OnAbility02Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) +{ + TestAbility02Handle = ServerHandle; + + TArray InputIds; + InputIds.Add(static_cast(AbilityInput::Ability02)); + Abilities->BindAbilityToInputIDs(ServerHandle, InputIds); +} +void AARCharacter::OnAbility03Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) +{ + TestAbility03Handle = ServerHandle; + + TArray InputIds; + InputIds.Add(static_cast(AbilityInput::Ability03)); + Abilities->BindAbilityToInputIDs(ServerHandle, InputIds); +} +void AARCharacter::OnAbility04Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle) +{ + TestAbility04Handle = ServerHandle; + + TArray InputIds; + InputIds.Add(static_cast(AbilityInput::Ability04)); + Abilities->BindAbilityToInputIDs(ServerHandle, InputIds); +} + ////////////////////////////////////////////////////////////////////////// // Input @@ -281,7 +351,7 @@ float AARCharacter::GetAttributeValue(FGAAttribute AttributeIn) const } void AARCharacter::ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) + struct FGAEffectProperty& InProperty, const FGAEffectContext& InContext) { Abilities->ModifyAttribute(ModIn, HandleIn, InProperty, InContext); } diff --git a/Source/ActionRPGGame/Private/ARGameInstance.cpp b/Source/ActionRPGGame/Private/ARGameInstance.cpp index 83f4946..b91fe34 100644 --- a/Source/ActionRPGGame/Private/ARGameInstance.cpp +++ b/Source/ActionRPGGame/Private/ARGameInstance.cpp @@ -10,7 +10,7 @@ #include "AssetRegistryModule.h" #include "Engine/AssetManager.h" #include "Abilities/GAAbilityBase.h" -#include "Effects/GAEffectCue.h" +#include "Effects/AFCueActor.h" #if WITH_AGONES #include "IAgones.h" @@ -55,7 +55,7 @@ void UARGameInstance::Init() if (UAssetManager* Manager = UAssetManager::GetIfValid()) { Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("Ability"), ContentPaths, UGAAbilityBase::StaticClass(), true); - Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("EffectCue"), ContentPaths, AGAEffectCue::StaticClass(), true); + Manager->ScanPathsForPrimaryAssets(FPrimaryAssetType("EffectCue"), ContentPaths, AAFCueActor::StaticClass(), true); } #if WITH_AGONES diff --git a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp index 6392148..262f1b3 100644 --- a/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp +++ b/Source/ActionRPGGame/Private/Weapons/ARWeaponAbilityBase.cpp @@ -65,8 +65,7 @@ void UARWeaponAbilityBase::ApplyDamageEffect(UObject* Target, FAFFunctionModifie { for (int32 Idx = 0; Idx < DamageEffects.Num(); Idx++) { - UGABlueprintLibrary::ApplyEffectToObject(DamageEffects[Idx] - , AppliedEffectHandles[Idx] + UGABlueprintLibrary::ApplyGameEffectToObject(DamageEffects[Idx] , Target , POwner , this @@ -106,19 +105,19 @@ void UARWeaponAbilityBase::AddUpgrade(FAFPropertytHandle& PropertyHandle , class AARCharacter* Character , float UpgradeValue) { - UGABlueprintLibrary::CreateEffectSpec(SpecHandle, PropertyHandle, this, Character, Character); + //UGABlueprintLibrary::CreateEffectSpec(SpecHandle, PropertyHandle, this, Character, Character); - EffectHandle = FGAEffectHandle::GenerateHandle(); - SpecHandle.CalculateAttributeModifier(EffectHandle); - SpecHandle.OverrideAttributeModifier(UpgradeValue); + //EffectHandle = FGAEffectHandle::GenerateHandle(); + //SpecHandle.CalculateAttributeModifier(EffectHandle); + //SpecHandle.OverrideAttributeModifier(UpgradeValue); - FGAEffect Effect(SpecHandle.GetPtr(), EffectHandle); + //FGAEffect Effect(SpecHandle.GetPtr(), EffectHandle); - UpgradeContainer.ApplyEffect(EffectHandle, Effect); + //UpgradeContainer.ApplyEffect(EffectHandle, Effect); - FAFContextHandle Context = FAFContextHandle::Generate(&DefaultContext); + //FAFContextHandle Context = FAFContextHandle::Generate(&DefaultContext); - FGAEffectMod Mod = SpecHandle.GetModifier(); - ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef(), Context); + //FGAEffectMod Mod = SpecHandle.GetModifier(); + //ModifyAttribute(Mod, EffectHandle, PropertyHandle.GetRef(), Context); } \ No newline at end of file diff --git a/Source/ActionRPGGame/Public/AI/ARAICharacter.h b/Source/ActionRPGGame/Public/AI/ARAICharacter.h index aa4d8c0..bd658f0 100644 --- a/Source/ActionRPGGame/Public/AI/ARAICharacter.h +++ b/Source/ActionRPGGame/Public/AI/ARAICharacter.h @@ -59,7 +59,7 @@ class ACTIONRPGGAME_API AARAICharacter : public ACharacter, public IAFAbilityInt virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) override; + struct FGAEffectProperty& InProperty, const FGAEffectContext& InContext) override; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override; diff --git a/Source/ActionRPGGame/Public/ARCharacter.h b/Source/ActionRPGGame/Public/ARCharacter.h index f059441..9185fa3 100644 --- a/Source/ActionRPGGame/Public/ARCharacter.h +++ b/Source/ActionRPGGame/Public/ARCharacter.h @@ -122,6 +122,25 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio UPROPERTY(BlueprintReadOnly, Replicated, Category = "Player Character Camera") FARCameraTransform CameraTransform; + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Test Ability") + TSoftClassPtr TestAbility01; + UPROPERTY(Transient) + FAFAbilitySpecHandle TestAbility01Handle; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Test Ability") + TSoftClassPtr TestAbility02; + UPROPERTY(Transient) + FAFAbilitySpecHandle TestAbility02Handle; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Test Ability") + TSoftClassPtr TestAbility03; + UPROPERTY(Transient) + FAFAbilitySpecHandle TestAbility03Handle; + + UPROPERTY(EditAnywhere, BlueprintReadOnly, Category = "Test Ability") + TSoftClassPtr TestAbility04; + UPROPERTY(Transient) + FAFAbilitySpecHandle TestAbility04Handle; public: AARCharacter(const FObjectInitializer& ObjectInitializer); virtual void OnConstruction(const FTransform& Transform) override; @@ -129,6 +148,12 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio virtual void BeginPlay() override; virtual void Tick(float DeltaSeconds) override; + + void OnAbility01Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle); + void OnAbility02Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle); + void OnAbility03Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle); + void OnAbility04Ready(FAFAbilitySpec Spec, FAFAbilitySpecHandle ServerHandle, FAFAbilitySpecHandle ClientHandle); + /** Base turn rate, in deg/sec. Other scaling may affect final turn rate. */ UPROPERTY(VisibleAnywhere, BlueprintReadOnly, Category=Camera) float BaseTurnRate; @@ -179,7 +204,7 @@ class AARCharacter : public ACharacter, public IAFAbilityInterface, public IOrio virtual float GetAttributeValue(FGAAttribute AttributeIn) const override; virtual void ModifyAttribute(FGAEffectMod& ModIn, const FGAEffectHandle& HandleIn, - struct FGAEffectProperty& InProperty, const FAFContextHandle& InContext) override; + struct FGAEffectProperty& InProperty, const FGAEffectContext& InContext) override; virtual FAFAttributeBase* GetAttribute(FGAAttribute AttributeIn) override; virtual void RemoveBonus(FGAAttribute AttributeIn, const FGAEffectHandle& HandleIn, EGAAttributeMod InMod) override;