Merge branch 'development' into cmake/win_fix_warn_4296

Signed-off-by: Esteban Papp <81431996+amznestebanpapp@users.noreply.github.com>
This commit is contained in:
Esteban Papp
2021-08-20 11:18:43 -07:00
116 changed files with 4638 additions and 4173 deletions
+5
View File
@@ -6,6 +6,8 @@
#
#
ly_get_list_relative_pal_filename(pal_dir ${CMAKE_CURRENT_LIST_DIR}/Source/Platform/${PAL_PLATFORM_NAME})
ly_add_target(
NAME Atom_Bootstrap.Headers HEADERONLY
NAMESPACE Gem
@@ -21,9 +23,12 @@ ly_add_target(
NAMESPACE Gem
FILES_CMAKE
bootstrap_files.cmake
${pal_dir}/bootstrap_${PAL_PLATFORM_NAME_LOWERCASE}_files.cmake
PLATFORM_INCLUDE_FILES
INCLUDE_DIRECTORIES
PRIVATE
Source
${pal_dir}
PUBLIC
Include
BUILD_DEPENDENCIES
@@ -38,6 +38,10 @@
#include <Atom/Bootstrap/BootstrapNotificationBus.h>
#include <Atom/RPI.Reflect/System/AnyAsset.h>
#include <AzCore/Console/IConsole.h>
#include <BootstrapSystemComponent_Traits_Platform.h>
AZ_CVAR(AZ::CVarFixedString, r_default_pipeline_name, AZ_TRAIT_BOOTSTRAPSYSTEMCOMPONENT_PIPELINE_NAME, nullptr, AZ::ConsoleFunctorFlags::DontReplicate, "Default Render pipeline name");
namespace AZ
{
@@ -50,8 +54,7 @@ namespace AZ
if (SerializeContext* serialize = azrtti_cast<SerializeContext*>(context))
{
serialize->Class<BootstrapSystemComponent, Component>()
->Version(0)
->Field("DefaultRenderPipelineAssetFile", &BootstrapSystemComponent::m_defaultPipelineAssetPath)
->Version(1)
;
if (EditContext* ec = serialize->GetEditContext())
@@ -60,8 +63,6 @@ namespace AZ
->ClassElement(Edit::ClassElements::EditorData, "")
->Attribute(Edit::Attributes::AppearsInAddComponentMenu, AZ_CRC("System", 0xc94d118b))
->Attribute(Edit::Attributes::AutoExpand, true)
->DataElement(Edit::UIHandlers::Default, &BootstrapSystemComponent::m_defaultPipelineAssetPath, "Default RenderPipeline Asset",
"The asset file path of default render pipeline for default window")
;
}
}
@@ -314,13 +315,15 @@ namespace AZ
// Create a render pipeline from the specified asset for the window context and add the pipeline to the scene.
// When running with no Asset Processor (for example in release), CompileAssetSync will return AssetStatus_Unknown.
AzFramework::AssetSystem::AssetStatus status = AzFramework::AssetSystem::AssetStatus_Unknown;
AzFramework::AssetSystemRequestBus::BroadcastResult(
status, &AzFramework::AssetSystemRequestBus::Events::CompileAssetSync, m_defaultPipelineAssetPath);
AZ_Assert(status == AzFramework::AssetSystem::AssetStatus_Compiled || status == AzFramework::AssetSystem::AssetStatus_Unknown, "Could not compile the default render pipeline at '%s'", m_defaultPipelineAssetPath.c_str());
const AZ::CVarFixedString pipelineName = static_cast<AZ::CVarFixedString>(r_default_pipeline_name);
AzFramework::AssetSystemRequestBus::BroadcastResult(status, &AzFramework::AssetSystemRequestBus::Events::CompileAssetSync, pipelineName.data());
AZ_Assert(status == AzFramework::AssetSystem::AssetStatus_Compiled || status == AzFramework::AssetSystem::AssetStatus_Unknown, "Could not compile the default render pipeline at '%s'", pipelineName.c_str());
Data::Asset<RPI::AnyAsset> pipelineAsset = RPI::AssetUtils::LoadAssetByProductPath<RPI::AnyAsset>(m_defaultPipelineAssetPath.c_str(), RPI::AssetUtils::TraceLevel::Error);
Data::Asset<RPI::AnyAsset> pipelineAsset = RPI::AssetUtils::LoadAssetByProductPath<RPI::AnyAsset>(pipelineName.data(), RPI::AssetUtils::TraceLevel::Error);
RPI::RenderPipelineDescriptor renderPipelineDescriptor = *RPI::GetDataFromAnyAsset<RPI::RenderPipelineDescriptor>(pipelineAsset);
renderPipelineDescriptor.m_name = AZStd::string::format("%s_%i", renderPipelineDescriptor.m_name.c_str(), viewportContext->GetId());
if (!scene->GetRenderPipeline(AZ::Name(renderPipelineDescriptor.m_name)))
{
RPI::RenderPipelinePtr renderPipeline = RPI::RenderPipeline::CreateRenderPipelineForWindow(renderPipelineDescriptor, *viewportContext->GetWindowContext().get());
@@ -112,10 +112,7 @@ namespace AZ
// The id of the render pipeline created by this component
RPI::RenderPipelineId m_renderPipelineId;
// Variables which are system component configuration
AZStd::string m_defaultPipelineAssetPath = "passes/MainRenderPipeline.azasset";
// Save a reference to the image created by the BRDF pipeline so it doesn't get auto deleted if it's ref count goes to zero
// For example, if we delete all the passes, we won't have to recreate the BRDF pipeline to recreate the BRDF texture
Data::Instance<RPI::AttachmentImage> m_brdfTexture;
@@ -0,0 +1,9 @@
/*
* 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
*
*/
#define AZ_TRAIT_BOOTSTRAPSYSTEMCOMPONENT_PIPELINE_NAME "passes/LowEndRenderPipeline.azasset"
@@ -0,0 +1,12 @@
#
# 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
#
#
set(FILES
BootstrapSystemComponent_Traits_Platform.h
)
@@ -0,0 +1,9 @@
/*
* 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
*
*/
#define AZ_TRAIT_BOOTSTRAPSYSTEMCOMPONENT_PIPELINE_NAME "passes/MainRenderPipeline.azasset"
@@ -0,0 +1,12 @@
#
# 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
#
#
set(FILES
BootstrapSystemComponent_Traits_Platform.h
)
@@ -0,0 +1,9 @@
/*
* 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
*
*/
#define AZ_TRAIT_BOOTSTRAPSYSTEMCOMPONENT_PIPELINE_NAME "passes/MainRenderPipeline.azasset"
@@ -0,0 +1,12 @@
#
# 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
#
#
set(FILES
BootstrapSystemComponent_Traits_Platform.h
)
@@ -0,0 +1,9 @@
/*
* 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
*
*/
#define AZ_TRAIT_BOOTSTRAPSYSTEMCOMPONENT_PIPELINE_NAME "passes/MainRenderPipeline.azasset"
@@ -0,0 +1,12 @@
#
# 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
#
#
set(FILES
BootstrapSystemComponent_Traits_Platform.h
)
@@ -0,0 +1,9 @@
/*
* 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
*
*/
#define AZ_TRAIT_BOOTSTRAPSYSTEMCOMPONENT_PIPELINE_NAME "passes/LowEndRenderPipeline.azasset"
@@ -0,0 +1,12 @@
#
# 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
#
#
set(FILES
BootstrapSystemComponent_Traits_Platform.h
)
@@ -0,0 +1,15 @@
{
"Type": "JsonSerialization",
"Version": 1,
"ClassName": "RenderPipelineDescriptor",
"ClassData": {
"Name": "LowEndPipeline",
"MainViewTag": "MainCamera",
"RootPassTemplate": "LowEndPipelineTemplate",
"RenderSettings": {
"MultisampleState": {
"samples": 1
}
}
}
}
@@ -204,6 +204,7 @@ namespace AZ
{
RHI::Ptr<Memory> nullMtlImagePtr = m_device->GetNullDescriptorManager().GetNullImage(shaderInputImage.m_type).GetMemory();
mtlTextures[imageArrayLen] = nullMtlImagePtr->GetGpuAddress<id<MTLTexture>>();
m_useNullDescriptorHeap = true;
}
imageArrayLen++;
}
@@ -282,12 +283,16 @@ namespace AZ
{
RHI::Ptr<Memory> nullMtlBufferMemPtr = nullDescriptorManager.GetNullImageBuffer().GetMemory();
mtlTextures[bufferArrayLen] = nullMtlBufferMemPtr->GetGpuAddress<id<MTLTexture>>();
m_useNullDescriptorHeap = true;
}
else
{
RHI::Ptr<Memory> nullMtlBufferMemPtr = nullDescriptorManager.GetNullBuffer().GetMemory();
mtlBuffers[bufferArrayLen] = nullMtlBufferMemPtr->GetGpuAddress<id<MTLBuffer>>();
mtlBufferOffsets[bufferArrayLen] = nullDescriptorManager.GetNullBuffer().GetOffset();
m_resourceBindings[shaderInputBuffer.m_name].insert(
ResourceBindingData{nullMtlBufferMemPtr, .m_bufferAccess = shaderInputBuffer.m_access}
);
}
}
@@ -499,5 +504,26 @@ namespace AZ
resourcesToMakeResidentMap[key].emplace(mtlResourceToBind);
}
}
bool ArgumentBuffer::IsNullHeapNeededForVertexStage(const ShaderResourceGroupVisibility& srgResourcesVisInfo) const
{
bool isUsedByVertexStage = false;
//Iterate over all the SRG entries
for (const auto& it : srgResourcesVisInfo.m_resourcesStageMask)
{
//Only the ones not added to m_resourceBindings would require null heap
if( m_resourceBindings.find(it.first) == m_resourceBindings.end())
{
isUsedByVertexStage |= RHI::CheckBitsAny(it.second, RHI::ShaderStageMask::Vertex);
}
}
return isUsedByVertexStage;
}
bool ArgumentBuffer::IsNullDescHeapNeeded() const
{
return m_useNullDescriptorHeap;
}
}
}
@@ -104,6 +104,8 @@ namespace AZ
GraphicsResourcesToMakeResidentMap& resourcesToMakeResidentGraphics) const;
void ClearResourceTracking();
bool IsNullHeapNeededForVertexStage(const ShaderResourceGroupVisibility& srgResourcesVisInfo) const;
bool IsNullDescHeapNeeded() const;
//////////////////////////////////////////////////////////////////////////
// RHI::DeviceObject
@@ -153,6 +155,7 @@ namespace AZ
MemoryView m_argumentBuffer;
MemoryView m_constantBuffer;
#endif
bool m_useNullDescriptorHeap = false;
};
}
}
@@ -245,6 +245,8 @@ namespace AZ
bool CommandList::SetArgumentBuffers(const PipelineState* pipelineState, RHI::PipelineStateType stateType)
{
bool bindNullDescriptorHeap = false;
MTLRenderStages mtlRenderStagesForNullDescHeap = 0;
ShaderResourceBindings& bindings = GetShaderResourceBindingsByPipelineType(stateType);
const PipelineLayout& pipelineLayout = pipelineState->GetPipelineLayout();
@@ -280,7 +282,8 @@ namespace AZ
uint32_t srgVisIndex = pipelineLayout.GetIndexBySlot(shaderResourceGroup->GetBindingSlot());
const RHI::ShaderStageMask& srgVisInfo = pipelineLayout.GetSrgVisibility(srgVisIndex);
const ShaderResourceGroupVisibility& srgResourcesVisInfo = pipelineLayout.GetSrgResourcesVisibility(srgVisIndex);
bool isSrgUpdatd = bindings.m_srgsByIndex[slot] != shaderResourceGroup;
if(isSrgUpdatd)
{
@@ -291,6 +294,9 @@ namespace AZ
if(srgVisInfo != RHI::ShaderStageMask::None)
{
bool isNullDescHeapNeeded = compiledArgBuffer.IsNullDescHeapNeeded();
bindNullDescriptorHeap |= isNullDescHeapNeeded;
//For graphics and compute shader stages, cache all the argument buffers, offsets and track the min/max indices
if(m_commandEncoderType == CommandEncoderType::Render)
{
@@ -300,7 +306,9 @@ namespace AZ
mtlVertexArgBuffers[slotIndex] = argBuffer;
mtlVertexArgBufferOffsets[slotIndex] = argBufferOffset;
bufferVertexRegisterIdMin = AZStd::min(slotIndex, bufferVertexRegisterIdMin);
bufferVertexRegisterIdMax = AZStd::max(slotIndex, bufferVertexRegisterIdMax);
bufferVertexRegisterIdMax = AZStd::max(slotIndex, bufferVertexRegisterIdMax);
mtlRenderStagesForNullDescHeap = shaderResourceGroup->IsNullHeapNeededForVertexStage(srgResourcesVisInfo) ?
mtlRenderStagesForNullDescHeap | MTLRenderStageVertex : mtlRenderStagesForNullDescHeap;
}
if( numBitsSet > 1 || srgVisInfo == RHI::ShaderStageMask::Fragment)
@@ -309,6 +317,7 @@ namespace AZ
mtlFragmentOrComputeArgBufferOffsets[slotIndex] = argBufferOffset;
bufferFragmentOrComputeRegisterIdMin = AZStd::min(slotIndex, bufferFragmentOrComputeRegisterIdMin);
bufferFragmentOrComputeRegisterIdMax = AZStd::max(slotIndex, bufferFragmentOrComputeRegisterIdMax);
mtlRenderStagesForNullDescHeap = isNullDescHeapNeeded ? mtlRenderStagesForNullDescHeap | MTLRenderStageFragment : mtlRenderStagesForNullDescHeap;
}
}
else if(m_commandEncoderType == CommandEncoderType::Compute)
@@ -329,7 +338,7 @@ namespace AZ
bindings.m_srgVisHashByIndex[slot] = srgResourcesVisHash;
if(srgVisInfo != RHI::ShaderStageMask::None)
{
const ShaderResourceGroupVisibility& srgResourcesVisInfo = pipelineLayout.GetSrgResourcesVisibility(srgVisIndex);
//For graphics and compute encoder make the resource resident (call UseResource) for the duration
//of the work associated with the current scope and ensure that it's in a
@@ -396,6 +405,10 @@ namespace AZ
stages: key.first.second];
}
if(bindNullDescriptorHeap)
{
MakeHeapsResident(mtlRenderStagesForNullDescHeap);
}
return true;
}
@@ -64,6 +64,7 @@ namespace AZ
{
[m_encoder endEncoding];
m_encoder = nil;
m_isNullDescHeapBound = false;
#if AZ_TRAIT_ATOM_METAL_COUNTER_SAMPLING
if (m_supportsInterDrawTimestamps)
{
@@ -73,18 +74,25 @@ namespace AZ
}
}
void CommandListBase::MakeHeapsResident()
void CommandListBase::MakeHeapsResident(MTLRenderStages renderStages)
{
if(m_isNullDescHeapBound)
{
return;
}
switch(m_commandEncoderType)
{
case CommandEncoderType::Render:
{
id<MTLRenderCommandEncoder> renderEncoder = GetEncoder<id<MTLRenderCommandEncoder>>();
for (id<MTLHeap> residentHeap : *m_residentHeaps)
if(renderStages != 0)
{
//MTLRenderStageVertex is not added to this as it was causing an immediate gpu crash on ios (first buffer commit)
[renderEncoder useHeap : residentHeap
stages : MTLRenderStageFragment];
id<MTLRenderCommandEncoder> renderEncoder = GetEncoder<id<MTLRenderCommandEncoder>>();
for (id<MTLHeap> residentHeap : *m_residentHeaps)
{
[renderEncoder useHeap : residentHeap
stages : renderStages];
}
}
break;
}
@@ -102,6 +110,7 @@ namespace AZ
AZ_Assert(false, "Encoder Type not supported");
}
}
m_isNullDescHeapBound = true;
}
void CommandListBase::CreateEncoder(CommandEncoderType encoderType)
@@ -119,16 +128,12 @@ namespace AZ
m_commandEncoderType = CommandEncoderType::Render;
m_encoder = [m_mtlCommandBuffer renderCommandEncoderWithDescriptor : m_renderPassDescriptor];
m_renderPassDescriptor = nil;
MakeHeapsResident();
break;
}
case CommandEncoderType::Compute:
{
m_commandEncoderType = CommandEncoderType::Compute;
m_encoder = [m_mtlCommandBuffer computeCommandEncoder];
MakeHeapsResident();
break;
}
case CommandEncoderType::Blit:
@@ -89,12 +89,14 @@ namespace AZ
/// Cache multisample state. Used mainly to validate the MSAA image descriptor against the one passed into the pipelinestate
RHI::MultisampleState m_renderPassMultiSampleState;
//! Go through all the heaps and call UseHeap on them to make them resident for the upcoming pass.
void MakeHeapsResident(MTLRenderStages renderStages);
private:
//! Go through all the heaps and call UseHeap on them to make them resident for the upcoming pass.
void MakeHeapsResident();
bool m_isEncoded = false;
bool m_isNullDescHeapBound = false;
RHI::HardwareQueueClass m_hardwareQueueClass = RHI::HardwareQueueClass::Graphics;
NSString* m_encoderScopeName = nullptr;
id <MTLCommandBuffer> m_mtlCommandBuffer = nil;
@@ -126,10 +126,10 @@ namespace AZ
Device& device = static_cast<Device&>(GetDevice());
m_nullBuffer.m_name = "NULL_DESCRIPTOR_BUFFER";
m_nullBuffer.m_bufferDescriptor.m_byteCount = 64;
m_nullBuffer.m_bufferDescriptor.m_byteCount = 1024;
m_nullBuffer.m_bufferDescriptor.m_bindFlags = RHI::BufferBindFlags::ShaderWrite;
m_nullBuffer.m_memoryView = device.CreateBufferCommitted(m_nullBuffer.m_bufferDescriptor);
m_nullBuffer.m_memoryView.SetName( m_nullBuffer.m_name.c_str());
if(!m_nullBuffer.m_memoryView.IsValid())
{
AZ_Assert(false, "Couldnt create a null buffer for ArgumentTable");
@@ -36,5 +36,10 @@ namespace AZ
{
GetCompiledArgumentBuffer().CollectUntrackedResources(commandEncoder, srgResourcesVisInfo, resourcesToMakeResidentCompute, resourcesToMakeResidentGraphics);
}
bool ShaderResourceGroup::IsNullHeapNeededForVertexStage(const ShaderResourceGroupVisibility& srgResourcesVisInfo) const
{
return GetCompiledArgumentBuffer().IsNullHeapNeededForVertexStage(srgResourcesVisInfo);
}
}
}
@@ -47,7 +47,8 @@ namespace AZ
const ShaderResourceGroupVisibility& srgResourcesVisInfo,
ArgumentBuffer::ComputeResourcesToMakeResidentMap& resourcesToMakeResidentCompute,
ArgumentBuffer::GraphicsResourcesToMakeResidentMap& resourcesToMakeResidentGraphics) const;
bool IsNullHeapNeededForVertexStage(const ShaderResourceGroupVisibility& srgResourcesVisInfo) const;
private:
ShaderResourceGroup() = default;
@@ -0,0 +1,23 @@
<?xml version="1.0" encoding="utf-8"?>
<AutoVisualizer xmlns="http://schemas.microsoft.com/vstudio/debugger/natvis/2010">
<Type Name="AZ::RPI::ShaderOptionGroup">
<DisplayString>shader option group</DisplayString>
<Expand>
<Item Name="id">m_id.m_key</Item>
<CustomListItems>
<Variable Name="iOption" InitialValue="-1" /><Loop>
<Break Condition="iOption &gt;= m_layout.px-&gt;m_options.m_last - m_layout.px-&gt;m_options.m_start - 1" />
<Exec>iOption++</Exec>
<!-- Thanks to the fact that options don't cross 32-bit boundaries, the following equation works -->
<!-- < "{ shader option name for option iOption }">(( the word in the bitset that corresponds to this option >> ( bit offset, adjusted by the corresponding word ))) & (( bit mask )) + ( this option's min value )</Item>-->
<!-- < "{m_layout.px -> m_options[iOption].m_name.m_data.px -> m_name}">((m_id.m_key.m_bits[(int) (m_layout.px -> m_options[iOption].m_bitOffset / m_id.m_key.BitsPerWord)] >> (m_layout.px -> m_options[iOption].m_bitOffset - ((int) (m_layout.px -> m_options[iOption].m_bitOffset / 32) * 32))) & ((1u << (m_layout.px -> m_options[iOption].m_bitCount)) - 1u)) + (m_layout.px-&gt;m_options[iOption].m_minValue.m_index)</Item>-->
<Item Name="{m_layout.px-&gt;m_options[iOption].m_name.m_data.px-&gt;m_name}">((m_id.m_key.m_bits[(int) (m_layout.px-&gt;m_options[iOption].m_bitOffset / m_id.m_key.BitsPerWord)] &gt;&gt; (m_layout.px-&gt;m_options[iOption].m_bitOffset - ((int) (m_layout.px-&gt;m_options[iOption].m_bitOffset / 32) * 32))) &amp; ((1u &lt;&lt; (m_layout.px-&gt;m_options[iOption].m_bitCount)) - 1u)) + (m_layout.px-&gt;m_options[iOption].m_minValue.m_index)</Item>
</Loop>
</CustomListItems>
</Expand>
</Type>
</AutoVisualizer>
@@ -9,4 +9,5 @@
set(FILES
Atom_RPI_Traits_Platform.h
Atom_RPI_Traits_Windows.h
../Common/VisualStudio/Natvis/shaderoptiongroup.natvis
)
@@ -19,6 +19,7 @@
#include <AzFramework/Asset/AssetSystemBus.h>
#include <AzQtComponents/Application/AzQtApplication.h>
#include <AzQtComponents/Components/StyleManager.h>
#include <AzToolsFramework/API/AssetDatabaseBus.h>
#include <AzToolsFramework/API/EditorPythonConsoleBus.h>
@@ -113,6 +114,8 @@ namespace AtomToolsFramework
AzToolsFramework::TraceLogger m_traceLogger;
AZStd::unique_ptr<AzQtComponents::StyleManager> m_styleManager;
//! Local user settings are used to store material browser tree expansion state
AZ::UserSettingsProvider m_localUserSettings;
@@ -21,6 +21,8 @@
#include <AzFramework/Network/AssetProcessorConnection.h>
#include <AzFramework/StringFunc/StringFunc.h>
#include <AzQtComponents/Components/GlobalEventFilter.h>
#include <AzToolsFramework/API/EditorPythonConsoleBus.h>
#include <AzToolsFramework/API/EditorPythonRunnerRequestsBus.h>
#include <AzToolsFramework/Asset/AssetSystemComponent.h>
@@ -61,14 +63,26 @@ namespace AtomToolsFramework
: Application(argc, argv)
, AzQtApplication(*argc, *argv)
{
// Suppress spam from the Source Control system
m_traceLogger.AddWindowFilter(AzToolsFramework::SCC_WINDOW);
installEventFilter(new AzQtComponents::GlobalEventFilter(this));
AZ::IO::FixedMaxPath engineRootPath;
if (auto settingsRegistry = AZ::SettingsRegistry::Get(); settingsRegistry != nullptr)
{
settingsRegistry->Get(engineRootPath.Native(), AZ::SettingsRegistryMergeUtils::FilePathKey_EngineRootFolder);
}
m_styleManager.reset(new AzQtComponents::StyleManager(this));
m_styleManager->initialize(this, engineRootPath);
connect(&m_timer, &QTimer::timeout, this, [&]()
{
this->PumpSystemEventLoopUntilEmpty();
this->Tick();
});
// Suppress spam from the Source Control system
m_traceLogger.AddWindowFilter(AzToolsFramework::SCC_WINDOW);
}
AtomToolsApplication ::~AtomToolsApplication()
@@ -6,46 +6,19 @@
*
*/
#if !defined(Q_MOC_RUN)
#include <MaterialEditorApplication.h>
#include <AzCore/IO/Path/Path.h>
#include <AzCore/Settings/SettingsRegistryMergeUtils.h>
#include <AzQtComponents/Components/GlobalEventFilter.h>
#include <AzQtComponents/Components/O3DEStylesheet.h>
#include <AzQtComponents/Components/StyleManager.h>
#include <AzQtComponents/Components/StyledDockWidget.h>
#include <AzQtComponents/Components/WindowDecorationWrapper.h>
#include <AzQtComponents/Utilities/HandleDpiAwareness.h>
#include <AzQtComponents/Utilities/QtPluginPaths.h>
#include <QtGui/private/qhighdpiscaling_p.h>
#include <QtWidgets/QApplication>
#endif
int main(int argc, char** argv)
{
AzQtComponents::AzQtApplication::InitializeDpiScaling();
MaterialEditor::MaterialEditorApplication app(&argc, &argv);
if (!app.LaunchLocalServer())
if (app.LaunchLocalServer())
{
return 0;
app.Start(AZ::ComponentApplication::Descriptor{});
app.exec();
app.Stop();
}
app.installEventFilter(new AzQtComponents::GlobalEventFilter(&app));
AZ::IO::FixedMaxPath engineRootPath;
if (auto settingsRegistry = AZ::SettingsRegistry::Get(); settingsRegistry != nullptr)
{
settingsRegistry->Get(engineRootPath.Native(), AZ::SettingsRegistryMergeUtils::FilePathKey_EngineRootFolder);
}
AzQtComponents::StyleManager styleManager(&app);
styleManager.initialize(&app, engineRootPath);
app.Start(AZ::ComponentApplication::Descriptor{});
app.exec();
app.Stop();
return 0;
}
@@ -6,46 +6,19 @@
*
*/
#include <AzCore/IO/Path/Path.h>
#include <AzCore/Settings/SettingsRegistryMergeUtils.h>
#include <AzQtComponents/Components/StyleManager.h>
#include <AzQtComponents/Utilities/QtPluginPaths.h>
#include <AzQtComponents/Components/GlobalEventFilter.h>
#include <AzQtComponents/Components/StyledDockWidget.h>
#include <AzQtComponents/Components/O3DEStylesheet.h>
#include <AzQtComponents/Utilities/QtPluginPaths.h>
#include <AzQtComponents/Utilities/HandleDpiAwareness.h>
#include <AzQtComponents/Components/WindowDecorationWrapper.h>
#include <AzQtComponents/Application/AzQtApplication.h>
#include <QtWidgets/QApplication>
#include <QtGui/private/qhighdpiscaling_p.h>
#include <Source/ShaderManagementConsoleApplication.h>
#include <ShaderManagementConsoleApplication.h>
int main(int argc, char** argv)
{
AzQtComponents::AzQtApplication::InitializeDpiScaling();
ShaderManagementConsole::ShaderManagementConsoleApplication app(&argc, &argv);
if (!app.LaunchLocalServer())
if (app.LaunchLocalServer())
{
return 0;
app.Start(AZ::ComponentApplication::Descriptor{});
app.exec();
app.Stop();
}
app.installEventFilter(new AzQtComponents::GlobalEventFilter(&app));
AZ::IO::FixedMaxPath engineRootPath;
if (auto settingsRegistry = AZ::SettingsRegistry::Get(); settingsRegistry != nullptr)
{
settingsRegistry->Get(engineRootPath.Native(), AZ::SettingsRegistryMergeUtils::FilePathKey_EngineRootFolder);
}
AzQtComponents::StyleManager styleManager(&app);
styleManager.initialize(&app, engineRootPath);
app.Start(AZ::ComponentApplication::Descriptor{});
app.exec();
app.Stop();
return 0;
}
@@ -122,7 +122,6 @@ namespace AZ
int m_currentHistoryIndex = -1; //!< The current index into the input history when browsing.
int m_maxEntriesToDisplay = DefaultMaxEntriesToDisplay; //!< The maximum entries to display.
int m_maxInputHistorySize = DefaultMaxInputHistorySize; //!< The maximum input history size.
int m_logLevelToSet = 0; //!< The minimum log level to set (see AZ::LogLevel).
bool m_isShowing = false; //!< Is the debug console currently being displayed?
bool m_autoScroll = true; //!< Should we auto-scroll as new entries are added?
bool m_forceScroll = false; //!< Do we need to force scroll after input entered?
@@ -12,6 +12,7 @@
#include <platform.h>
#include <AzCore/AzCore_Traits_Platform.h>
#include <AzCore/Debug/Profiler.h>
#include <AzCore/std/containers/set.h>
#include <AzCore/std/string/conversions.h>
#include <AzCore/StringFunc/StringFunc.h>
@@ -1779,8 +1780,8 @@ namespace Audio
AK::MemoryMgr::CategoryStats categoryStats;
AK::MemoryMgr::GetCategoryStats(memInfo.m_poolId, categoryStats);
memInfo.m_memoryUsed = categoryStats.uUsed;
memInfo.m_peakUsed = categoryStats.uPeakUsed;
memInfo.m_memoryUsed = static_cast<AZ::u32>(categoryStats.uUsed);
memInfo.m_peakUsed = static_cast<AZ::u32>(categoryStats.uPeakUsed);
memInfo.m_numAllocs = categoryStats.uAllocs;
memInfo.m_numFrees = categoryStats.uFrees;
}
@@ -1789,9 +1790,9 @@ namespace Audio
AK::MemoryMgr::GetGlobalStats(globalStats);
auto& memInfo = m_debugMemoryInfo.back();
memInfo.m_memoryReserved = globalStats.uReserved;
memInfo.m_memoryUsed = globalStats.uUsed;
memInfo.m_peakUsed = globalStats.uMax;
memInfo.m_memoryReserved = static_cast<AZ::u32>(globalStats.uReserved);
memInfo.m_memoryUsed = static_cast<AZ::u32>(globalStats.uUsed);
memInfo.m_peakUsed = static_cast<AZ::u32>(globalStats.uMax);
// return the memory infos...
return m_debugMemoryInfo;
@@ -769,124 +769,6 @@ namespace Audio
return (eStatus == eARS_SUCCESS || eStatus == eARS_FAILURE);
}
#if !defined(AUDIO_RELEASE)
// Debug Logging Helper
AZStd::string ToString()
{
static const AZStd::unordered_map<const EAudioManagerRequestType, const AZStd::string> managerRequests
{
{ eAMRT_INIT_AUDIO_IMPL, "INIT IMPL" },
{ eAMRT_RELEASE_AUDIO_IMPL, "RELEASE IMPL" },
{ eAMRT_RESERVE_AUDIO_OBJECT_ID, "RESERVE OBJECT ID" },
{ eAMRT_CREATE_SOURCE, "CREATE SOURCE" },
{ eAMRT_DESTROY_SOURCE, "DESTROY SOURCE" },
{ eAMRT_PARSE_CONTROLS_DATA, "PARSE CONTROLS" },
{ eAMRT_PARSE_PRELOADS_DATA, "PARSE PRELOADS" },
{ eAMRT_CLEAR_CONTROLS_DATA, "CLEAR CONTROLS" },
{ eAMRT_CLEAR_PRELOADS_DATA, "CLEAR PRELOADS" },
{ eAMRT_PRELOAD_SINGLE_REQUEST, "PRELOAD SINGLE" },
{ eAMRT_UNLOAD_SINGLE_REQUEST, "UNLOAD SINGLE" },
{ eAMRT_UNLOAD_AFCM_DATA_BY_SCOPE, "UNLOAD SCOPE" },
{ eAMRT_REFRESH_AUDIO_SYSTEM, "REFRESH AUDIO SYSTEM" },
{ eAMRT_LOSE_FOCUS, "LOSE FOCUS" },
{ eAMRT_GET_FOCUS, "GET FOCUS" },
{ eAMRT_MUTE_ALL, "MUTE" },
{ eAMRT_UNMUTE_ALL, "UNMUTE" },
{ eAMRT_STOP_ALL_SOUNDS, "STOP ALL" },
{ eAMRT_DRAW_DEBUG_INFO, "DRAW DEBUG" },
{ eAMRT_CHANGE_LANGUAGE, "CHANGE LANGUAGE" },
{ eAMRT_SET_AUDIO_PANNING_MODE, "SET PANNING MODE" },
};
static const AZStd::unordered_map<const EAudioCallbackManagerRequestType, const AZStd::string> callbackRequests
{
{ eACMRT_REPORT_STARTED_EVENT, "STARTED EVENT" },
{ eACMRT_REPORT_FINISHED_EVENT, "FINISHED EVENT" },
{ eACMRT_REPORT_FINISHED_TRIGGER_INSTANCE, "FINISHED TRIGGER INSTANCE" },
};
static const AZStd::unordered_map<const EAudioListenerRequestType, const AZStd::string> listenerRequests
{
{ eALRT_SET_POSITION, "SET POSITION" },
};
static const AZStd::unordered_map<const EAudioObjectRequestType, const AZStd::string> objectRequests
{
{ eAORT_PREPARE_TRIGGER, "PREPARE TRIGGER" },
{ eAORT_UNPREPARE_TRIGGER, "UNPREPARE TRIGGER" },
{ eAORT_EXECUTE_TRIGGER, "EXECUTE TRIGGER" },
{ eAORT_STOP_TRIGGER, "STOP TRIGGER" },
{ eAORT_STOP_ALL_TRIGGERS, "STOP ALL" },
{ eAORT_SET_POSITION, "SET POSITION" },
{ eAORT_SET_RTPC_VALUE, "SET RTPC" },
{ eAORT_SET_SWITCH_STATE, "SET SWITCH" },
{ eAORT_SET_ENVIRONMENT_AMOUNT, "SET ENV AMOUNT" },
{ eAORT_RESET_ENVIRONMENTS, "RESET ENVS" },
{ eAORT_RESET_RTPCS, "RESET RTPCS" },
{ eAORT_RELEASE_OBJECT, "RELEASE OBJECT" },
{ eAORT_EXECUTE_SOURCE_TRIGGER, "EXECUTE SOURCE TRIGGER" },
{ eAORT_SET_MULTI_POSITIONS, "SET MULTI POSITIONS" },
};
std::stringstream ss;
ss << "AudioRequest(";
if (pData->eRequestType == eART_AUDIO_MANAGER_REQUEST)
{
ss << "AUDIO MANAGER : ";
auto requestStr = managerRequests.at(static_cast<const SAudioManagerRequestDataInternalBase*>(pData.get())->eType);
ss << requestStr.c_str();
}
if (pData->eRequestType == eART_AUDIO_CALLBACK_MANAGER_REQUEST)
{
ss << "AUDIO CALLBACK MGR : ";
auto requestStr = callbackRequests.at(static_cast<const SAudioCallbackManagerRequestDataInternalBase*>(pData.get())->eType);
ss << requestStr.c_str();
}
if (pData->eRequestType == eART_AUDIO_LISTENER_REQUEST)
{
ss << "AUDIO LISTENER : ";
auto requestStr = listenerRequests.at(static_cast<const SAudioListenerRequestDataInternalBase*>(pData.get())->eType);
ss << requestStr.c_str();
}
if (pData->eRequestType == eART_AUDIO_OBJECT_REQUEST)
{
ss << "AUDIO OBJECT : ";
auto requestStr = objectRequests.at(static_cast<const SAudioObjectRequestDataInternalBase*>(pData.get())->eType);
ss << requestStr.c_str();
}
ss << "): [";
if (nFlags & eARF_PRIORITY_NORMAL)
{
ss << "PRIORITY NORMAL, ";
}
if (nFlags & eARF_PRIORITY_HIGH)
{
ss << "PRIORITY HIGH, ";
}
if (nFlags & eARF_EXECUTE_BLOCKING)
{
ss << "EXECUTE BLOCKING, ";
}
if (nFlags & eARF_SYNC_CALLBACK)
{
ss << "SYNC CALLBACK, ";
}
if (nFlags & eARF_SYNC_FINISHED_CALLBACK)
{
ss << "SYNC FINISHED CALLBACK, ";
}
if (nFlags & eARF_THREAD_SAFE_PUSH)
{
ss << "THREAD SAFE PUSH, ";
}
ss << "]";
return AZStd::string(ss.str().c_str());
}
#endif // !AUDIO_RELEASE
TATLEnumFlagsType nFlags;
TAudioObjectID nAudioObjectID;
void* pOwner;
@@ -616,7 +616,7 @@ namespace Audio
void CAudioSystem::ProcessRequestThreadSafe(CAudioRequestInternal request)
{
// Audio Thread!
AZ_PROFILE_SCOPE(Audio, "Thread-Safe Request: %s", request.ToString().c_str());
AZ_PROFILE_SCOPE(Audio, "Process Thread-Safe Request");
if (m_oATL.CanProcessRequests())
{
@@ -641,7 +641,7 @@ namespace Audio
{
// Todo: This should handle request priority, use request priority as bus Address and process in priority order.
AZ_PROFILE_SCOPE(Audio, "Normal Request: %s", request.ToString().c_str());
AZ_PROFILE_SCOPE(Audio, "Process Normal Request");
AZ_Assert(g_mainThreadId != AZStd::this_thread::get_id(), "AudioSystem::ProcessRequestByPriority - called from Main thread!");
@@ -672,7 +672,7 @@ namespace Audio
{
if (!(request.nInternalInfoFlags & eARIF_WAITING_FOR_REMOVAL))
{
AZ_PROFILE_SCOPE(Audio, "Blocking Request: %s", request.ToString().c_str());
AZ_PROFILE_SCOPE(Audio, "Process Blocking Request");
if (request.eStatus == eARS_NONE)
{
+2 -4
View File
@@ -17,8 +17,8 @@ ly_add_target(
PUBLIC
Include
BUILD_DEPENDENCIES
PRIVATE
Legacy::CryCommon
PUBLIC
AZ::AzCore
)
ly_add_target(
@@ -33,7 +33,6 @@ ly_add_target(
Include
BUILD_DEPENDENCIES
PRIVATE
Legacy::CryCommon
Gem::GameState.Static
)
@@ -58,7 +57,6 @@ if(PAL_TRAIT_BUILD_TESTS_SUPPORTED)
BUILD_DEPENDENCIES
PRIVATE
AZ::AzTest
Legacy::CryCommon
Gem::GameState.Static
)
ly_add_googletest(
+5 -3
View File
@@ -21,6 +21,7 @@ ly_add_target(
INTERFACE
Gem::GameState
Gem::LocalUser
Gem::LyShine.Static
Gem::SaveData.Static
Gem::MessagePopup.Static
Legacy::CryCommon
@@ -47,6 +48,7 @@ ly_add_target(
Gem::LmbrCentral
)
# Clients and Servers use the above module. There is no editor or tools module required.
ly_create_alias(NAME GameStateSamples.Clients NAMESPACE Gem TARGETS GameStateSamples)
ly_create_alias(NAME GameStateSamples.Servers NAMESPACE Gem TARGETS GameStateSamples)
# Clients and Servers use the above module, and it contains assets so is needed by builders.
ly_create_alias(NAME GameStateSamples.Clients NAMESPACE Gem TARGETS Gem::GameStateSamples)
ly_create_alias(NAME GameStateSamples.Servers NAMESPACE Gem TARGETS Gem::GameStateSamples)
ly_create_alias(NAME GameStateSamples.Builders NAMESPACE Gem TARGETS Gem::UiBasics.Builders Gem::LyShineExamples.Builders)
@@ -7,6 +7,7 @@
*/
#include <AzCore/Component/ComponentApplicationBus.h>
#include <AzCore/Component/TickBus.h>
#include <AzCore/Memory/SystemAllocator.h>
#include <AzCore/Module/Module.h>
#include <AzCore/std/smart_ptr/make_shared.h>
@@ -55,6 +56,7 @@ namespace GameStateSamples
//!
class GameStateSamplesModule
: public CryHooksModule
, public AZ::TickBus::Handler
, public GameOptionRequestBus::Handler
{
public:
@@ -86,6 +88,22 @@ namespace GameStateSamples
{
CryHooksModule::OnCrySystemInitialized(system, systemInitParams);
AZ::TickBus::Handler::BusConnect();
}
void OnTick([[maybe_unused]]float deltaTime, [[maybe_unused]]AZ::ScriptTimePoint scriptTimePoint) override
{
// Ideally this would be called at startup (either above in OnCrySystemInitialized, or better during AZ system component
// initialisation), but because the initial game state depends on loading a UI canvas using LYShine we need to wait until
// the first tick, because LyShine in turn is not properly initialized until UiRenderer::OnBootstrapSceneReady has been
// called, which doesn't happen until a queued tick event that gets called right at the end of initialisation before we
// enter the main game loop.
CreateAndPushInitialGameState();
AZ::TickBus::Handler::BusDisconnect();
}
void CreateAndPushInitialGameState()
{
REGISTER_INT("sys_primaryUserSelectionEnabled", 2, VF_NULL,
"Controls whether the game forces selection of a primary user at startup.\n"
"0 : Skip selection of a primary user at startup on all platform.\n"
@@ -212,8 +212,11 @@ namespace LmbrCentral
template <typename TComponent, typename TConfiguration>
void EditorWrappedComponentBase<TComponent, TConfiguration>::OnEntityVisibilityChanged(bool visibility)
{
m_visible = visibility;
ConfigurationChanged();
if (m_visible != visibility)
{
m_visible = visibility;
ConfigurationChanged();
}
}
template <typename TComponent, typename TConfiguration>
@@ -59,7 +59,8 @@ namespace Multiplayer
(
const PrefabEntityId& prefabEntryId,
NetEntityRole netEntityRole,
const AZ::Transform& transform
const AZ::Transform& transform,
AutoActivate autoActivate = AutoActivate::Activate
) = 0;
//! Creates new entities of the given archetype
@@ -89,6 +90,11 @@ namespace Multiplayer
//! @return the total number of entities tracked by this INetworkEntityManager instance
virtual uint32_t GetEntityCount() const = 0;
//! Returns the Net Entity ID for a given AZ Entity ID.
//! @param entityId the AZ Entity ID
//! @return the Net Entity ID
virtual NetEntityId GetNetEntityIdById(const AZ::EntityId& entityId) const = 0;
//! Adds the provided entity to the internal entity map identified by the provided netEntityId.
//! @param netEntityId the identifier to use for the added entity
//! @param entity the entity to add to the internal entity map
@@ -130,9 +130,9 @@ void {{ PropertyName }}({{ ', '.join(paramDefines) }});
{#
#}
{% macro DeclareRpcInvocations(Component, Section, HandleOn, ProctectedSection) %}
{% macro DeclareRpcInvocations(Component, Section, HandleOn, IsProtected) %}
{% call(Property) AutoComponentMacros.ParseRemoteProcedures(Component, Section, HandleOn) %}
{% if Property.attrib['IsPublic']|booleanTrue == ProctectedSection %}
{% if Property.attrib['IsPublic']|booleanTrue != IsProtected %}
{{ DeclareRpcInvocation(Property, HandleOn) -}}
{% endif %}
{% endcall %}
@@ -386,8 +386,6 @@ namespace {{ Component.attrib['Namespace'] }}
{{ DeclareNetworkPropertyAccessors(Component, 'Autonomous', 'Authority', false)|indent(8) -}}
{{ DeclareNetworkPropertyAccessors(Component, 'Autonomous', 'Authority', true)|indent(8) -}}
{{ DeclareArchetypePropertyGetters(Component)|indent(8) -}}
{{ DeclareRpcInvocations(Component, 'Server', 'Authority', false)|indent(8) -}}
{{ DeclareRpcInvocations(Component, 'Server', 'Authority', true)|indent(8) -}}
{{ DeclareRpcInvocations(Component, 'Client', 'Authority', false)|indent(8) -}}
{{ DeclareRpcInvocations(Component, 'Client', 'Authority', true)|indent(8) -}}
{{ DeclareRpcInvocations(Component, 'Autonomous', 'Authority', false)|indent(8) -}}
@@ -445,8 +443,8 @@ namespace {{ Component.attrib['Namespace'] }}
static AZStd::unique_ptr<Multiplayer::IMultiplayerComponentInput> AllocateComponentInput();
{{ ComponentBaseName }}() = default;
~{{ ComponentBaseName }}() override = default;
{{ ComponentBaseName }}();
~{{ ComponentBaseName }}() override;
void Init() override;
void Activate() override;
@@ -318,7 +318,11 @@ void {{ ClassName }}::{{ UpperFirst(Property.attrib['Name']) }}({{ ', '.join(par
constexpr AzNetworking::ReliabilityType isReliable = Multiplayer::ReliabilityType::Unreliable;
{% endif %}
{% if InvokeFrom == 'Server' or InvokeFrom =='Client' %}
const Multiplayer::NetComponentId netComponentId = GetNetComponentId();
{% else %}
const Multiplayer::NetComponentId netComponentId = GetParent().GetNetComponentId();
{% endif %}
Multiplayer::NetworkEntityRpcMessage rpcMessage(Multiplayer::RpcDeliveryType::{{ InvokeFrom }}To{{ HandleOn }}, GetNetEntityId(), netComponentId, rpcId, isReliable);
{% if paramNames|count > 0 %}
{{ UpperFirst(Component.attrib['Name']) }}Internal::{{ UpperFirst(Property.attrib['Name']) }}RpcStruct rpcStruct({{ ', '.join(paramNames) }});
@@ -345,9 +349,9 @@ void {{ ClassName }}::Signal{{ UpperFirst(Property.attrib['Name']) }}({{ ', '.jo
{#
#}
{% macro DefineRpcInvocations(Component, ClassName, InvokeFrom, HandleOn, ProctectedSection) %}
{% macro DefineRpcInvocations(Component, ClassName, InvokeFrom, HandleOn, IsProtected) %}
{% call(Property) AutoComponentMacros.ParseRemoteProcedures(Component, InvokeFrom, HandleOn) %}
{% if Property.attrib['IsPublic']|booleanTrue == ProctectedSection %}
{% if Property.attrib['IsPublic']|booleanTrue != IsProtected %}
{{ DefineRpcInvocation(Component, ClassName, Property, InvokeFrom, HandleOn) -}}
{% if Property.attrib['GenerateEventBindings']|booleanTrue == true %}
{{ DefineRpcSignal(Component, ClassName, Property, InvokeFrom) -}}
@@ -1490,6 +1494,10 @@ namespace {{ Component.attrib['Namespace'] }}
{% endif %}
}
{{ ComponentBaseName }}::{{ ComponentBaseName }}() = default;
{{ ComponentBaseName }}::~{{ ComponentBaseName }}() = default;
void {{ ComponentBaseName }}::Init()
{
if (m_netBindComponent == nullptr)
@@ -643,6 +643,7 @@ namespace Multiplayer
{
controlledEntity.GetNetBindComponent()->SetOwningConnectionId(connection->GetConnectionId());
}
controlledEntity.Activate();
if (connection->GetUserData() == nullptr) // Only add user data if the connect event handler has not already done so
{
@@ -763,6 +764,7 @@ namespace Multiplayer
{
controlledEntityNetBindComponent->SetAllowAutonomy(true);
}
controlledEntity.Activate();
}
AZLOG_INFO("Multiplayer operating in %s mode", GetEnumString(m_agentType));
@@ -969,7 +971,7 @@ namespace Multiplayer
NetworkEntityHandle MultiplayerSystemComponent::SpawnDefaultPlayerPrefab()
{
PrefabEntityId playerPrefabEntityId(AZ::Name(static_cast<AZ::CVarFixedString>(sv_defaultPlayerSpawnAsset).c_str()));
INetworkEntityManager::EntityList entityList = m_networkEntityManager.CreateEntitiesImmediate(playerPrefabEntityId, NetEntityRole::Authority, AZ::Transform::CreateIdentity());
INetworkEntityManager::EntityList entityList = m_networkEntityManager.CreateEntitiesImmediate(playerPrefabEntityId, NetEntityRole::Authority, AZ::Transform::CreateIdentity(), Multiplayer::AutoActivate::DoNotActivate);
NetworkEntityHandle controlledEntity;
if (entityList.size() > 0)
@@ -73,6 +73,11 @@ namespace Multiplayer
return m_networkEntityTracker.Get(netEntityId);
}
NetEntityId NetworkEntityManager::GetNetEntityIdById(const AZ::EntityId& entityId) const
{
return m_networkEntityTracker.Get(entityId);
}
uint32_t NetworkEntityManager::GetEntityCount() const
{
return static_cast<uint32_t>(m_networkEntityTracker.size());
@@ -304,7 +309,7 @@ namespace Multiplayer
}
INetworkEntityManager::EntityList NetworkEntityManager::CreateEntitiesImmediate(
const AzFramework::Spawnable& spawnable, NetEntityRole netEntityRole)
const AzFramework::Spawnable& spawnable, NetEntityRole netEntityRole, AutoActivate autoActivate)
{
INetworkEntityManager::EntityList returnList;
@@ -354,6 +359,11 @@ namespace Multiplayer
const NetEntityId netEntityId = NextId();
netBindComponent->PreInit(clone, prefabEntityId, netEntityId, netEntityRole);
if (autoActivate == AutoActivate::DoNotActivate)
{
clone->SetRuntimeActiveByDefault(false);
}
AzFramework::GameEntityContextRequestBus::Broadcast(
&AzFramework::GameEntityContextRequestBus::Events::AddGameEntity, clone);
@@ -373,10 +383,11 @@ namespace Multiplayer
(
const PrefabEntityId& prefabEntryId,
NetEntityRole netEntityRole,
const AZ::Transform& transform
const AZ::Transform& transform,
AutoActivate autoActivate
)
{
return CreateEntitiesImmediate(prefabEntryId, NextId(), netEntityRole, AutoActivate::Activate, transform);
return CreateEntitiesImmediate(prefabEntryId, NextId(), netEntityRole, autoActivate, transform);
}
INetworkEntityManager::EntityList NetworkEntityManager::CreateEntitiesImmediate
@@ -409,7 +420,7 @@ namespace Multiplayer
if (entityIndex == PrefabEntityId::AllIndices)
{
return CreateEntitiesImmediate(*netSpawnable, netEntityRole);
return CreateEntitiesImmediate(*netSpawnable, netEntityRole, autoActivate);
}
const AzFramework::Spawnable::EntityList& entities = netSpawnable->GetEntities();
@@ -41,13 +41,15 @@ namespace Multiplayer
MultiplayerComponentRegistry* GetMultiplayerComponentRegistry() override;
HostId GetHostId() const override;
ConstNetworkEntityHandle GetEntity(NetEntityId netEntityId) const override;
NetEntityId GetNetEntityIdById(const AZ::EntityId& entityId) const override;
EntityList CreateEntitiesImmediate(const AzFramework::Spawnable& spawnable, NetEntityRole netEntityRole);
EntityList CreateEntitiesImmediate(const AzFramework::Spawnable& spawnable, NetEntityRole netEntityRole, AutoActivate autoActivate);
EntityList CreateEntitiesImmediate
(
const PrefabEntityId& prefabEntryId,
NetEntityRole netEntityRole,
const AZ::Transform& transform
const AZ::Transform& transform,
AutoActivate autoActivate = AutoActivate::Activate
) override;
EntityList CreateEntitiesImmediate
(
@@ -18,6 +18,7 @@ namespace Multiplayer
++m_addChangeDirty;
AZ_Assert(m_entityMap.end() == m_entityMap.find(netEntityId), "Attempting to add the same entity to the entity map multiple times");
m_entityMap[netEntityId] = entity;
m_netEntityIdMap[entity->GetId()] = netEntityId;
}
NetworkEntityHandle NetworkEntityTracker::Get(NetEntityId netEntityId)
@@ -32,6 +33,16 @@ namespace Multiplayer
return ConstNetworkEntityHandle(entity, netEntityId, this);
}
NetEntityId NetworkEntityTracker::Get(const AZ::EntityId& entityId) const
{
auto found = m_netEntityIdMap.find(entityId);
if (found != m_netEntityIdMap.end())
{
return found->second;
}
return Multiplayer::InvalidNetEntityId;
}
bool NetworkEntityTracker::Exists(NetEntityId netEntityId) const
{
return (m_entityMap.find(netEntityId) != m_entityMap.end());
@@ -50,12 +61,22 @@ namespace Multiplayer
void NetworkEntityTracker::erase(NetEntityId netEntityId)
{
++m_deleteChangeDirty;
m_entityMap.erase(netEntityId);
auto found = m_entityMap.find(netEntityId);
if (found != m_entityMap.end())
{
m_netEntityIdMap.erase(found->second->GetId());
m_entityMap.erase(found);
}
}
NetworkEntityTracker::EntityMap::iterator NetworkEntityTracker::erase(EntityMap::iterator iter)
{
++m_deleteChangeDirty;
if (iter != m_entityMap.end())
{
m_netEntityIdMap.erase(iter->second->GetId());
}
return m_entityMap.erase(iter);
}
@@ -22,6 +22,7 @@ namespace Multiplayer
public:
using EntityMap = AZStd::unordered_map<NetEntityId, AZ::Entity*>;
using NetEntityIdMap = AZStd::unordered_map<AZ::EntityId, NetEntityId>;
using iterator = EntityMap::iterator;
using const_iterator = EntityMap::const_iterator;
@@ -36,6 +37,8 @@ namespace Multiplayer
NetworkEntityHandle Get(NetEntityId netEntityId);
ConstNetworkEntityHandle Get(NetEntityId netEntityId) const;
NetEntityId Get(const AZ::EntityId& entityId) const;
//! Returns true if the netEntityId exists.
bool Exists(NetEntityId netEntityId) const;
@@ -74,6 +77,7 @@ namespace Multiplayer
private:
EntityMap m_entityMap;
NetEntityIdMap m_netEntityIdMap;
uint32_t m_deleteChangeDirty = 0;
uint32_t m_addChangeDirty = 0;
};
@@ -48,6 +48,7 @@ namespace Multiplayer
inline void NetworkEntityTracker::clear()
{
m_entityMap.clear();
m_netEntityIdMap.clear();
}
inline uint32_t NetworkEntityTracker::GetChangeDirty(const AZ::Entity* entity) const
@@ -14,7 +14,6 @@
#include <AzCore/Math/IntersectSegment.h>
#include <AzCore/Math/Transform.h>
#include <AzCore/Math/Vector3.h>
#include <MathConversion.h>
namespace AZ
{
@@ -20,7 +20,7 @@ namespace SurfaceData
SurfaceDataSystemComponent::CreateDescriptor(),
SurfaceDataColliderComponent::CreateDescriptor(),
SurfaceDataShapeComponent::CreateDescriptor(),
TerrainSurfaceDataSystemComponent::CreateDescriptor(),
Terrain::TerrainSurfaceDataSystemComponent::CreateDescriptor(),
});
}
@@ -28,7 +28,7 @@ namespace SurfaceData
{
return AZ::ComponentTypeList{
azrtti_typeid<SurfaceDataSystemComponent>(),
azrtti_typeid<TerrainSurfaceDataSystemComponent>(),
azrtti_typeid<Terrain::TerrainSurfaceDataSystemComponent>(),
};
}
}
@@ -6,20 +6,16 @@
*
*/
#include "TerrainSurfaceDataSystemComponent.h"
#include <TerrainSurfaceDataSystemComponent.h>
#include <AzCore/Debug/Profiler.h>
#include <AzCore/Math/MathUtils.h>
#include <AzCore/Serialization/EditContext.h>
#include <AzCore/Serialization/SerializeContext.h>
#include <AzFramework/Terrain/TerrainDataRequestBus.h>
#include <MathConversion.h>
#include <SurfaceData/SurfaceDataSystemRequestBus.h>
#include <SurfaceData/SurfaceTag.h>
#include <SurfaceData/Utility/SurfaceDataUtility.h>
#include <ISystem.h>
namespace SurfaceData
namespace Terrain
{
//////////////////////////////////////////////////////////////////////////
// TerrainSurfaceDataSystemConfig
@@ -98,26 +94,23 @@ namespace SurfaceData
void TerrainSurfaceDataSystemComponent::Activate()
{
m_providerHandle = InvalidSurfaceDataRegistryHandle;
m_system = GetISystem();
CrySystemEventBus::Handler::BusConnect();
AZ::HeightmapUpdateNotificationBus::Handler::BusConnect();
m_providerHandle = SurfaceData::InvalidSurfaceDataRegistryHandle;
AzFramework::Terrain::TerrainDataNotificationBus::Handler::BusConnect();
UpdateTerrainData(AZ::Aabb::CreateNull());
}
void TerrainSurfaceDataSystemComponent::Deactivate()
{
if (m_providerHandle != InvalidSurfaceDataRegistryHandle)
if (m_providerHandle != SurfaceData::InvalidSurfaceDataRegistryHandle)
{
SurfaceDataSystemRequestBus::Broadcast(&SurfaceDataSystemRequestBus::Events::UnregisterSurfaceDataProvider, m_providerHandle);
m_providerHandle = InvalidSurfaceDataRegistryHandle;
SurfaceData::SurfaceDataSystemRequestBus::Broadcast(
&SurfaceData::SurfaceDataSystemRequestBus::Events::UnregisterSurfaceDataProvider, m_providerHandle);
m_providerHandle = SurfaceData::InvalidSurfaceDataRegistryHandle;
}
SurfaceDataProviderRequestBus::Handler::BusDisconnect();
AZ::HeightmapUpdateNotificationBus::Handler::BusDisconnect();
CrySystemEventBus::Handler::BusDisconnect();
m_system = nullptr;
SurfaceData::SurfaceDataProviderRequestBus::Handler::BusDisconnect();
AzFramework::Terrain::TerrainDataNotificationBus::Handler::BusDisconnect();
// Clear the cached terrain bounds data
{
@@ -146,17 +139,8 @@ namespace SurfaceData
return false;
}
void TerrainSurfaceDataSystemComponent::OnCrySystemInitialized(ISystem& system, [[maybe_unused]] const SSystemInitParams& systemInitParams)
{
m_system = &system;
}
void TerrainSurfaceDataSystemComponent::OnCrySystemShutdown([[maybe_unused]] ISystem& system)
{
m_system = nullptr;
}
void TerrainSurfaceDataSystemComponent::GetSurfacePoints(const AZ::Vector3& inPosition, SurfacePointList& surfacePointList) const
void TerrainSurfaceDataSystemComponent::GetSurfacePoints(
const AZ::Vector3& inPosition, SurfaceData::SurfacePointList& surfacePointList) const
{
if (m_terrainBoundsIsValid)
{
@@ -168,12 +152,13 @@ namespace SurfaceData
const float terrainHeight = terrain->GetHeight(inPosition, AzFramework::Terrain::TerrainDataRequests::Sampler::BILINEAR, &isTerrainValidAtPoint);
const bool isHole = !isTerrainValidAtPoint;
SurfacePoint point;
SurfaceData::SurfacePoint point;
point.m_entityId = GetEntityId();
point.m_position = AZ::Vector3(inPosition.GetX(), inPosition.GetY(), terrainHeight);
point.m_normal = terrain->GetNormal(inPosition);
const AZ::Crc32 terrainTag = isHole ? Constants::s_terrainHoleTagCrc : Constants::s_terrainTagCrc;
AddMaxValueForMasks(point.m_masks, terrainTag, 1.0f);
const AZ::Crc32 terrainTag =
isHole ? SurfaceData::Constants::s_terrainHoleTagCrc : SurfaceData::Constants::s_terrainTagCrc;
SurfaceData::AddMaxValueForMasks(point.m_masks, terrainTag, 1.0f);
surfacePointList.push_back(point);
}
// Only one handler should exist.
@@ -189,11 +174,11 @@ namespace SurfaceData
return terrain ? terrain->GetTerrainAabb() : AZ::Aabb::CreateNull();
}
SurfaceTagVector TerrainSurfaceDataSystemComponent::GetSurfaceTags() const
SurfaceData::SurfaceTagVector TerrainSurfaceDataSystemComponent::GetSurfaceTags() const
{
SurfaceTagVector tags;
tags.push_back(Constants::s_terrainHoleTagCrc);
tags.push_back(Constants::s_terrainTagCrc);
SurfaceData::SurfaceTagVector tags;
tags.push_back(SurfaceData::Constants::s_terrainHoleTagCrc);
tags.push_back(SurfaceData::Constants::s_terrainTagCrc);
return tags;
}
@@ -203,7 +188,7 @@ namespace SurfaceData
bool terrainValidAfterUpdate = false;
AZ::Aabb terrainBoundsBeforeUpdate = m_terrainBounds;
SurfaceDataRegistryEntry registryEntry;
SurfaceData::SurfaceDataRegistryEntry registryEntry;
registryEntry.m_entityId = GetEntityId();
registryEntry.m_bounds = GetSurfaceAabb();
registryEntry.m_tags = GetSurfaceTags();
@@ -215,38 +200,44 @@ namespace SurfaceData
if (terrainValidBeforeUpdate && terrainValidAfterUpdate)
{
AZ_Assert((m_providerHandle != InvalidSurfaceDataRegistryHandle), "Invalid surface data handle");
AZ_Assert((m_providerHandle != SurfaceData::InvalidSurfaceDataRegistryHandle), "Invalid surface data handle");
// Our terrain was valid before and after, it just changed in some way. If we have a valid dirty region passed in
// then it's possible that the heightmap has been modified in the Editor. Otherwise, just notify that the entire
// terrain has changed in some way.
if (dirtyRegion.IsValid())
{
SurfaceDataSystemRequestBus::Broadcast(&SurfaceDataSystemRequestBus::Events::RefreshSurfaceData, dirtyRegion);
SurfaceData::SurfaceDataSystemRequestBus::Broadcast(
&SurfaceData::SurfaceDataSystemRequestBus::Events::RefreshSurfaceData, dirtyRegion);
}
else
{
SurfaceDataSystemRequestBus::Broadcast(&SurfaceDataSystemRequestBus::Events::UpdateSurfaceDataProvider, m_providerHandle, registryEntry);
SurfaceData::SurfaceDataSystemRequestBus::Broadcast(
&SurfaceData::SurfaceDataSystemRequestBus::Events::UpdateSurfaceDataProvider, m_providerHandle, registryEntry);
}
}
else if (!terrainValidBeforeUpdate && terrainValidAfterUpdate)
{
// Our terrain has become valid, so register as a provider and save off the registry handles
AZ_Assert((m_providerHandle == InvalidSurfaceDataRegistryHandle), "Surface Provider data handle is initialized before our terrain became valid");
SurfaceDataSystemRequestBus::BroadcastResult(m_providerHandle, &SurfaceDataSystemRequestBus::Events::RegisterSurfaceDataProvider, registryEntry);
AZ_Assert(
(m_providerHandle == SurfaceData::InvalidSurfaceDataRegistryHandle),
"Surface Provider data handle is initialized before our terrain became valid");
SurfaceData::SurfaceDataSystemRequestBus::BroadcastResult(
m_providerHandle, &SurfaceData::SurfaceDataSystemRequestBus::Events::RegisterSurfaceDataProvider, registryEntry);
// Start listening for surface data events
AZ_Assert((m_providerHandle != InvalidSurfaceDataRegistryHandle), "Invalid surface data handle");
SurfaceDataProviderRequestBus::Handler::BusConnect(m_providerHandle);
AZ_Assert((m_providerHandle != SurfaceData::InvalidSurfaceDataRegistryHandle), "Invalid surface data handle");
SurfaceData::SurfaceDataProviderRequestBus::Handler::BusConnect(m_providerHandle);
}
else if (terrainValidBeforeUpdate && !terrainValidAfterUpdate)
{
// Our terrain has stopped being valid, so unregister and stop listening for surface data events
AZ_Assert((m_providerHandle != InvalidSurfaceDataRegistryHandle), "Invalid surface data handle");
SurfaceDataSystemRequestBus::Broadcast(&SurfaceDataSystemRequestBus::Events::UnregisterSurfaceDataProvider, m_providerHandle);
m_providerHandle = InvalidSurfaceDataRegistryHandle;
AZ_Assert((m_providerHandle != SurfaceData::InvalidSurfaceDataRegistryHandle), "Invalid surface data handle");
SurfaceData::SurfaceDataSystemRequestBus::Broadcast(
&SurfaceData::SurfaceDataSystemRequestBus::Events::UnregisterSurfaceDataProvider, m_providerHandle);
m_providerHandle = SurfaceData::InvalidSurfaceDataRegistryHandle;
SurfaceDataProviderRequestBus::Handler::BusDisconnect();
SurfaceData::SurfaceDataProviderRequestBus::Handler::BusDisconnect();
}
else
{
@@ -255,8 +246,9 @@ namespace SurfaceData
}
void TerrainSurfaceDataSystemComponent::HeightmapModified(const AZ::Aabb& bounds)
void TerrainSurfaceDataSystemComponent::OnTerrainDataChanged(
const AZ::Aabb& dirtyRegion, [[maybe_unused]] TerrainDataChangedMask dataChangedMask)
{
UpdateTerrainData(bounds);
UpdateTerrainData(dirtyRegion);
}
}
@@ -10,12 +10,11 @@
#include <AzCore/Component/Component.h>
#include <AzCore/Component/Entity.h>
#include <AzCore/EBus/EBus.h>
#include <CrySystemBus.h>
#include <HeightmapUpdateNotificationBus.h>
#include <AzFramework/Terrain/TerrainDataRequestBus.h>
#include <SurfaceData/SurfaceDataModifierRequestBus.h>
#include <SurfaceData/SurfaceDataProviderRequestBus.h>
namespace SurfaceData
namespace Terrain
{
class TerrainSurfaceDataSystemConfig
: public AZ::ComponentConfig
@@ -31,9 +30,8 @@ namespace SurfaceData
*/
class TerrainSurfaceDataSystemComponent
: public AZ::Component
, private SurfaceDataProviderRequestBus::Handler
, private AZ::HeightmapUpdateNotificationBus::Handler
, private CrySystemEventBus::Handler
, private SurfaceData::SurfaceDataProviderRequestBus::Handler
, private AzFramework::Terrain::TerrainDataNotificationBus::Handler
{
friend class EditorTerrainSurfaceDataSystemComponent;
TerrainSurfaceDataSystemComponent(const TerrainSurfaceDataSystemConfig&);
@@ -58,25 +56,19 @@ namespace SurfaceData
//////////////////////////////////////////////////////////////////////////
// SurfaceDataProviderRequestBus
void GetSurfacePoints(const AZ::Vector3& inPosition, SurfacePointList& surfacePointList) const;
////////////////////////////////////////////////////////////////////////////
// CrySystemEvents
void OnCrySystemInitialized(ISystem& system, const SSystemInitParams& systemInitParams) override;
void OnCrySystemShutdown(ISystem& system) override;
void GetSurfacePoints(const AZ::Vector3& inPosition, SurfaceData::SurfacePointList& surfacePointList) const;
//////////////////////////////////////////////////////////////////////////
// AZ::HeightmapUpdateNotificationBus
void HeightmapModified(const AZ::Aabb& bounds) override;
// AzFramework::Terrain::TerrainDataNotificationBus
void OnTerrainDataChanged(const AZ::Aabb& dirtyRegion, TerrainDataChangedMask dataChangedMask) override;
private:
void UpdateTerrainData(const AZ::Aabb& dirtyRegion);
AZ::Aabb GetSurfaceAabb() const;
SurfaceTagVector GetSurfaceTags() const;
SurfaceDataRegistryHandle m_providerHandle = InvalidSurfaceDataRegistryHandle;
SurfaceData::SurfaceTagVector GetSurfaceTags() const;
SurfaceData::SurfaceDataRegistryHandle m_providerHandle = SurfaceData::InvalidSurfaceDataRegistryHandle;
TerrainSurfaceDataSystemConfig m_configuration;
ISystem* m_system = nullptr;
AZ::Aabb m_terrainBounds = AZ::Aabb::CreateNull();
AZStd::atomic_bool m_terrainBoundsIsValid{ false };