Merge branch 'main' into Atom/santorac/NewLayeringWorkflow

This commit is contained in:
Chris Santora
2021-05-12 17:45:28 -07:00
1542 changed files with 31413 additions and 174078 deletions
@@ -21,6 +21,8 @@
#include <Atom/RPI.Edit/Material/MaterialSourceData.h>
#include <Atom/RPI.Edit/Material/MaterialTypeSourceData.h>
#include <Atom/Document/MaterialDocumentSettings.h>
#include <QFileDialog>
namespace MaterialEditor
@@ -69,8 +71,11 @@ namespace MaterialEditor
QObject::connect(m_ui->m_materialTypeComboBox, static_cast<void (QComboBox::*)(const int)>(&QComboBox::currentIndexChanged), this, [this]() { UpdateMaterialTypeSelection(); });
QObject::connect(m_ui->m_materialTypeComboBox, &QComboBox::currentTextChanged, this, [this]() { UpdateMaterialTypeSelection(); });
// Select StandardPBR by default but we will later data drive this with editor settings
const int index = m_ui->m_materialTypeComboBox->findText("StandardPBR");
// Select the default material type from settings
auto settings =
AZ::UserSettings::CreateFind<MaterialDocumentSettings>(AZ::Crc32("MaterialDocumentSettings"), AZ::UserSettings::CT_GLOBAL);
const int index = m_ui->m_materialTypeComboBox->findText(settings->m_defaultMaterialTypeName.c_str());
if (index >= 0)
{
m_ui->m_materialTypeComboBox->setCurrentIndex(index);
@@ -0,0 +1,20 @@
<?xml version="1.0" encoding="UTF-8"?>
<svg width="256px" height="256px" viewBox="0 0 256 256" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
<title>Icons / Application Icons / Material Editor</title>
<defs>
<polygon id="path-1" points="7.67007885e-15 0 256 0 256 256.000195 7.67007885e-15 256.000195"></polygon>
</defs>
<g id="Icons-/-Application-Icons-/-Material-Editor" stroke="none" stroke-width="1" fill="none" fill-rule="evenodd">
<g id="Group" transform="translate(-0.000000, 0.000000)">
<g id="Fill-1-Clipped" transform="translate(-0.000000, 0.000000)">
<mask id="mask-2" fill="white">
<use xlink:href="#path-1"></use>
</mask>
<g id="path-1"></g>
<path d="M184.641349,-0.000129743592 L71.3589754,-0.000129743592 C32.1115389,-0.000129743592 7.67007885e-15,32.1114092 7.67007885e-15,71.3588457 L7.67007885e-15,184.641219 C7.67007885e-15,223.888656 32.1115389,256.000195 71.3589754,256.000195 L184.641349,256.000195 C223.888785,256.000195 256.000324,223.888656 256.000324,184.641219 L256.000324,71.3588457 C256.000324,32.1114092 223.888785,-0.000129743592 184.641349,-0.000129743592" id="Fill-1" fill="#1E70EB" fill-rule="nonzero" mask="url(#mask-2)"></path>
</g>
<path d="M128.000162,32.2473156 C74.9006511,32.2473156 32.2467966,74.9005214 32.2467966,128.000681 C32.2467966,181.099543 74.9006511,223.752749 128.000162,223.752749 C181.099673,223.752749 223.752879,181.099543 223.752879,128.000681 C223.752879,74.9005214 181.099673,32.2473156 128.000162,32.2473156 L128.000162,32.2473156 Z M198.508668,93.1813935 L168.912209,93.1813935 C166.301119,79.2534189 162.81945,65.3254443 157.595973,54.8797877 C175.005617,62.7143545 189.804171,75.7717496 198.508668,93.1813935 L198.508668,93.1813935 Z M154.114304,128.000681 C154.114304,134.09344 154.114304,140.186848 153.243724,145.409676 L102.755952,145.409676 C101.885372,140.186848 101.885372,134.09344 101.885372,128.000681 C101.885372,121.906625 101.885372,115.813217 102.755952,110.590389 L153.243724,110.590389 C154.114304,115.813217 154.114304,121.906625 154.114304,128.000681 L154.114304,128.000681 Z M128.000162,206.343105 C120.165595,206.343105 109.719939,189.804041 104.497111,162.81932 L150.632634,162.81932 C146.280386,189.804041 135.83408,206.343105 128.000162,206.343105 L128.000162,206.343105 Z M104.497111,93.1813935 C109.719939,66.1960238 120.165595,49.6569595 128.000162,49.6569595 C135.83408,49.6569595 146.280386,66.1960238 151.502565,93.1813935 L104.497111,93.1813935 Z M99.2742823,54.8797877 C94.0508053,65.3254443 89.6985565,79.2534189 87.0874667,93.1813935 L57.4910073,93.1813935 C66.1961536,75.7717496 80.9940589,62.7143545 99.2742823,54.8797877 L99.2742823,54.8797877 Z M51.3975995,110.590389 L84.4757282,110.590389 L84.4757282,128.000681 C84.4757282,134.09344 84.4757282,139.316269 85.3463077,145.409676 L51.3975995,145.409676 C50.52702,140.186848 49.6564405,134.09344 49.6564405,128.000681 C49.6564405,121.906625 50.52702,115.813217 51.3975995,110.590389 L51.3975995,110.590389 Z M57.4910073,162.81932 L87.0874667,162.81932 C89.6985565,176.746646 93.1808745,190.674621 98.4037028,201.120277 C80.9940589,193.28571 66.1961536,180.228964 57.4910073,162.81932 L57.4910073,162.81932 Z M156.725393,201.120277 C161.948222,190.674621 166.301119,177.617874 168.042278,162.81932 L197.638089,162.81932 C189.804171,180.228964 175.005617,193.28571 156.725393,201.120277 L156.725393,201.120277 Z M204.602076,145.409676 L171.523947,145.409676 C172.394527,139.316269 172.394527,134.09344 172.394527,128.000681 C172.394527,121.906625 172.394527,116.683796 171.523947,110.590389 L204.602076,110.590389 C205.472656,115.813217 206.343235,121.906625 206.343235,128.000681 C206.343235,134.09344 205.472656,140.186848 204.602076,145.409676 L204.602076,145.409676 Z" id="Fill-4" fill="#FFFFFF" fill-rule="nonzero"></path>
<path d="M128.000162,212.590259 L128.000162,125.542689 L128.000162,38.4944696 C128.000162,12.3803281 223.752879,73.3137573 223.752879,125.542689 C223.752879,177.770972 128.000162,238.705049 128.000162,212.590259" id="Fill-6" fill="#FFFFFF" fill-rule="nonzero"></path>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 4.2 KiB

@@ -1,6 +1,7 @@
<RCC>
<qresource prefix="/">
<file>MaterialEditor.qss</file>
<file>Icons/materialeditor.svg</file>
<file>Icons/material.svg</file>
<file>Icons/materialtype.svg</file>
<file>Icons/mesh.svg</file>
@@ -10,45 +10,51 @@
*
*/
#include <AzFramework/StringFunc/StringFunc.h>
#include <AzFramework/Application/Application.h>
#include <AzToolsFramework/AssetBrowser/AssetBrowserEntry.h>
#include <AzToolsFramework/API/EditorPythonRunnerRequestsBus.h>
#include <AzToolsFramework/API/EditorAssetSystemAPI.h>
#include <AzToolsFramework/PythonTerminal/ScriptTermDialog.h>
#include <AzQtComponents/Components/StyleManager.h>
#include <AzQtComponents/Utilities/QtPluginPaths.h>
#include <AtomToolsFramework/Util/Util.h>
#include <Atom/Document/MaterialDocumentRequestBus.h>
#include <Atom/Document/MaterialDocumentSystemRequestBus.h>
#include <Atom/Window/MaterialEditorWindowNotificationBus.h>
#include <Atom/RHI/Factory.h>
#include <Atom/RPI.Edit/Common/AssetUtils.h>
#include <Atom/RPI.Edit/Common/JsonUtils.h>
#include <Atom/RPI.Edit/Material/MaterialSourceData.h>
#include <Atom/RPI.Edit/Material/MaterialTypeSourceData.h>
#include <Atom/RPI.Reflect/Image/StreamingImageAsset.h>
#include <Atom/Document/MaterialDocumentRequestBus.h>
#include <Atom/Document/MaterialDocumentSystemRequestBus.h>
#include <Atom/Window/MaterialEditorWindowNotificationBus.h>
#include <Atom/Window/MaterialEditorWindowSettings.h>
#include <AtomToolsFramework/Util/Util.h>
#include <AzFramework/Application/Application.h>
#include <AzFramework/StringFunc/StringFunc.h>
#include <AzQtComponents/Components/StyleManager.h>
#include <AzQtComponents/Components/WindowDecorationWrapper.h>
#include <AzQtComponents/Utilities/QtPluginPaths.h>
#include <AzToolsFramework/API/EditorAssetSystemAPI.h>
#include <AzToolsFramework/API/EditorPythonRunnerRequestsBus.h>
#include <AzToolsFramework/AssetBrowser/AssetBrowserEntry.h>
#include <AzToolsFramework/PythonTerminal/ScriptTermDialog.h>
#include <Viewport/MaterialViewportWidget.h>
#include <Viewport/MaterialViewportWidget.h>
#include <Window/MaterialEditorWindow.h>
#include <Window/PerformanceMonitor/PerformanceMonitorWidget.h>
#include <Window/HelpDialog/HelpDialog.h>
#include <Window/MaterialBrowserWidget.h>
#include <Window/MaterialInspector/MaterialInspector.h>
#include <Window/ViewportSettingsInspector/ViewportSettingsInspector.h>
#include <Window/CreateMaterialDialog/CreateMaterialDialog.h>
#include <Window/HelpDialog/HelpDialog.h>
#include <Window/SettingsDialog/SettingsDialog.h>
#include <Window/MaterialBrowserWidget.h>
#include <Window/MaterialEditorWindow.h>
#include <Window/MaterialInspector/MaterialInspector.h>
#include <Window/PerformanceMonitor/PerformanceMonitorWidget.h>
#include <Window/ViewportSettingsInspector/ViewportSettingsInspector.h>
AZ_PUSH_DISABLE_WARNING(4251 4800, "-Wunknown-warning-option") // disable warnings spawned by QT
#include <QApplication>
#include <QByteArray>
#include <QCloseEvent>
#include <QVariant>
#include <QDesktopWidget>
#include <QFileDialog>
#include <QWindow>
#include <QVBoxLayout>
#include <QVariant>
#include <QWindow>
AZ_POP_DISABLE_WARNING
namespace MaterialEditor
@@ -56,9 +62,18 @@ namespace MaterialEditor
MaterialEditorWindow::MaterialEditorWindow(QWidget* parent /* = 0 */)
: AzQtComponents::DockMainWindow(parent)
{
resize(1280, 1024);
// Among other things, we need the window wrapper to save the main window size, position, and state
auto mainWindowWrapper =
new AzQtComponents::WindowDecorationWrapper(AzQtComponents::WindowDecorationWrapper::OptionAutoTitleBarButtons);
mainWindowWrapper->setGuest(this);
mainWindowWrapper->enableSaveRestoreGeometry("amazon", "MaterialEditor", "mainWindowGeometry");
// set the style sheet for RPE highlighting and other styling
AzQtComponents::StyleManager::setStyleSheet(this, QStringLiteral(":/MaterialEditor.qss"));
QApplication::setWindowIcon(QIcon(":/Icons/materialtype.svg"));
QApplication::setWindowIcon(QIcon(":/Icons/materialeditor.svg"));
AZ::Name apiName = AZ::RHI::Factory::Get().GetName();
if (!apiName.IsEmpty())
@@ -74,6 +89,7 @@ namespace MaterialEditor
m_advancedDockManager = new AzQtComponents::FancyDocking(this);
setObjectName("MaterialEditorWindow");
setDockNestingEnabled(true);
setCorner(Qt::TopLeftCorner, Qt::LeftDockWidgetArea);
setCorner(Qt::BottomLeftCorner, Qt::LeftDockWidgetArea);
@@ -81,17 +97,21 @@ namespace MaterialEditor
setCorner(Qt::BottomRightCorner, Qt::RightDockWidgetArea);
m_menuBar = new QMenuBar(this);
m_menuBar->setObjectName("MenuBar");
setMenuBar(m_menuBar);
m_toolBar = new MaterialEditorToolBar(this);
m_toolBar->setObjectName("ToolBar");
addToolBar(m_toolBar);
m_centralWidget = new QWidget(this);
m_tabWidget = new AzQtComponents::TabWidget(m_centralWidget);
m_tabWidget->setObjectName("TabWidget");
m_tabWidget->setSizePolicy(QSizePolicy::Ignored, QSizePolicy::Preferred);
m_tabWidget->setContentsMargins(0, 0, 0, 0);
m_materialViewport = new MaterialViewportWidget(m_centralWidget);
m_materialViewport->setObjectName("Viewport");
m_materialViewport->setSizePolicy(QSizePolicy::MinimumExpanding, QSizePolicy::MinimumExpanding);
QVBoxLayout* vl = new QVBoxLayout(m_centralWidget);
@@ -103,7 +123,8 @@ namespace MaterialEditor
setCentralWidget(m_centralWidget);
m_statusBar = new StatusBarWidget(this);
this->statusBar()->addPermanentWidget(m_statusBar, 1);
m_statusBar->setObjectName("StatusBar");
statusBar()->addPermanentWidget(m_statusBar, 1);
SetupMenu();
SetupTabs();
@@ -118,6 +139,19 @@ namespace MaterialEditor
SetDockWidgetVisible("Performance Monitor", false);
SetDockWidgetVisible("Python Terminal", false);
// Restore geometry and show the window
mainWindowWrapper->showFromSettings();
// Restore additional state for docked windows
auto windowSettings = AZ::UserSettings::CreateFind<MaterialEditorWindowSettings>(
AZ::Crc32("MaterialEditorWindowSettings"), AZ::UserSettings::CT_GLOBAL);
if (!windowSettings->m_mainWindowState.empty())
{
QByteArray windowState(windowSettings->m_mainWindowState.data(), windowSettings->m_mainWindowState.size());
m_advancedDockManager->restoreState(windowState);
}
MaterialEditorWindowRequestBus::Handler::BusConnect();
MaterialDocumentNotificationBus::Handler::BusConnect();
OnDocumentOpened(AZ::Uuid::CreateNull());
@@ -144,8 +178,9 @@ namespace MaterialEditor
}
auto dockWidget = new AzQtComponents::StyledDockWidget(name.c_str());
dockWidget->setObjectName(name.c_str());
dockWidget->setObjectName(QString("%1_DockWidget").arg(name.c_str()));
dockWidget->setFeatures(QDockWidget::DockWidgetClosable | QDockWidget::DockWidgetFloatable | QDockWidget::DockWidgetMovable);
widget->setObjectName(name.c_str());
widget->setParent(dockWidget);
widget->setMinimumSize(QSize(300, 300));
dockWidget->setWidget(widget);
@@ -203,15 +238,16 @@ namespace MaterialEditor
QSize requestedWindowSize = size() + offset;
resize(requestedWindowSize);
AZ_Assert(m_materialViewport->size() == requestedViewportSize,
AZ_Assert(
m_materialViewport->size() == requestedViewportSize,
"Resizing the window did not give the expected viewport size. Requested %d x %d but got %d x %d.",
requestedViewportSize.width(), requestedViewportSize.height(),
m_materialViewport->size().width(), m_materialViewport->size().height());
requestedViewportSize.width(), requestedViewportSize.height(), m_materialViewport->size().width(),
m_materialViewport->size().height());
QSize newDeviceSize = m_materialViewport->size();
AZ_Warning("Material Editor", newDeviceSize.width() == width && newDeviceSize.height() == height,
"Resizing the window did not give the expected frame size. Requested %d x %d but got %d x %d.",
width, height,
AZ_Warning(
"Material Editor", newDeviceSize.width() == width && newDeviceSize.height() == height,
"Resizing the window did not give the expected frame size. Requested %d x %d but got %d x %d.", width, height,
newDeviceSize.width(), newDeviceSize.height());
}
@@ -235,6 +271,13 @@ namespace MaterialEditor
return;
}
// Capture docking state before shutdown
auto windowSettings = AZ::UserSettings::CreateFind<MaterialEditorWindowSettings>(
AZ::Crc32("MaterialEditorWindowSettings"), AZ::UserSettings::CT_GLOBAL);
QByteArray windowState = m_advancedDockManager->saveState();
windowSettings->m_mainWindowState.assign(windowState.begin(), windowState.end());
MaterialEditorWindowNotificationBus::Broadcast(&MaterialEditorWindowNotifications::OnMaterialEditorWindowClosing);
}
@@ -272,7 +315,7 @@ namespace MaterialEditor
m_actionUndo->setEnabled(canUndo);
m_actionRedo->setEnabled(canRedo);
m_actionPreferences->setEnabled(false);
m_actionSettings->setEnabled(true);
m_actionAssetBrowser->setEnabled(true);
m_actionInspector->setEnabled(true);
@@ -465,9 +508,11 @@ namespace MaterialEditor
m_menuEdit->addSeparator();
m_actionPreferences = m_menuEdit->addAction("&Preferences...", [this]() {
m_actionSettings = m_menuEdit->addAction("&Settings...", [this]() {
SettingsDialog dialog(this);
dialog.exec();
}, QKeySequence::Preferences);
m_actionPreferences->setEnabled(false);
m_actionSettings->setEnabled(true);
m_menuView = m_menuBar->addMenu("&View");
@@ -512,8 +557,8 @@ namespace MaterialEditor
m_menuHelp = m_menuBar->addMenu("&Help");
m_actionHelp = m_menuHelp->addAction("&Help...", [this]() {
HelpDialog dlg(this);
dlg.exec();
HelpDialog dialog(this);
dialog.exec();
});
m_actionAbout = m_menuHelp->addAction("&About...", [this]() {
@@ -119,7 +119,7 @@ namespace MaterialEditor
QMenu* m_menuEdit = {};
QAction* m_actionUndo = {};
QAction* m_actionRedo = {};
QAction* m_actionPreferences = {};
QAction* m_actionSettings = {};
QMenu* m_menuView = {};
QAction* m_actionAssetBrowser = {};
@@ -10,25 +10,24 @@
*
*/
#include <AzCore/Serialization/SerializeContext.h>
#include <AzCore/Serialization/EditContext.h>
#include <Atom/Window/MaterialEditorWindowFactoryRequestBus.h>
#include <Atom/Window/MaterialEditorWindowSettings.h>
#include <AzCore/RTTI/BehaviorContext.h>
#include <AzToolsFramework/API/ViewPaneOptions.h>
#include <AzCore/Serialization/EditContext.h>
#include <AzCore/Serialization/SerializeContext.h>
#include <AzToolsFramework/API/EditorAssetSystemAPI.h>
#include <AzToolsFramework/API/ToolsApplicationAPI.h>
#include <AzToolsFramework/API/ViewPaneOptions.h>
#include <AzToolsFramework/UI/UICore/QWidgetSavedState.h>
#include <Atom/Window/MaterialEditorWindowFactoryRequestBus.h>
#include <Source/Window/MaterialEditorWindowComponent.h>
#include <Source/Window/MaterialEditorWindow.h>
#include <Source/Window/ViewportSettingsInspector/ViewportSettingsInspector.h>
#include <Window/MaterialEditorWindow.h>
#include <Window/MaterialEditorWindowComponent.h>
#include <Window/ViewportSettingsInspector/ViewportSettingsInspector.h>
namespace MaterialEditor
{
void MaterialEditorWindowComponent::Reflect(AZ::ReflectContext* context)
{
GeneralViewportSettings::Reflect(context);
MaterialEditorWindowSettings::Reflect(context);
if (AZ::SerializeContext* serialize = azrtti_cast<AZ::SerializeContext*>(context))
{
@@ -102,7 +101,6 @@ namespace MaterialEditor
m_materialEditorBrowserInteractions.reset(aznew MaterialEditorBrowserInteractions);
m_window.reset(aznew MaterialEditorWindow);
m_window->show();
}
void MaterialEditorWindowComponent::DestroyMaterialEditorWindow()
@@ -0,0 +1,50 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#include <Atom/Window/MaterialEditorWindowSettings.h>
#include <AzCore/RTTI/BehaviorContext.h>
#include <AzCore/Serialization/EditContext.h>
namespace MaterialEditor
{
void MaterialEditorWindowSettings::Reflect(AZ::ReflectContext* context)
{
if (auto serializeContext = azrtti_cast<AZ::SerializeContext*>(context))
{
serializeContext->Class<MaterialEditorWindowSettings, AZ::UserSettings>()
->Version(1)
->Field("mainWindowState", &MaterialEditorWindowSettings::m_mainWindowState)
->Field("inspectorCollapsedGroups", &MaterialEditorWindowSettings::m_inspectorCollapsedGroups)
;
if (auto editContext = serializeContext->GetEditContext())
{
editContext->Class<MaterialEditorWindowSettings>(
"MaterialEditorWindowSettings", "")
->ClassElement(AZ::Edit::ClassElements::EditorData, "")
->Attribute(AZ::Edit::Attributes::AutoExpand, true)
;
}
}
if (auto behaviorContext = azrtti_cast<AZ::BehaviorContext*>(context))
{
behaviorContext->Class<MaterialEditorWindowSettings>("MaterialEditorWindowSettings")
->Attribute(AZ::Script::Attributes::Scope, AZ::Script::Attributes::ScopeFlags::Common)
->Attribute(AZ::Script::Attributes::Category, "Editor")
->Attribute(AZ::Script::Attributes::Module, "render")
->Constructor()
->Constructor<const MaterialEditorWindowSettings&>()
;
}
}
} // namespace MaterialEditor
@@ -1,14 +1,14 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#include <Atom/RPI.Edit/Common/AssetUtils.h>
#include <Atom/RPI.Edit/Material/MaterialPropertyId.h>
@@ -21,13 +21,16 @@
#include <AtomToolsFramework/Inspector/InspectorPropertyGroupWidget.h>
#include <AtomToolsFramework/Util/MaterialPropertyUtil.h>
#include <Source/Window/MaterialInspector/MaterialInspector.h>
#include <Window/MaterialInspector/MaterialInspector.h>
namespace MaterialEditor
{
MaterialInspector::MaterialInspector(QWidget* parent)
: AtomToolsFramework::InspectorWidget(parent)
{
m_windowSettings = AZ::UserSettings::CreateFind<MaterialEditorWindowSettings>(
AZ::Crc32("MaterialEditorWindowSettings"), AZ::UserSettings::CT_GLOBAL);
MaterialDocumentNotificationBus::Handler::BusConnect();
}
@@ -39,6 +42,7 @@ namespace MaterialEditor
void MaterialInspector::Reset()
{
m_documentPath.clear();
m_documentId = AZ::Uuid::CreateNull();
m_groups = {};
@@ -46,6 +50,22 @@ namespace MaterialEditor
AtomToolsFramework::InspectorWidget::Reset();
}
bool MaterialInspector::ShouldGroupAutoExpanded(const AZStd::string& groupNameId) const
{
auto stateItr = m_windowSettings->m_inspectorCollapsedGroups.find(GetGroupSaveStateKey(groupNameId));
return stateItr == m_windowSettings->m_inspectorCollapsedGroups.end();
}
void MaterialInspector::OnGroupExpanded(const AZStd::string& groupNameId)
{
m_windowSettings->m_inspectorCollapsedGroups.erase(GetGroupSaveStateKey(groupNameId));
}
void MaterialInspector::OnGroupCollapsed(const AZStd::string& groupNameId)
{
m_windowSettings->m_inspectorCollapsedGroups.insert(GetGroupSaveStateKey(groupNameId));
}
void MaterialInspector::OnDocumentOpened(const AZ::Uuid& documentId)
{
AddGroupsBegin();
@@ -55,6 +75,8 @@ namespace MaterialEditor
bool isOpen = false;
MaterialDocumentRequestBus::EventResult(isOpen, m_documentId, &MaterialDocumentRequestBus::Events::IsOpen);
MaterialDocumentRequestBus::EventResult(m_documentPath, m_documentId, &MaterialDocumentRequestBus::Events::GetAbsolutePath);
if (!m_documentId.IsNull() && isOpen)
{
// Create the top group for displaying details about the material
@@ -70,10 +92,24 @@ namespace MaterialEditor
AddGroupsEnd();
}
AZ::Crc32 MaterialInspector::GetGroupSaveStateKey(const AZStd::string& groupNameId) const
{
return AZ::Crc32(AZStd::string::format("MaterialInspector::PropertyGroup::%s::%s", m_documentPath.c_str(), groupNameId.c_str()));
}
bool MaterialInspector::CompareInstanceNodeProperties(
const AzToolsFramework::InstanceDataNode* source, const AzToolsFramework::InstanceDataNode* target) const
{
AZ_UNUSED(source);
const AtomToolsFramework::DynamicProperty* property = AtomToolsFramework::FindDynamicPropertyForInstanceDataNode(target);
return property && AtomToolsFramework::ArePropertyValuesEqual(property->GetValue(), property->GetConfig().m_parentValue);
}
void MaterialInspector::AddDetailsGroup()
{
const AZ::RPI::MaterialTypeSourceData* materialTypeSourceData = nullptr;
MaterialDocumentRequestBus::EventResult(materialTypeSourceData, m_documentId, &MaterialDocumentRequestBus::Events::GetMaterialTypeSourceData);
MaterialDocumentRequestBus::EventResult(
materialTypeSourceData, m_documentId, &MaterialDocumentRequestBus::Events::GetMaterialTypeSourceData);
const AZStd::string groupNameId = "details";
const AZStd::string groupDisplayName = "Details";
@@ -81,20 +117,19 @@ namespace MaterialEditor
auto& group = m_groups[groupNameId];
AtomToolsFramework::DynamicProperty property;
MaterialDocumentRequestBus::EventResult(property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty, AZ::Name("details.materialType"));
MaterialDocumentRequestBus::EventResult(
property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty, AZ::Name("details.materialType"));
group.m_properties.push_back(property);
property = {};
MaterialDocumentRequestBus::EventResult(property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty, AZ::Name("details.parentMaterial"));
MaterialDocumentRequestBus::EventResult(
property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty, AZ::Name("details.parentMaterial"));
group.m_properties.push_back(property);
// Passing in same group as main and comparison instance to enable custom value comparison for highlighting modified properties
auto propertyGroupWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(&group, &group, group.TYPEINFO_Uuid(), this, this,
[this](const AzToolsFramework::InstanceDataNode* source, const AzToolsFramework::InstanceDataNode* target) {
AZ_UNUSED(source);
const AtomToolsFramework::DynamicProperty* property = AtomToolsFramework::FindDynamicPropertyForInstanceDataNode(target);
return property && AtomToolsFramework::ArePropertyValuesEqual(property->GetValue(), property->GetConfig().m_parentValue);
});
auto propertyGroupWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(
&group, &group, group.TYPEINFO_Uuid(), this, this, GetGroupSaveStateKey(groupNameId),
[this](const auto source, const auto target) { return CompareInstanceNodeProperties(source, target); });
AddGroup(groupNameId, groupDisplayName, groupDescription, propertyGroupWidget);
}
@@ -114,32 +149,33 @@ namespace MaterialEditor
for (const auto& uvNamePair : uvNameMap)
{
AtomToolsFramework::DynamicProperty property;
MaterialDocumentRequestBus::EventResult(property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty, AZ::RPI::MaterialPropertyId(groupNameId, uvNamePair.m_shaderInput.ToString()).GetFullName());
MaterialDocumentRequestBus::EventResult(
property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty,
AZ::RPI::MaterialPropertyId(groupNameId, uvNamePair.m_shaderInput.ToString()).GetFullName());
group.m_properties.push_back(property);
property.SetValue(property.GetConfig().m_parentValue);
}
// Passing in same group as main and comparison instance to enable custom value comparison for highlighting modified properties
auto propertyGroupWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(&group, &group, group.TYPEINFO_Uuid(), this, this,
[this](const AzToolsFramework::InstanceDataNode* source, const AzToolsFramework::InstanceDataNode* target) {
AZ_UNUSED(source);
const AtomToolsFramework::DynamicProperty* property = AtomToolsFramework::FindDynamicPropertyForInstanceDataNode(target);
return property && AtomToolsFramework::ArePropertyValuesEqual(property->GetValue(), property->GetConfig().m_parentValue);
});
auto propertyGroupWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(
&group, &group, group.TYPEINFO_Uuid(), this, this, GetGroupSaveStateKey(groupNameId),
[this](const auto source, const auto target) { return CompareInstanceNodeProperties(source, target); });
AddGroup(groupNameId, groupDisplayName, groupDescription, propertyGroupWidget);
}
void MaterialInspector::AddPropertiesGroup()
{
const AZ::RPI::MaterialTypeSourceData* materialTypeSourceData = nullptr;
MaterialDocumentRequestBus::EventResult(materialTypeSourceData, m_documentId, &MaterialDocumentRequestBus::Events::GetMaterialTypeSourceData);
MaterialDocumentRequestBus::EventResult(
materialTypeSourceData, m_documentId, &MaterialDocumentRequestBus::Events::GetMaterialTypeSourceData);
for (const auto& groupDefinition : materialTypeSourceData->GetGroupDefinitionsInDisplayOrder())
{
const AZStd::string& groupNameId = groupDefinition.m_nameId;
const AZStd::string& groupDisplayName = !groupDefinition.m_displayName.empty() ? groupDefinition.m_displayName : groupNameId;
const AZStd::string& groupDescription = !groupDefinition.m_description.empty() ? groupDefinition.m_description : groupDisplayName;
const AZStd::string& groupDescription =
!groupDefinition.m_description.empty() ? groupDefinition.m_description : groupDisplayName;
auto& group = m_groups[groupNameId];
const auto& propertyLayout = materialTypeSourceData->m_propertyLayout;
@@ -150,18 +186,17 @@ namespace MaterialEditor
for (const auto& propertyDefinition : propertyListItr->second)
{
AtomToolsFramework::DynamicProperty property;
MaterialDocumentRequestBus::EventResult(property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty, AZ::RPI::MaterialPropertyId(groupNameId, propertyDefinition.m_nameId).GetFullName());
MaterialDocumentRequestBus::EventResult(
property, m_documentId, &MaterialDocumentRequestBus::Events::GetProperty,
AZ::RPI::MaterialPropertyId(groupNameId, propertyDefinition.m_nameId).GetFullName());
group.m_properties.push_back(property);
}
}
// Passing in same group as main and comparison instance to enable custom value comparison for highlighting modified properties
auto propertyGroupWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(&group, &group, group.TYPEINFO_Uuid(), this, this,
[this](const AzToolsFramework::InstanceDataNode* source, const AzToolsFramework::InstanceDataNode* target) {
AZ_UNUSED(source);
const AtomToolsFramework::DynamicProperty* property = AtomToolsFramework::FindDynamicPropertyForInstanceDataNode(target);
return property && AtomToolsFramework::ArePropertyValuesEqual(property->GetValue(), property->GetConfig().m_parentValue);
});
auto propertyGroupWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(
&group, &group, group.TYPEINFO_Uuid(), this, this, GetGroupSaveStateKey(groupNameId),
[this](const auto source, const auto target) { return CompareInstanceNodeProperties(source, target); });
AddGroup(groupNameId, groupDisplayName, groupDescription, propertyGroupWidget);
}
}
@@ -177,7 +212,8 @@ namespace MaterialEditor
if (!AtomToolsFramework::ArePropertyValuesEqual(reflectedProperty.GetValue(), property.GetValue()))
{
reflectedProperty.SetValue(property.GetValue());
AtomToolsFramework::InspectorRequestBus::Event(documentId, &AtomToolsFramework::InspectorRequestBus::Events::RefreshGroup, groupPair.first);
AtomToolsFramework::InspectorRequestBus::Event(
documentId, &AtomToolsFramework::InspectorRequestBus::Events::RefreshGroup, groupPair.first);
}
return;
}
@@ -224,7 +260,8 @@ namespace MaterialEditor
{
// For some reason the reflected property editor notifications are not symmetrical
// This function is called continuously anytime a property changes until the edit has completed
// Because of that, we have to track whether or not we are continuing to edit the same property to know when editing has started and ended
// Because of that, we have to track whether or not we are continuing to edit the same property to know when editing has started and
// ended
const AtomToolsFramework::DynamicProperty* property = AtomToolsFramework::FindDynamicPropertyForInstanceDataNode(pNode);
if (property)
{
@@ -243,23 +280,24 @@ namespace MaterialEditor
{
if (m_activeProperty == property)
{
MaterialDocumentRequestBus::Event(m_documentId, &MaterialDocumentRequestBus::Events::SetPropertyValue,
property->GetId(), property->GetValue());
MaterialDocumentRequestBus::Event(
m_documentId, &MaterialDocumentRequestBus::Events::SetPropertyValue, property->GetId(), property->GetValue());
}
}
}
void MaterialInspector::SetPropertyEditingComplete(AzToolsFramework::InstanceDataNode* pNode)
{
// As above, there are symmetrical functions on the notification interface for when editing begins and ends and has been completed but they are not being called following that pattern.
// when this function executes the changes to the property are ready to be committed or reverted
// As above, there are symmetrical functions on the notification interface for when editing begins and ends and has been completed
// but they are not being called following that pattern. when this function executes the changes to the property are ready to be
// committed or reverted
const AtomToolsFramework::DynamicProperty* property = AtomToolsFramework::FindDynamicPropertyForInstanceDataNode(pNode);
if (property)
{
if (m_activeProperty == property)
{
MaterialDocumentRequestBus::Event(m_documentId, &MaterialDocumentRequestBus::Events::SetPropertyValue,
property->GetId(), property->GetValue());
MaterialDocumentRequestBus::Event(
m_documentId, &MaterialDocumentRequestBus::Events::SetPropertyValue, property->GetId(), property->GetValue());
MaterialDocumentRequestBus::Event(m_documentId, &MaterialDocumentRequestBus::Events::EndEdit);
m_activeProperty = nullptr;
@@ -268,4 +306,4 @@ namespace MaterialEditor
}
} // namespace MaterialEditor
#include <Source/Window/MaterialInspector/moc_MaterialInspector.cpp>
#include <Window/MaterialInspector/moc_MaterialInspector.cpp>
@@ -20,6 +20,7 @@
#include <AtomToolsFramework/Inspector/InspectorWidget.h>
#include <Atom/Document/MaterialDocumentNotificationBus.h>
#include <Atom/Window/MaterialEditorWindowSettings.h>
#endif
namespace MaterialEditor
@@ -41,7 +42,16 @@ namespace MaterialEditor
// AtomToolsFramework::InspectorRequestBus::Handler overrides...
void Reset() override;
protected:
bool ShouldGroupAutoExpanded(const AZStd::string& groupNameId) const override;
void OnGroupExpanded(const AZStd::string& groupNameId) override;
void OnGroupCollapsed(const AZStd::string& groupNameId) override;
private:
AZ::Crc32 GetGroupSaveStateKey(const AZStd::string& groupNameId) const;
bool CompareInstanceNodeProperties(
const AzToolsFramework::InstanceDataNode* source, const AzToolsFramework::InstanceDataNode* target) const;
void AddDetailsGroup();
void AddUvNamesGroup();
void AddPropertiesGroup();
@@ -65,6 +75,8 @@ namespace MaterialEditor
const AtomToolsFramework::DynamicProperty* m_activeProperty = nullptr;
AZ::Uuid m_documentId = AZ::Uuid::CreateNull();
AZStd::string m_documentPath;
AZStd::unordered_map<AZStd::string, AtomToolsFramework::DynamicPropertyGroup> m_groups;
AZStd::intrusive_ptr<MaterialEditorWindowSettings> m_windowSettings;
};
} // namespace MaterialEditor
@@ -0,0 +1,43 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#include <Window/SettingsDialog/SettingsDialog.h>
#include <Window/SettingsDialog/SettingsWidget.h>
#include <QDialogButtonBox>
#include <QVBoxLayout>
namespace MaterialEditor
{
SettingsDialog::SettingsDialog(QWidget* parent)
: QDialog(parent)
{
setWindowTitle("Material Editor Settings");
setFixedSize(600, 300);
setLayout(new QVBoxLayout(this));
auto settingsWidget = new SettingsWidget(this);
settingsWidget->Populate();
layout()->addWidget(settingsWidget);
// Create the bottom row of the dialog with action buttons
auto buttonBox = new QDialogButtonBox(QDialogButtonBox::Ok, this);
layout()->addWidget(buttonBox);
QObject::connect(buttonBox, &QDialogButtonBox::accepted, this, &QDialog::accept);
QObject::connect(buttonBox, &QDialogButtonBox::rejected, this, &QDialog::reject);
setModal(true);
}
} // namespace MaterialEditor
//#include <Window/SettingsDialog/moc_SettingsDialog.cpp>
@@ -0,0 +1,27 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#pragma once
#include <QDialog>
namespace MaterialEditor
{
class SettingsDialog
: public QDialog
{
Q_OBJECT
public:
SettingsDialog(QWidget* parent = nullptr);
~SettingsDialog() = default;
};
} // namespace MaterialEditor
@@ -0,0 +1,72 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#include <Window/SettingsDialog/SettingsWidget.h>
#include <AtomToolsFramework/Inspector/InspectorPropertyGroupWidget.h>
namespace MaterialEditor
{
SettingsWidget::SettingsWidget(QWidget* parent)
: AtomToolsFramework::InspectorWidget(parent)
{
m_documentSettings =
AZ::UserSettings::CreateFind<MaterialDocumentSettings>(AZ::Crc32("MaterialDocumentSettings"), AZ::UserSettings::CT_GLOBAL);
}
SettingsWidget::~SettingsWidget()
{
AtomToolsFramework::InspectorRequestBus::Handler::BusDisconnect();
}
void SettingsWidget::Populate()
{
AddGroupsBegin();
AddDocumentGroup();
AddGroupsEnd();
}
void SettingsWidget::AddDocumentGroup()
{
const AZStd::string groupNameId = "documentSettings";
const AZStd::string groupDisplayName = "Document Settings";
const AZStd::string groupDescription = "Document Settings";
const AZ::Crc32 saveStateKey(AZStd::string::format("SettingsWidget::DocumentGroup"));
AddGroup(
groupNameId, groupDisplayName, groupDescription,
new AtomToolsFramework::InspectorPropertyGroupWidget(
m_documentSettings.get(), nullptr, m_documentSettings->TYPEINFO_Uuid(), this, this, saveStateKey));
}
void SettingsWidget::Reset()
{
AtomToolsFramework::InspectorRequestBus::Handler::BusDisconnect();
AtomToolsFramework::InspectorWidget::Reset();
}
void SettingsWidget::BeforePropertyModified(AzToolsFramework::InstanceDataNode* pNode)
{
AZ_UNUSED(pNode);
}
void SettingsWidget::AfterPropertyModified(AzToolsFramework::InstanceDataNode* pNode)
{
AZ_UNUSED(pNode);
}
void SettingsWidget::SetPropertyEditingComplete(AzToolsFramework::InstanceDataNode* pNode)
{
AZ_UNUSED(pNode);
}
} // namespace MaterialEditor
//#include <Window/SettingsWidget/moc_SettingsWidget.cpp>
@@ -0,0 +1,54 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#pragma once
#if !defined(Q_MOC_RUN)
#include <Atom/Document/MaterialDocumentSettings.h>
#include <AtomToolsFramework/Inspector/InspectorWidget.h>
#include <AzToolsFramework/UI/PropertyEditor/PropertyEditorAPI_Internals.h>
#endif
namespace MaterialEditor
{
//! Provides controls for viewing and editing settings.
class SettingsWidget
: public AtomToolsFramework::InspectorWidget
, private AzToolsFramework::IPropertyEditorNotify
{
Q_OBJECT
public:
AZ_CLASS_ALLOCATOR(SettingsWidget, AZ::SystemAllocator, 0);
explicit SettingsWidget(QWidget* parent = nullptr);
~SettingsWidget() override;
void Populate();
private:
void AddDocumentGroup();
// AtomToolsFramework::InspectorRequestBus::Handler overrides...
void Reset() override;
// AzToolsFramework::IPropertyEditorNotify overrides...
void BeforePropertyModified(AzToolsFramework::InstanceDataNode* pNode) override;
void AfterPropertyModified(AzToolsFramework::InstanceDataNode* pNode) override;
void SetPropertyEditingActive([[maybe_unused]] AzToolsFramework::InstanceDataNode* pNode) override {}
void SetPropertyEditingComplete(AzToolsFramework::InstanceDataNode* pNode) override;
void SealUndoStack() override {}
void RequestPropertyContextMenu(AzToolsFramework::InstanceDataNode*, const QPoint&) override {}
void PropertySelectionChanged(AzToolsFramework::InstanceDataNode*, bool) override {}
AZStd::intrusive_ptr<MaterialDocumentSettings> m_documentSettings;
};
} // namespace MaterialEditor
@@ -10,13 +10,13 @@
*
*/
#include <Atom/Document/MaterialEditorSettingsBus.h>
#include <Atom/Viewport/MaterialViewportNotificationBus.h>
#include <Atom/Viewport/MaterialViewportRequestBus.h>
#include <Atom/Viewport/MaterialViewportSettings.h>
#include <AzCore/std/containers/vector.h>
#include <Source/Window/ToolBar/LightingPresetComboBox.h>
#include <Source/Window/ToolBar/MaterialEditorToolBar.h>
#include <Source/Window/ToolBar/ModelPresetComboBox.h>
#include <Window/ToolBar/LightingPresetComboBox.h>
#include <Window/ToolBar/MaterialEditorToolBar.h>
#include <Window/ToolBar/ModelPresetComboBox.h>
AZ_PUSH_DISABLE_WARNING(4251 4800, "-Wunknown-warning-option") // disable warnings spawned by QT
#include <AzQtComponents/Components/Widgets/ToolBar.h>
@@ -33,15 +33,16 @@ namespace MaterialEditor
{
AzQtComponents::ToolBar::addMainToolBarStyle(this);
AZStd::intrusive_ptr<MaterialViewportSettings> viewportSettings =
AZ::UserSettings::CreateFind<MaterialViewportSettings>(AZ::Crc32("MaterialViewportSettings"), AZ::UserSettings::CT_GLOBAL);
// Add toggle grid button
m_toggleGrid = addAction(QIcon(":/Icons/grid.svg"), "Toggle Grid");
m_toggleGrid->setCheckable(true);
connect(m_toggleGrid, &QAction::triggered, [this]() {
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SetGridEnabled, m_toggleGrid->isChecked());
});
bool enableGrid = false;
MaterialViewportRequestBus::BroadcastResult(enableGrid, &MaterialViewportRequestBus::Events::GetGridEnabled);
m_toggleGrid->setChecked(enableGrid);
});
m_toggleGrid->setChecked(viewportSettings->m_enableGrid);
// Add toggle shadow catcher button
m_toggleShadowCatcher = addAction(QIcon(":/Icons/shadow.svg"), "Toggle Shadow Catcher");
@@ -49,34 +50,32 @@ namespace MaterialEditor
connect(m_toggleShadowCatcher, &QAction::triggered, [this]() {
MaterialViewportRequestBus::Broadcast(
&MaterialViewportRequestBus::Events::SetShadowCatcherEnabled, m_toggleShadowCatcher->isChecked());
});
bool enableShadowCatcher = false;
MaterialViewportRequestBus::BroadcastResult(enableShadowCatcher, &MaterialViewportRequestBus::Events::GetShadowCatcherEnabled);
m_toggleShadowCatcher->setChecked(enableShadowCatcher);
});
m_toggleShadowCatcher->setChecked(viewportSettings->m_enableShadowCatcher);
// Add mapping selection button
QToolButton* toneMappingButton = new QToolButton(this);
QMenu* toneMappingMenu = new QMenu(toneMappingButton);
m_operationNames =
{
{ AZ::Render::DisplayMapperOperationType::Reinhard, "Reinhard" },
{ AZ::Render::DisplayMapperOperationType::GammaSRGB, "GammaSRGB" },
{ AZ::Render::DisplayMapperOperationType::Passthrough, "Passthrough" },
{ AZ::Render::DisplayMapperOperationType::AcesLut, "AcesLut" },
{ AZ::Render::DisplayMapperOperationType::Aces, "Aces" }
};
m_operationNames = {
{AZ::Render::DisplayMapperOperationType::Reinhard, "Reinhard"},
{AZ::Render::DisplayMapperOperationType::GammaSRGB, "GammaSRGB"},
{AZ::Render::DisplayMapperOperationType::Passthrough, "Passthrough"},
{AZ::Render::DisplayMapperOperationType::AcesLut, "AcesLut"},
{AZ::Render::DisplayMapperOperationType::Aces, "Aces"}};
for (auto operationNamePair : m_operationNames)
{
m_operationActions[operationNamePair.first] = toneMappingMenu->addAction(operationNamePair.second, [operationNamePair]() {
MaterialViewportRequestBus::Broadcast(
&MaterialViewportRequestBus::Events::SetDisplayMapperOperationType,
operationNamePair.first);
});
&MaterialViewportRequestBus::Events::SetDisplayMapperOperationType, operationNamePair.first);
});
m_operationActions[operationNamePair.first]->setCheckable(true);
m_operationActions[operationNamePair.first]->setChecked(
operationNamePair.first == viewportSettings->m_displayMapperOperationType);
}
m_operationActions[AZ::Render::DisplayMapperOperationType::Aces]->setChecked(true);
toneMappingButton->setMenu(toneMappingMenu);
toneMappingButton->setText("Tone Mapping");
toneMappingButton->setIcon(QIcon(":/Icons/toneMapping.svg"));
@@ -122,4 +121,4 @@ namespace MaterialEditor
} // namespace MaterialEditor
#include <Source/Window/ToolBar/moc_MaterialEditorToolBar.cpp>
#include <Window/ToolBar/moc_MaterialEditorToolBar.cpp>
@@ -1,86 +1,40 @@
/*
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
* All or portions of this file Copyright (c) Amazon.com, Inc. or its affiliates or
* its licensors.
*
* For complete copyright and license terms please see the LICENSE at the root of this
* distribution (the "License"). All use of this software is governed by the License,
* or, if provided, by the license below or the license accompanying this file. Do not
* remove or modify any license notices. This file is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
*
*/
#include <Window/ViewportSettingsInspector/ViewportSettingsInspector.h>
#include <Atom/Viewport/MaterialViewportRequestBus.h>
#include <AtomToolsFramework/Inspector/InspectorPropertyGroupWidget.h>
#include <AtomToolsFramework/Util/Util.h>
#include <Window/PresetBrowserDialogs/LightingPresetBrowserDialog.h>
#include <Window/PresetBrowserDialogs/ModelPresetBrowserDialog.h>
#include <Window/ViewportSettingsInspector/ViewportSettingsInspector.h>
#include <QAction>
#include <QApplication>
#include <QHBoxLayout>
#include <QPushButton>
#include <QToolButton>
#include <QAction>
#include <QHBoxLayout>
#include <QVBoxLayout>
namespace MaterialEditor
{
void GeneralViewportSettings::Reflect(AZ::ReflectContext* context)
{
if (auto serializeContext = azrtti_cast<AZ::SerializeContext*>(context))
{
serializeContext->Class<GeneralViewportSettings>()
->Version(1)
->Field("enableGrid", &GeneralViewportSettings::m_enableGrid)
->Field("enableShadowCatcher", &GeneralViewportSettings::m_enableShadowCatcher)
->Field("enableAlternateSkybox", &GeneralViewportSettings::m_enableAlternateSkybox)
->Field("fieldOfView", &GeneralViewportSettings::m_fieldOfView)
->Field("displayMapperOperationType", &GeneralViewportSettings::m_displayMapperOperationType)
;
if (auto editContext = serializeContext->GetEditContext())
{
editContext->Class<GeneralViewportSettings>(
"GeneralViewportSettings", "")
->ClassElement(AZ::Edit::ClassElements::EditorData, "")
->Attribute(AZ::Edit::Attributes::AutoExpand, true)
->DataElement(AZ::Edit::UIHandlers::Default, &GeneralViewportSettings::m_enableGrid, "Enable Grid", "")
->DataElement(AZ::Edit::UIHandlers::Default, &GeneralViewportSettings::m_enableShadowCatcher, "Enable Shadow Catcher", "")
->DataElement(AZ::Edit::UIHandlers::Default, &GeneralViewportSettings::m_enableAlternateSkybox, "Enable Alternate Skybox", "")
->DataElement(AZ::Edit::UIHandlers::Slider, &GeneralViewportSettings::m_fieldOfView, "Field Of View", "")
->Attribute(AZ::Edit::Attributes::Min, 60.0f)
->Attribute(AZ::Edit::Attributes::Max, 120.0f)
->DataElement(AZ::Edit::UIHandlers::ComboBox, &GeneralViewportSettings::m_displayMapperOperationType, "Display Mapper Type", "")
->EnumAttribute(AZ::Render::DisplayMapperOperationType::Aces, "Aces")
->EnumAttribute(AZ::Render::DisplayMapperOperationType::AcesLut, "AcesLut")
->EnumAttribute(AZ::Render::DisplayMapperOperationType::Passthrough, "Passthrough")
->EnumAttribute(AZ::Render::DisplayMapperOperationType::GammaSRGB, "GammaSRGB")
->EnumAttribute(AZ::Render::DisplayMapperOperationType::Reinhard, "Reinhard")
;
}
}
if (auto behaviorContext = azrtti_cast<AZ::BehaviorContext*>(context))
{
behaviorContext->Class<GeneralViewportSettings>("GeneralViewportSettings")
->Attribute(AZ::Script::Attributes::Scope, AZ::Script::Attributes::ScopeFlags::Common)
->Attribute(AZ::Script::Attributes::Category, "Editor")
->Attribute(AZ::Script::Attributes::Module, "render")
->Constructor()
->Constructor<const GeneralViewportSettings&>()
->Property("enableGrid", BehaviorValueProperty(&GeneralViewportSettings::m_enableGrid))
->Property("enableShadowCatcher", BehaviorValueProperty(&GeneralViewportSettings::m_enableShadowCatcher))
->Property("enableAlternateSkybox", BehaviorValueProperty(&GeneralViewportSettings::m_enableAlternateSkybox))
->Property("fieldOfView", BehaviorValueProperty(&GeneralViewportSettings::m_fieldOfView))
->Property("displayMapperOperationType", BehaviorValueProperty(&GeneralViewportSettings::m_displayMapperOperationType))
;
}
}
ViewportSettingsInspector::ViewportSettingsInspector(QWidget* parent)
: AtomToolsFramework::InspectorWidget(parent)
{
m_viewportSettings =
AZ::UserSettings::CreateFind<MaterialViewportSettings>(AZ::Crc32("MaterialViewportSettings"), AZ::UserSettings::CT_GLOBAL);
m_windowSettings = AZ::UserSettings::CreateFind<MaterialEditorWindowSettings>(
AZ::Crc32("MaterialEditorWindowSettings"), AZ::UserSettings::CT_GLOBAL);
MaterialViewportNotificationBus::Handler::BusConnect();
}
@@ -92,7 +46,7 @@ namespace MaterialEditor
AtomToolsFramework::InspectorRequestBus::Handler::BusDisconnect();
}
void ViewportSettingsInspector::Popuate()
void ViewportSettingsInspector::Populate()
{
AddGroupsBegin();
AddGeneralGroup();
@@ -103,20 +57,21 @@ namespace MaterialEditor
void ViewportSettingsInspector::AddGeneralGroup()
{
const AZStd::string groupNameId = "general";
const AZStd::string groupDisplayName = "General";
const AZStd::string groupDescription = "General";
const AZStd::string groupNameId = "generalSettings";
const AZStd::string groupDisplayName = "General Settings";
const AZStd::string groupDescription = "General Settings";
AddGroup(
groupNameId, groupDisplayName, groupDescription,
new AtomToolsFramework::InspectorPropertyGroupWidget(&m_generalSettings, nullptr, m_generalSettings.TYPEINFO_Uuid(), this));
new AtomToolsFramework::InspectorPropertyGroupWidget(
m_viewportSettings.get(), nullptr, m_viewportSettings->TYPEINFO_Uuid(), this, this, GetGroupSaveStateKey(groupNameId)));
}
void ViewportSettingsInspector::AddModelGroup()
{
const AZStd::string groupNameId = "model";
const AZStd::string groupDisplayName = "Model";
const AZStd::string groupDescription = "Model";
const AZStd::string groupNameId = "modelSettings";
const AZStd::string groupDisplayName = "Model Settings";
const AZStd::string groupDescription = "Model Settings";
auto groupWidget = new QWidget(this);
auto buttonGroupWidget = new QWidget(groupWidget);
@@ -142,7 +97,7 @@ namespace MaterialEditor
if (m_modelPreset)
{
auto inspectorWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(
m_modelPreset.get(), nullptr, m_modelPreset.get()->TYPEINFO_Uuid(), this, groupWidget);
m_modelPreset.get(), nullptr, m_modelPreset.get()->TYPEINFO_Uuid(), this, groupWidget, GetGroupSaveStateKey(groupNameId));
groupWidget->layout()->addWidget(inspectorWidget);
}
@@ -201,9 +156,9 @@ namespace MaterialEditor
void ViewportSettingsInspector::AddLightingGroup()
{
const AZStd::string groupNameId = "lighting";
const AZStd::string groupDisplayName = "Lighting";
const AZStd::string groupDescription = "Lighting";
const AZStd::string groupNameId = "lightingSettings";
const AZStd::string groupDisplayName = "Lighting Settings";
const AZStd::string groupDescription = "Lighting Settings";
auto groupWidget = new QWidget(this);
auto buttonGroupWidget = new QWidget(groupWidget);
@@ -229,7 +184,8 @@ namespace MaterialEditor
if (m_lightingPreset)
{
auto inspectorWidget = new AtomToolsFramework::InspectorPropertyGroupWidget(
m_lightingPreset.get(), nullptr, m_lightingPreset.get()->TYPEINFO_Uuid(), this, groupWidget);
m_lightingPreset.get(), nullptr, m_lightingPreset.get()->TYPEINFO_Uuid(), this, groupWidget,
GetGroupSaveStateKey(groupNameId));
groupWidget->layout()->addWidget(inspectorWidget);
}
@@ -247,8 +203,7 @@ namespace MaterialEditor
AZ::Render::LightingPresetPtr preset;
MaterialViewportRequestBus::BroadcastResult(
preset, &MaterialViewportRequestBus::Events::AddLightingPreset, AZ::Render::LightingPreset());
MaterialViewportRequestBus::Broadcast(
&MaterialViewportRequestBus::Events::SaveLightingPreset, preset, savePath);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SaveLightingPreset, preset, savePath);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SelectLightingPreset, preset);
}
}
@@ -272,7 +227,8 @@ namespace MaterialEditor
MaterialViewportRequestBus::BroadcastResult(preset, &MaterialViewportRequestBus::Events::GetLightingPresetSelection);
AZStd::string defaultPath;
MaterialViewportRequestBus::BroadcastResult(defaultPath, &MaterialViewportRequestBus::Events::GetLightingPresetLastSavePath, preset);
MaterialViewportRequestBus::BroadcastResult(
defaultPath, &MaterialViewportRequestBus::Events::GetLightingPresetLastSavePath, preset);
if (defaultPath.empty())
{
@@ -300,13 +256,15 @@ namespace MaterialEditor
m_lightingPreset.reset();
MaterialViewportRequestBus::BroadcastResult(m_lightingPreset, &MaterialViewportRequestBus::Events::GetLightingPresetSelection);
MaterialViewportRequestBus::BroadcastResult(m_generalSettings.m_enableGrid, &MaterialViewportRequestBus::Events::GetGridEnabled);
MaterialViewportRequestBus::BroadcastResult(m_viewportSettings->m_enableGrid, &MaterialViewportRequestBus::Events::GetGridEnabled);
MaterialViewportRequestBus::BroadcastResult(
m_generalSettings.m_enableShadowCatcher, &MaterialViewportRequestBus::Events::GetShadowCatcherEnabled);
m_viewportSettings->m_enableShadowCatcher, &MaterialViewportRequestBus::Events::GetShadowCatcherEnabled);
MaterialViewportRequestBus::BroadcastResult(
m_generalSettings.m_enableAlternateSkybox, &MaterialViewportRequestBus::Events::GetAlternateSkyboxEnabled);
MaterialViewportRequestBus::BroadcastResult(m_generalSettings.m_fieldOfView, &MaterialViewportRequestBus::Handler::GetFieldOfView);
MaterialViewportRequestBus::BroadcastResult(m_generalSettings.m_displayMapperOperationType, &MaterialViewportRequestBus::Handler::GetDisplayMapperOperationType);
m_viewportSettings->m_enableAlternateSkybox, &MaterialViewportRequestBus::Events::GetAlternateSkyboxEnabled);
MaterialViewportRequestBus::BroadcastResult(
m_viewportSettings->m_fieldOfView, &MaterialViewportRequestBus::Handler::GetFieldOfView);
MaterialViewportRequestBus::BroadcastResult(
m_viewportSettings->m_displayMapperOperationType, &MaterialViewportRequestBus::Handler::GetDisplayMapperOperationType);
AtomToolsFramework::InspectorRequestBus::Handler::BusDisconnect();
AtomToolsFramework::InspectorWidget::Reset();
@@ -316,7 +274,7 @@ namespace MaterialEditor
{
if (m_lightingPreset != preset)
{
Popuate();
Populate();
}
}
@@ -324,37 +282,37 @@ namespace MaterialEditor
{
if (m_modelPreset != preset)
{
Popuate();
Populate();
}
}
void ViewportSettingsInspector::OnShadowCatcherEnabledChanged(bool enable)
{
m_generalSettings.m_enableShadowCatcher = enable;
m_viewportSettings->m_enableShadowCatcher = enable;
RefreshGroup("general");
}
void ViewportSettingsInspector::OnGridEnabledChanged(bool enable)
{
m_generalSettings.m_enableGrid = enable;
m_viewportSettings->m_enableGrid = enable;
RefreshGroup("general");
}
void ViewportSettingsInspector::OnAlternateSkyboxEnabledChanged(bool enable)
{
m_generalSettings.m_enableAlternateSkybox = enable;
m_viewportSettings->m_enableAlternateSkybox = enable;
RefreshGroup("general");
}
void ViewportSettingsInspector::OnFieldOfViewChanged(float fieldOfView)
{
m_generalSettings.m_fieldOfView = fieldOfView;
m_viewportSettings->m_fieldOfView = fieldOfView;
RefreshGroup("general");
}
void ViewportSettingsInspector::OnDisplayMapperOperationTypeChanged(AZ::Render::DisplayMapperOperationType operationType)
{
m_generalSettings.m_displayMapperOperationType = operationType;
m_viewportSettings->m_displayMapperOperationType = operationType;
RefreshGroup("general");
}
@@ -379,13 +337,14 @@ namespace MaterialEditor
{
MaterialViewportNotificationBus::Broadcast(&MaterialViewportNotificationBus::Events::OnLightingPresetChanged, m_lightingPreset);
MaterialViewportNotificationBus::Broadcast(&MaterialViewportNotificationBus::Events::OnModelPresetChanged, m_modelPreset);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SetGridEnabled, m_generalSettings.m_enableGrid);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SetGridEnabled, m_viewportSettings->m_enableGrid);
MaterialViewportRequestBus::Broadcast(
&MaterialViewportRequestBus::Events::SetShadowCatcherEnabled, m_generalSettings.m_enableShadowCatcher);
&MaterialViewportRequestBus::Events::SetShadowCatcherEnabled, m_viewportSettings->m_enableShadowCatcher);
MaterialViewportRequestBus::Broadcast(
&MaterialViewportRequestBus::Events::SetAlternateSkyboxEnabled, m_generalSettings.m_enableAlternateSkybox);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Handler::SetFieldOfView, m_generalSettings.m_fieldOfView);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Handler::SetDisplayMapperOperationType, m_generalSettings.m_displayMapperOperationType);
&MaterialViewportRequestBus::Events::SetAlternateSkyboxEnabled, m_viewportSettings->m_enableAlternateSkybox);
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Handler::SetFieldOfView, m_viewportSettings->m_fieldOfView);
MaterialViewportRequestBus::Broadcast(
&MaterialViewportRequestBus::Handler::SetDisplayMapperOperationType, m_viewportSettings->m_displayMapperOperationType);
}
AZStd::string ViewportSettingsInspector::GetDefaultUniqueSaveFilePath(const AZStd::string& baseName) const
@@ -398,6 +357,28 @@ namespace MaterialEditor
savePath = AtomToolsFramework::GetUniqueFileInfo(savePath.c_str()).absoluteFilePath().toUtf8().constData();
return savePath;
}
AZ::Crc32 ViewportSettingsInspector::GetGroupSaveStateKey(const AZStd::string& groupNameId) const
{
return AZ::Crc32(AZStd::string::format("ViewportSettingsInspector::PropertyGroup::%s", groupNameId.c_str()));
}
bool ViewportSettingsInspector::ShouldGroupAutoExpanded(const AZStd::string& groupNameId) const
{
auto stateItr = m_windowSettings->m_inspectorCollapsedGroups.find(GetGroupSaveStateKey(groupNameId));
return stateItr == m_windowSettings->m_inspectorCollapsedGroups.end();
}
void ViewportSettingsInspector::OnGroupExpanded(const AZStd::string& groupNameId)
{
m_windowSettings->m_inspectorCollapsedGroups.erase(GetGroupSaveStateKey(groupNameId));
}
void ViewportSettingsInspector::OnGroupCollapsed(const AZStd::string& groupNameId)
{
m_windowSettings->m_inspectorCollapsedGroups.insert(GetGroupSaveStateKey(groupNameId));
}
} // namespace MaterialEditor
#include <Source/Window/ViewportSettingsInspector/moc_ViewportSettingsInspector.cpp>
@@ -14,28 +14,17 @@
#if !defined(Q_MOC_RUN)
#include <ACES/Aces.h>
#include <Atom/Viewport/MaterialViewportNotificationBus.h>
#include <Atom/Feature/Utils/LightingPreset.h>
#include <Atom/Feature/Utils/ModelPreset.h>
#include <AzToolsFramework/UI/PropertyEditor/PropertyEditorAPI_Internals.h>
#include <Atom/Viewport/MaterialViewportNotificationBus.h>
#include <Atom/Viewport/MaterialViewportSettings.h>
#include <Atom/Window/MaterialEditorWindowSettings.h>
#include <AtomToolsFramework/Inspector/InspectorWidget.h>
#include <AzToolsFramework/UI/PropertyEditor/PropertyEditorAPI_Internals.h>
#endif
namespace MaterialEditor
{
struct GeneralViewportSettings
{
AZ_TYPE_INFO(GeneralViewportSettings, "{16150503-A314-4765-82A3-172670C9EA90}");
AZ_CLASS_ALLOCATOR(GeneralViewportSettings, AZ::SystemAllocator, 0);
static void Reflect(AZ::ReflectContext* context);
bool m_enableGrid = true;
bool m_enableShadowCatcher = true;
bool m_enableAlternateSkybox = false;
float m_fieldOfView = 90.0f;
AZ::Render::DisplayMapperOperationType m_displayMapperOperationType = AZ::Render::DisplayMapperOperationType::Aces;
};
//! Provides controls for viewing and editing a material document settings.
//! The settings can be divided into cards, with each one showing a subset of properties.
class ViewportSettingsInspector
@@ -51,7 +40,7 @@ namespace MaterialEditor
~ViewportSettingsInspector() override;
private:
void Popuate();
void Populate();
void AddGeneralGroup();
void AddModelGroup();
@@ -90,8 +79,14 @@ namespace MaterialEditor
AZStd::string GetDefaultUniqueSaveFilePath(const AZStd::string& baseName) const;
GeneralViewportSettings m_generalSettings;
AZ::Crc32 GetGroupSaveStateKey(const AZStd::string& groupNameId) const;
bool ShouldGroupAutoExpanded(const AZStd::string& groupNameId) const override;
void OnGroupExpanded(const AZStd::string& groupNameId) override;
void OnGroupCollapsed(const AZStd::string& groupNameId) override;
AZ::Render::ModelPresetPtr m_modelPreset;
AZ::Render::LightingPresetPtr m_lightingPreset;
AZStd::intrusive_ptr<MaterialViewportSettings> m_viewportSettings;
AZStd::intrusive_ptr<MaterialEditorWindowSettings> m_windowSettings;
};
} // namespace MaterialEditor