merging latest dev with small conflict resolution taking theirs
Signed-off-by: Gene Walters <genewalt@amazon.com>
This commit is contained in:
@@ -6,12 +6,7 @@
|
||||
#
|
||||
#
|
||||
|
||||
################################################################################
|
||||
# Atom Renderer: Automated Tests
|
||||
# Runs EditorPythonBindings (hydra) scripts inside the Editor to verify test results for the Atom renderer.
|
||||
################################################################################
|
||||
|
||||
if(PAL_TRAIT_BUILD_HOST_TOOLS AND PAL_TRAIT_BUILD_TESTS_SUPPORTED AND AutomatedTesting IN_LIST LY_PROJECTS)
|
||||
if(PAL_TRAIT_BUILD_HOST_TOOLS AND PAL_TRAIT_BUILD_TESTS_SUPPORTED)
|
||||
ly_add_pytest(
|
||||
NAME AutomatedTesting::Atom_TestSuite_Main
|
||||
TEST_SUITE main
|
||||
|
||||
@@ -25,6 +25,7 @@ TEST_DIRECTORY = os.path.join(os.path.dirname(__file__), "tests")
|
||||
class TestAtomEditorComponentsMain(object):
|
||||
"""Holds tests for Atom components."""
|
||||
|
||||
@pytest.mark.xfail(reason="This test is being marked xfail as it failed during an unrelated development run. See LYN-7530 for more details.")
|
||||
def test_AtomEditorComponents_AddedToEntity(self, request, editor, level, workspace, project, launcher_platform):
|
||||
"""
|
||||
Please review the hydra script run by this test for more specific test info.
|
||||
|
||||
@@ -14,33 +14,50 @@ from ly_test_tools.o3de.editor_test import EditorSharedTest, EditorTestSuite
|
||||
@pytest.mark.parametrize("launcher_platform", ['windows_editor'])
|
||||
class TestAutomation(EditorTestSuite):
|
||||
|
||||
@pytest.mark.test_case_id("C32078118")
|
||||
class AtomEditorComponents_DecalAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_DecalAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078119")
|
||||
class AtomEditorComponents_DepthOfFieldAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_DepthOfFieldAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078120")
|
||||
class AtomEditorComponents_DirectionalLightAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_DirectionalLightAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078121")
|
||||
class AtomEditorComponents_ExposureControlAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_ExposureControlAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078115")
|
||||
class AtomEditorComponents_GlobalSkylightIBLAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_GlobalSkylightIBLAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078125")
|
||||
class AtomEditorComponents_PhysicalSkyAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_PhysicalSkyAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078131")
|
||||
class AtomEditorComponents_PostFXRadiusWeightModifierAdded(EditorSharedTest):
|
||||
from Atom.tests import (
|
||||
hydra_AtomEditorComponents_PostFXRadiusWeightModifierAdded as test_module)
|
||||
|
||||
@pytest.mark.test_case_id("C32078117")
|
||||
class AtomEditorComponents_LightAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_LightAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C36525660")
|
||||
class AtomEditorComponents_DisplayMapperAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_DisplayMapperAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078128")
|
||||
class AtomEditorComponents_ReflectionProbeAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_ReflectionProbeAdded as test_module
|
||||
|
||||
@pytest.mark.test_case_id("C32078124")
|
||||
class AtomEditorComponents_MeshAdded(EditorSharedTest):
|
||||
from Atom.tests import hydra_AtomEditorComponents_MeshAdded as test_module
|
||||
|
||||
class ShaderAssetBuilder_RecompilesShaderAsChainOfDependenciesChanges(EditorSharedTest):
|
||||
from Atom.tests import hydra_ShaderAssetBuilder_RecompilesShaderAsChainOfDependenciesChanges as test_module
|
||||
|
||||
@@ -0,0 +1,171 @@
|
||||
"""
|
||||
Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
|
||||
SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
"""
|
||||
|
||||
class Tests:
|
||||
creation_undo = (
|
||||
"UNDO Entity creation success",
|
||||
"UNDO Entity creation failed")
|
||||
creation_redo = (
|
||||
"REDO Entity creation success",
|
||||
"REDO Entity creation failed")
|
||||
mesh_entity_creation = (
|
||||
"Mesh Entity successfully created",
|
||||
"Mesh Entity failed to be created")
|
||||
mesh_component_added = (
|
||||
"Entity has a Mesh component",
|
||||
"Entity failed to find Mesh component")
|
||||
mesh_asset_specified = (
|
||||
"Mesh asset set",
|
||||
"Mesh asset not set")
|
||||
enter_game_mode = (
|
||||
"Entered game mode",
|
||||
"Failed to enter game mode")
|
||||
exit_game_mode = (
|
||||
"Exited game mode",
|
||||
"Couldn't exit game mode")
|
||||
is_visible = (
|
||||
"Entity is visible",
|
||||
"Entity was not visible")
|
||||
is_hidden = (
|
||||
"Entity is hidden",
|
||||
"Entity was not hidden")
|
||||
entity_deleted = (
|
||||
"Entity deleted",
|
||||
"Entity was not deleted")
|
||||
deletion_undo = (
|
||||
"UNDO deletion success",
|
||||
"UNDO deletion failed")
|
||||
deletion_redo = (
|
||||
"REDO deletion success",
|
||||
"REDO deletion failed")
|
||||
|
||||
|
||||
def AtomEditorComponents_Mesh_AddedToEntity():
|
||||
"""
|
||||
Summary:
|
||||
Tests the Mesh component can be added to an entity and has the expected functionality.
|
||||
|
||||
Test setup:
|
||||
- Wait for Editor idle loop.
|
||||
- Open the "Base" level.
|
||||
|
||||
Expected Behavior:
|
||||
The component can be added, used in game mode, hidden/shown, deleted, and has accurate required components.
|
||||
Creation and deletion undo/redo should also work.
|
||||
|
||||
Test Steps:
|
||||
1) Create a Mesh entity with no components.
|
||||
2) Add a Mesh component to Mesh entity.
|
||||
3) UNDO the entity creation and component addition.
|
||||
4) REDO the entity creation and component addition.
|
||||
5) Specify the Mesh component asset
|
||||
6) Enter/Exit game mode.
|
||||
7) Test IsHidden.
|
||||
8) Test IsVisible.
|
||||
9) Delete Mesh entity.
|
||||
10) UNDO deletion.
|
||||
11) REDO deletion.
|
||||
12) Look for errors.
|
||||
|
||||
:return: None
|
||||
"""
|
||||
|
||||
import os
|
||||
|
||||
import azlmbr.legacy.general as general
|
||||
|
||||
from editor_python_test_tools.asset_utils import Asset
|
||||
from editor_python_test_tools.editor_entity_utils import EditorEntity
|
||||
from editor_python_test_tools.utils import Report, Tracer, TestHelper as helper
|
||||
|
||||
with Tracer() as error_tracer:
|
||||
# Test setup begins.
|
||||
# Setup: Wait for Editor idle loop before executing Python hydra scripts then open "Base" level.
|
||||
helper.init_idle()
|
||||
helper.open_level("", "Base")
|
||||
|
||||
# Test steps begin.
|
||||
# 1. Create a Mesh entity with no components.
|
||||
mesh_name = "Mesh"
|
||||
mesh_entity = EditorEntity.create_editor_entity(mesh_name)
|
||||
Report.critical_result(Tests.mesh_entity_creation, mesh_entity.exists())
|
||||
|
||||
# 2. Add a Mesh component to Mesh entity.
|
||||
mesh_component = mesh_entity.add_component(mesh_name)
|
||||
Report.critical_result(
|
||||
Tests.mesh_component_added,
|
||||
mesh_entity.has_component(mesh_name))
|
||||
|
||||
# 3. UNDO the entity creation and component addition.
|
||||
# -> UNDO component addition.
|
||||
general.undo()
|
||||
# -> UNDO naming entity.
|
||||
general.undo()
|
||||
# -> UNDO selecting entity.
|
||||
general.undo()
|
||||
# -> UNDO entity creation.
|
||||
general.undo()
|
||||
general.idle_wait_frames(1)
|
||||
Report.result(Tests.creation_undo, not mesh_entity.exists())
|
||||
|
||||
# 4. REDO the entity creation and component addition.
|
||||
# -> REDO entity creation.
|
||||
general.redo()
|
||||
# -> REDO selecting entity.
|
||||
general.redo()
|
||||
# -> REDO naming entity.
|
||||
general.redo()
|
||||
# -> REDO component addition.
|
||||
general.redo()
|
||||
general.idle_wait_frames(1)
|
||||
Report.result(Tests.creation_redo, mesh_entity.exists())
|
||||
|
||||
# 5. Set Mesh component asset property
|
||||
mesh_property_asset = 'Controller|Configuration|Mesh Asset'
|
||||
model_path = os.path.join('Objects', 'shaderball', 'shaderball_default_1m.azmodel')
|
||||
model = Asset.find_asset_by_path(model_path)
|
||||
mesh_component.set_component_property_value(mesh_property_asset, model.id)
|
||||
Report.result(Tests.mesh_asset_specified,
|
||||
mesh_component.get_component_property_value(mesh_property_asset) == model.id)
|
||||
|
||||
# 6. Enter/Exit game mode.
|
||||
helper.enter_game_mode(Tests.enter_game_mode)
|
||||
general.idle_wait_frames(1)
|
||||
helper.exit_game_mode(Tests.exit_game_mode)
|
||||
|
||||
# 7. Test IsHidden.
|
||||
mesh_entity.set_visibility_state(False)
|
||||
Report.result(Tests.is_hidden, mesh_entity.is_hidden() is True)
|
||||
|
||||
# 8. Test IsVisible.
|
||||
mesh_entity.set_visibility_state(True)
|
||||
general.idle_wait_frames(1)
|
||||
Report.result(Tests.is_visible, mesh_entity.is_visible() is True)
|
||||
|
||||
# 9. Delete Mesh entity.
|
||||
mesh_entity.delete()
|
||||
Report.result(Tests.entity_deleted, not mesh_entity.exists())
|
||||
|
||||
# 10. UNDO deletion.
|
||||
general.undo()
|
||||
Report.result(Tests.deletion_undo, mesh_entity.exists())
|
||||
|
||||
# 11. REDO deletion.
|
||||
general.redo()
|
||||
Report.result(Tests.deletion_redo, not mesh_entity.exists())
|
||||
|
||||
# 12. Look for errors or asserts.
|
||||
helper.wait_for_condition(lambda: error_tracer.has_errors or error_tracer.has_asserts, 1.0)
|
||||
for error_info in error_tracer.errors:
|
||||
Report.info(f"Error: {error_info.filename} {error_info.function} | {error_info.message}")
|
||||
for assert_info in error_tracer.asserts:
|
||||
Report.info(f"Assert: {assert_info.filename} {assert_info.function} | {assert_info.message}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
from editor_python_test_tools.utils import Report
|
||||
Report.start_test(AtomEditorComponents_Mesh_AddedToEntity)
|
||||
+194
@@ -0,0 +1,194 @@
|
||||
"""
|
||||
Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
|
||||
SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
"""
|
||||
|
||||
class Tests:
|
||||
creation_undo = (
|
||||
"UNDO Entity creation success",
|
||||
"UNDO Entity creation failed")
|
||||
creation_redo = (
|
||||
"REDO Entity creation success",
|
||||
"REDO Entity creation failed")
|
||||
reflection_probe_creation = (
|
||||
"Reflection Probe Entity successfully created",
|
||||
"Reflection Probe Entity failed to be created")
|
||||
reflection_probe_component = (
|
||||
"Entity has a Reflection Probe component",
|
||||
"Entity failed to find Reflection Probe component")
|
||||
reflection_probe_disabled = (
|
||||
"Reflection Probe component disabled",
|
||||
"Reflection Probe component was not disabled.")
|
||||
reflection_map_generated = (
|
||||
"Reflection Probe cubemap generated",
|
||||
"Reflection Probe cubemap not generated")
|
||||
box_shape_component = (
|
||||
"Entity has a Box Shape component",
|
||||
"Entity did not have a Box Shape component")
|
||||
reflection_probe_enabled = (
|
||||
"Reflection Probe component enabled",
|
||||
"Reflection Probe component was not enabled.")
|
||||
enter_game_mode = (
|
||||
"Entered game mode",
|
||||
"Failed to enter game mode")
|
||||
exit_game_mode = (
|
||||
"Exited game mode",
|
||||
"Couldn't exit game mode")
|
||||
is_visible = (
|
||||
"Entity is visible",
|
||||
"Entity was not visible")
|
||||
is_hidden = (
|
||||
"Entity is hidden",
|
||||
"Entity was not hidden")
|
||||
entity_deleted = (
|
||||
"Entity deleted",
|
||||
"Entity was not deleted")
|
||||
deletion_undo = (
|
||||
"UNDO deletion success",
|
||||
"UNDO deletion failed")
|
||||
deletion_redo = (
|
||||
"REDO deletion success",
|
||||
"REDO deletion failed")
|
||||
|
||||
|
||||
def AtomEditorComponents_ReflectionProbe_AddedToEntity():
|
||||
"""
|
||||
Summary:
|
||||
Tests the Reflection Probe component can be added to an entity and has the expected functionality.
|
||||
|
||||
Test setup:
|
||||
- Wait for Editor idle loop.
|
||||
- Open the "Base" level.
|
||||
|
||||
Expected Behavior:
|
||||
The component can be added, used in game mode, hidden/shown, deleted, and has accurate required components.
|
||||
Creation and deletion undo/redo should also work.
|
||||
|
||||
Test Steps:
|
||||
1) Create a Reflection Probe entity with no components.
|
||||
2) Add a Reflection Probe component to Reflection Probe entity.
|
||||
3) UNDO the entity creation and component addition.
|
||||
4) REDO the entity creation and component addition.
|
||||
5) Verify Reflection Probe component not enabled.
|
||||
6) Add Shape component since it is required by the Reflection Probe component.
|
||||
7) Verify Reflection Probe component is enabled.
|
||||
8) Enter/Exit game mode.
|
||||
9) Test IsHidden.
|
||||
10) Test IsVisible.
|
||||
11) Verify cubemap generation
|
||||
12) Delete Reflection Probe entity.
|
||||
13) UNDO deletion.
|
||||
14) REDO deletion.
|
||||
15) Look for errors.
|
||||
|
||||
:return: None
|
||||
"""
|
||||
|
||||
import azlmbr.legacy.general as general
|
||||
import azlmbr.math as math
|
||||
import azlmbr.render as render
|
||||
|
||||
from editor_python_test_tools.editor_entity_utils import EditorEntity
|
||||
from editor_python_test_tools.utils import Report, Tracer, TestHelper as helper
|
||||
|
||||
with Tracer() as error_tracer:
|
||||
# Test setup begins.
|
||||
# Setup: Wait for Editor idle loop before executing Python hydra scripts then open "Base" level.
|
||||
helper.init_idle()
|
||||
helper.open_level("", "Base")
|
||||
|
||||
# Test steps begin.
|
||||
# 1. Create a Reflection Probe entity with no components.
|
||||
reflection_probe_name = "Reflection Probe"
|
||||
reflection_probe_entity = EditorEntity.create_editor_entity_at(
|
||||
math.Vector3(512.0, 512.0, 34.0), reflection_probe_name)
|
||||
Report.critical_result(Tests.reflection_probe_creation, reflection_probe_entity.exists())
|
||||
|
||||
# 2. Add a Reflection Probe component to Reflection Probe entity.
|
||||
reflection_probe_component = reflection_probe_entity.add_component(reflection_probe_name)
|
||||
Report.critical_result(
|
||||
Tests.reflection_probe_component,
|
||||
reflection_probe_entity.has_component(reflection_probe_name))
|
||||
|
||||
# 3. UNDO the entity creation and component addition.
|
||||
# -> UNDO component addition.
|
||||
general.undo()
|
||||
# -> UNDO naming entity.
|
||||
general.undo()
|
||||
# -> UNDO selecting entity.
|
||||
general.undo()
|
||||
# -> UNDO entity creation.
|
||||
general.undo()
|
||||
general.idle_wait_frames(1)
|
||||
Report.result(Tests.creation_undo, not reflection_probe_entity.exists())
|
||||
|
||||
# 4. REDO the entity creation and component addition.
|
||||
# -> REDO entity creation.
|
||||
general.redo()
|
||||
# -> REDO selecting entity.
|
||||
general.redo()
|
||||
# -> REDO naming entity.
|
||||
general.redo()
|
||||
# -> REDO component addition.
|
||||
general.redo()
|
||||
general.idle_wait_frames(1)
|
||||
Report.result(Tests.creation_redo, reflection_probe_entity.exists())
|
||||
|
||||
# 5. Verify Reflection Probe component not enabled.
|
||||
Report.result(Tests.reflection_probe_disabled, not reflection_probe_component.is_enabled())
|
||||
|
||||
# 6. Add Box Shape component since it is required by the Reflection Probe component.
|
||||
box_shape = "Box Shape"
|
||||
reflection_probe_entity.add_component(box_shape)
|
||||
Report.result(Tests.box_shape_component, reflection_probe_entity.has_component(box_shape))
|
||||
|
||||
# 7. Verify Reflection Probe component is enabled.
|
||||
Report.result(Tests.reflection_probe_enabled, reflection_probe_component.is_enabled())
|
||||
|
||||
# 8. Enter/Exit game mode.
|
||||
helper.enter_game_mode(Tests.enter_game_mode)
|
||||
general.idle_wait_frames(1)
|
||||
helper.exit_game_mode(Tests.exit_game_mode)
|
||||
|
||||
# 9. Test IsHidden.
|
||||
reflection_probe_entity.set_visibility_state(False)
|
||||
Report.result(Tests.is_hidden, reflection_probe_entity.is_hidden() is True)
|
||||
|
||||
# 10. Test IsVisible.
|
||||
reflection_probe_entity.set_visibility_state(True)
|
||||
general.idle_wait_frames(1)
|
||||
Report.result(Tests.is_visible, reflection_probe_entity.is_visible() is True)
|
||||
|
||||
# 11. Verify cubemap generation
|
||||
render.EditorReflectionProbeBus(azlmbr.bus.Event, "BakeReflectionProbe", reflection_probe_entity.id)
|
||||
Report.result(
|
||||
Tests.reflection_map_generated,
|
||||
helper.wait_for_condition(
|
||||
lambda: reflection_probe_component.get_component_property_value("Cubemap|Baked Cubemap Path") != "",
|
||||
20.0))
|
||||
|
||||
# 12. Delete Reflection Probe entity.
|
||||
reflection_probe_entity.delete()
|
||||
Report.result(Tests.entity_deleted, not reflection_probe_entity.exists())
|
||||
|
||||
# 13. UNDO deletion.
|
||||
general.undo()
|
||||
Report.result(Tests.deletion_undo, reflection_probe_entity.exists())
|
||||
|
||||
# 14. REDO deletion.
|
||||
general.redo()
|
||||
Report.result(Tests.deletion_redo, not reflection_probe_entity.exists())
|
||||
|
||||
# 15. Look for errors or asserts.
|
||||
helper.wait_for_condition(lambda: error_tracer.has_errors or error_tracer.has_asserts, 1.0)
|
||||
for error_info in error_tracer.errors:
|
||||
Report.info(f"Error: {error_info.filename} {error_info.function} | {error_info.message}")
|
||||
for assert_info in error_tracer.asserts:
|
||||
Report.info(f"Assert: {assert_info.filename} {assert_info.function} | {assert_info.message}")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
from editor_python_test_tools.utils import Report
|
||||
Report.start_test(AtomEditorComponents_ReflectionProbe_AddedToEntity)
|
||||
@@ -487,8 +487,6 @@ void LevelEditorMenuHandler::PopulateEditMenu(ActionManager::MenuWrapper& editMe
|
||||
editMenu.AddAction(AzToolsFramework::EditPivot);
|
||||
editMenu.AddAction(AzToolsFramework::EditReset);
|
||||
editMenu.AddAction(AzToolsFramework::EditResetManipulator);
|
||||
editMenu.AddAction(AzToolsFramework::EditResetLocal);
|
||||
editMenu.AddAction(AzToolsFramework::EditResetWorld);
|
||||
|
||||
// Hide Selection
|
||||
editMenu.AddAction(AzToolsFramework::HideSelection);
|
||||
|
||||
@@ -2124,6 +2124,8 @@ bool CCryEditApp::FixDanglingSharedMemory(const QString& sharedMemName) const
|
||||
|
||||
int CCryEditApp::ExitInstance(int exitCode)
|
||||
{
|
||||
AZ_TracePrintf("Exit", "Called ExitInstance() with exit code: 0x%x", exitCode);
|
||||
|
||||
if (m_pEditor)
|
||||
{
|
||||
m_pEditor->OnBeginShutdownSequence();
|
||||
|
||||
@@ -96,7 +96,7 @@ namespace SandboxEditor
|
||||
cameras.AddCamera(m_firstPersonTranslateCamera);
|
||||
cameras.AddCamera(m_firstPersonScrollCamera);
|
||||
cameras.AddCamera(m_firstPersonFocusCamera);
|
||||
cameras.AddCamera(m_pivotCamera);
|
||||
cameras.AddCamera(m_orbitCamera);
|
||||
});
|
||||
|
||||
return controller;
|
||||
@@ -135,7 +135,7 @@ namespace SandboxEditor
|
||||
m_firstPersonRotateCamera->SetActivationEndedFn(showCursor);
|
||||
|
||||
m_firstPersonPanCamera = AZStd::make_shared<AzFramework::PanCameraInput>(
|
||||
SandboxEditor::CameraFreePanChannelId(), AzFramework::LookPan, AzFramework::TranslatePivot);
|
||||
SandboxEditor::CameraFreePanChannelId(), AzFramework::LookPan, AzFramework::TranslatePivotLook);
|
||||
|
||||
m_firstPersonPanCamera->m_panSpeedFn = []
|
||||
{
|
||||
@@ -155,7 +155,7 @@ namespace SandboxEditor
|
||||
const auto translateCameraInputChannelIds = BuildTranslateCameraInputChannelIds();
|
||||
|
||||
m_firstPersonTranslateCamera = AZStd::make_shared<AzFramework::TranslateCameraInput>(
|
||||
translateCameraInputChannelIds, AzFramework::LookTranslation, AzFramework::TranslatePivot);
|
||||
translateCameraInputChannelIds, AzFramework::LookTranslation, AzFramework::TranslatePivotLook);
|
||||
|
||||
m_firstPersonTranslateCamera->m_translateSpeedFn = []
|
||||
{
|
||||
@@ -167,7 +167,7 @@ namespace SandboxEditor
|
||||
return SandboxEditor::CameraBoostMultiplier();
|
||||
};
|
||||
|
||||
m_firstPersonScrollCamera = AZStd::make_shared<AzFramework::ScrollTranslationCameraInput>();
|
||||
m_firstPersonScrollCamera = AZStd::make_shared<AzFramework::LookScrollTranslationCameraInput>();
|
||||
|
||||
m_firstPersonScrollCamera->m_scrollSpeedFn = []
|
||||
{
|
||||
@@ -196,82 +196,82 @@ namespace SandboxEditor
|
||||
|
||||
m_firstPersonFocusCamera->SetPivotFn(pivotFn);
|
||||
|
||||
m_pivotCamera = AZStd::make_shared<AzFramework::PivotCameraInput>(SandboxEditor::CameraPivotChannelId());
|
||||
m_orbitCamera = AZStd::make_shared<AzFramework::OrbitCameraInput>(SandboxEditor::CameraOrbitChannelId());
|
||||
|
||||
m_pivotCamera->SetPivotFn(
|
||||
m_orbitCamera->SetPivotFn(
|
||||
[pivotFn]([[maybe_unused]] const AZ::Vector3& position, [[maybe_unused]] const AZ::Vector3& direction)
|
||||
{
|
||||
return pivotFn();
|
||||
});
|
||||
|
||||
m_pivotRotateCamera = AZStd::make_shared<AzFramework::RotateCameraInput>(SandboxEditor::CameraPivotLookChannelId());
|
||||
m_orbitRotateCamera = AZStd::make_shared<AzFramework::RotateCameraInput>(SandboxEditor::CameraOrbitLookChannelId());
|
||||
|
||||
m_pivotRotateCamera->m_rotateSpeedFn = []
|
||||
m_orbitRotateCamera->m_rotateSpeedFn = []
|
||||
{
|
||||
return SandboxEditor::CameraRotateSpeed();
|
||||
};
|
||||
|
||||
m_pivotRotateCamera->m_invertYawFn = []
|
||||
m_orbitRotateCamera->m_invertYawFn = []
|
||||
{
|
||||
return SandboxEditor::CameraPivotYawRotationInverted();
|
||||
return SandboxEditor::CameraOrbitYawRotationInverted();
|
||||
};
|
||||
|
||||
m_pivotTranslateCamera = AZStd::make_shared<AzFramework::TranslateCameraInput>(
|
||||
translateCameraInputChannelIds, AzFramework::LookTranslation, AzFramework::TranslateOffset);
|
||||
m_orbitTranslateCamera = AZStd::make_shared<AzFramework::TranslateCameraInput>(
|
||||
translateCameraInputChannelIds, AzFramework::LookTranslation, AzFramework::TranslateOffsetOrbit);
|
||||
|
||||
m_pivotTranslateCamera->m_translateSpeedFn = []
|
||||
m_orbitTranslateCamera->m_translateSpeedFn = []
|
||||
{
|
||||
return SandboxEditor::CameraTranslateSpeed();
|
||||
};
|
||||
|
||||
m_pivotTranslateCamera->m_boostMultiplierFn = []
|
||||
m_orbitTranslateCamera->m_boostMultiplierFn = []
|
||||
{
|
||||
return SandboxEditor::CameraBoostMultiplier();
|
||||
};
|
||||
|
||||
m_pivotDollyScrollCamera = AZStd::make_shared<AzFramework::PivotDollyScrollCameraInput>();
|
||||
m_orbitDollyScrollCamera = AZStd::make_shared<AzFramework::OrbitDollyScrollCameraInput>();
|
||||
|
||||
m_pivotDollyScrollCamera->m_scrollSpeedFn = []
|
||||
m_orbitDollyScrollCamera->m_scrollSpeedFn = []
|
||||
{
|
||||
return SandboxEditor::CameraScrollSpeed();
|
||||
};
|
||||
|
||||
m_pivotDollyMoveCamera = AZStd::make_shared<AzFramework::PivotDollyMotionCameraInput>(SandboxEditor::CameraPivotDollyChannelId());
|
||||
m_orbitDollyMoveCamera = AZStd::make_shared<AzFramework::OrbitDollyMotionCameraInput>(SandboxEditor::CameraOrbitDollyChannelId());
|
||||
|
||||
m_pivotDollyMoveCamera->m_motionSpeedFn = []
|
||||
m_orbitDollyMoveCamera->m_motionSpeedFn = []
|
||||
{
|
||||
return SandboxEditor::CameraDollyMotionSpeed();
|
||||
};
|
||||
|
||||
m_pivotPanCamera = AZStd::make_shared<AzFramework::PanCameraInput>(
|
||||
SandboxEditor::CameraPivotPanChannelId(), AzFramework::LookPan, AzFramework::TranslateOffset);
|
||||
m_orbitPanCamera = AZStd::make_shared<AzFramework::PanCameraInput>(
|
||||
SandboxEditor::CameraOrbitPanChannelId(), AzFramework::LookPan, AzFramework::TranslateOffsetOrbit);
|
||||
|
||||
m_pivotPanCamera->m_panSpeedFn = []
|
||||
m_orbitPanCamera->m_panSpeedFn = []
|
||||
{
|
||||
return SandboxEditor::CameraPanSpeed();
|
||||
};
|
||||
|
||||
m_pivotPanCamera->m_invertPanXFn = []
|
||||
m_orbitPanCamera->m_invertPanXFn = []
|
||||
{
|
||||
return SandboxEditor::CameraPanInvertedX();
|
||||
};
|
||||
|
||||
m_pivotPanCamera->m_invertPanYFn = []
|
||||
m_orbitPanCamera->m_invertPanYFn = []
|
||||
{
|
||||
return SandboxEditor::CameraPanInvertedY();
|
||||
};
|
||||
|
||||
m_pivotFocusCamera =
|
||||
AZStd::make_shared<AzFramework::FocusCameraInput>(SandboxEditor::CameraFocusChannelId(), AzFramework::FocusPivot);
|
||||
m_orbitFocusCamera =
|
||||
AZStd::make_shared<AzFramework::FocusCameraInput>(SandboxEditor::CameraFocusChannelId(), AzFramework::FocusOrbit);
|
||||
|
||||
m_pivotFocusCamera->SetPivotFn(pivotFn);
|
||||
m_orbitFocusCamera->SetPivotFn(pivotFn);
|
||||
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(m_pivotRotateCamera);
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(m_pivotTranslateCamera);
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(m_pivotDollyScrollCamera);
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(m_pivotDollyMoveCamera);
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(m_pivotPanCamera);
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(m_pivotFocusCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(m_orbitRotateCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(m_orbitTranslateCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(m_orbitDollyScrollCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(m_orbitDollyMoveCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(m_orbitPanCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(m_orbitFocusCamera);
|
||||
}
|
||||
|
||||
void EditorModularViewportCameraComposer::OnEditorModularViewportCameraComposerSettingsChanged()
|
||||
@@ -282,12 +282,12 @@ namespace SandboxEditor
|
||||
m_firstPersonRotateCamera->SetRotateInputChannelId(SandboxEditor::CameraFreeLookChannelId());
|
||||
m_firstPersonFocusCamera->SetFocusInputChannelId(SandboxEditor::CameraFocusChannelId());
|
||||
|
||||
m_pivotCamera->SetPivotInputChannelId(SandboxEditor::CameraPivotChannelId());
|
||||
m_pivotTranslateCamera->SetTranslateCameraInputChannelIds(translateCameraInputChannelIds);
|
||||
m_pivotPanCamera->SetPanInputChannelId(SandboxEditor::CameraPivotPanChannelId());
|
||||
m_pivotRotateCamera->SetRotateInputChannelId(SandboxEditor::CameraPivotLookChannelId());
|
||||
m_pivotDollyMoveCamera->SetDollyInputChannelId(SandboxEditor::CameraPivotDollyChannelId());
|
||||
m_pivotFocusCamera->SetFocusInputChannelId(SandboxEditor::CameraFocusChannelId());
|
||||
m_orbitCamera->SetOrbitInputChannelId(SandboxEditor::CameraOrbitChannelId());
|
||||
m_orbitTranslateCamera->SetTranslateCameraInputChannelIds(translateCameraInputChannelIds);
|
||||
m_orbitPanCamera->SetPanInputChannelId(SandboxEditor::CameraOrbitPanChannelId());
|
||||
m_orbitRotateCamera->SetRotateInputChannelId(SandboxEditor::CameraOrbitLookChannelId());
|
||||
m_orbitDollyMoveCamera->SetDollyInputChannelId(SandboxEditor::CameraOrbitDollyChannelId());
|
||||
m_orbitFocusCamera->SetFocusInputChannelId(SandboxEditor::CameraFocusChannelId());
|
||||
}
|
||||
|
||||
void EditorModularViewportCameraComposer::OnViewportViewEntityChanged(const AZ::EntityId& viewEntityId)
|
||||
|
||||
@@ -41,15 +41,15 @@ namespace SandboxEditor
|
||||
AZStd::shared_ptr<AzFramework::RotateCameraInput> m_firstPersonRotateCamera;
|
||||
AZStd::shared_ptr<AzFramework::PanCameraInput> m_firstPersonPanCamera;
|
||||
AZStd::shared_ptr<AzFramework::TranslateCameraInput> m_firstPersonTranslateCamera;
|
||||
AZStd::shared_ptr<AzFramework::ScrollTranslationCameraInput> m_firstPersonScrollCamera;
|
||||
AZStd::shared_ptr<AzFramework::LookScrollTranslationCameraInput> m_firstPersonScrollCamera;
|
||||
AZStd::shared_ptr<AzFramework::FocusCameraInput> m_firstPersonFocusCamera;
|
||||
AZStd::shared_ptr<AzFramework::PivotCameraInput> m_pivotCamera;
|
||||
AZStd::shared_ptr<AzFramework::RotateCameraInput> m_pivotRotateCamera;
|
||||
AZStd::shared_ptr<AzFramework::TranslateCameraInput> m_pivotTranslateCamera;
|
||||
AZStd::shared_ptr<AzFramework::PivotDollyScrollCameraInput> m_pivotDollyScrollCamera;
|
||||
AZStd::shared_ptr<AzFramework::PivotDollyMotionCameraInput> m_pivotDollyMoveCamera;
|
||||
AZStd::shared_ptr<AzFramework::PanCameraInput> m_pivotPanCamera;
|
||||
AZStd::shared_ptr<AzFramework::FocusCameraInput> m_pivotFocusCamera;
|
||||
AZStd::shared_ptr<AzFramework::OrbitCameraInput> m_orbitCamera;
|
||||
AZStd::shared_ptr<AzFramework::RotateCameraInput> m_orbitRotateCamera;
|
||||
AZStd::shared_ptr<AzFramework::TranslateCameraInput> m_orbitTranslateCamera;
|
||||
AZStd::shared_ptr<AzFramework::OrbitDollyScrollCameraInput> m_orbitDollyScrollCamera;
|
||||
AZStd::shared_ptr<AzFramework::OrbitDollyMotionCameraInput> m_orbitDollyMoveCamera;
|
||||
AZStd::shared_ptr<AzFramework::PanCameraInput> m_orbitPanCamera;
|
||||
AZStd::shared_ptr<AzFramework::FocusCameraInput> m_orbitFocusCamera;
|
||||
|
||||
AzFramework::ViewportId m_viewportId;
|
||||
};
|
||||
|
||||
@@ -73,7 +73,7 @@ void CEditorPreferencesPage_ViewportCamera::Reflect(AZ::SerializeContext& serial
|
||||
->Field("TranslateSmoothing", &CameraMovementSettings::m_translateSmoothing)
|
||||
->Field("TranslateSmoothness", &CameraMovementSettings::m_translateSmoothness)
|
||||
->Field("CaptureCursorLook", &CameraMovementSettings::m_captureCursorLook)
|
||||
->Field("PivotYawRotationInverted", &CameraMovementSettings::m_pivotYawRotationInverted)
|
||||
->Field("OrbitYawRotationInverted", &CameraMovementSettings::m_orbitYawRotationInverted)
|
||||
->Field("PanInvertedX", &CameraMovementSettings::m_panInvertedX)
|
||||
->Field("PanInvertedY", &CameraMovementSettings::m_panInvertedY);
|
||||
|
||||
@@ -86,12 +86,12 @@ void CEditorPreferencesPage_ViewportCamera::Reflect(AZ::SerializeContext& serial
|
||||
->Field("TranslateUp", &CameraInputSettings::m_translateUpChannelId)
|
||||
->Field("TranslateDown", &CameraInputSettings::m_translateDownChannelId)
|
||||
->Field("Boost", &CameraInputSettings::m_boostChannelId)
|
||||
->Field("Pivot", &CameraInputSettings::m_pivotChannelId)
|
||||
->Field("Orbit", &CameraInputSettings::m_orbitChannelId)
|
||||
->Field("FreeLook", &CameraInputSettings::m_freeLookChannelId)
|
||||
->Field("FreePan", &CameraInputSettings::m_freePanChannelId)
|
||||
->Field("PivotLook", &CameraInputSettings::m_pivotLookChannelId)
|
||||
->Field("PivotDolly", &CameraInputSettings::m_pivotDollyChannelId)
|
||||
->Field("PivotPan", &CameraInputSettings::m_pivotPanChannelId)
|
||||
->Field("OrbitLook", &CameraInputSettings::m_orbitLookChannelId)
|
||||
->Field("OrbitDolly", &CameraInputSettings::m_orbitDollyChannelId)
|
||||
->Field("OrbitPan", &CameraInputSettings::m_orbitPanChannelId)
|
||||
->Field("Focus", &CameraInputSettings::m_focusChannelId);
|
||||
|
||||
serialize.Class<CEditorPreferencesPage_ViewportCamera>()
|
||||
@@ -144,8 +144,8 @@ void CEditorPreferencesPage_ViewportCamera::Reflect(AZ::SerializeContext& serial
|
||||
->Attribute(AZ::Edit::Attributes::Min, minValue)
|
||||
->Attribute(AZ::Edit::Attributes::Visibility, &CameraMovementSettings::TranslateSmoothingVisibility)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::CheckBox, &CameraMovementSettings::m_pivotYawRotationInverted, "Camera Pivot Yaw Inverted",
|
||||
"Inverted yaw rotation while pivoting")
|
||||
AZ::Edit::UIHandlers::CheckBox, &CameraMovementSettings::m_orbitYawRotationInverted, "Camera Orbit Yaw Inverted",
|
||||
"Inverted yaw rotation while orbiting")
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::CheckBox, &CameraMovementSettings::m_panInvertedX, "Invert Pan X",
|
||||
"Invert direction of pan in local X axis")
|
||||
@@ -186,8 +186,8 @@ void CEditorPreferencesPage_ViewportCamera::Reflect(AZ::SerializeContext& serial
|
||||
"Key/button to move the camera more quickly")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_pivotChannelId, "Pivot",
|
||||
"Key/button to begin the camera pivot behavior")
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_orbitChannelId, "Orbit",
|
||||
"Key/button to begin the camera orbit behavior")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_freeLookChannelId, "Free Look",
|
||||
@@ -197,19 +197,19 @@ void CEditorPreferencesPage_ViewportCamera::Reflect(AZ::SerializeContext& serial
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_freePanChannelId, "Free Pan", "Key/button to begin camera free pan")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_pivotLookChannelId, "Pivot Look",
|
||||
"Key/button to begin camera pivot look")
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_orbitLookChannelId, "Orbit Look",
|
||||
"Key/button to begin camera orbit look")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_pivotDollyChannelId, "Pivot Dolly",
|
||||
"Key/button to begin camera pivot dolly")
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_orbitDollyChannelId, "Orbit Dolly",
|
||||
"Key/button to begin camera orbit dolly")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_pivotPanChannelId, "Pivot Pan",
|
||||
"Key/button to begin camera pivot pan")
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_orbitPanChannelId, "Orbit Pan",
|
||||
"Key/button to begin camera orbit pan")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames)
|
||||
->DataElement(
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_focusChannelId, "Focus", "Key/button to focus camera pivot")
|
||||
AZ::Edit::UIHandlers::ComboBox, &CameraInputSettings::m_focusChannelId, "Focus", "Key/button to focus camera orbit")
|
||||
->Attribute(AZ::Edit::Attributes::StringList, &GetEditorInputNames);
|
||||
|
||||
editContext->Class<CEditorPreferencesPage_ViewportCamera>("Viewport Preferences", "Viewport Preferences")
|
||||
@@ -268,7 +268,7 @@ void CEditorPreferencesPage_ViewportCamera::OnApply()
|
||||
SandboxEditor::SetCameraTranslateSmoothness(m_cameraMovementSettings.m_translateSmoothness);
|
||||
SandboxEditor::SetCameraTranslateSmoothingEnabled(m_cameraMovementSettings.m_translateSmoothing);
|
||||
SandboxEditor::SetCameraCaptureCursorForLook(m_cameraMovementSettings.m_captureCursorLook);
|
||||
SandboxEditor::SetCameraPivotYawRotationInverted(m_cameraMovementSettings.m_pivotYawRotationInverted);
|
||||
SandboxEditor::SetCameraOrbitYawRotationInverted(m_cameraMovementSettings.m_orbitYawRotationInverted);
|
||||
SandboxEditor::SetCameraPanInvertedX(m_cameraMovementSettings.m_panInvertedX);
|
||||
SandboxEditor::SetCameraPanInvertedY(m_cameraMovementSettings.m_panInvertedY);
|
||||
|
||||
@@ -279,12 +279,12 @@ void CEditorPreferencesPage_ViewportCamera::OnApply()
|
||||
SandboxEditor::SetCameraTranslateUpChannelId(m_cameraInputSettings.m_translateUpChannelId);
|
||||
SandboxEditor::SetCameraTranslateDownChannelId(m_cameraInputSettings.m_translateDownChannelId);
|
||||
SandboxEditor::SetCameraTranslateBoostChannelId(m_cameraInputSettings.m_boostChannelId);
|
||||
SandboxEditor::SetCameraPivotChannelId(m_cameraInputSettings.m_pivotChannelId);
|
||||
SandboxEditor::SetCameraOrbitChannelId(m_cameraInputSettings.m_orbitChannelId);
|
||||
SandboxEditor::SetCameraFreeLookChannelId(m_cameraInputSettings.m_freeLookChannelId);
|
||||
SandboxEditor::SetCameraFreePanChannelId(m_cameraInputSettings.m_freePanChannelId);
|
||||
SandboxEditor::SetCameraPivotLookChannelId(m_cameraInputSettings.m_pivotLookChannelId);
|
||||
SandboxEditor::SetCameraPivotDollyChannelId(m_cameraInputSettings.m_pivotDollyChannelId);
|
||||
SandboxEditor::SetCameraPivotPanChannelId(m_cameraInputSettings.m_pivotPanChannelId);
|
||||
SandboxEditor::SetCameraOrbitLookChannelId(m_cameraInputSettings.m_orbitLookChannelId);
|
||||
SandboxEditor::SetCameraOrbitDollyChannelId(m_cameraInputSettings.m_orbitDollyChannelId);
|
||||
SandboxEditor::SetCameraOrbitPanChannelId(m_cameraInputSettings.m_orbitPanChannelId);
|
||||
SandboxEditor::SetCameraFocusChannelId(m_cameraInputSettings.m_focusChannelId);
|
||||
|
||||
SandboxEditor::EditorModularViewportCameraComposerNotificationBus::Broadcast(
|
||||
@@ -304,7 +304,7 @@ void CEditorPreferencesPage_ViewportCamera::InitializeSettings()
|
||||
m_cameraMovementSettings.m_translateSmoothness = SandboxEditor::CameraTranslateSmoothness();
|
||||
m_cameraMovementSettings.m_translateSmoothing = SandboxEditor::CameraTranslateSmoothingEnabled();
|
||||
m_cameraMovementSettings.m_captureCursorLook = SandboxEditor::CameraCaptureCursorForLook();
|
||||
m_cameraMovementSettings.m_pivotYawRotationInverted = SandboxEditor::CameraPivotYawRotationInverted();
|
||||
m_cameraMovementSettings.m_orbitYawRotationInverted = SandboxEditor::CameraOrbitYawRotationInverted();
|
||||
m_cameraMovementSettings.m_panInvertedX = SandboxEditor::CameraPanInvertedX();
|
||||
m_cameraMovementSettings.m_panInvertedY = SandboxEditor::CameraPanInvertedY();
|
||||
|
||||
@@ -315,11 +315,11 @@ void CEditorPreferencesPage_ViewportCamera::InitializeSettings()
|
||||
m_cameraInputSettings.m_translateUpChannelId = SandboxEditor::CameraTranslateUpChannelId().GetName();
|
||||
m_cameraInputSettings.m_translateDownChannelId = SandboxEditor::CameraTranslateDownChannelId().GetName();
|
||||
m_cameraInputSettings.m_boostChannelId = SandboxEditor::CameraTranslateBoostChannelId().GetName();
|
||||
m_cameraInputSettings.m_pivotChannelId = SandboxEditor::CameraPivotChannelId().GetName();
|
||||
m_cameraInputSettings.m_orbitChannelId = SandboxEditor::CameraOrbitChannelId().GetName();
|
||||
m_cameraInputSettings.m_freeLookChannelId = SandboxEditor::CameraFreeLookChannelId().GetName();
|
||||
m_cameraInputSettings.m_freePanChannelId = SandboxEditor::CameraFreePanChannelId().GetName();
|
||||
m_cameraInputSettings.m_pivotLookChannelId = SandboxEditor::CameraPivotLookChannelId().GetName();
|
||||
m_cameraInputSettings.m_pivotDollyChannelId = SandboxEditor::CameraPivotDollyChannelId().GetName();
|
||||
m_cameraInputSettings.m_pivotPanChannelId = SandboxEditor::CameraPivotPanChannelId().GetName();
|
||||
m_cameraInputSettings.m_orbitLookChannelId = SandboxEditor::CameraOrbitLookChannelId().GetName();
|
||||
m_cameraInputSettings.m_orbitDollyChannelId = SandboxEditor::CameraOrbitDollyChannelId().GetName();
|
||||
m_cameraInputSettings.m_orbitPanChannelId = SandboxEditor::CameraOrbitPanChannelId().GetName();
|
||||
m_cameraInputSettings.m_focusChannelId = SandboxEditor::CameraFocusChannelId().GetName();
|
||||
}
|
||||
|
||||
@@ -54,7 +54,7 @@ private:
|
||||
float m_translateSmoothness;
|
||||
bool m_translateSmoothing;
|
||||
bool m_captureCursorLook;
|
||||
bool m_pivotYawRotationInverted;
|
||||
bool m_orbitYawRotationInverted;
|
||||
bool m_panInvertedX;
|
||||
bool m_panInvertedY;
|
||||
|
||||
@@ -80,12 +80,12 @@ private:
|
||||
AZStd::string m_translateUpChannelId;
|
||||
AZStd::string m_translateDownChannelId;
|
||||
AZStd::string m_boostChannelId;
|
||||
AZStd::string m_pivotChannelId;
|
||||
AZStd::string m_orbitChannelId;
|
||||
AZStd::string m_freeLookChannelId;
|
||||
AZStd::string m_freePanChannelId;
|
||||
AZStd::string m_pivotLookChannelId;
|
||||
AZStd::string m_pivotDollyChannelId;
|
||||
AZStd::string m_pivotPanChannelId;
|
||||
AZStd::string m_orbitLookChannelId;
|
||||
AZStd::string m_orbitDollyChannelId;
|
||||
AZStd::string m_orbitPanChannelId;
|
||||
AZStd::string m_focusChannelId;
|
||||
};
|
||||
|
||||
|
||||
@@ -28,7 +28,7 @@ namespace SandboxEditor
|
||||
constexpr AZStd::string_view CameraRotateSpeedSetting = "/Amazon/Preferences/Editor/Camera/RotateSpeed";
|
||||
constexpr AZStd::string_view CameraScrollSpeedSetting = "/Amazon/Preferences/Editor/Camera/DollyScrollSpeed";
|
||||
constexpr AZStd::string_view CameraDollyMotionSpeedSetting = "/Amazon/Preferences/Editor/Camera/DollyMotionSpeed";
|
||||
constexpr AZStd::string_view CameraPivotYawRotationInvertedSetting = "/Amazon/Preferences/Editor/Camera/YawRotationInverted";
|
||||
constexpr AZStd::string_view CameraOrbitYawRotationInvertedSetting = "/Amazon/Preferences/Editor/Camera/YawRotationInverted";
|
||||
constexpr AZStd::string_view CameraPanInvertedXSetting = "/Amazon/Preferences/Editor/Camera/PanInvertedX";
|
||||
constexpr AZStd::string_view CameraPanInvertedYSetting = "/Amazon/Preferences/Editor/Camera/PanInvertedY";
|
||||
constexpr AZStd::string_view CameraPanSpeedSetting = "/Amazon/Preferences/Editor/Camera/PanSpeed";
|
||||
@@ -44,12 +44,12 @@ namespace SandboxEditor
|
||||
constexpr AZStd::string_view CameraTranslateUpIdSetting = "/Amazon/Preferences/Editor/Camera/CameraTranslateUpId";
|
||||
constexpr AZStd::string_view CameraTranslateDownIdSetting = "/Amazon/Preferences/Editor/Camera/CameraTranslateUpDownId";
|
||||
constexpr AZStd::string_view CameraTranslateBoostIdSetting = "/Amazon/Preferences/Editor/Camera/TranslateBoostId";
|
||||
constexpr AZStd::string_view CameraPivotIdSetting = "/Amazon/Preferences/Editor/Camera/PivotId";
|
||||
constexpr AZStd::string_view CameraOrbitIdSetting = "/Amazon/Preferences/Editor/Camera/OrbitId";
|
||||
constexpr AZStd::string_view CameraFreeLookIdSetting = "/Amazon/Preferences/Editor/Camera/FreeLookId";
|
||||
constexpr AZStd::string_view CameraFreePanIdSetting = "/Amazon/Preferences/Editor/Camera/FreePanId";
|
||||
constexpr AZStd::string_view CameraPivotLookIdSetting = "/Amazon/Preferences/Editor/Camera/PivotLookId";
|
||||
constexpr AZStd::string_view CameraPivotDollyIdSetting = "/Amazon/Preferences/Editor/Camera/PivotDollyId";
|
||||
constexpr AZStd::string_view CameraPivotPanIdSetting = "/Amazon/Preferences/Editor/Camera/PivotPanId";
|
||||
constexpr AZStd::string_view CameraOrbitLookIdSetting = "/Amazon/Preferences/Editor/Camera/OrbitLookId";
|
||||
constexpr AZStd::string_view CameraOrbitDollyIdSetting = "/Amazon/Preferences/Editor/Camera/OrbitDollyId";
|
||||
constexpr AZStd::string_view CameraOrbitPanIdSetting = "/Amazon/Preferences/Editor/Camera/OrbitPanId";
|
||||
constexpr AZStd::string_view CameraFocusIdSetting = "/Amazon/Preferences/Editor/Camera/FocusId";
|
||||
|
||||
template<typename T>
|
||||
@@ -240,14 +240,14 @@ namespace SandboxEditor
|
||||
SetRegistry(CameraDollyMotionSpeedSetting, speed);
|
||||
}
|
||||
|
||||
bool CameraPivotYawRotationInverted()
|
||||
bool CameraOrbitYawRotationInverted()
|
||||
{
|
||||
return GetRegistry(CameraPivotYawRotationInvertedSetting, false);
|
||||
return GetRegistry(CameraOrbitYawRotationInvertedSetting, false);
|
||||
}
|
||||
|
||||
void SetCameraPivotYawRotationInverted(const bool inverted)
|
||||
void SetCameraOrbitYawRotationInverted(const bool inverted)
|
||||
{
|
||||
SetRegistry(CameraPivotYawRotationInvertedSetting, inverted);
|
||||
SetRegistry(CameraOrbitYawRotationInvertedSetting, inverted);
|
||||
}
|
||||
|
||||
bool CameraPanInvertedX()
|
||||
@@ -404,14 +404,14 @@ namespace SandboxEditor
|
||||
SetRegistry(CameraTranslateBoostIdSetting, cameraTranslateBoostId);
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId CameraPivotChannelId()
|
||||
AzFramework::InputChannelId CameraOrbitChannelId()
|
||||
{
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraPivotIdSetting, AZStd::string("keyboard_key_modifier_alt_l")).c_str());
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraOrbitIdSetting, AZStd::string("keyboard_key_modifier_alt_l")).c_str());
|
||||
}
|
||||
|
||||
void SetCameraPivotChannelId(AZStd::string_view cameraPivotId)
|
||||
void SetCameraOrbitChannelId(AZStd::string_view cameraOrbitId)
|
||||
{
|
||||
SetRegistry(CameraPivotIdSetting, cameraPivotId);
|
||||
SetRegistry(CameraOrbitIdSetting, cameraOrbitId);
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId CameraFreeLookChannelId()
|
||||
@@ -434,34 +434,34 @@ namespace SandboxEditor
|
||||
SetRegistry(CameraFreePanIdSetting, cameraFreePanId);
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId CameraPivotLookChannelId()
|
||||
AzFramework::InputChannelId CameraOrbitLookChannelId()
|
||||
{
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraPivotLookIdSetting, AZStd::string("mouse_button_left")).c_str());
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraOrbitLookIdSetting, AZStd::string("mouse_button_left")).c_str());
|
||||
}
|
||||
|
||||
void SetCameraPivotLookChannelId(AZStd::string_view cameraPivotLookId)
|
||||
void SetCameraOrbitLookChannelId(AZStd::string_view cameraOrbitLookId)
|
||||
{
|
||||
SetRegistry(CameraPivotLookIdSetting, cameraPivotLookId);
|
||||
SetRegistry(CameraOrbitLookIdSetting, cameraOrbitLookId);
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId CameraPivotDollyChannelId()
|
||||
AzFramework::InputChannelId CameraOrbitDollyChannelId()
|
||||
{
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraPivotDollyIdSetting, AZStd::string("mouse_button_right")).c_str());
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraOrbitDollyIdSetting, AZStd::string("mouse_button_right")).c_str());
|
||||
}
|
||||
|
||||
void SetCameraPivotDollyChannelId(AZStd::string_view cameraPivotDollyId)
|
||||
void SetCameraOrbitDollyChannelId(AZStd::string_view cameraOrbitDollyId)
|
||||
{
|
||||
SetRegistry(CameraPivotDollyIdSetting, cameraPivotDollyId);
|
||||
SetRegistry(CameraOrbitDollyIdSetting, cameraOrbitDollyId);
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId CameraPivotPanChannelId()
|
||||
AzFramework::InputChannelId CameraOrbitPanChannelId()
|
||||
{
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraPivotPanIdSetting, AZStd::string("mouse_button_middle")).c_str());
|
||||
return AzFramework::InputChannelId(GetRegistry(CameraOrbitPanIdSetting, AZStd::string("mouse_button_middle")).c_str());
|
||||
}
|
||||
|
||||
void SetCameraPivotPanChannelId(AZStd::string_view cameraPivotPanId)
|
||||
void SetCameraOrbitPanChannelId(AZStd::string_view cameraOrbitPanId)
|
||||
{
|
||||
SetRegistry(CameraPivotPanIdSetting, cameraPivotPanId);
|
||||
SetRegistry(CameraOrbitPanIdSetting, cameraOrbitPanId);
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId CameraFocusChannelId()
|
||||
|
||||
@@ -71,8 +71,8 @@ namespace SandboxEditor
|
||||
SANDBOX_API float CameraDollyMotionSpeed();
|
||||
SANDBOX_API void SetCameraDollyMotionSpeed(float speed);
|
||||
|
||||
SANDBOX_API bool CameraPivotYawRotationInverted();
|
||||
SANDBOX_API void SetCameraPivotYawRotationInverted(bool inverted);
|
||||
SANDBOX_API bool CameraOrbitYawRotationInverted();
|
||||
SANDBOX_API void SetCameraOrbitYawRotationInverted(bool inverted);
|
||||
|
||||
SANDBOX_API bool CameraPanInvertedX();
|
||||
SANDBOX_API void SetCameraPanInvertedX(bool inverted);
|
||||
@@ -119,8 +119,8 @@ namespace SandboxEditor
|
||||
SANDBOX_API AzFramework::InputChannelId CameraTranslateBoostChannelId();
|
||||
SANDBOX_API void SetCameraTranslateBoostChannelId(AZStd::string_view cameraTranslateBoostId);
|
||||
|
||||
SANDBOX_API AzFramework::InputChannelId CameraPivotChannelId();
|
||||
SANDBOX_API void SetCameraPivotChannelId(AZStd::string_view cameraPivotId);
|
||||
SANDBOX_API AzFramework::InputChannelId CameraOrbitChannelId();
|
||||
SANDBOX_API void SetCameraOrbitChannelId(AZStd::string_view cameraOrbitId);
|
||||
|
||||
SANDBOX_API AzFramework::InputChannelId CameraFreeLookChannelId();
|
||||
SANDBOX_API void SetCameraFreeLookChannelId(AZStd::string_view cameraFreeLookId);
|
||||
@@ -128,14 +128,14 @@ namespace SandboxEditor
|
||||
SANDBOX_API AzFramework::InputChannelId CameraFreePanChannelId();
|
||||
SANDBOX_API void SetCameraFreePanChannelId(AZStd::string_view cameraFreePanId);
|
||||
|
||||
SANDBOX_API AzFramework::InputChannelId CameraPivotLookChannelId();
|
||||
SANDBOX_API void SetCameraPivotLookChannelId(AZStd::string_view cameraPivotLookId);
|
||||
SANDBOX_API AzFramework::InputChannelId CameraOrbitLookChannelId();
|
||||
SANDBOX_API void SetCameraOrbitLookChannelId(AZStd::string_view cameraOrbitLookId);
|
||||
|
||||
SANDBOX_API AzFramework::InputChannelId CameraPivotDollyChannelId();
|
||||
SANDBOX_API void SetCameraPivotDollyChannelId(AZStd::string_view cameraPivotDollyId);
|
||||
SANDBOX_API AzFramework::InputChannelId CameraOrbitDollyChannelId();
|
||||
SANDBOX_API void SetCameraOrbitDollyChannelId(AZStd::string_view cameraOrbitDollyId);
|
||||
|
||||
SANDBOX_API AzFramework::InputChannelId CameraPivotPanChannelId();
|
||||
SANDBOX_API void SetCameraPivotPanChannelId(AZStd::string_view cameraPivotPanId);
|
||||
SANDBOX_API AzFramework::InputChannelId CameraOrbitPanChannelId();
|
||||
SANDBOX_API void SetCameraOrbitPanChannelId(AZStd::string_view cameraOrbitPanId);
|
||||
|
||||
SANDBOX_API AzFramework::InputChannelId CameraFocusChannelId();
|
||||
SANDBOX_API void SetCameraFocusChannelId(AZStd::string_view cameraFocusId);
|
||||
|
||||
@@ -173,6 +173,7 @@ namespace AZ
|
||||
|
||||
if (assetTracker)
|
||||
{
|
||||
assetTracker->FixUpAsset(*instance);
|
||||
assetTracker->AddAsset(*instance);
|
||||
}
|
||||
|
||||
@@ -185,7 +186,20 @@ namespace AZ
|
||||
return context.Report(result, message);
|
||||
}
|
||||
|
||||
void SerializedAssetTracker::AddAsset(Asset<AssetData>& asset)
|
||||
void SerializedAssetTracker::SetAssetFixUp(AssetFixUp assetFixUpCallback)
|
||||
{
|
||||
m_assetFixUpCallback = AZStd::move(assetFixUpCallback);
|
||||
}
|
||||
|
||||
void SerializedAssetTracker::FixUpAsset(Asset<AssetData>& asset)
|
||||
{
|
||||
if (m_assetFixUpCallback)
|
||||
{
|
||||
m_assetFixUpCallback(asset);
|
||||
}
|
||||
}
|
||||
|
||||
void SerializedAssetTracker::AddAsset(Asset<AssetData> asset)
|
||||
{
|
||||
m_serializedAssets.emplace_back(asset);
|
||||
}
|
||||
@@ -199,5 +213,6 @@ namespace AZ
|
||||
{
|
||||
return m_serializedAssets;
|
||||
}
|
||||
|
||||
} // namespace Data
|
||||
} // namespace AZ
|
||||
|
||||
@@ -39,13 +39,18 @@ namespace AZ
|
||||
{
|
||||
public:
|
||||
AZ_RTTI(SerializedAssetTracker, "{1E067091-8C0A-44B1-A455-6E97663F6963}");
|
||||
using AssetFixUp = AZStd::function<void(Asset<AssetData>& asset)>;
|
||||
|
||||
void AddAsset(Asset<AssetData>& asset);
|
||||
void SetAssetFixUp(AssetFixUp assetFixUpCallback);
|
||||
void FixUpAsset(Asset<AssetData>& asset);
|
||||
|
||||
void AddAsset(Asset<AssetData> asset);
|
||||
AZStd::vector<Asset<AssetData>>& GetTrackedAssets();
|
||||
const AZStd::vector<Asset<AssetData>>& GetTrackedAssets() const;
|
||||
|
||||
private:
|
||||
AZStd::vector<Asset<AssetData>> m_serializedAssets;
|
||||
AssetFixUp m_assetFixUpCallback;
|
||||
};
|
||||
} // namespace Data
|
||||
} // namespace AZ
|
||||
|
||||
@@ -224,6 +224,8 @@ namespace AZ
|
||||
|
||||
void Debug::Trace::Terminate(int exitCode)
|
||||
{
|
||||
AZ_TracePrintf("Exit", "Called Terminate() with exit code: 0x%x", exitCode);
|
||||
AZ::Debug::Trace::PrintCallstack("Exit");
|
||||
Platform::Terminate(exitCode);
|
||||
}
|
||||
|
||||
|
||||
@@ -160,8 +160,8 @@ namespace AZ
|
||||
/**
|
||||
* Locking primitive that is used when executing events in the event queue.
|
||||
*/
|
||||
using EventQueueMutexType = typename AZStd::Utils::if_c<AZStd::is_same<typename Traits::EventQueueMutexType, NullMutex>::value, // if EventQueueMutexType==NullMutex use MutexType otherwise EventQueueMutexType
|
||||
MutexType, typename Traits::EventQueueMutexType>::type;
|
||||
using EventQueueMutexType = AZStd::conditional_t<AZStd::is_same<typename Traits::EventQueueMutexType, NullMutex>::value, // if EventQueueMutexType==NullMutex use MutexType otherwise EventQueueMutexType
|
||||
MutexType, typename Traits::EventQueueMutexType>;
|
||||
|
||||
/**
|
||||
* Pointer to an address on the bus.
|
||||
@@ -180,14 +180,22 @@ namespace AZ
|
||||
* `<BusName>::ExecuteQueuedEvents()`.
|
||||
* By default, the event queue is disabled.
|
||||
*/
|
||||
static const bool EnableEventQueue = Traits::EnableEventQueue;
|
||||
static const bool EventQueueingActiveByDefault = Traits::EventQueueingActiveByDefault;
|
||||
static const bool EnableQueuedReferences = Traits::EnableQueuedReferences;
|
||||
static constexpr bool EnableEventQueue = Traits::EnableEventQueue;
|
||||
static constexpr bool EventQueueingActiveByDefault = Traits::EventQueueingActiveByDefault;
|
||||
static constexpr bool EnableQueuedReferences = Traits::EnableQueuedReferences;
|
||||
|
||||
/**
|
||||
* True if the EBus supports more than one address. Otherwise, false.
|
||||
*/
|
||||
static const bool HasId = Traits::AddressPolicy != EBusAddressPolicy::Single;
|
||||
static constexpr bool HasId = Traits::AddressPolicy != EBusAddressPolicy::Single;
|
||||
|
||||
/**
|
||||
* Template Lock Guard class that wraps around the Mutex
|
||||
* The EBus uses for Dispatching Events.
|
||||
* This is not the EBus Context Mutex if LocklessDispatch is true
|
||||
*/
|
||||
template <typename DispatchMutex>
|
||||
using DispatchLockGuard = typename Traits::template DispatchLockGuard<DispatchMutex, Traits::LocklessDispatch>;
|
||||
};
|
||||
|
||||
/**
|
||||
@@ -460,7 +468,7 @@ namespace AZ
|
||||
using BusPtr = typename Traits::BusPtr;
|
||||
|
||||
/**
|
||||
* Helper to queue an event by BusIdType only when function queueing is enabled
|
||||
* Helper to queue an event by BusIdType only when function queueing is enabled
|
||||
* @param id Address ID. Handlers that are connected to this ID will receive the event.
|
||||
* @param func Function pointer of the event to dispatch.
|
||||
* @param args Function arguments that are passed to each handler.
|
||||
@@ -581,7 +589,7 @@ namespace AZ
|
||||
, public EBusBroadcaster<Bus, Traits>
|
||||
, public EBusEventer<Bus, Traits>
|
||||
, public EBusEventEnumerator<Bus, Traits>
|
||||
, public AZStd::Utils::if_c<Traits::EnableEventQueue, EBusEventQueue<Bus, Traits>, EBusNullQueue>::type
|
||||
, public AZStd::conditional_t<Traits::EnableEventQueue, EBusEventQueue<Bus, Traits>, EBusNullQueue>
|
||||
{
|
||||
};
|
||||
|
||||
@@ -599,7 +607,7 @@ namespace AZ
|
||||
: public EventDispatcher<Bus, Traits>
|
||||
, public EBusBroadcaster<Bus, Traits>
|
||||
, public EBusBroadcastEnumerator<Bus, Traits>
|
||||
, public AZStd::Utils::if_c<Traits::EnableEventQueue, EBusBroadcastQueue<Bus, Traits>, EBusNullQueue>::type
|
||||
, public AZStd::conditional_t<Traits::EnableEventQueue, EBusBroadcastQueue<Bus, Traits>, EBusNullQueue>
|
||||
{
|
||||
};
|
||||
|
||||
|
||||
@@ -236,6 +236,17 @@ namespace AZ
|
||||
* code before or after an event.
|
||||
*/
|
||||
using EventProcessingPolicy = EBusEventProcessingPolicy;
|
||||
|
||||
/**
|
||||
* Template Lock Guard class that wraps around the Mutex
|
||||
* The EBus Context uses the LockGuard when dispatching
|
||||
* (either AZStd::scoped_lock<MutexType> or NullLockGuard<MutexType>)
|
||||
* The IsLocklessDispatch bool is there to defer evaluation of the LocklessDispatch constant
|
||||
* Otherwise the value above in EBusTraits.h is always used and not the value
|
||||
* that the derived trait class sets.
|
||||
*/
|
||||
template <typename DispatchMutex, bool IsLocklessDispatch>
|
||||
using DispatchLockGuard = AZStd::conditional_t<IsLocklessDispatch, AZ::Internal::NullLockGuard<DispatchMutex>, AZStd::scoped_lock<DispatchMutex>>;
|
||||
};
|
||||
|
||||
namespace Internal
|
||||
@@ -496,6 +507,14 @@ namespace AZ
|
||||
*/
|
||||
static const bool HasId = Traits::AddressPolicy != EBusAddressPolicy::Single;
|
||||
|
||||
/**
|
||||
* Template Lock Guard class that wraps around the Mutex
|
||||
* The EBus uses for Dispatching Events.
|
||||
* This is not EBus Context Mutex when LocklessDispatch is set
|
||||
*/
|
||||
template <typename DispatchMutex>
|
||||
using DispatchLockGuard = typename ImplTraits::template DispatchLockGuard<DispatchMutex>;
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// Check to help identify common mistakes
|
||||
/// @cond EXCLUDE_DOCS
|
||||
@@ -620,11 +639,11 @@ namespace AZ
|
||||
using ContextMutexType = AZStd::conditional_t<BusTraits::LocklessDispatch && AZStd::is_same_v<MutexType, AZ::NullMutex>, AZStd::shared_mutex, MutexType>;
|
||||
|
||||
/**
|
||||
* The scoped lock guard to use (either AZStd::scoped_lock<MutexType> or NullLockGuard<MutexType>
|
||||
* The scoped lock guard to use
|
||||
* during broadcast/event dispatch.
|
||||
* @see EBusTraits::LocklessDispatch
|
||||
*/
|
||||
using DispatchLockGuard = AZStd::conditional_t<BusTraits::LocklessDispatch, AZ::Internal::NullLockGuard<ContextMutexType>, AZStd::scoped_lock<ContextMutexType>>;
|
||||
using DispatchLockGuard = DispatchLockGuard<ContextMutexType>;
|
||||
|
||||
/**
|
||||
* The scoped lock guard to use during connection. Some specialized policies execute handler methods which
|
||||
@@ -704,6 +723,11 @@ namespace AZ
|
||||
static Context& GetOrCreateContext(bool trackCallstack=true);
|
||||
|
||||
static bool IsInDispatch(Context* context = GetContext(false));
|
||||
|
||||
/**
|
||||
* Returns whether the EBus context is in the middle of a dispatch on the current thread
|
||||
*/
|
||||
static bool IsInDispatchThisThread(Context* context = GetContext(false));
|
||||
/// @cond EXCLUDE_DOCS
|
||||
struct RouterCallstackEntry
|
||||
: public CallstackEntry
|
||||
@@ -1208,6 +1232,13 @@ AZ_POP_DISABLE_WARNING
|
||||
return context != nullptr && context->m_dispatches > 0;
|
||||
}
|
||||
|
||||
template<class Interface, class Traits>
|
||||
bool EBus<Interface, Traits>::IsInDispatchThisThread(Context* context)
|
||||
{
|
||||
return context != nullptr && context->s_callstack != nullptr
|
||||
&& context->s_callstack->m_prev != nullptr;
|
||||
}
|
||||
|
||||
//=========================================================================
|
||||
template<class Interface, class Traits>
|
||||
EBus<Interface, Traits>::RouterCallstackEntry::RouterCallstackEntry(Iterator it, const BusIdType* busId, bool isQueued, bool isReverse)
|
||||
|
||||
@@ -18,6 +18,14 @@
|
||||
#include <AzCore/std/parallel/thread.h>
|
||||
#include <AzCore/Math/MathUtils.h>
|
||||
|
||||
#include <AzCore/Console/IConsole.h>
|
||||
|
||||
#include <AzCore/Threading/ThreadUtils.h>
|
||||
|
||||
AZ_CVAR(float, cl_jobThreadsConcurrencyRatio, 0.6f, nullptr, AZ::ConsoleFunctorFlags::Null, "Legacy Job system multiplier on the number of hw threads the machine creates at initialization");
|
||||
AZ_CVAR(uint32_t, cl_jobThreadsNumReserved, 2, nullptr, AZ::ConsoleFunctorFlags::Null, "Legacy Job system number of hardware threads that are reserved for O3DE system threads");
|
||||
AZ_CVAR(uint32_t, cl_jobThreadsMinNumber, 2, nullptr, AZ::ConsoleFunctorFlags::Null, "Legacy Job system minimum number of worker threads to create after scaling the number of hw threads");
|
||||
|
||||
namespace AZ
|
||||
{
|
||||
//=========================================================================
|
||||
@@ -46,9 +54,10 @@ namespace AZ
|
||||
JobManagerThreadDesc threadDesc;
|
||||
|
||||
int numberOfWorkerThreads = m_numberOfWorkerThreads;
|
||||
if (numberOfWorkerThreads <= 0)
|
||||
if (numberOfWorkerThreads <= 0) // spawn default number of threads
|
||||
{
|
||||
numberOfWorkerThreads = AZ::GetMin(static_cast<unsigned int>(desc.m_workerThreads.capacity()), AZStd::thread::hardware_concurrency());
|
||||
uint32_t scaledHardwareThreads = Threading::CalcNumWorkerThreads(cl_jobThreadsConcurrencyRatio, cl_jobThreadsMinNumber, cl_jobThreadsNumReserved);
|
||||
numberOfWorkerThreads = AZ::GetMin(static_cast<unsigned int>(desc.m_workerThreads.capacity()), scaledHardwareThreads);
|
||||
#if (AZ_TRAIT_MAX_JOB_MANAGER_WORKER_THREADS)
|
||||
numberOfWorkerThreads = AZ::GetMin(numberOfWorkerThreads, AZ_TRAIT_MAX_JOB_MANAGER_WORKER_THREADS);
|
||||
#endif // (AZ_TRAIT_MAX_JOB_MANAGER_WORKER_THREADS)
|
||||
|
||||
@@ -36,7 +36,7 @@ namespace AZ
|
||||
*/
|
||||
int m_stackSize;
|
||||
|
||||
JobManagerThreadDesc(int cpuId = -1, int priority = -100000, int stackSize = -1)
|
||||
JobManagerThreadDesc(int cpuId = -1, int priority = 0, int stackSize = -1)
|
||||
: m_cpuId(cpuId)
|
||||
, m_priority(priority)
|
||||
, m_stackSize(stackSize)
|
||||
|
||||
@@ -308,11 +308,11 @@ namespace AZ
|
||||
|
||||
void TaskExecutor::SetInstance(TaskExecutor* executor)
|
||||
{
|
||||
if (!executor)
|
||||
if (!executor) // allow unsetting the executor
|
||||
{
|
||||
s_executor.Reset();
|
||||
}
|
||||
else if (!s_executor) // ignore any calls to set after the first (this happens in unit tests that create new system entities)
|
||||
else if (!s_executor) // ignore any extra executors after the first (this happens during unit tests)
|
||||
{
|
||||
s_executor = AZ::Environment::CreateVariable<TaskExecutor*>(s_executorName, executor);
|
||||
}
|
||||
|
||||
@@ -11,9 +11,15 @@
|
||||
#include <AzCore/Task/TaskGraphSystemComponent.h>
|
||||
#include <AzCore/Serialization/SerializeContext.h>
|
||||
#include <AzCore/Serialization/EditContext.h>
|
||||
#include <AzCore/Math/MathUtils.h>
|
||||
#include <AzCore/Threading/ThreadUtils.h>
|
||||
|
||||
// Create a cvar as a central location for experimentation with switching from the Job system to TaskGraph system.
|
||||
AZ_CVAR(bool, cl_activateTaskGraph, false, nullptr, AZ::ConsoleFunctorFlags::Null, "Flag clients of TaskGraph to switch between jobs/taskgraph (Note does not disable task graph system)");
|
||||
AZ_CVAR(float, cl_taskGraphThreadsConcurrencyRatio, 1.0f, nullptr, AZ::ConsoleFunctorFlags::Null, "TaskGraph calculate the number of worker threads to spawn by scaling the number of hw threads, value is clamped between 0.0f and 1.0f");
|
||||
AZ_CVAR(uint32_t, cl_taskGraphThreadsNumReserved, 2, nullptr, AZ::ConsoleFunctorFlags::Null, "TaskGraph number of hardware threads that are reserved for O3DE system threads. Value is clamped between 0 and the number of logical cores in the system");
|
||||
AZ_CVAR(uint32_t, cl_taskGraphThreadsMinNumber, 2, nullptr, AZ::ConsoleFunctorFlags::Null, "TaskGraph minimum number of worker threads to create after scaling the number of hw threads");
|
||||
|
||||
static constexpr uint32_t TaskExecutorServiceCrc = AZ_CRC_CE("TaskExecutorService");
|
||||
|
||||
namespace AZ
|
||||
@@ -24,8 +30,8 @@ namespace AZ
|
||||
|
||||
if (Interface<TaskGraphActiveInterface>::Get() == nullptr)
|
||||
{
|
||||
Interface<TaskGraphActiveInterface>::Register(this);
|
||||
m_taskExecutor = aznew TaskExecutor();
|
||||
Interface<TaskGraphActiveInterface>::Register(this); // small window that another thread can try to use taskgraph between this line and the set instance.
|
||||
m_taskExecutor = aznew TaskExecutor(Threading::CalcNumWorkerThreads(cl_taskGraphThreadsConcurrencyRatio, cl_taskGraphThreadsMinNumber, cl_taskGraphThreadsNumReserved));
|
||||
TaskExecutor::SetInstance(m_taskExecutor);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
|
||||
#include <AzCore/Threading/ThreadUtils.h>
|
||||
#include <AzCore/std/parallel/thread.h>
|
||||
#include <AzCore/Math/MathUtils.h>
|
||||
|
||||
namespace AZ::Threading
|
||||
{
|
||||
uint32_t CalcNumWorkerThreads(float workerThreadsRatio, uint32_t minNumWorkerThreads, uint32_t reservedNumThreads)
|
||||
{
|
||||
const uint32_t maxHardwareThreads = AZStd::thread::hardware_concurrency();
|
||||
const uint32_t numReservedThreads = AZ::GetMin<uint32_t>(reservedNumThreads, maxHardwareThreads); // protect against num reserved being bigger than the number of hw threads
|
||||
const uint32_t maxWorkerThreads = maxHardwareThreads - numReservedThreads;
|
||||
const float requestedWorkerThreads = AZ::GetClamp<float>(workerThreadsRatio, 0.0f, 1.0f) * static_cast<float>(maxWorkerThreads);
|
||||
const uint32_t requestedWorkerThreadsRounded = AZStd::lround(requestedWorkerThreads);
|
||||
const uint32_t numWorkerThreads = AZ::GetMax<uint32_t>(minNumWorkerThreads, requestedWorkerThreadsRounded);
|
||||
return numWorkerThreads;
|
||||
}
|
||||
};
|
||||
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AzCore/base.h>
|
||||
|
||||
namespace AZ::Threading
|
||||
{
|
||||
//! Calculates the number of worker threads a system should use based on the number of hardware threads a device has.
|
||||
//! result = max (minNumWorkerThreads, workerThreadsRatio * (num_hardware_threads - reservedNumThreads))
|
||||
//! @param workerThreadsRatio scale applied to the calculated maximum number of threads available after reserved threads have been accounted for. Clamped between 0 and 1.
|
||||
//! @param minNumWorkerThreads minimum value that will be returned. Value is unclamped and can be more than num_hardware_threads.
|
||||
//! @param reservedNumThreads number of hardware threads to reserve for O3DE system threads. Value clamped to num_hardware_threads.
|
||||
//! @return number of worker threads for the calling system to allocate
|
||||
uint32_t CalcNumWorkerThreads(float workerThreadsRatio, uint32_t minNumWorkerThreads, uint32_t reservedNumThreads);
|
||||
};
|
||||
@@ -639,6 +639,8 @@ set(FILES
|
||||
Threading/ThreadSafeDeque.inl
|
||||
Threading/ThreadSafeObject.h
|
||||
Threading/ThreadSafeObject.inl
|
||||
Threading/ThreadUtils.h
|
||||
Threading/ThreadUtils.cpp
|
||||
Time/ITime.h
|
||||
Time/TimeSystemComponent.cpp
|
||||
Time/TimeSystemComponent.h
|
||||
|
||||
+4
@@ -59,6 +59,10 @@ namespace AZStd
|
||||
{
|
||||
priority = desc->m_priority;
|
||||
}
|
||||
else
|
||||
{
|
||||
priority = SCHED_OTHER;
|
||||
}
|
||||
if (desc->m_name)
|
||||
{
|
||||
name = desc->m_name;
|
||||
|
||||
@@ -2088,7 +2088,7 @@ namespace UnitTest
|
||||
DisconnectNextHandlerByIdImpl multiHandler2;
|
||||
multiHandler2.BusConnect(DisconnectNextHandlerByIdImpl::firstBusAddress);
|
||||
multiHandler2.BusConnect(DisconnectNextHandlerByIdImpl::secondBusAddress);
|
||||
|
||||
|
||||
// Set the first handler m_nextHandler field to point to the second handler
|
||||
multiHandler1.m_nextHandler = &multiHandler2;
|
||||
|
||||
@@ -2807,7 +2807,7 @@ namespace UnitTest
|
||||
AZStd::this_thread::sleep_for(AZStd::chrono::milliseconds(m_val % m_maxSleep));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void DoConnect() override
|
||||
{
|
||||
MyEventGroupBus::Handler::BusConnect(m_id);
|
||||
@@ -2854,7 +2854,7 @@ namespace UnitTest
|
||||
}
|
||||
|
||||
MyEventGroupBus::Event(id, &MyEventGroupBus::Events::Calculate, i, i * 2, i << 4);
|
||||
|
||||
|
||||
LocklessConnectorBus::Event(id, &LocklessConnectorBus::Events::DoDisconnect);
|
||||
|
||||
bool failed = (AZStd::find_if(&sentinel[0], end, [](char s) { return s != 0; }) != end);
|
||||
@@ -2891,7 +2891,7 @@ namespace UnitTest
|
||||
{
|
||||
MyEventGroupImpl()
|
||||
{
|
||||
|
||||
|
||||
}
|
||||
|
||||
~MyEventGroupImpl() override
|
||||
@@ -3614,7 +3614,7 @@ namespace UnitTest
|
||||
{
|
||||
AZStd::this_thread::yield();
|
||||
}
|
||||
|
||||
|
||||
EXPECT_GE(AZStd::chrono::system_clock::now(), endTime);
|
||||
};
|
||||
AZStd::thread connectThread([&connectHandler, &waitHandler]()
|
||||
@@ -3813,7 +3813,7 @@ namespace UnitTest
|
||||
struct LastHandlerDisconnectHandler
|
||||
: public LastHandlerDisconnectBus::Handler
|
||||
{
|
||||
void OnEvent() override
|
||||
void OnEvent() override
|
||||
{
|
||||
++m_numOnEvents;
|
||||
BusDisconnect();
|
||||
@@ -3854,7 +3854,7 @@ namespace UnitTest
|
||||
struct DisconnectAssertHandler
|
||||
: public DisconnectAssertBus::Handler
|
||||
{
|
||||
|
||||
|
||||
};
|
||||
|
||||
TEST_F(EBus, HandlerDestroyedWithoutDisconnect_Asserts)
|
||||
@@ -3995,6 +3995,191 @@ namespace UnitTest
|
||||
|
||||
idTestRequest.Disconnect();
|
||||
}
|
||||
|
||||
// IsInDispatchThisThread
|
||||
struct IsInThreadDispatchRequests
|
||||
: AZ::EBusTraits
|
||||
{
|
||||
using MutexType = AZStd::recursive_mutex;
|
||||
};
|
||||
|
||||
using IsInThreadDispatchBus = AZ::EBus<IsInThreadDispatchRequests>;
|
||||
|
||||
class IsInThreadDispatchHandler
|
||||
: public IsInThreadDispatchBus::Handler
|
||||
{};
|
||||
|
||||
TEST_F(EBus, InvokingIsInThisThread_ReturnsSuccess_OnlyIfThreadIsInDispatch)
|
||||
{
|
||||
IsInThreadDispatchHandler handler;
|
||||
handler.BusConnect();
|
||||
|
||||
auto ThreadDispatcher = [](IsInThreadDispatchRequests*)
|
||||
{
|
||||
EXPECT_TRUE(IsInThreadDispatchBus::IsInDispatchThisThread());
|
||||
auto PerThreadBusDispatch = []()
|
||||
{
|
||||
EXPECT_FALSE(IsInThreadDispatchBus::IsInDispatchThisThread());
|
||||
};
|
||||
AZStd::array threads{ AZStd::thread(PerThreadBusDispatch), AZStd::thread(PerThreadBusDispatch) };
|
||||
for (AZStd::thread& thread : threads)
|
||||
{
|
||||
thread.join();
|
||||
}
|
||||
};
|
||||
|
||||
static constexpr size_t ThreadDispatcherIterations = 4;
|
||||
for (size_t iteration = 0; iteration < ThreadDispatcherIterations; ++iteration)
|
||||
{
|
||||
EXPECT_FALSE(IsInThreadDispatchBus::IsInDispatchThisThread());
|
||||
IsInThreadDispatchBus::Broadcast(ThreadDispatcher);
|
||||
EXPECT_FALSE(IsInThreadDispatchBus::IsInDispatchThisThread());
|
||||
}
|
||||
}
|
||||
|
||||
// Thread Dispatch Policy
|
||||
struct ThreadDispatchTestBusTraits
|
||||
: AZ::EBusTraits
|
||||
{
|
||||
using MutexType = AZStd::recursive_mutex;
|
||||
|
||||
struct PostThreadDispatchTestInvoker
|
||||
{
|
||||
~PostThreadDispatchTestInvoker();
|
||||
};
|
||||
|
||||
template <typename DispatchMutex>
|
||||
struct ThreadDispatchTestLockGuard
|
||||
{
|
||||
ThreadDispatchTestLockGuard(DispatchMutex& contextMutex)
|
||||
: m_lock{ contextMutex }
|
||||
{}
|
||||
ThreadDispatchTestLockGuard(DispatchMutex& contextMutex, AZStd::adopt_lock_t adopt_lock)
|
||||
: m_lock{ contextMutex, adopt_lock }
|
||||
{}
|
||||
ThreadDispatchTestLockGuard(const ThreadDispatchTestLockGuard&) = delete;
|
||||
ThreadDispatchTestLockGuard& operator=(const ThreadDispatchTestLockGuard&) = delete;
|
||||
private:
|
||||
PostThreadDispatchTestInvoker m_threadPolicyInvoker;
|
||||
using LockType = AZStd::conditional_t<LocklessDispatch, AZ::Internal::NullLockGuard<DispatchMutex>, AZStd::scoped_lock<DispatchMutex>>;
|
||||
LockType m_lock;
|
||||
};
|
||||
|
||||
template <typename DispatchMutex, bool IsLocklessDispatch>
|
||||
using DispatchLockGuard = ThreadDispatchTestLockGuard<DispatchMutex>;
|
||||
|
||||
static inline AZStd::atomic<int32_t> s_threadPostDispatchCalls;
|
||||
};
|
||||
|
||||
class ThreadDispatchTestRequests
|
||||
{
|
||||
public:
|
||||
virtual void FirstCall() = 0;
|
||||
virtual void SecondCall() = 0;
|
||||
virtual void ThirdCall() = 0;
|
||||
};
|
||||
|
||||
using ThreadDispatchTestBus = AZ::EBus<ThreadDispatchTestRequests, ThreadDispatchTestBusTraits>;
|
||||
|
||||
ThreadDispatchTestBusTraits::PostThreadDispatchTestInvoker::~PostThreadDispatchTestInvoker()
|
||||
{
|
||||
if (!ThreadDispatchTestBus::IsInDispatchThisThread())
|
||||
{
|
||||
++s_threadPostDispatchCalls;
|
||||
}
|
||||
}
|
||||
|
||||
class ThreadDispatchTestHandler
|
||||
: public ThreadDispatchTestBus::Handler
|
||||
{
|
||||
public:
|
||||
void Connect()
|
||||
{
|
||||
ThreadDispatchTestBus::Handler::BusConnect();
|
||||
}
|
||||
void Disconnect()
|
||||
{
|
||||
ThreadDispatchTestBus::Handler::BusDisconnect();
|
||||
}
|
||||
|
||||
void FirstCall() override
|
||||
{
|
||||
ThreadDispatchTestBus::Broadcast(&ThreadDispatchTestBus::Events::SecondCall);
|
||||
}
|
||||
void SecondCall() override
|
||||
{
|
||||
ThreadDispatchTestBus::Broadcast(&ThreadDispatchTestBus::Events::ThirdCall);
|
||||
}
|
||||
void ThirdCall() override
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
template <typename ParamType>
|
||||
class EBusParamFixture
|
||||
: public ScopedAllocatorSetupFixture
|
||||
, public ::testing::WithParamInterface<ParamType>
|
||||
{};
|
||||
|
||||
struct ThreadDispatchParams
|
||||
{
|
||||
size_t m_threadCount{};
|
||||
size_t m_handlerCount{};
|
||||
};
|
||||
|
||||
using ThreadDispatchParamFixture = EBusParamFixture<ThreadDispatchParams>;
|
||||
|
||||
INSTANTIATE_TEST_CASE_P(
|
||||
ThreadDispatch,
|
||||
ThreadDispatchParamFixture,
|
||||
::testing::Values(
|
||||
ThreadDispatchParams{ 1, 1 },
|
||||
ThreadDispatchParams{ 2, 1 },
|
||||
ThreadDispatchParams{ 1, 2 },
|
||||
ThreadDispatchParams{ 2, 2 },
|
||||
ThreadDispatchParams{ 16, 8 }
|
||||
)
|
||||
);
|
||||
|
||||
TEST_P(ThreadDispatchParamFixture, CustomDispatchLockGuard_InvokesPostDispatchFunction_AfterThreadHasFinishedDispatch)
|
||||
{
|
||||
ThreadDispatchTestBusTraits::s_threadPostDispatchCalls = 0;
|
||||
ThreadDispatchParams threadDispatchParams = GetParam();
|
||||
AZStd::vector<AZStd::thread> testThreads;
|
||||
AZStd::vector<ThreadDispatchTestHandler> testHandlers(threadDispatchParams.m_handlerCount);
|
||||
for (ThreadDispatchTestHandler& testHandler : testHandlers)
|
||||
{
|
||||
testHandler.Connect();
|
||||
}
|
||||
|
||||
static constexpr size_t DispatchThreadCalls = 3;
|
||||
const size_t totalThreadDispatchCalls = threadDispatchParams.m_threadCount * DispatchThreadCalls;
|
||||
|
||||
auto DispatchThreadWorker = []()
|
||||
{
|
||||
ThreadDispatchTestBus::Broadcast(&ThreadDispatchTestBus::Events::FirstCall);
|
||||
ThreadDispatchTestBus::Broadcast(&ThreadDispatchTestBus::Events::SecondCall);
|
||||
ThreadDispatchTestBus::Broadcast(&ThreadDispatchTestBus::Events::ThirdCall);
|
||||
};
|
||||
|
||||
for (size_t threadIndex = 0; threadIndex < threadDispatchParams.m_threadCount; ++threadIndex)
|
||||
{
|
||||
testThreads.emplace_back(DispatchThreadWorker);
|
||||
}
|
||||
|
||||
for (AZStd::thread& thread : testThreads)
|
||||
{
|
||||
thread.join();
|
||||
}
|
||||
|
||||
for (ThreadDispatchTestHandler& testHandler : testHandlers)
|
||||
{
|
||||
testHandler.Disconnect();
|
||||
}
|
||||
|
||||
EXPECT_EQ(totalThreadDispatchCalls, ThreadDispatchTestBusTraits::s_threadPostDispatchCalls);
|
||||
ThreadDispatchTestBusTraits::s_threadPostDispatchCalls = 0;
|
||||
}
|
||||
} // namespace UnitTest
|
||||
|
||||
#if defined(HAVE_BENCHMARK)
|
||||
@@ -4370,7 +4555,7 @@ namespace Benchmark
|
||||
Bus::ExecuteQueuedEvents();
|
||||
}
|
||||
s_benchmarkEBusEnv<Bus>.Disconnect(state);
|
||||
|
||||
|
||||
}
|
||||
BUS_BENCHMARK_REGISTER_ALL(BM_EBus_ExecuteBroadcast);
|
||||
|
||||
|
||||
@@ -533,8 +533,8 @@ namespace AzFramework
|
||||
m_translateCameraInputChannelIds = translateCameraInputChannelIds;
|
||||
}
|
||||
|
||||
PivotCameraInput::PivotCameraInput(const InputChannelId& pivotChannelId)
|
||||
: m_pivotChannelId(pivotChannelId)
|
||||
OrbitCameraInput::OrbitCameraInput(const InputChannelId& orbitChannelId)
|
||||
: m_orbitChannelId(orbitChannelId)
|
||||
{
|
||||
m_pivotFn = []([[maybe_unused]] const AZ::Vector3& position, [[maybe_unused]] const AZ::Vector3& direction)
|
||||
{
|
||||
@@ -542,11 +542,11 @@ namespace AzFramework
|
||||
};
|
||||
}
|
||||
|
||||
bool PivotCameraInput::HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, const float scrollDelta)
|
||||
bool OrbitCameraInput::HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, const float scrollDelta)
|
||||
{
|
||||
if (const auto* input = AZStd::get_if<DiscreteInputEvent>(&event))
|
||||
{
|
||||
if (input->m_channelId == m_pivotChannelId)
|
||||
if (input->m_channelId == m_orbitChannelId)
|
||||
{
|
||||
if (input->m_state == InputChannel::State::Began)
|
||||
{
|
||||
@@ -561,13 +561,13 @@ namespace AzFramework
|
||||
|
||||
if (Active())
|
||||
{
|
||||
return m_pivotCameras.HandleEvents(event, cursorDelta, scrollDelta);
|
||||
return m_orbitCameras.HandleEvents(event, cursorDelta, scrollDelta);
|
||||
}
|
||||
|
||||
return !Idle();
|
||||
}
|
||||
|
||||
Camera PivotCameraInput::StepCamera(
|
||||
Camera OrbitCameraInput::StepCamera(
|
||||
const Camera& targetCamera, const ScreenVector& cursorDelta, const float scrollDelta, const float deltaTime)
|
||||
{
|
||||
Camera nextCamera = targetCamera;
|
||||
@@ -581,12 +581,12 @@ namespace AzFramework
|
||||
if (Active())
|
||||
{
|
||||
MovePivotDetached(nextCamera, m_pivotFn(targetCamera.Translation(), targetCamera.Rotation().GetBasisY()));
|
||||
nextCamera = m_pivotCameras.StepCamera(nextCamera, cursorDelta, scrollDelta, deltaTime);
|
||||
nextCamera = m_orbitCameras.StepCamera(nextCamera, cursorDelta, scrollDelta, deltaTime);
|
||||
}
|
||||
|
||||
if (Ending())
|
||||
{
|
||||
m_pivotCameras.Reset();
|
||||
m_orbitCameras.Reset();
|
||||
|
||||
nextCamera.m_pivot = nextCamera.Translation();
|
||||
nextCamera.m_offset = AZ::Vector3::CreateZero();
|
||||
@@ -595,12 +595,12 @@ namespace AzFramework
|
||||
return nextCamera;
|
||||
}
|
||||
|
||||
void PivotCameraInput::SetPivotInputChannelId(const InputChannelId& pivotChanneId)
|
||||
void OrbitCameraInput::SetOrbitInputChannelId(const InputChannelId& orbitChanneId)
|
||||
{
|
||||
m_pivotChannelId = pivotChanneId;
|
||||
m_orbitChannelId = orbitChanneId;
|
||||
}
|
||||
|
||||
PivotDollyScrollCameraInput::PivotDollyScrollCameraInput()
|
||||
OrbitDollyScrollCameraInput::OrbitDollyScrollCameraInput()
|
||||
{
|
||||
m_scrollSpeedFn = []() constexpr
|
||||
{
|
||||
@@ -608,7 +608,7 @@ namespace AzFramework
|
||||
};
|
||||
}
|
||||
|
||||
bool PivotDollyScrollCameraInput::HandleEvents(
|
||||
bool OrbitDollyScrollCameraInput::HandleEvents(
|
||||
const InputEvent& event, [[maybe_unused]] const ScreenVector& cursorDelta, [[maybe_unused]] const float scrollDelta)
|
||||
{
|
||||
if (const auto* scroll = AZStd::get_if<ScrollEvent>(&event))
|
||||
@@ -619,7 +619,7 @@ namespace AzFramework
|
||||
return !Idle();
|
||||
}
|
||||
|
||||
static Camera PivotDolly(const Camera& targetCamera, const float delta)
|
||||
static Camera OrbitDolly(const Camera& targetCamera, const float delta)
|
||||
{
|
||||
Camera nextCamera = targetCamera;
|
||||
|
||||
@@ -646,18 +646,18 @@ namespace AzFramework
|
||||
return nextCamera;
|
||||
}
|
||||
|
||||
Camera PivotDollyScrollCameraInput::StepCamera(
|
||||
Camera OrbitDollyScrollCameraInput::StepCamera(
|
||||
const Camera& targetCamera,
|
||||
[[maybe_unused]] const ScreenVector& cursorDelta,
|
||||
const float scrollDelta,
|
||||
[[maybe_unused]] const float deltaTime)
|
||||
{
|
||||
const auto nextCamera = PivotDolly(targetCamera, aznumeric_cast<float>(scrollDelta) * m_scrollSpeedFn());
|
||||
const auto nextCamera = OrbitDolly(targetCamera, aznumeric_cast<float>(scrollDelta) * m_scrollSpeedFn());
|
||||
EndActivation();
|
||||
return nextCamera;
|
||||
}
|
||||
|
||||
PivotDollyMotionCameraInput::PivotDollyMotionCameraInput(const InputChannelId& dollyChannelId)
|
||||
OrbitDollyMotionCameraInput::OrbitDollyMotionCameraInput(const InputChannelId& dollyChannelId)
|
||||
: m_dollyChannelId(dollyChannelId)
|
||||
{
|
||||
m_motionSpeedFn = []() constexpr
|
||||
@@ -666,28 +666,28 @@ namespace AzFramework
|
||||
};
|
||||
}
|
||||
|
||||
bool PivotDollyMotionCameraInput::HandleEvents(
|
||||
bool OrbitDollyMotionCameraInput::HandleEvents(
|
||||
const InputEvent& event, [[maybe_unused]] const ScreenVector& cursorDelta, [[maybe_unused]] const float scrollDelta)
|
||||
{
|
||||
HandleActivationEvents(event, m_dollyChannelId, cursorDelta, m_clickDetector, *this);
|
||||
return CameraInputUpdatingAfterMotion(*this);
|
||||
}
|
||||
|
||||
Camera PivotDollyMotionCameraInput::StepCamera(
|
||||
Camera OrbitDollyMotionCameraInput::StepCamera(
|
||||
const Camera& targetCamera,
|
||||
const ScreenVector& cursorDelta,
|
||||
[[maybe_unused]] const float scrollDelta,
|
||||
[[maybe_unused]] const float deltaTime)
|
||||
{
|
||||
return PivotDolly(targetCamera, aznumeric_cast<float>(cursorDelta.m_y) * m_motionSpeedFn());
|
||||
return OrbitDolly(targetCamera, aznumeric_cast<float>(cursorDelta.m_y) * m_motionSpeedFn());
|
||||
}
|
||||
|
||||
void PivotDollyMotionCameraInput::SetDollyInputChannelId(const InputChannelId& dollyChannelId)
|
||||
void OrbitDollyMotionCameraInput::SetDollyInputChannelId(const InputChannelId& dollyChannelId)
|
||||
{
|
||||
m_dollyChannelId = dollyChannelId;
|
||||
}
|
||||
|
||||
ScrollTranslationCameraInput::ScrollTranslationCameraInput()
|
||||
LookScrollTranslationCameraInput::LookScrollTranslationCameraInput()
|
||||
{
|
||||
m_scrollSpeedFn = []() constexpr
|
||||
{
|
||||
@@ -695,7 +695,7 @@ namespace AzFramework
|
||||
};
|
||||
}
|
||||
|
||||
bool ScrollTranslationCameraInput::HandleEvents(
|
||||
bool LookScrollTranslationCameraInput::HandleEvents(
|
||||
const InputEvent& event, [[maybe_unused]] const ScreenVector& cursorDelta, [[maybe_unused]] const float scrollDelta)
|
||||
{
|
||||
if (const auto* scroll = AZStd::get_if<ScrollEvent>(&event))
|
||||
@@ -706,7 +706,7 @@ namespace AzFramework
|
||||
return !Idle();
|
||||
}
|
||||
|
||||
Camera ScrollTranslationCameraInput::StepCamera(
|
||||
Camera LookScrollTranslationCameraInput::StepCamera(
|
||||
const Camera& targetCamera,
|
||||
[[maybe_unused]] const ScreenVector& cursorDelta,
|
||||
const float scrollDelta,
|
||||
|
||||
@@ -30,8 +30,11 @@ namespace AzFramework
|
||||
AZ::Vector3 EulerAngles(const AZ::Matrix3x3& orientation);
|
||||
|
||||
//! A simple camera representation using spherical coordinates as input (pitch, yaw, pivot and offset).
|
||||
//! The cameras transform and view can be obtained through accessor functions that use the internal
|
||||
//! The camera's transform and view can be obtained through accessor functions that use the internal
|
||||
//! spherical coordinates to calculate the position and orientation.
|
||||
//! @note Modifying m_pivot directly and leaving m_offset as zero will produce a free look camera effect, giving
|
||||
//! m_offset a value (e.g. in negative Y only) will produce an orbit camera effect, modifying X and Z of m_offset
|
||||
//! will further alter the camera translation in relation to m_pivot so it appears off center.
|
||||
struct Camera
|
||||
{
|
||||
AZ::Vector3 m_pivot = AZ::Vector3::CreateZero(); //!< Pivot point to rotate about (modified in world space).
|
||||
@@ -291,7 +294,7 @@ namespace AzFramework
|
||||
Cameras m_cameras; //!< Represents a collection of camera inputs that together provide a camera controller.
|
||||
|
||||
private:
|
||||
ScreenVector m_motionDelta; //!< The delta used for look/pivot/pan (rotation + translation) - two dimensional.
|
||||
ScreenVector m_motionDelta; //!< The delta used for look/orbit/pan (rotation + translation) - two dimensional.
|
||||
CursorState m_cursorState; //!< The current and previous position of the cursor (used to calculate movement delta).
|
||||
float m_scrollDelta = 0.0f; //!< The delta used for dolly/movement (translation) - one dimensional.
|
||||
bool m_handlingEvents = false; //!< Is the camera system currently handling events (events are consumed and not propagated).
|
||||
@@ -316,7 +319,7 @@ namespace AzFramework
|
||||
return AZStd::fmod(yaw + AZ::Constants::TwoPi, AZ::Constants::TwoPi);
|
||||
}
|
||||
|
||||
//! A camera input to handle motion deltas that can rotate or pivot the camera.
|
||||
//! A camera input to handle motion deltas that can change the orientation of the camera (update pitch and yaw).
|
||||
class RotateCameraInput : public CameraInput
|
||||
{
|
||||
public:
|
||||
@@ -348,15 +351,16 @@ namespace AzFramework
|
||||
//! PanAxes build function that will return a pair of pan axes depending on the camera orientation.
|
||||
using PanAxesFn = AZStd::function<PanAxes(const Camera& camera)>;
|
||||
|
||||
//! PanAxes to use while in 'look' camera behavior (free look).
|
||||
//! PanAxes to use while in 'look' or 'orbit' camera behavior.
|
||||
inline PanAxes LookPan(const Camera& camera)
|
||||
{
|
||||
const AZ::Matrix3x3 orientation = camera.Rotation();
|
||||
return { orientation.GetBasisX(), orientation.GetBasisZ() };
|
||||
}
|
||||
|
||||
//! PanAxes to use while in 'pivot' camera behavior.
|
||||
inline PanAxes PivotPan(const Camera& camera)
|
||||
//! Optional PanAxes to use while in 'orbit' camera behavior.
|
||||
//! @note This will move the camera in the local X/Y plane instead of usual X/Z plane.
|
||||
inline PanAxes OrbitPan(const Camera& camera)
|
||||
{
|
||||
const AZ::Matrix3x3 orientation = camera.Rotation();
|
||||
|
||||
@@ -370,14 +374,23 @@ namespace AzFramework
|
||||
return { basisX, basisY };
|
||||
}
|
||||
|
||||
//! TranslationDeltaFn is used by PanCameraInput and TranslateCameraInput
|
||||
//! @note Choose the appropriate function if the behavior should be operating as a free look camera (TranslatePivotLook)
|
||||
//! or an orbit camera (TranslateOffsetOrbit).
|
||||
using TranslationDeltaFn = AZStd::function<void(Camera& camera, const AZ::Vector3& delta)>;
|
||||
|
||||
inline void TranslatePivot(Camera& camera, const AZ::Vector3& delta)
|
||||
//! Update the pivot camera position.
|
||||
//! @note delta will need to have been transformed to world space, e.g. To move the camera right, (1, 0, 0) must
|
||||
//! first be transformed by the orientation of the camera before being applied to m_pivot.
|
||||
inline void TranslatePivotLook(Camera& camera, const AZ::Vector3& delta)
|
||||
{
|
||||
camera.m_pivot += delta;
|
||||
}
|
||||
|
||||
inline void TranslateOffset(Camera& camera, const AZ::Vector3& delta)
|
||||
//! Update the offset camera position.
|
||||
//! @note delta still needs to be transformed to world space (as with TranslatePivotLook) but internally this is undone
|
||||
//! to be performed in local space when being applied to m_offset.
|
||||
inline void TranslateOffsetOrbit(Camera& camera, const AZ::Vector3& delta)
|
||||
{
|
||||
camera.m_offset += camera.View().TransformVector(delta);
|
||||
}
|
||||
@@ -409,7 +422,7 @@ namespace AzFramework
|
||||
//! Axes to use while translating the camera.
|
||||
using TranslationAxesFn = AZStd::function<AZ::Matrix3x3(const Camera& camera)>;
|
||||
|
||||
//! TranslationAxes to use while in 'look' camera behavior (free look).
|
||||
//! TranslationAxes to use while in 'look' or 'orbit' camera behavior.
|
||||
inline AZ::Matrix3x3 LookTranslation(const Camera& camera)
|
||||
{
|
||||
const AZ::Matrix3x3 orientation = camera.Rotation();
|
||||
@@ -421,8 +434,8 @@ namespace AzFramework
|
||||
return AZ::Matrix3x3::CreateFromColumns(basisX, basisY, basisZ);
|
||||
}
|
||||
|
||||
//! TranslationAxes to use while in 'pivot' camera behavior.
|
||||
inline AZ::Matrix3x3 PivotTranslation(const Camera& camera)
|
||||
//! Optional TranslationAxes to use while in 'orbit' camera behavior.
|
||||
inline AZ::Matrix3x3 OrbitTranslation(const Camera& camera)
|
||||
{
|
||||
const AZ::Matrix3x3 orientation = camera.Rotation();
|
||||
|
||||
@@ -535,11 +548,11 @@ namespace AzFramework
|
||||
bool m_boost = false; //!< Is the translation speed currently being multiplied/scaled upwards.
|
||||
};
|
||||
|
||||
//! A camera input to handle discrete scroll events that can modify the camera pivot distance.
|
||||
class PivotDollyScrollCameraInput : public CameraInput
|
||||
//! A camera input to handle discrete scroll events that can modify the camera offset.
|
||||
class OrbitDollyScrollCameraInput : public CameraInput
|
||||
{
|
||||
public:
|
||||
PivotDollyScrollCameraInput();
|
||||
OrbitDollyScrollCameraInput();
|
||||
|
||||
// CameraInput overrides ...
|
||||
bool HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, float scrollDelta) override;
|
||||
@@ -548,11 +561,11 @@ namespace AzFramework
|
||||
AZStd::function<float()> m_scrollSpeedFn;
|
||||
};
|
||||
|
||||
//! A camera input to handle motion deltas that can modify the camera pivot distance.
|
||||
class PivotDollyMotionCameraInput : public CameraInput
|
||||
//! A camera input to handle motion deltas that can modify the camera offset.
|
||||
class OrbitDollyMotionCameraInput : public CameraInput
|
||||
{
|
||||
public:
|
||||
explicit PivotDollyMotionCameraInput(const InputChannelId& dollyChannelId);
|
||||
explicit OrbitDollyMotionCameraInput(const InputChannelId& dollyChannelId);
|
||||
|
||||
// CameraInput overrides ...
|
||||
bool HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, float scrollDelta) override;
|
||||
@@ -569,10 +582,10 @@ namespace AzFramework
|
||||
};
|
||||
|
||||
//! A camera input to handle discrete scroll events that can scroll (translate) the camera along its forward axis.
|
||||
class ScrollTranslationCameraInput : public CameraInput
|
||||
class LookScrollTranslationCameraInput : public CameraInput
|
||||
{
|
||||
public:
|
||||
ScrollTranslationCameraInput();
|
||||
LookScrollTranslationCameraInput();
|
||||
|
||||
// CameraInput overrides ...
|
||||
bool HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, float scrollDelta) override;
|
||||
@@ -583,36 +596,36 @@ namespace AzFramework
|
||||
|
||||
//! A camera input that doubles as its own set of camera inputs.
|
||||
//! It is 'exclusive', so does not overlap with other sibling camera inputs - it runs its own set of camera inputs as 'children'.
|
||||
class PivotCameraInput : public CameraInput
|
||||
class OrbitCameraInput : public CameraInput
|
||||
{
|
||||
public:
|
||||
using PivotFn = AZStd::function<AZ::Vector3(const AZ::Vector3& position, const AZ::Vector3& direction)>;
|
||||
|
||||
explicit PivotCameraInput(const InputChannelId& pivotChannelId);
|
||||
explicit OrbitCameraInput(const InputChannelId& orbitChannelId);
|
||||
|
||||
// CameraInput overrides ...
|
||||
bool HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, float scrollDelta) override;
|
||||
Camera StepCamera(const Camera& targetCamera, const ScreenVector& cursorDelta, float scrollDelta, float deltaTime) override;
|
||||
bool Exclusive() const override;
|
||||
|
||||
void SetPivotInputChannelId(const InputChannelId& pivotChanneId);
|
||||
void SetOrbitInputChannelId(const InputChannelId& orbitChanneId);
|
||||
|
||||
Cameras m_pivotCameras; //!< The camera inputs to run when this camera input is active (only these will run as it is exclusive).
|
||||
Cameras m_orbitCameras; //!< The camera inputs to run when this camera input is active (only these will run as it is exclusive).
|
||||
|
||||
//! Override the default behavior for how a pivot point is calculated.
|
||||
void SetPivotFn(PivotFn pivotFn);
|
||||
|
||||
private:
|
||||
InputChannelId m_pivotChannelId; //!< Input channel to begin the pivot camera input.
|
||||
PivotFn m_pivotFn; //!< The pivot position to use for this pivot camera (how is the pivot point calculated/retrieved).
|
||||
InputChannelId m_orbitChannelId; //!< Input channel to begin the orbit camera input.
|
||||
PivotFn m_pivotFn; //!< The pivot position to use for this orbit camera (how is the pivot point calculated/retrieved).
|
||||
};
|
||||
|
||||
inline void PivotCameraInput::SetPivotFn(PivotFn pivotFn)
|
||||
inline void OrbitCameraInput::SetPivotFn(PivotFn pivotFn)
|
||||
{
|
||||
m_pivotFn = AZStd::move(pivotFn);
|
||||
}
|
||||
|
||||
inline bool PivotCameraInput::Exclusive() const
|
||||
inline bool OrbitCameraInput::Exclusive() const
|
||||
{
|
||||
return true;
|
||||
}
|
||||
@@ -624,9 +637,9 @@ namespace AzFramework
|
||||
return AZ::Vector3::CreateZero();
|
||||
}
|
||||
|
||||
//! Callback to use for FocusCameraInput when a pivot camera is being used.
|
||||
//! Callback to use for FocusCameraInput when a orbit camera is being used.
|
||||
//! @note This is when offset is non zero.
|
||||
inline AZ::Vector3 FocusPivot(const float length)
|
||||
inline AZ::Vector3 FocusOrbit(const float length)
|
||||
{
|
||||
return AZ::Vector3::CreateAxisY(-length);
|
||||
}
|
||||
@@ -667,7 +680,9 @@ namespace AzFramework
|
||||
bool HandleEvents(const InputEvent& event, const ScreenVector& cursorDelta, float scrollDelta) override;
|
||||
Camera StepCamera(const Camera& targetCamera, const ScreenVector& cursorDelta, float scrollDelta, float deltaTime) override;
|
||||
|
||||
//! HandleEvents delegates directly to m_handleEventsFn.
|
||||
AZStd::function<bool(CameraInput&, const InputEvent&, const ScreenVector&, float)> m_handleEventsFn;
|
||||
//! StepCamera delegates directly to m_stepCameraFn.
|
||||
AZStd::function<Camera(CameraInput&, const Camera&, const ScreenVector&, float, float)> m_stepCameraFn;
|
||||
};
|
||||
|
||||
|
||||
@@ -53,31 +53,31 @@ namespace UnitTest
|
||||
};
|
||||
|
||||
m_firstPersonTranslateCamera = AZStd::make_shared<AzFramework::TranslateCameraInput>(
|
||||
m_translateCameraInputChannelIds, AzFramework::LookTranslation, AzFramework::TranslatePivot);
|
||||
m_translateCameraInputChannelIds, AzFramework::LookTranslation, AzFramework::TranslatePivotLook);
|
||||
|
||||
m_pivotCamera = AZStd::make_shared<AzFramework::PivotCameraInput>(m_pivotChannelId);
|
||||
m_pivotCamera->SetPivotFn(
|
||||
m_orbitCamera = AZStd::make_shared<AzFramework::OrbitCameraInput>(m_orbitChannelId);
|
||||
m_orbitCamera->SetPivotFn(
|
||||
[this](const AZ::Vector3&, const AZ::Vector3&)
|
||||
{
|
||||
return m_pivot;
|
||||
});
|
||||
|
||||
auto pivotRotateCamera = AZStd::make_shared<AzFramework::RotateCameraInput>(AzFramework::InputDeviceMouse::Button::Left);
|
||||
auto orbitRotateCamera = AZStd::make_shared<AzFramework::RotateCameraInput>(AzFramework::InputDeviceMouse::Button::Left);
|
||||
// set rotate speed to be a value that will scale motion delta (pixels moved) by a thousandth.
|
||||
pivotRotateCamera->m_rotateSpeedFn = []()
|
||||
orbitRotateCamera->m_rotateSpeedFn = []()
|
||||
{
|
||||
return 0.001f;
|
||||
};
|
||||
|
||||
auto pivotTranslateCamera = AZStd::make_shared<AzFramework::TranslateCameraInput>(
|
||||
m_translateCameraInputChannelIds, AzFramework::PivotTranslation, AzFramework::TranslateOffset);
|
||||
auto orbitTranslateCamera = AZStd::make_shared<AzFramework::TranslateCameraInput>(
|
||||
m_translateCameraInputChannelIds, AzFramework::OrbitTranslation, AzFramework::TranslateOffsetOrbit);
|
||||
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(pivotRotateCamera);
|
||||
m_pivotCamera->m_pivotCameras.AddCamera(pivotTranslateCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(orbitRotateCamera);
|
||||
m_orbitCamera->m_orbitCameras.AddCamera(orbitTranslateCamera);
|
||||
|
||||
m_cameraSystem->m_cameras.AddCamera(m_firstPersonRotateCamera);
|
||||
m_cameraSystem->m_cameras.AddCamera(m_firstPersonTranslateCamera);
|
||||
m_cameraSystem->m_cameras.AddCamera(m_pivotCamera);
|
||||
m_cameraSystem->m_cameras.AddCamera(m_orbitCamera);
|
||||
|
||||
// these tests rely on using motion delta, not cursor positions (default is true)
|
||||
AzFramework::ed_cameraSystemUseCursor = false;
|
||||
@@ -87,7 +87,7 @@ namespace UnitTest
|
||||
{
|
||||
AzFramework::ed_cameraSystemUseCursor = true;
|
||||
|
||||
m_pivotCamera.reset();
|
||||
m_orbitCamera.reset();
|
||||
m_firstPersonRotateCamera.reset();
|
||||
m_firstPersonTranslateCamera.reset();
|
||||
|
||||
@@ -97,11 +97,11 @@ namespace UnitTest
|
||||
AllocatorsTestFixture::TearDown();
|
||||
}
|
||||
|
||||
AzFramework::InputChannelId m_pivotChannelId = AzFramework::InputChannelId("keyboard_key_modifier_alt_l");
|
||||
AzFramework::InputChannelId m_orbitChannelId = AzFramework::InputChannelId("keyboard_key_modifier_alt_l");
|
||||
AzFramework::TranslateCameraInputChannelIds m_translateCameraInputChannelIds;
|
||||
AZStd::shared_ptr<AzFramework::RotateCameraInput> m_firstPersonRotateCamera;
|
||||
AZStd::shared_ptr<AzFramework::TranslateCameraInput> m_firstPersonTranslateCamera;
|
||||
AZStd::shared_ptr<AzFramework::PivotCameraInput> m_pivotCamera;
|
||||
AZStd::shared_ptr<AzFramework::OrbitCameraInput> m_orbitCamera;
|
||||
AZ::Vector3 m_pivot = AZ::Vector3::CreateZero();
|
||||
|
||||
//! This is approximately Pi/2 * 1000 - this can be used to rotate the camera 90 degrees (pitch or yaw based
|
||||
@@ -109,17 +109,17 @@ namespace UnitTest
|
||||
inline static const int PixelMotionDelta = 1570;
|
||||
};
|
||||
|
||||
TEST_F(CameraInputFixture, BeginAndEndPivotCameraInputConsumesCorrectEvents)
|
||||
TEST_F(CameraInputFixture, BeginAndEndOrbitCameraInputConsumesCorrectEvents)
|
||||
{
|
||||
// begin pivot camera
|
||||
// begin orbit camera
|
||||
const bool consumed1 = HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ AzFramework::InputDeviceKeyboard::Key::ModifierAltL,
|
||||
AzFramework::InputChannel::State::Began });
|
||||
// begin listening for pivot rotate (click detector) - event is not consumed
|
||||
// begin listening for orbit rotate (click detector) - event is not consumed
|
||||
const bool consumed2 = HandleEventAndUpdate(
|
||||
AzFramework::DiscreteInputEvent{ AzFramework::InputDeviceMouse::Button::Left, AzFramework::InputChannel::State::Began });
|
||||
// begin pivot rotate (mouse has moved sufficient distance to initiate)
|
||||
// begin orbit rotate (mouse has moved sufficient distance to initiate)
|
||||
const bool consumed3 = HandleEventAndUpdate(AzFramework::HorizontalMotionEvent{ 5 });
|
||||
// end pivot (mouse up) - event is not consumed
|
||||
// end orbit (mouse up) - event is not consumed
|
||||
const bool consumed4 = HandleEventAndUpdate(
|
||||
AzFramework::DiscreteInputEvent{ AzFramework::InputDeviceMouse::Button::Left, AzFramework::InputChannel::State::Ended });
|
||||
|
||||
@@ -260,10 +260,10 @@ namespace UnitTest
|
||||
EXPECT_TRUE(activationEnded);
|
||||
}
|
||||
|
||||
TEST_F(CameraInputFixture, PivotCameraInputHandlesLookAtPointAndSelfAtSamePositionWhenPivoting)
|
||||
TEST_F(CameraInputFixture, OrbitCameraInputHandlesLookAtPointAndSelfAtSamePositionWhenOrbiting)
|
||||
{
|
||||
// create pathological lookAtFn that just returns the same position as the camera
|
||||
m_pivotCamera->SetPivotFn(
|
||||
m_orbitCamera->SetPivotFn(
|
||||
[](const AZ::Vector3& position, [[maybe_unused]] const AZ::Vector3& direction)
|
||||
{
|
||||
return position;
|
||||
@@ -275,7 +275,7 @@ namespace UnitTest
|
||||
AZ::Transform::CreateFromQuaternionAndTranslation(
|
||||
AZ::Quaternion::CreateFromEulerAnglesDegrees(AZ::Vector3(0.0f, 0.0f, 90.0f)), expectedCameraPosition));
|
||||
|
||||
HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ m_pivotChannelId, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ m_orbitChannelId, AzFramework::InputChannel::State::Began });
|
||||
|
||||
// verify the camera yaw has not changed and pivot point matches the expected camera position
|
||||
using ::testing::FloatNear;
|
||||
@@ -321,14 +321,14 @@ namespace UnitTest
|
||||
EXPECT_THAT(m_camera.m_offset, IsClose(AZ::Vector3::CreateZero()));
|
||||
}
|
||||
|
||||
TEST_F(CameraInputFixture, PivotRotateCameraInputRotatesPitchOffsetByNinetyDegreesWithRequiredPixelDelta)
|
||||
TEST_F(CameraInputFixture, OrbitRotateCameraInputRotatesPitchOffsetByNinetyDegreesWithRequiredPixelDelta)
|
||||
{
|
||||
const auto cameraStartingPosition = AZ::Vector3::CreateAxisY(-20.0f);
|
||||
m_targetCamera.m_pivot = cameraStartingPosition;
|
||||
|
||||
m_pivot = AZ::Vector3::CreateAxisY(-10.0f);
|
||||
|
||||
HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ m_pivotChannelId, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ m_orbitChannelId, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(
|
||||
AzFramework::DiscreteInputEvent{ AzFramework::InputDeviceMouse::Button::Left, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(AzFramework::VerticalMotionEvent{ PixelMotionDelta });
|
||||
@@ -344,14 +344,14 @@ namespace UnitTest
|
||||
EXPECT_THAT(m_camera.Translation(), IsCloseTolerance(expectedCameraEndingPosition, 0.01f));
|
||||
}
|
||||
|
||||
TEST_F(CameraInputFixture, PivotRotateCameraInputRotatesYawOffsetByNinetyDegreesWithRequiredPixelDelta)
|
||||
TEST_F(CameraInputFixture, OrbitRotateCameraInputRotatesYawOffsetByNinetyDegreesWithRequiredPixelDelta)
|
||||
{
|
||||
const auto cameraStartingPosition = AZ::Vector3(15.0f, -20.0f, 0.0f);
|
||||
m_targetCamera.m_pivot = cameraStartingPosition;
|
||||
|
||||
m_pivot = AZ::Vector3(10.0f, -10.0f, 0.0f);
|
||||
|
||||
HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ m_pivotChannelId, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(AzFramework::DiscreteInputEvent{ m_orbitChannelId, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(
|
||||
AzFramework::DiscreteInputEvent{ AzFramework::InputDeviceMouse::Button::Left, AzFramework::InputChannel::State::Began });
|
||||
HandleEventAndUpdate(AzFramework::HorizontalMotionEvent{ -PixelMotionDelta });
|
||||
|
||||
@@ -6,10 +6,11 @@
|
||||
*
|
||||
*/
|
||||
|
||||
#include <AzQtComponents/AzQtComponents_Traits_Platform.h>
|
||||
#include <AzQtComponents/Components/Widgets/FileDialog.h>
|
||||
|
||||
#include <QMessageBox>
|
||||
#include <QRegExp>
|
||||
#include <QRegularExpression>
|
||||
|
||||
namespace AzQtComponents
|
||||
{
|
||||
@@ -24,7 +25,12 @@ namespace AzQtComponents
|
||||
// Trigger Qt's save filename dialog
|
||||
// If filePath isn't empty, it means we are prompting again because the filename was invalid,
|
||||
// so pass it instead of the directory so the filename is pre-filled in for the user
|
||||
filePath = QFileDialog::getSaveFileName(parent, caption, (filePath.isEmpty()) ? dir : filePath, filter, selectedFilter, options);
|
||||
QString localSelectedFilter;
|
||||
filePath = QFileDialog::getSaveFileName(parent, caption, (filePath.isEmpty()) ? dir : filePath, filter, &localSelectedFilter, options);
|
||||
if (selectedFilter)
|
||||
{
|
||||
*selectedFilter = localSelectedFilter;
|
||||
}
|
||||
|
||||
if (!filePath.isEmpty())
|
||||
{
|
||||
@@ -32,15 +38,39 @@ namespace AzQtComponents
|
||||
QString fileName = fileInfo.fileName();
|
||||
|
||||
// Check if the filename has any invalid characters
|
||||
QRegExp validFileNameRegex("^[a-zA-Z0-9_\\-./]*$");
|
||||
shouldPromptAgain = !validFileNameRegex.exactMatch(fileName);
|
||||
QRegularExpression validFileNameRegex("^[a-zA-Z0-9_\\-./]*$");
|
||||
QRegularExpressionMatch validFileNameMatch = validFileNameRegex.match(fileName);
|
||||
|
||||
// If the filename had invalid characters, then show a warning message and then we will re-prompt the save filename dialog
|
||||
if (shouldPromptAgain)
|
||||
if (!validFileNameMatch.hasMatch())
|
||||
{
|
||||
QMessageBox::warning(parent, QObject::tr("Invalid filename"),
|
||||
QObject::tr("O3DE assets are restricted to alphanumeric characters, hyphens (-), underscores (_), and dots (.)\n\n%1").arg(fileName));
|
||||
shouldPromptAgain = true;
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
shouldPromptAgain = false;
|
||||
}
|
||||
#if AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_APPLY_MISSING_EXTENSION
|
||||
// If a filter was selected, then make sure that the resulting filename ends with that extension. On systems that use the default QFileDialog,
|
||||
// the extension is not guaranteed to be set in the resulting filename
|
||||
if (FileDialog::ApplyMissingExtension(localSelectedFilter, filePath))
|
||||
{
|
||||
// If an extension had to be applied, then the file dialog did not handle the case of overwriting existing files.
|
||||
// We need to check that condition before we proceed
|
||||
QFileInfo updatedFilePath(filePath);
|
||||
|
||||
if (updatedFilePath.exists())
|
||||
{
|
||||
QMessageBox::StandardButton overwriteSelection = QMessageBox::question(parent,
|
||||
QObject::tr("File exists"),
|
||||
QObject::tr("%1 exists. Do you want to overwrite the existing file?").arg(updatedFilePath.fileName()));
|
||||
shouldPromptAgain = (overwriteSelection == QMessageBox::No);
|
||||
}
|
||||
}
|
||||
#endif // AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_APPLY_MISSING_EXTENSION
|
||||
}
|
||||
else
|
||||
{
|
||||
@@ -51,4 +81,56 @@ namespace AzQtComponents
|
||||
|
||||
return filePath;
|
||||
}
|
||||
|
||||
bool FileDialog::ApplyMissingExtension(const QString& selectedFilter, QString& filePath)
|
||||
{
|
||||
if (selectedFilter.isEmpty())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// According to the QT documentation for QFileDialog, the selected filter will come in the form
|
||||
// <Filter Name> (<filter pattern1> <filter pattern2> .. <filter patternN> )
|
||||
//
|
||||
// For example:
|
||||
// "Images (*.gif *.png *.jpg)"
|
||||
//
|
||||
// Extract the contents of the <filter pattern>(s) inside the parenthesis and split them based on a whitespace or comma
|
||||
const QRegularExpression filterContent(".*\\((?<filters>[^\\)]+)\\)");
|
||||
QRegularExpressionMatch filterContentMatch = filterContent.match(selectedFilter);
|
||||
if (!filterContentMatch.hasMatch())
|
||||
{
|
||||
return false;
|
||||
}
|
||||
QString filterExtensionsString = filterContentMatch.captured("filters");
|
||||
QStringList filterExtensionsFull = filterExtensionsString.split(" ", Qt::SkipEmptyParts);
|
||||
if (filterExtensionsFull.length() <= 0)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
// If there are multiple suffixes in the selected filter, then default to the first one if a suffix needs to be appended
|
||||
QString defaultSuffix = filterExtensionsFull[0].mid(1);
|
||||
|
||||
// Iterate through the filter patterns to see if the current filename matches
|
||||
QFileInfo fileInfo(filePath);
|
||||
bool extensionNeeded = true;
|
||||
for (const QString& filterExtensionFull : filterExtensionsFull)
|
||||
{
|
||||
QString wildcardExpression = QRegularExpression::wildcardToRegularExpression(filterExtensionFull);
|
||||
QRegularExpression filterPattern(wildcardExpression, AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_FILTER_CASE_SENSITIVITY);
|
||||
QRegularExpressionMatch filterPatternMatch = filterPattern.match(fileInfo.fileName());
|
||||
if (filterPatternMatch.hasMatch())
|
||||
{
|
||||
// The filename matches one of the filter patterns already, the extension does not need to be added to the filename
|
||||
extensionNeeded = false;
|
||||
}
|
||||
}
|
||||
if (extensionNeeded)
|
||||
{
|
||||
// If the current (if any) suffix does not match, automatically add the default suffix for the selected filter
|
||||
filePath.append(defaultSuffix);
|
||||
}
|
||||
return extensionNeeded;
|
||||
}
|
||||
} // namespace AzQtComponents
|
||||
|
||||
@@ -24,6 +24,12 @@ namespace AzQtComponents
|
||||
static QString GetSaveFileName(QWidget* parent = nullptr, const QString& caption = QString(),
|
||||
const QString& dir = QString(), const QString& filter = QString(),
|
||||
QString* selectedFilter = nullptr, QFileDialog::Options options = QFileDialog::Options());
|
||||
|
||||
//! Helper method that parses a selected filter from Qt's QFileDialog::getSaveFileName and applies the
|
||||
//! selected filter's extension to the filePath if it doesnt already have the extension. This is needed
|
||||
//! on platforms that do not have a default file dialog (These platforms uses Qt's custom file dialog which will
|
||||
//! not apply the filter's extension automatically on user entered filenames)
|
||||
static bool ApplyMissingExtension(const QString& selectedFilter, QString& filePath);
|
||||
};
|
||||
|
||||
} // namespace AzQtComponents
|
||||
|
||||
@@ -12,4 +12,6 @@ set(FILES
|
||||
../../Utilities/QtWindowUtilities_linux.cpp
|
||||
../../Utilities/ScreenGrabber_linux.cpp
|
||||
../../../Platform/Linux/AzQtComponents/Components/StyledDockWidget_Linux.cpp
|
||||
../../../Platform/Linux/AzQtComponents/AzQtComponents_Traits_Linux.h
|
||||
../../../Platform/Linux/AzQtComponents/AzQtComponents_Traits_Platform.h
|
||||
)
|
||||
|
||||
@@ -12,4 +12,6 @@ set(FILES
|
||||
../../Utilities/QtWindowUtilities_mac.mm
|
||||
../../Utilities/ScreenGrabber_mac.mm
|
||||
../../../Platform/Mac/AzQtComponents/Components/StyledDockWidget_Mac.cpp
|
||||
../../../Platform/Mac/AzQtComponents/AzQtComponents_Traits_Mac.h
|
||||
../../../Platform/Mac/AzQtComponents/AzQtComponents_Traits_Platform.h
|
||||
)
|
||||
|
||||
+2
@@ -17,4 +17,6 @@ set(FILES
|
||||
../../Components/TitleBarOverdrawScreenHandler_win.h
|
||||
../../Components/TitleBarOverdrawScreenHandler_win.cpp
|
||||
../../../Platform/Windows/AzQtComponents/Components/StyledDockWidget_Windows.cpp
|
||||
../../../Platform/Windows/AzQtComponents/AzQtComponents_Traits_Windows.h
|
||||
../../../Platform/Windows/AzQtComponents/AzQtComponents_Traits_Platform.h
|
||||
)
|
||||
|
||||
@@ -0,0 +1,65 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
|
||||
#include <AzTest/AzTest.h>
|
||||
#include <AzQtComponents/Components/Widgets/FileDialog.h>
|
||||
#include <QString>
|
||||
|
||||
TEST(AzQtComponents, ApplyMissingExtension_UpdateMissingExtension_Success)
|
||||
{
|
||||
const QString textFiler{"Text Files (*.txt)"};
|
||||
QString testPath{"testFile"};
|
||||
bool result = AzQtComponents::FileDialog::ApplyMissingExtension(textFiler, testPath);
|
||||
EXPECT_TRUE(result);
|
||||
EXPECT_STRCASEEQ("testFile.txt", testPath.toUtf8().constData());
|
||||
}
|
||||
|
||||
TEST(AzQtComponents, ApplyMissingExtension_NoUpdateExistingExtension_Success)
|
||||
{
|
||||
const QString textFiler{"Text Files (*.txt)"};
|
||||
QString testPath{"testFile.txt"};
|
||||
bool result = AzQtComponents::FileDialog::ApplyMissingExtension(textFiler, testPath);
|
||||
EXPECT_FALSE(result);
|
||||
EXPECT_STRCASEEQ("testFile.txt", testPath.toUtf8().constData());
|
||||
}
|
||||
|
||||
TEST(AzQtComponents, ApplyMissingExtension_UpdateMissingExtensionMultipleExtensionFilter_Success)
|
||||
{
|
||||
const QString textFiler{"Image Files (*.jpg *.bmp *.png)"};
|
||||
QString testPath{"testFile"};
|
||||
bool result = AzQtComponents::FileDialog::ApplyMissingExtension(textFiler, testPath);
|
||||
EXPECT_TRUE(result);
|
||||
EXPECT_STRCASEEQ("testFile.jpg", testPath.toUtf8().constData());
|
||||
}
|
||||
|
||||
TEST(AzQtComponents, ApplyMissingExtension_NoUpdateMissingExtensionMultipleExtensionFilter_Success)
|
||||
{
|
||||
const QString textFiler{"Image Files (*.jpg *.bmp *.png)"};
|
||||
QString testPath{"testFile.png"};
|
||||
bool result = AzQtComponents::FileDialog::ApplyMissingExtension(textFiler, testPath);
|
||||
EXPECT_FALSE(result);
|
||||
EXPECT_STRCASEEQ("testFile.png", testPath.toUtf8().constData());
|
||||
}
|
||||
|
||||
TEST(AzQtComponents, ApplyMissingExtension_NoUpdateMissingExtensionEmptyFilter_Success)
|
||||
{
|
||||
const QString textFiler{""};
|
||||
QString testPath{"testFile"};
|
||||
bool result = AzQtComponents::FileDialog::ApplyMissingExtension(textFiler, testPath);
|
||||
EXPECT_FALSE(result);
|
||||
EXPECT_STRCASEEQ("testFile", testPath.toUtf8().constData());
|
||||
}
|
||||
|
||||
TEST(AzQtComponents, ApplyMissingExtension_NoUpdateMissingExtensionInvalidFilter_Success)
|
||||
{
|
||||
const QString textFiler{"Bad Filter!!"};
|
||||
QString testPath{"testFile"};
|
||||
bool result = AzQtComponents::FileDialog::ApplyMissingExtension(textFiler, testPath);
|
||||
EXPECT_FALSE(result);
|
||||
EXPECT_STRCASEEQ("testFile", testPath.toUtf8().constData());
|
||||
}
|
||||
@@ -9,6 +9,7 @@
|
||||
set(FILES
|
||||
Tests/AzQtComponentTests.cpp
|
||||
Tests/ColorControllerTests.cpp
|
||||
Tests/FileDialogTests.cpp
|
||||
Tests/FloatToStringConversionTests.cpp
|
||||
Tests/HexParsingTests.cpp
|
||||
Tests/StyleSheetCacheTests.cpp
|
||||
|
||||
@@ -10,6 +10,8 @@ if(NOT PAL_TRAIT_BUILD_HOST_TOOLS)
|
||||
return()
|
||||
endif()
|
||||
|
||||
ly_get_list_relative_pal_filename(pal_dir ${CMAKE_CURRENT_LIST_DIR}/Platform/${PAL_PLATFORM_NAME})
|
||||
|
||||
ly_add_target(
|
||||
NAME AzQtComponents SHARED
|
||||
NAMESPACE AZ
|
||||
@@ -26,6 +28,7 @@ ly_add_target(
|
||||
AzQtComponents
|
||||
PUBLIC
|
||||
.
|
||||
${pal_dir}
|
||||
COMPILE_DEFINITIONS
|
||||
PRIVATE
|
||||
AZ_QT_COMPONENTS_EXPORT_SYMBOLS
|
||||
@@ -53,6 +56,7 @@ ly_add_target(
|
||||
.
|
||||
AzQtComponents
|
||||
AzQtComponents/Gallery
|
||||
${pal_dir}
|
||||
BUILD_DEPENDENCIES
|
||||
PRIVATE
|
||||
3rdParty::Qt::Svg
|
||||
@@ -86,6 +90,7 @@ if(PAL_TRAIT_BUILD_TESTS_SUPPORTED)
|
||||
PRIVATE
|
||||
Tests
|
||||
AzQtComponents
|
||||
${pal_dir}
|
||||
BUILD_DEPENDENCIES
|
||||
PRIVATE
|
||||
AZ::AzQtComponents
|
||||
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#define AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_APPLY_MISSING_EXTENSION 1
|
||||
#define AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_FILTER_CASE_SENSITIVITY QRegularExpression::NoPatternOption
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include <AzQtComponents/AzQtComponents_Traits_Linux.h>
|
||||
@@ -0,0 +1,11 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#define AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_APPLY_MISSING_EXTENSION 0
|
||||
#define AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_FILTER_CASE_SENSITIVITY QRegularExpression::NoPatternOption
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include <AzQtComponents/AzQtComponents_Traits_Mac.h>
|
||||
+10
@@ -0,0 +1,10 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#include <AzQtComponents/AzQtComponents_Traits_Windows.h>
|
||||
+11
@@ -0,0 +1,11 @@
|
||||
/*
|
||||
* Copyright (c) Contributors to the Open 3D Engine Project.
|
||||
* For complete copyright and license terms please see the LICENSE at the root of this distribution.
|
||||
*
|
||||
* SPDX-License-Identifier: Apache-2.0 OR MIT
|
||||
*
|
||||
*/
|
||||
#pragma once
|
||||
|
||||
#define AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_APPLY_MISSING_EXTENSION 0
|
||||
#define AZ_TRAIT_AZQTCOMPONENTS_FILE_DIALOG_FILTER_CASE_SENSITIVITY QRegularExpression::CaseInsensitiveOption
|
||||
@@ -410,7 +410,7 @@ namespace AzToolsFramework
|
||||
filter.append(ext);
|
||||
if (i < n - 1)
|
||||
{
|
||||
filter.append(", ");
|
||||
filter.append(" ");
|
||||
}
|
||||
}
|
||||
filter.append(")");
|
||||
|
||||
@@ -224,6 +224,7 @@ namespace AzToolsFramework
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
AZ::Data::SerializedAssetTracker* assetTracker = settings.m_metadata.Find<AZ::Data::SerializedAssetTracker>();
|
||||
|
||||
referencedAssets = AZStd::move(assetTracker->GetTrackedAssets());
|
||||
@@ -245,6 +246,30 @@ namespace AzToolsFramework
|
||||
entityIdMapper.SetEntityIdGenerationApproach(InstanceEntityIdMapper::EntityIdGenerationApproach::Random);
|
||||
}
|
||||
|
||||
// some assets may come in from the JSON serialzier with no AssetID, but have an asset hint
|
||||
// this attempts to fix up the assets using the assetHint field
|
||||
auto fixUpInvalidAssets = [](AZ::Data::Asset<AZ::Data::AssetData>& asset)
|
||||
{
|
||||
if (!asset.GetId().IsValid() && !asset.GetHint().empty())
|
||||
{
|
||||
AZ::Data::AssetId assetId;
|
||||
AZ::Data::AssetCatalogRequestBus::BroadcastResult(
|
||||
assetId,
|
||||
&AZ::Data::AssetCatalogRequestBus::Events::GetAssetIdByPath,
|
||||
asset.GetHint().c_str(),
|
||||
AZ::Data::s_invalidAssetType,
|
||||
false);
|
||||
|
||||
if (assetId.IsValid())
|
||||
{
|
||||
asset.Create(assetId, true);
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
auto tracker = AZ::Data::SerializedAssetTracker{};
|
||||
tracker.SetAssetFixUp(fixUpInvalidAssets);
|
||||
|
||||
AZ::JsonDeserializerSettings settings;
|
||||
// The InstanceEntityIdMapper is registered twice because it's used in several places during deserialization where one is
|
||||
// specific for the InstanceEntityIdMapper and once for the generic JsonEntityIdMapper. Because the Json Serializer's meta
|
||||
@@ -252,16 +277,17 @@ namespace AzToolsFramework
|
||||
settings.m_metadata.Add(static_cast<AZ::JsonEntityIdSerializer::JsonEntityIdMapper*>(&entityIdMapper));
|
||||
settings.m_metadata.Add(&entityIdMapper);
|
||||
settings.m_metadata.Create<InstanceEntityScrubber>(newlyAddedEntities);
|
||||
settings.m_metadata.Add(tracker);
|
||||
|
||||
AZStd::string scratchBuffer;
|
||||
auto issueReportingCallback = [&scratchBuffer](
|
||||
AZStd::string_view message, AZ::JsonSerializationResult::ResultCode result,
|
||||
AZStd::string_view path) -> AZ::JsonSerializationResult::ResultCode
|
||||
AZStd::string_view message, AZ::JsonSerializationResult::ResultCode result,
|
||||
AZStd::string_view path) -> AZ::JsonSerializationResult::ResultCode
|
||||
{
|
||||
return Internal::JsonIssueReporter(scratchBuffer, message, result, path);
|
||||
};
|
||||
settings.m_reporting = AZStd::move(issueReportingCallback);
|
||||
|
||||
|
||||
AZ::JsonSerializationResult::ResultCode result = AZ::JsonSerialization::Load(instance, prefabDom, settings);
|
||||
|
||||
AZ::Data::AssetManager::Instance().ResumeAssetRelease();
|
||||
|
||||
+1
-1
@@ -1025,7 +1025,7 @@ namespace AzToolsFramework
|
||||
->Attribute(AZ::Edit::Attributes::ViewportIcon, "Icons/Components/Viewport/LuaScript.svg")
|
||||
->Attribute(AZ::Edit::Attributes::PrimaryAssetType, AZ::AzTypeInfo<AZ::ScriptAsset>::Uuid())
|
||||
->Attribute(AZ::Edit::Attributes::ViewportIcon, "Icons/Components/Viewport/Script.png")
|
||||
->Attribute(AZ::Edit::Attributes::HelpPageURL, "https://o3de.org/docs/user-guide/components/reference/lua-script/")
|
||||
->Attribute(AZ::Edit::Attributes::HelpPageURL, "https://o3de.org/docs/user-guide/components/reference/scripting/lua-script/")
|
||||
->DataElement("AssetRef", &ScriptEditorComponent::m_scriptAsset, "Script", "Which script to use")
|
||||
->Attribute(AZ::Edit::Attributes::ChangeNotify, &ScriptEditorComponent::ScriptHasChanged)
|
||||
->Attribute("BrowseIcon", ":/stylesheet/img/UI20/browse-edit-select-files.svg")
|
||||
|
||||
+2
-42
@@ -103,10 +103,6 @@ namespace AzToolsFramework
|
||||
static const char* const ResetEntityTransformDesc = "Reset transform based on manipulator mode";
|
||||
static const char* const ResetManipulatorTitle = "Reset Manipulator";
|
||||
static const char* const ResetManipulatorDesc = "Reset the manipulator to recenter it on the selected entity";
|
||||
static const char* const ResetTransformLocalTitle = "Reset Transform (Local)";
|
||||
static const char* const ResetTransformLocalDesc = "Reset transform to local space";
|
||||
static const char* const ResetTransformWorldTitle = "Reset Transform (World)";
|
||||
static const char* const ResetTransformWorldDesc = "Reset transform to world space";
|
||||
|
||||
static const char* const EntityBoxSelectUndoRedoDesc = "Box Select Entities";
|
||||
static const char* const EntityDeselectUndoRedoDesc = "Deselect Entity";
|
||||
@@ -2424,45 +2420,9 @@ namespace AzToolsFramework
|
||||
|
||||
AddAction(
|
||||
m_actions, { QKeySequence(Qt::CTRL + Qt::Key_R) }, EditResetManipulator, ResetManipulatorTitle, ResetManipulatorDesc,
|
||||
AZStd::bind(AZStd::mem_fn(&EditorTransformComponentSelection::DelegateClearManipulatorOverride), this));
|
||||
|
||||
AddAction(
|
||||
m_actions, { QKeySequence(Qt::ALT + Qt::Key_R) }, EditResetLocal, ResetTransformLocalTitle, ResetTransformLocalDesc,
|
||||
[this]()
|
||||
[this]
|
||||
{
|
||||
switch (m_mode)
|
||||
{
|
||||
case Mode::Rotation:
|
||||
ResetOrientationForSelectedEntitiesLocal();
|
||||
break;
|
||||
case Mode::Scale:
|
||||
CopyScaleToSelectedEntitiesIndividualWorld(1.0f);
|
||||
break;
|
||||
case Mode::Translation:
|
||||
// do nothing
|
||||
break;
|
||||
}
|
||||
});
|
||||
|
||||
AddAction(
|
||||
m_actions, { QKeySequence(Qt::SHIFT + Qt::Key_R) }, EditResetWorld, ResetTransformWorldTitle, ResetTransformWorldDesc,
|
||||
[this]()
|
||||
{
|
||||
switch (m_mode)
|
||||
{
|
||||
case Mode::Rotation:
|
||||
{
|
||||
// begin an undo batch so operations inside CopyOrientation... and
|
||||
// DelegateClear... are grouped into a single undo/redo
|
||||
ScopedUndoBatch undoBatch{ ResetTransformWorldTitle };
|
||||
CopyOrientationToSelectedEntitiesIndividual(AZ::Quaternion::CreateIdentity());
|
||||
ClearManipulatorOrientationOverride();
|
||||
}
|
||||
break;
|
||||
case Mode::Scale:
|
||||
case Mode::Translation:
|
||||
break;
|
||||
}
|
||||
DelegateClearManipulatorOverride();
|
||||
});
|
||||
|
||||
AddAction(
|
||||
|
||||
-2
@@ -31,8 +31,6 @@ namespace AzToolsFramework
|
||||
constexpr inline AZ::Crc32 EditPivot = AZ_CRC_CE("com.o3de.action.editortransform.editpivot");
|
||||
constexpr inline AZ::Crc32 EditReset = AZ_CRC_CE("com.o3de.action.editortransform.editreset");
|
||||
constexpr inline AZ::Crc32 EditResetManipulator = AZ_CRC_CE("com.o3de.action.editortransform.editresetmanipulator");
|
||||
constexpr inline AZ::Crc32 EditResetLocal = AZ_CRC_CE("com.o3de.action.editortransform.editresetlocal");
|
||||
constexpr inline AZ::Crc32 EditResetWorld = AZ_CRC_CE("com.o3de.action.editortransform.editresetworld");
|
||||
constexpr inline AZ::Crc32 ViewportUiVisible = AZ_CRC_CE("com.o3de.action.editortransform.viewportuivisible");
|
||||
//@}
|
||||
|
||||
|
||||
@@ -25,7 +25,7 @@ namespace UnitTest
|
||||
R"X(Executing RC.EXE: '"E:\lyengine\dev\windows\bin\profile\rc.exe" "E:/Directory/File.tga")X",
|
||||
R"X(Executing RC.EXE with working directory : '')X",
|
||||
R"X(ResourceCompiler 64 - bit DEBUG)X",
|
||||
R"X(Platform support : PC, PowerVR, etc2Comp)X",
|
||||
R"X(Platform support : PC, PowerVR)X",
|
||||
R"X(Version 1.1.8.6 Nov 5 2018 13 : 28 : 28)X"
|
||||
};
|
||||
|
||||
|
||||
@@ -222,6 +222,9 @@ void UpdateFPExceptionsMaskForThreads()
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
int DebugCallStack::handleException(EXCEPTION_POINTERS* exception_pointer)
|
||||
{
|
||||
AZ_TracePrintf("Exit", "Exception with exit code: 0x%x", exception_pointer->ExceptionRecord->ExceptionCode);
|
||||
AZ::Debug::Trace::PrintCallstack("Exit");
|
||||
|
||||
if (gEnv == NULL)
|
||||
{
|
||||
return EXCEPTION_EXECUTE_HANDLER;
|
||||
|
||||
@@ -395,7 +395,7 @@ namespace LUAEditor
|
||||
|
||||
void LUAEditorMainWindow::OnLuaDocumentation()
|
||||
{
|
||||
QDesktopServices::openUrl(QUrl("http://docs.aws.amazon.com/lumberyard/latest/developerguide/lua-scripting-intro.html"));
|
||||
QDesktopServices::openUrl(QUrl("https://o3de.org/docs/user-guide/scripting/lua/"));
|
||||
}
|
||||
|
||||
void LUAEditorMainWindow::OnMenuCloseCurrentWindow()
|
||||
|
||||
@@ -24,7 +24,7 @@ namespace AWSCore
|
||||
/**
|
||||
* Add required SystemComponents to the SystemEntity.
|
||||
*/
|
||||
virtual AZ::ComponentTypeList GetRequiredSystemComponents() const override;
|
||||
AZ::ComponentTypeList GetRequiredSystemComponents() const override;
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
@@ -42,7 +42,7 @@ namespace AWSCore
|
||||
|
||||
|
||||
AWSCoreConfiguration();
|
||||
~AWSCoreConfiguration() = default;
|
||||
~AWSCoreConfiguration() override = default;
|
||||
|
||||
void ActivateConfig();
|
||||
void DeactivateConfig();
|
||||
|
||||
@@ -23,7 +23,7 @@ namespace AWSCore
|
||||
{
|
||||
public:
|
||||
AWSDefaultCredentialHandler();
|
||||
~AWSDefaultCredentialHandler() = default;
|
||||
~AWSDefaultCredentialHandler() override = default;
|
||||
|
||||
//! Activate handler and its credentials provider, make sure activation
|
||||
//! invoked after AWSNativeSDK init to avoid memory leak
|
||||
|
||||
+3
-4
@@ -15,13 +15,12 @@
|
||||
namespace AWSCore
|
||||
{
|
||||
//! Defines AWSCoreAttributionConsent QT dialog as QT message box.
|
||||
class AWSCoreAttributionConsentDialog :
|
||||
public QMessageBox
|
||||
class AWSCoreAttributionConsentDialog
|
||||
: public QMessageBox
|
||||
{
|
||||
public:
|
||||
AZ_CLASS_ALLOCATOR(AWSCoreAttributionConsentDialog, AZ::SystemAllocator, 0);
|
||||
AWSCoreAttributionConsentDialog();
|
||||
virtual ~AWSCoreAttributionConsentDialog() = default;
|
||||
|
||||
~AWSCoreAttributionConsentDialog() override = default;
|
||||
};
|
||||
} // namespace AWSCore
|
||||
|
||||
@@ -18,4 +18,4 @@ namespace AWSCore
|
||||
static constexpr char AwsAttributionAttributeKeyActiveAWSGems[] = "aws_gems";
|
||||
static constexpr char AwsAttributionAttributeKeyTimestamp[] = "timestamp";
|
||||
|
||||
} // namespace AWSCOre
|
||||
} // namespace AWSCore
|
||||
|
||||
@@ -34,7 +34,7 @@ namespace AWSCore
|
||||
"Failed to launch Resource Mapping Tool, please check <a href=\"file:///%s\">logs</a> for details.";
|
||||
|
||||
AWSCoreEditorMenu(const QString& text);
|
||||
~AWSCoreEditorMenu();
|
||||
~AWSCoreEditorMenu() override;
|
||||
|
||||
private:
|
||||
QAction* AddExternalLinkAction(const AZStd::string& name, const AZStd::string& url, const AZStd::string& icon = "");
|
||||
|
||||
@@ -71,7 +71,7 @@ namespace AWSCore
|
||||
};
|
||||
|
||||
AWSResourceMappingManager();
|
||||
~AWSResourceMappingManager() = default;
|
||||
~AWSResourceMappingManager() override = default;
|
||||
|
||||
void ActivateManager();
|
||||
void DeactivateManager();
|
||||
|
||||
@@ -64,9 +64,6 @@ namespace AWSCore
|
||||
|
||||
/// Initialize an AwsApiClientJobConfig object.
|
||||
///
|
||||
/// \param DefaultConfigType - the type of the config object from which
|
||||
/// default values will be taken.
|
||||
///
|
||||
/// \param defaultConfig - the config object that provides values when
|
||||
/// no override has been set in this object. The default is nullptr, which
|
||||
/// will cause a default value to be used.
|
||||
@@ -83,10 +80,10 @@ namespace AWSCore
|
||||
}
|
||||
}
|
||||
|
||||
virtual ~AwsApiClientJobConfig() = default;
|
||||
~AwsApiClientJobConfig() override = default;
|
||||
|
||||
/// Gets a client initialized used currently applied settings. If
|
||||
/// any settings change after first use, code must call
|
||||
/// any settings change after first use, code must call
|
||||
/// ApplySettings before those changes will take effect.
|
||||
std::shared_ptr<ClientType> GetClient() override
|
||||
{
|
||||
@@ -112,7 +109,7 @@ namespace AWSCore
|
||||
}
|
||||
else
|
||||
{
|
||||
// If no explict credenitals are provided then AWS C++ SDK will perform standard search
|
||||
// If no explicit credentials are provided then AWS C++ SDK will perform standard search
|
||||
return std::make_shared<ClientType>(Aws::Auth::AWSCredentials(), GetClientConfiguration());
|
||||
}
|
||||
}
|
||||
|
||||
@@ -14,14 +14,12 @@
|
||||
|
||||
namespace AWSCore
|
||||
{
|
||||
|
||||
/// Base class for all AWS jobs. Primarily exists so that
|
||||
/// Base class for all AWS jobs. Primarily exists so that
|
||||
/// AwsApiJob::s_config can be used for settings that apply to
|
||||
/// all AWS jobs.
|
||||
class AwsApiJob
|
||||
: public AZ::Job
|
||||
{
|
||||
|
||||
public:
|
||||
// To use a different allocator, extend this class and use this macro.
|
||||
AZ_CLASS_ALLOCATOR(AwsApiJob, AZ::SystemAllocator, 0);
|
||||
@@ -33,11 +31,10 @@ namespace AWSCore
|
||||
|
||||
protected:
|
||||
AwsApiJob(bool isAutoDelete, IConfig* config = GetDefaultConfig());
|
||||
virtual ~AwsApiJob();
|
||||
~AwsApiJob() override = default;
|
||||
|
||||
/// Used for error messages.
|
||||
static const char* COMPONENT_DISPLAY_NAME;
|
||||
|
||||
};
|
||||
|
||||
} // namespace AWSCore
|
||||
|
||||
@@ -96,9 +96,6 @@ namespace AWSCore
|
||||
|
||||
/// Initialize an AwsApiClientJobConfig object.
|
||||
///
|
||||
/// \param DefaultConfigType - the type of the config object from which
|
||||
/// default values will be taken.
|
||||
///
|
||||
/// \param defaultConfig - the config object that provides values when
|
||||
/// no override has been set in this object. The default is nullptr, which
|
||||
/// will cause a default value to be used.
|
||||
@@ -146,7 +143,7 @@ namespace AWSCore
|
||||
#endif
|
||||
Override<Aws::String> caFile;
|
||||
|
||||
/// Applys settings changes made after first use.
|
||||
/// Applies settings changes made after first use.
|
||||
virtual void ApplySettings();
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
@@ -217,7 +214,7 @@ namespace AWSCore
|
||||
: protected AWSCoreNotificationsBus::Handler
|
||||
{
|
||||
public:
|
||||
~AwsApiJobConfigHolder()
|
||||
~AwsApiJobConfigHolder() override
|
||||
{
|
||||
AWSCoreNotificationsBus::Handler::BusDisconnect();
|
||||
}
|
||||
|
||||
@@ -145,10 +145,10 @@ namespace AWSCore
|
||||
AWS_API_REQUEST_TRAITS_TEMPLATE_DEFINITION_HELPER
|
||||
typename AWS_API_REQUEST_TRAITS_TEMPLATE_INSTANCE_HELPER::AsyncFunctionType AWS_API_REQUEST_TRAITS_TEMPLATE_INSTANCE_HELPER::AsyncFunction = _AsyncFunction;
|
||||
|
||||
/// Macro that simplifies the declaration of an AwsRequstJob that has a result.
|
||||
/// Macro that simplifies the declaration of an AwsRequestJob that has a result.
|
||||
#define AWS_API_REQUEST_JOB(SERVICE, REQUEST) AWSCore::AwsApiRequestJob<AWS_API_REQUEST_TRAITS(SERVICE, REQUEST)>
|
||||
|
||||
/// Macro that simplifies the declaration of an AwsRequstJob that has no result.
|
||||
/// Macro that simplifies the declaration of an AwsRequestJob that has no result.
|
||||
#define AWS_API_REQUEST_JOB_NO_RESULT(SERVICE, REQUEST) AWSCore::AwsApiRequestJob<AWS_API_REQUEST_TRAITS_NO_RESULT(SERVICE, REQUEST)>
|
||||
|
||||
/// An Az::Job that that executes a specific AWS request.
|
||||
@@ -257,7 +257,7 @@ namespace AWSCore
|
||||
/// of request data until your running on the job's worker thread,
|
||||
/// instead of setting the request data before calling Start.
|
||||
///
|
||||
/// \param true if the request should be made.
|
||||
/// \return true if the request should be made.
|
||||
virtual bool PrepareRequest()
|
||||
{
|
||||
return true;
|
||||
|
||||
@@ -39,7 +39,7 @@ namespace AWSCore
|
||||
: public AZ::ComponentBus
|
||||
{
|
||||
public:
|
||||
virtual ~HttpClientComponentNotifications() {}
|
||||
~HttpClientComponentNotifications() override = default;
|
||||
virtual void OnHttpRequestSuccess(int responseCode, AZStd::string responseBody) {}
|
||||
virtual void OnHttpRequestFailure(int responseCode) {}
|
||||
};
|
||||
@@ -55,7 +55,7 @@ namespace AWSCore
|
||||
{
|
||||
public:
|
||||
AZ_COMPONENT(HttpClientComponent, "{23ECDBDF-129A-4670-B9B4-1E0B541ACD61}");
|
||||
virtual ~HttpClientComponent() = default;
|
||||
~HttpClientComponent() override = default;
|
||||
|
||||
void Init() override;
|
||||
void Activate() override;
|
||||
|
||||
@@ -178,7 +178,7 @@ namespace AWSCore
|
||||
};
|
||||
|
||||
/// Override to process the response to the HTTP request before callbacks are fired.
|
||||
/// WARNING: This gets called on the job's thread, so observe thread safety precations.
|
||||
/// WARNING: This gets called on the job's thread, so observe thread safety precautions.
|
||||
virtual void ProcessResponse(const std::shared_ptr<Aws::Http::HttpResponse>& response)
|
||||
{
|
||||
AZ_UNUSED(response);
|
||||
|
||||
@@ -29,24 +29,24 @@ namespace AWSCore
|
||||
Ch Peek() const
|
||||
{
|
||||
int c = m_is.peek();
|
||||
return c == std::char_traits<char>::eof() ? '\0' : (Ch)c;
|
||||
return c == std::char_traits<char>::eof() ? '\0' : static_cast<Ch>(c);
|
||||
}
|
||||
|
||||
Ch Take()
|
||||
{
|
||||
int c = m_is.get();
|
||||
return c == std::char_traits<char>::eof() ? '\0' : (Ch)c;
|
||||
return c == std::char_traits<char>::eof() ? '\0' : static_cast<Ch>(c);
|
||||
}
|
||||
|
||||
size_t Tell() const
|
||||
{
|
||||
return (size_t)m_is.tellg();
|
||||
return static_cast<size_t>(m_is.tellg());
|
||||
}
|
||||
|
||||
Ch* PutBegin()
|
||||
{
|
||||
AZ_Assert(false, "Not Implemented");
|
||||
return 0;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
void Put(Ch)
|
||||
|
||||
@@ -161,7 +161,7 @@ namespace AWSCore
|
||||
}
|
||||
|
||||
/// Write JSON format content directly to the writer's output stream.
|
||||
/// This can be used to efficently output static content.
|
||||
/// This can be used to efficiently output static content.
|
||||
bool WriteJson(const Ch* json)
|
||||
{
|
||||
if (json)
|
||||
@@ -182,7 +182,7 @@ namespace AWSCore
|
||||
}
|
||||
|
||||
/// Write an object. The object can implement a WriteJson function
|
||||
/// or you can provide an GobalWriteJson template function
|
||||
/// or you can provide an GlobalWriteJson template function
|
||||
/// specialization.
|
||||
template<class ObjectType>
|
||||
bool Object(const ObjectType& obj)
|
||||
|
||||
@@ -36,7 +36,7 @@ namespace AWSCore
|
||||
class RequestBuilder
|
||||
{
|
||||
public:
|
||||
RequestBuilder() = default;
|
||||
RequestBuilder();
|
||||
|
||||
/// Converts the provided object to JSON and sends it as the
|
||||
/// body of the request. The object can implement the following
|
||||
|
||||
@@ -20,7 +20,7 @@ namespace AWSCore
|
||||
{
|
||||
|
||||
public:
|
||||
virtual const AZStd::string GetServiceUrl() = 0;
|
||||
virtual AZStd::string GetServiceUrl() = 0;
|
||||
};
|
||||
|
||||
/// Encapsulates what code needs to know about a service in order to
|
||||
@@ -81,9 +81,6 @@ namespace AWSCore
|
||||
|
||||
/// Initialize an ServiceClientJobConfig object.
|
||||
///
|
||||
/// \param DefaultConfigType - the type of the config object from which
|
||||
/// default values will be taken.
|
||||
///
|
||||
/// \param defaultConfig - the config object that provides values when
|
||||
/// no override has been set in this object. The default is nullptr, which
|
||||
/// will cause a default value to be used.
|
||||
@@ -102,7 +99,7 @@ namespace AWSCore
|
||||
|
||||
/// This implementation assumes the caller will cache this value as
|
||||
/// needed. See it's use in ServiceRequestJobConfig.
|
||||
const AZStd::string GetServiceUrl() override
|
||||
AZStd::string GetServiceUrl() override
|
||||
{
|
||||
if (endpointOverride.has_value())
|
||||
{
|
||||
|
||||
@@ -119,7 +119,7 @@ namespace AWSCore
|
||||
Error error;
|
||||
|
||||
/// Determines if the AWS credentials, as supplied by the credentialsProvider from
|
||||
/// the ServiceReqestJobConfig object (which defaults to the user's credentials),
|
||||
/// the ServiceRequestJobConfig object (which defaults to the user's credentials),
|
||||
/// are used to sign the request. The default is true. Override this and return false
|
||||
/// if calling a public API and want to avoid the overhead of signing requests.
|
||||
bool UseAWSCredentials() {
|
||||
@@ -565,13 +565,11 @@ namespace AWSCore
|
||||
}
|
||||
|
||||
AZStd::string requestContent;
|
||||
AZStd::string responseContent;
|
||||
|
||||
std::istreambuf_iterator<AZStd::string::value_type> eos;
|
||||
|
||||
std::shared_ptr<Aws::IOStream> requestStream = response->GetOriginatingRequest().GetContentBody();
|
||||
if (requestStream)
|
||||
{
|
||||
std::istreambuf_iterator<AZStd::string::value_type> eos;
|
||||
requestStream->clear();
|
||||
requestStream->seekg(0);
|
||||
requestContent = AZStd::string{ std::istreambuf_iterator<AZStd::string::value_type>(*requestStream.get()),eos };
|
||||
@@ -584,7 +582,7 @@ namespace AWSCore
|
||||
Aws::IOStream& responseStream = response->GetResponseBody();
|
||||
responseStream.clear();
|
||||
responseStream.seekg(0);
|
||||
responseContent = AZStd::string{ std::istreambuf_iterator<AZStd::string::value_type>(responseStream),responseEos };
|
||||
AZStd::string responseContent = AZStd::string{ std::istreambuf_iterator<AZStd::string::value_type>(responseStream), responseEos };
|
||||
responseContent = EscapePercentCharsInString(responseContent);
|
||||
responseStream.seekg(0);
|
||||
|
||||
|
||||
@@ -44,9 +44,6 @@ namespace AWSCore
|
||||
|
||||
/// Initialize an ServiceRequestJobConfig object.
|
||||
///
|
||||
/// \param DefaultConfigType - the type of the config object from which
|
||||
/// default values will be taken.
|
||||
///
|
||||
/// \param defaultConfig - the config object that provides values when
|
||||
/// no override has been set in this object. The default is nullptr, which
|
||||
/// will cause a default value to be used.
|
||||
|
||||
@@ -79,7 +79,7 @@ namespace AWSCore
|
||||
QMenuBar* menuBar = mainWindow->menuBar();
|
||||
QList<QAction*> actionList = menuBar->actions();
|
||||
QAction* insertPivot = nullptr;
|
||||
for (QList<QAction*>::iterator itr = actionList.begin(); itr != actionList.end(); itr++)
|
||||
for (QList<QAction*>::iterator itr = actionList.begin(); itr != actionList.end(); ++itr)
|
||||
{
|
||||
if (QString::compare((*itr)->text(), EDITOR_HELP_MENU_TEXT) == 0)
|
||||
{
|
||||
@@ -88,7 +88,7 @@ namespace AWSCore
|
||||
}
|
||||
}
|
||||
|
||||
auto menu = m_awsCoreEditorManager->GetAWSCoreEditorMenu();
|
||||
const auto menu = m_awsCoreEditorManager->GetAWSCoreEditorMenu();
|
||||
if (insertPivot)
|
||||
{
|
||||
menuBar->insertMenu(insertPivot, menu);
|
||||
|
||||
@@ -35,8 +35,7 @@ namespace AWSCore
|
||||
this->setDefaultButton(QMessageBox::Save);
|
||||
this->button(QMessageBox::Cancel)->hide();
|
||||
this->setIcon(QMessageBox::Information);
|
||||
QGridLayout* layout = (QGridLayout*)this->layout();
|
||||
if (layout)
|
||||
if (QGridLayout* layout = static_cast<QGridLayout*>(this->layout()))
|
||||
{
|
||||
layout->setVerticalSpacing(20);
|
||||
layout->setHorizontalSpacing(10);
|
||||
|
||||
@@ -68,19 +68,19 @@ namespace AWSCore
|
||||
AZ_Assert(fileIO, "File IO is not initialized.");
|
||||
|
||||
// Resolve path to editor_aws_preferences.setreg
|
||||
AZStd::string editorAWSPreferencesFilePath =
|
||||
const AZStd::string editorAWSPreferencesFilePath =
|
||||
AZStd::string::format("@user@/%s/%s", AZ::SettingsRegistryInterface::RegistryFolder, EditorAWSPreferencesFileName);
|
||||
AZStd::array<char, AZ::IO::MaxPathLength> resolvedPathAWSPreference{};
|
||||
if (!fileIO->ResolvePath(editorAWSPreferencesFilePath.c_str(), resolvedPathAWSPreference.data(), resolvedPathAWSPreference.size()))
|
||||
AZ::IO::FixedMaxPath resolvedPathAWSPreference;
|
||||
if (!fileIO->ResolvePath(resolvedPathAWSPreference, AZ::IO::PathView(editorAWSPreferencesFilePath)))
|
||||
{
|
||||
AZ_Warning("AWSAttributionManager", false, "Error resolving path %s", resolvedPathAWSPreference.data());
|
||||
AZ_Warning("AWSAttributionManager", false, "Error resolving path %s", resolvedPathAWSPreference.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
if (fileIO->Exists(resolvedPathAWSPreference.data()))
|
||||
if (fileIO->Exists(resolvedPathAWSPreference.c_str()))
|
||||
{
|
||||
m_settingsRegistry->MergeSettingsFile(
|
||||
resolvedPathAWSPreference.data(), AZ::SettingsRegistryInterface::Format::JsonMergePatch, "");
|
||||
resolvedPathAWSPreference.String(), AZ::SettingsRegistryInterface::Format::JsonMergePatch, "");
|
||||
}
|
||||
}
|
||||
|
||||
@@ -136,8 +136,8 @@ namespace AWSCore
|
||||
return true;
|
||||
}
|
||||
|
||||
AZStd::chrono::seconds lastSendTimeStamp = AZStd::chrono::seconds(lastSendTimeStampSeconds);
|
||||
AZStd::chrono::seconds secondsSinceLastSend =
|
||||
const AZStd::chrono::seconds lastSendTimeStamp = AZStd::chrono::seconds(lastSendTimeStampSeconds);
|
||||
const AZStd::chrono::seconds secondsSinceLastSend =
|
||||
AZStd::chrono::duration_cast<AZStd::chrono::seconds>(AZStd::chrono::system_clock::now().time_since_epoch()) - lastSendTimeStamp;
|
||||
if (static_cast<AZ::u64>(secondsSinceLastSend.count()) >= delayInSeconds)
|
||||
{
|
||||
@@ -154,7 +154,7 @@ namespace AWSCore
|
||||
if (credentialResult.result)
|
||||
{
|
||||
std::shared_ptr<Aws::Auth::AWSCredentialsProvider> provider = credentialResult.result;
|
||||
auto creds = provider->GetAWSCredentials();
|
||||
const auto creds = provider->GetAWSCredentials();
|
||||
if (!creds.IsEmpty())
|
||||
{
|
||||
return true;
|
||||
@@ -200,9 +200,13 @@ namespace AWSCore
|
||||
AZ_Assert(fileIO, "File IO is not initialized.");
|
||||
|
||||
// Resolve path to editor_aws_preferences.setreg
|
||||
AZStd::string editorPreferencesFilePath = AZStd::string::format("@user@/%s/%s", AZ::SettingsRegistryInterface::RegistryFolder, EditorAWSPreferencesFileName);
|
||||
AZStd::array<char, AZ::IO::MaxPathLength> resolvedPath {};
|
||||
fileIO->ResolvePath(editorPreferencesFilePath.c_str(), resolvedPath.data(), resolvedPath.size());
|
||||
const AZStd::string editorPreferencesFilePath = AZStd::string::format("@user@/%s/%s", AZ::SettingsRegistryInterface::RegistryFolder, EditorAWSPreferencesFileName);
|
||||
AZ::IO::FixedMaxPath resolvedPathAWSPreference;
|
||||
if (!fileIO->ResolvePath(resolvedPathAWSPreference, AZ::IO::PathView(editorPreferencesFilePath)))
|
||||
{
|
||||
AZ_Warning("AWSAttributionManager", false, "Error resolving path %s", editorPreferencesFilePath.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
AZ::SettingsRegistryMergeUtils::DumperSettings dumperSettings;
|
||||
dumperSettings.m_prettifyOutput = true;
|
||||
@@ -215,14 +219,14 @@ namespace AWSCore
|
||||
{
|
||||
AZ_Warning(
|
||||
"AWSAttributionManager", false, R"(Unable to save changes to the Editor AWS Preferences registry file at "%s"\n)",
|
||||
resolvedPath.data());
|
||||
resolvedPathAWSPreference.c_str());
|
||||
return;
|
||||
}
|
||||
|
||||
bool saved {};
|
||||
constexpr auto configurationMode =
|
||||
AZ::IO::SystemFile::SF_OPEN_CREATE | AZ::IO::SystemFile::SF_OPEN_CREATE_PATH | AZ::IO::SystemFile::SF_OPEN_WRITE_ONLY;
|
||||
if (AZ::IO::SystemFile outputFile; outputFile.Open(resolvedPath.data(), configurationMode))
|
||||
if (AZ::IO::SystemFile outputFile; outputFile.Open(resolvedPathAWSPreference.c_str(), configurationMode))
|
||||
{
|
||||
saved = outputFile.Write(stringBuffer.data(), stringBuffer.size()) == stringBuffer.size();
|
||||
}
|
||||
|
||||
@@ -54,7 +54,7 @@ namespace AWSCore
|
||||
{
|
||||
if (m_resourceMappingToolWatcher->IsProcessRunning())
|
||||
{
|
||||
m_resourceMappingToolWatcher->TerminateProcess(AZ::u32(-1));
|
||||
m_resourceMappingToolWatcher->TerminateProcess(static_cast<AZ::u32>(-1));
|
||||
}
|
||||
m_resourceMappingToolWatcher.reset();
|
||||
}
|
||||
@@ -214,7 +214,7 @@ namespace AWSCore
|
||||
QMenu* AWSCoreEditorMenu::SetAWSFeatureSubMenu(const AZStd::string& menuText)
|
||||
{
|
||||
auto actionList = this->actions();
|
||||
for (QList<QAction*>::iterator itr = actionList.begin(); itr != actionList.end(); itr++)
|
||||
for (QList<QAction*>::iterator itr = actionList.begin(); itr != actionList.end(); ++itr)
|
||||
{
|
||||
if (QString::compare((*itr)->text(), menuText.c_str()) == 0)
|
||||
{
|
||||
|
||||
@@ -22,10 +22,6 @@ namespace AWSCore
|
||||
{
|
||||
}
|
||||
|
||||
AwsApiJob::~AwsApiJob()
|
||||
{
|
||||
}
|
||||
|
||||
AwsApiJob::Config* AwsApiJob::GetDefaultConfig()
|
||||
{
|
||||
static AwsApiJobConfigHolder<AwsApiJob::Config> s_configHolder{};
|
||||
|
||||
@@ -49,7 +49,7 @@ namespace AWSCore
|
||||
{
|
||||
m_fileFields.emplace_back(FileField{ std::move(fieldName), std::move(fileName) , AZStd::vector<char>{} });
|
||||
m_fileFields.back().m_fileData.reserve(length);
|
||||
m_fileFields.back().m_fileData.assign((const char*)bytes, (const char*)bytes + length);
|
||||
m_fileFields.back().m_fileData.assign(static_cast<const char*>(bytes), static_cast<const char*>(bytes) + length);
|
||||
}
|
||||
|
||||
void MultipartFormData::SetCustomBoundary(AZStd::string boundary)
|
||||
|
||||
@@ -10,6 +10,10 @@
|
||||
|
||||
namespace AWSCore
|
||||
{
|
||||
RequestBuilder::RequestBuilder()
|
||||
: m_httpMethod(Aws::Http::HttpMethod::HTTP_GET)
|
||||
{
|
||||
}
|
||||
|
||||
bool RequestBuilder::SetPathParameterUnescaped(const char* key, const char* value)
|
||||
{
|
||||
|
||||
@@ -26,7 +26,6 @@ namespace AWSCore
|
||||
: m_status(Status::NotLoaded)
|
||||
, m_defaultAccountId("")
|
||||
, m_defaultRegion("")
|
||||
, m_resourceMappings()
|
||||
{
|
||||
}
|
||||
|
||||
@@ -164,7 +163,7 @@ namespace AWSCore
|
||||
m_defaultRegion = jsonDocument.FindMember(ResourceMappingRegionKeyName)->value.GetString();
|
||||
|
||||
auto resourceMappings = jsonDocument.FindMember(ResourceMappingResourcesKeyName)->value.GetObject();
|
||||
for (auto mappingIter = resourceMappings.MemberBegin(); mappingIter != resourceMappings.MemberEnd(); mappingIter++)
|
||||
for (auto mappingIter = resourceMappings.MemberBegin(); mappingIter != resourceMappings.MemberEnd(); ++mappingIter)
|
||||
{
|
||||
auto mappingValue = mappingIter->value.GetObject();
|
||||
if (mappingValue.MemberCount() != 0)
|
||||
|
||||
@@ -71,7 +71,7 @@ namespace AWSCore
|
||||
[](DynamoDBGetItemRequestJob* job) // OnSuccess handler
|
||||
{
|
||||
auto item = job->result.GetItem();
|
||||
if (item.size() > 0)
|
||||
if (!item.empty())
|
||||
{
|
||||
DynamoDBAttributeValueMap result;
|
||||
for (const auto& itermPair : item)
|
||||
|
||||
@@ -40,7 +40,7 @@ public:
|
||||
AWSCoreNotificationsBus::Handler::BusConnect();
|
||||
}
|
||||
|
||||
~AWSCoreNotificationsBusMock()
|
||||
~AWSCoreNotificationsBusMock() override
|
||||
{
|
||||
AWSCoreNotificationsBus::Handler::BusDisconnect();
|
||||
}
|
||||
|
||||
@@ -18,7 +18,7 @@ class AWSCVarCredentialHandlerTest
|
||||
{
|
||||
public:
|
||||
AWSCVarCredentialHandlerTest() = default;
|
||||
virtual ~AWSCVarCredentialHandlerTest() = default;
|
||||
~AWSCVarCredentialHandlerTest() override = default;
|
||||
|
||||
void SetUp() override
|
||||
{
|
||||
|
||||
@@ -36,14 +36,14 @@ public:
|
||||
m_credentialsProvider.reset();
|
||||
}
|
||||
|
||||
int GetCredentialHandlerOrder() const
|
||||
int GetCredentialHandlerOrder() const override
|
||||
{
|
||||
return 1;
|
||||
}
|
||||
|
||||
std::shared_ptr<Aws::Auth::AWSCredentialsProvider> GetCredentialsProvider()
|
||||
std::shared_ptr<Aws::Auth::AWSCredentialsProvider> GetCredentialsProvider() override
|
||||
{
|
||||
m_handlerCounter++;
|
||||
++m_handlerCounter;
|
||||
return m_credentialsProvider;
|
||||
}
|
||||
|
||||
@@ -72,14 +72,14 @@ public:
|
||||
m_credentialsProvider.reset();
|
||||
}
|
||||
|
||||
int GetCredentialHandlerOrder() const
|
||||
int GetCredentialHandlerOrder() const override
|
||||
{
|
||||
return 2;
|
||||
}
|
||||
|
||||
std::shared_ptr<Aws::Auth::AWSCredentialsProvider> GetCredentialsProvider()
|
||||
std::shared_ptr<Aws::Auth::AWSCredentialsProvider> GetCredentialsProvider() override
|
||||
{
|
||||
m_handlerCounter++;
|
||||
++m_handlerCounter;
|
||||
return m_credentialsProvider;
|
||||
}
|
||||
|
||||
@@ -115,10 +115,10 @@ public:
|
||||
|
||||
TEST_F(AWSCredentialBusTest, GetCredentialsProvider_CallFromMultithread_GetExpectedCredentialsProviderAndNumberOfCalls)
|
||||
{
|
||||
int testThreadNumber = 10;
|
||||
constexpr int testThreadNumber = 10;
|
||||
AZStd::atomic<int> actualEbusCalls = 0;
|
||||
AZStd::vector<AZStd::thread> testThreadPool;
|
||||
for (int index = 0; index < testThreadNumber; index++)
|
||||
for (int index = 0; index < testThreadNumber; ++index)
|
||||
{
|
||||
testThreadPool.emplace_back(AZStd::thread([&]() {
|
||||
AWSCredentialResult result;
|
||||
|
||||
@@ -49,7 +49,7 @@ class AWSDefaultCredentialHandlerTest
|
||||
{
|
||||
public:
|
||||
AWSDefaultCredentialHandlerTest() = default;
|
||||
virtual ~AWSDefaultCredentialHandlerTest() = default;
|
||||
~AWSDefaultCredentialHandlerTest() override = default;
|
||||
|
||||
void SetUp() override
|
||||
{
|
||||
|
||||
@@ -23,6 +23,11 @@ class AWSApiClientJobConfigTest
|
||||
, public AWSCredentialRequestBus::Handler
|
||||
{
|
||||
public:
|
||||
AWSApiClientJobConfigTest()
|
||||
: m_credentialHandlerCounter(0)
|
||||
{
|
||||
}
|
||||
|
||||
void SetUp() override
|
||||
{
|
||||
AWSNativeSDKInit::InitializationManager::InitAwsApi();
|
||||
|
||||
@@ -84,7 +84,7 @@ class ServiceClientJobConfigTest
|
||||
void ReloadConfigFile(bool reloadConfigFileName = false) override
|
||||
{
|
||||
AZ_UNUSED(reloadConfigFileName);
|
||||
};
|
||||
}
|
||||
};
|
||||
|
||||
TEST_F(ServiceClientJobConfigTest, GetServiceUrl_CreateServiceWithServiceNameOnly_GetExpectedFeatureServiceUrl)
|
||||
|
||||
@@ -217,7 +217,7 @@ TEST_F(AWSResourceMappingManagerTest, ActivateManager_ParseValidConfigFile_Confi
|
||||
CreateTestConfigFile(TEST_VALID_RESOURCE_MAPPING_CONFIG_FILE);
|
||||
m_resourceMappingManager->ActivateManager();
|
||||
|
||||
int testThreadNumber = 10;
|
||||
constexpr int testThreadNumber = 10;
|
||||
AZStd::atomic<int> actualEbusCalls = 0;
|
||||
AZStd::vector<AZStd::thread> testThreadPool;
|
||||
for (int index = 0; index < testThreadNumber; index++)
|
||||
@@ -226,7 +226,7 @@ TEST_F(AWSResourceMappingManagerTest, ActivateManager_ParseValidConfigFile_Confi
|
||||
AZStd::string actualAccountId;
|
||||
AWSResourceMappingRequestBus::BroadcastResult(actualAccountId, &AWSResourceMappingRequests::GetDefaultAccountId);
|
||||
EXPECT_FALSE(actualAccountId.empty());
|
||||
actualEbusCalls++;
|
||||
++actualEbusCalls;
|
||||
}));
|
||||
}
|
||||
|
||||
|
||||
@@ -44,19 +44,19 @@ TEST_F(AWSResourceMappingUtilsTest, FormatRESTApiUrl_PassingInvalidRESTApiId_Ret
|
||||
{
|
||||
auto actualUrl = AWSResourceMappingUtils::FormatRESTApiUrl("", TEST_VALID_RESTAPI_REGION, TEST_VALID_RESTAPI_STAGE);
|
||||
|
||||
EXPECT_TRUE(actualUrl == "");
|
||||
EXPECT_TRUE(actualUrl.empty());
|
||||
}
|
||||
|
||||
TEST_F(AWSResourceMappingUtilsTest, FormatRESTApiUrl_PassingInvalidRESTApiRegion_ReturnEmptyResult)
|
||||
{
|
||||
auto actualUrl = AWSResourceMappingUtils::FormatRESTApiUrl(TEST_VALID_RESTAPI_ID, "", TEST_VALID_RESTAPI_STAGE);
|
||||
|
||||
EXPECT_TRUE(actualUrl == "");
|
||||
EXPECT_TRUE(actualUrl.empty());
|
||||
}
|
||||
|
||||
TEST_F(AWSResourceMappingUtilsTest, FormatRESTApiUrl_PassingInvalidRESTApiStage_ReturnEmptyResult)
|
||||
{
|
||||
auto actualUrl = AWSResourceMappingUtils::FormatRESTApiUrl(TEST_VALID_RESTAPI_ID, TEST_VALID_RESTAPI_REGION, "");
|
||||
|
||||
EXPECT_TRUE(actualUrl == "");
|
||||
EXPECT_TRUE(actualUrl.empty());
|
||||
}
|
||||
|
||||
@@ -23,7 +23,7 @@ public:
|
||||
AWSScriptBehaviorDynamoDBNotificationBus::Handler::BusConnect();
|
||||
}
|
||||
|
||||
~AWSScriptBehaviorDynamoDBNotificationBusHandlerMock()
|
||||
~AWSScriptBehaviorDynamoDBNotificationBusHandlerMock() override
|
||||
{
|
||||
AWSScriptBehaviorDynamoDBNotificationBus::Handler::BusDisconnect();
|
||||
}
|
||||
|
||||
@@ -22,7 +22,7 @@ public:
|
||||
AWSScriptBehaviorLambdaNotificationBus::Handler::BusConnect();
|
||||
}
|
||||
|
||||
~AWSScriptBehaviorLambdaNotificationBusHandlerMock()
|
||||
~AWSScriptBehaviorLambdaNotificationBusHandlerMock() override
|
||||
{
|
||||
AWSScriptBehaviorLambdaNotificationBus::Handler::BusDisconnect();
|
||||
}
|
||||
|
||||
@@ -24,7 +24,7 @@ public:
|
||||
AWSScriptBehaviorS3NotificationBus::Handler::BusConnect();
|
||||
}
|
||||
|
||||
~AWSScriptBehaviorS3NotificationBusHandlerMock()
|
||||
~AWSScriptBehaviorS3NotificationBusHandlerMock() override
|
||||
{
|
||||
AWSScriptBehaviorS3NotificationBus::Handler::BusDisconnect();
|
||||
}
|
||||
|
||||
@@ -107,8 +107,8 @@ class AWSCoreFixture
|
||||
: public UnitTest::ScopedAllocatorSetupFixture
|
||||
{
|
||||
public:
|
||||
AWSCoreFixture() {}
|
||||
virtual ~AWSCoreFixture() = default;
|
||||
AWSCoreFixture() = default;
|
||||
~AWSCoreFixture() override = default;
|
||||
|
||||
void SetUp() override
|
||||
{
|
||||
|
||||
@@ -64,6 +64,16 @@ To add additional dependencies, for example other CDK libraries, just add
|
||||
them to your `setup.py` file and rerun the `pip install -r requirements.txt`
|
||||
command.
|
||||
|
||||
## Optional Features
|
||||
Server access logging is enabled by default. To disable the feature, use the following commands to synthesize and deploy this CDK application.
|
||||
|
||||
```
|
||||
$ cdk synth -c disable_access_log=true --all
|
||||
$ cdk deploy -c disable_access_log=true --all
|
||||
```
|
||||
|
||||
See https://docs.aws.amazon.com/AmazonS3/latest/userguide/ServerLogs.html for more information about server access logging.
|
||||
|
||||
## Useful commands
|
||||
|
||||
* `cdk ls` list all stacks in the app
|
||||
|
||||
@@ -57,8 +57,9 @@ example_stack = ExampleResources(
|
||||
tags={Constants.O3DE_PROJECT_TAG_NAME: PROJECT_NAME, Constants.O3DE_FEATURE_TAG_NAME: FEATURE_NAME},
|
||||
env=env
|
||||
)
|
||||
#
|
||||
# Add the common stack as a dependency of the feature stack
|
||||
|
||||
# Add the core stack as a dependency of the feature stack since the feature stack
|
||||
# requires the core stack outputs for deployment.
|
||||
example_stack.add_dependency(core_construct.common_stack)
|
||||
|
||||
app.synth()
|
||||
|
||||
@@ -60,17 +60,6 @@ class CoreStack(core.Stack):
|
||||
type='TAG_FILTERS_1_0')
|
||||
)
|
||||
|
||||
# Create an S3 bucket for Amazon S3 server access logging
|
||||
# See https://docs.aws.amazon.com/AmazonS3/latest/dev/security-best-practices.html
|
||||
self._server_access_logs_bucket = s3.Bucket(
|
||||
self,
|
||||
f'{self._project_name}-{self._feature_name}-Access-Log-Bucket',
|
||||
block_public_access=s3.BlockPublicAccess.BLOCK_ALL,
|
||||
encryption=s3.BucketEncryption.S3_MANAGED,
|
||||
access_control=s3.BucketAccessControl.LOG_DELIVERY_WRITE
|
||||
)
|
||||
self._server_access_logs_bucket.grant_read(self._admin_group)
|
||||
|
||||
# Define exports
|
||||
# Export resource group
|
||||
self._resource_group_output = core.CfnOutput(
|
||||
@@ -94,10 +83,22 @@ class CoreStack(core.Stack):
|
||||
export_name=f"{self._project_name}:AdminGroup",
|
||||
value=self._admin_group.group_arn)
|
||||
|
||||
# Export access log bucket name
|
||||
self._server_access_logs_bucket_output = core.CfnOutput(
|
||||
self,
|
||||
id=f'ServerAccessLogsBucketOutput',
|
||||
description='Name of the S3 bucket for storing server access logs generated by the sample CDK application(s)',
|
||||
export_name=f"{self._project_name}:ServerAccessLogsBucket",
|
||||
value=self._server_access_logs_bucket.bucket_name)
|
||||
# Create an S3 bucket for Amazon S3 server access logging
|
||||
# See https://docs.aws.amazon.com/AmazonS3/latest/dev/security-best-practices.html
|
||||
if self.node.try_get_context('disable_access_log') != 'true':
|
||||
self._server_access_logs_bucket = s3.Bucket(
|
||||
self,
|
||||
f'{self._project_name}-{self._feature_name}-Access-Log-Bucket',
|
||||
block_public_access=s3.BlockPublicAccess.BLOCK_ALL,
|
||||
encryption=s3.BucketEncryption.S3_MANAGED,
|
||||
access_control=s3.BucketAccessControl.LOG_DELIVERY_WRITE
|
||||
)
|
||||
self._server_access_logs_bucket.grant_read(self._admin_group)
|
||||
|
||||
# Export access log bucket name
|
||||
self._server_access_logs_bucket_output = core.CfnOutput(
|
||||
self,
|
||||
id=f'ServerAccessLogsBucketOutput',
|
||||
description='Name of the S3 bucket for storing server access logs generated by the sample CDK application(s)',
|
||||
export_name=f"{self._project_name}:ServerAccessLogsBucket",
|
||||
value=self._server_access_logs_bucket.bucket_name)
|
||||
|
||||
@@ -118,19 +118,23 @@ class ExampleResources(core.Stack):
|
||||
# https://docs.aws.amazon.com/AmazonS3/latest/userguide/serv-side-encryption.html
|
||||
# 3. Enable Amazon S3 server access logging
|
||||
# https://docs.aws.amazon.com/AmazonS3/latest/userguide/ServerLogs.html
|
||||
server_access_logs_bucket = s3.Bucket.from_bucket_name(
|
||||
self,
|
||||
f'{self._project_name}-{self._feature_name}-ImportedAccessLogsBucket',
|
||||
core.Fn.import_value(f"{self._project_name}:ServerAccessLogsBucket")
|
||||
)
|
||||
server_access_logs_bucket = None
|
||||
if self.node.try_get_context('disable_access_log') != 'true':
|
||||
server_access_logs_bucket = s3.Bucket.from_bucket_name(
|
||||
self,
|
||||
f'{self._project_name}-{self._feature_name}-ImportedAccessLogsBucket',
|
||||
core.Fn.import_value(f"{self._project_name}:ServerAccessLogsBucket")
|
||||
)
|
||||
|
||||
example_bucket = s3.Bucket(
|
||||
self,
|
||||
f'{self._project_name}-{self._feature_name}-Example-S3bucket',
|
||||
block_public_access=s3.BlockPublicAccess.BLOCK_ALL,
|
||||
encryption=s3.BucketEncryption.S3_MANAGED,
|
||||
server_access_logs_bucket=server_access_logs_bucket,
|
||||
server_access_logs_prefix=f'{self._project_name}-{self._feature_name}-{self.region}-AccessLogs'
|
||||
server_access_logs_bucket=
|
||||
server_access_logs_bucket if server_access_logs_bucket else None,
|
||||
server_access_logs_prefix=
|
||||
f'{self._project_name}-{self._feature_name}-{self.region}-AccessLogs' if server_access_logs_bucket else None
|
||||
)
|
||||
|
||||
s3_deployment.BucketDeployment(
|
||||
|
||||
@@ -74,7 +74,12 @@ namespace AWSMetrics
|
||||
{
|
||||
behaviorContext->EBus<AWSMetricsRequestBus>("AWSMetricsRequestBus", "Generate and submit metrics to the metrics analytics pipeline")
|
||||
->Attribute(AZ::Script::Attributes::Category, "AWSMetrics")
|
||||
->Event("SubmitMetrics", &AWSMetricsRequestBus::Events::SubmitMetrics)
|
||||
->Event(
|
||||
"SubmitMetrics", &AWSMetricsRequestBus::Events::SubmitMetrics,
|
||||
{ { { "Metrics Attributes list", "The list of metrics attributes to submit." },
|
||||
{ "Event priority", "Priority of the event. Defaults to 0, which is highest priority." },
|
||||
{ "Event source override", "Event source used to override the default, 'AWSMetricGem'." },
|
||||
{ "Buffer metrics", "Whether to buffer metrics and send them in a batch." } } })
|
||||
->Event("FlushMetrics", &AWSMetricsRequestBus::Events::FlushMetrics)
|
||||
;
|
||||
|
||||
|
||||
@@ -63,13 +63,10 @@ ly_add_target(
|
||||
3rdParty::Qt::Widgets
|
||||
3rdParty::Qt::Gui
|
||||
3rdParty::astc-encoder
|
||||
3rdParty::etc2comp
|
||||
3rdParty::PVRTexTool
|
||||
3rdParty::squish-ccr
|
||||
3rdParty::tiff
|
||||
3rdParty::ISPCTexComp
|
||||
3rdParty::ilmbase
|
||||
Legacy::CryCommon
|
||||
AZ::AzFramework
|
||||
AZ::AzToolsFramework
|
||||
AZ::AzQtComponents
|
||||
|
||||
+1
-11
@@ -39,16 +39,7 @@ namespace ImageProcessingAtom
|
||||
ePixelFormat_ASTC_10x8,
|
||||
ePixelFormat_ASTC_10x10,
|
||||
ePixelFormat_ASTC_12x10,
|
||||
ePixelFormat_ASTC_12x12,
|
||||
//Formats supported by PowerVR GPU. Mainly for ios devices.
|
||||
ePixelFormat_PVRTC2, //2bpp
|
||||
ePixelFormat_PVRTC4, //4bpp
|
||||
//formats for opengl and opengles 3.0 (android devices)
|
||||
ePixelFormat_EAC_R11, //one channel unsigned data
|
||||
ePixelFormat_EAC_RG11, //two channel unsigned data
|
||||
ePixelFormat_ETC2, //Compresses RGB888 data, it taks 4x4 groups of pixel data and compresses each into a 64-bit
|
||||
ePixelFormat_ETC2a1, //Compresses RGB888A1 data, it taks 4x4 groups of pixel data and compresses each into a 64-bit
|
||||
ePixelFormat_ETC2a, //Compresses RGBA8888 data with full alpha support
|
||||
ePixelFormat_ASTC_12x12,
|
||||
|
||||
// Standardized Compressed DXGI Formats (DX10+)
|
||||
// Data in these compressed formats is hardware decodable on all DX10 chips, and manageable with the DX10-API.
|
||||
@@ -88,7 +79,6 @@ namespace ImageProcessingAtom
|
||||
};
|
||||
|
||||
bool IsASTCFormat(EPixelFormat fmt);
|
||||
bool IsETCFormat(EPixelFormat fmt);
|
||||
} // namespace ImageProcessingAtom
|
||||
|
||||
namespace AZ
|
||||
|
||||
@@ -109,13 +109,6 @@ namespace ImageProcessingAtom
|
||||
->Value("ASTC_10x10", EPixelFormat::ePixelFormat_ASTC_10x10)
|
||||
->Value("ASTC_12x10", EPixelFormat::ePixelFormat_ASTC_12x10)
|
||||
->Value("ASTC_12x12", EPixelFormat::ePixelFormat_ASTC_12x12)
|
||||
->Value("PVRTC2", EPixelFormat::ePixelFormat_PVRTC2)
|
||||
->Value("PVRTC4", EPixelFormat::ePixelFormat_PVRTC4)
|
||||
->Value("EAC_R11", EPixelFormat::ePixelFormat_EAC_R11)
|
||||
->Value("EAC_RG11", EPixelFormat::ePixelFormat_EAC_RG11)
|
||||
->Value("ETC2", EPixelFormat::ePixelFormat_ETC2)
|
||||
->Value("ETC2a1", EPixelFormat::ePixelFormat_ETC2a1)
|
||||
->Value("ETC2a", EPixelFormat::ePixelFormat_ETC2a)
|
||||
->Value("BC1", EPixelFormat::ePixelFormat_BC1)
|
||||
->Value("BC1a", EPixelFormat::ePixelFormat_BC1a)
|
||||
->Value("BC3", EPixelFormat::ePixelFormat_BC3)
|
||||
|
||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user