Merge branch 'stabilization/2110' into Atom/santorac/MaterialEditorHandlesMissingTextures
This commit is contained in:
@@ -6,61 +6,26 @@
|
||||
*
|
||||
*/
|
||||
|
||||
#include <AzCore/Component/TickBus.h>
|
||||
#include <AzCore/Serialization/SerializeContext.h>
|
||||
#include <AzCore/Serialization/EditContext.h>
|
||||
#include <AzCore/RTTI/BehaviorContext.h>
|
||||
#include <AzCore/Jobs/JobFunction.h>
|
||||
|
||||
#include <AzFramework/Asset/AssetSystemBus.h>
|
||||
#include <AzFramework/StringFunc/StringFunc.h>
|
||||
#include <AzFramework/IO/LocalFileIO.h>
|
||||
#include <AzToolsFramework/API/EditorAssetSystemAPI.h>
|
||||
#include <AzToolsFramework/AssetBrowser/AssetBrowserEntry.h>
|
||||
|
||||
#include <Viewport/MaterialViewportComponent.h>
|
||||
#include <Atom/Viewport/MaterialViewportNotificationBus.h>
|
||||
#include <Atom/Viewport/MaterialViewportSettings.h>
|
||||
|
||||
#include <Atom/ImageProcessing/ImageObject.h>
|
||||
#include <Atom/ImageProcessing/ImageProcessingBus.h>
|
||||
|
||||
#include <AzCore/Serialization/Json/JsonUtils.h>
|
||||
|
||||
#include <Atom/RPI.Reflect/Asset/AssetUtils.h>
|
||||
#include <Atom/RPI.Reflect/System/AnyAsset.h>
|
||||
#include <Atom/RPI.Edit/Common/AssetUtils.h>
|
||||
#include <Atom/RPI.Edit/Common/JsonUtils.h>
|
||||
#include <Atom/RPI.Reflect/Asset/AssetUtils.h>
|
||||
#include <Atom/RPI.Reflect/System/AnyAsset.h>
|
||||
#include <Atom/Viewport/MaterialViewportNotificationBus.h>
|
||||
#include <Atom/Viewport/MaterialViewportSettings.h>
|
||||
#include <AzCore/Component/TickBus.h>
|
||||
#include <AzCore/RTTI/BehaviorContext.h>
|
||||
#include <AzCore/Serialization/EditContext.h>
|
||||
#include <AzCore/Serialization/Json/JsonUtils.h>
|
||||
#include <AzCore/Serialization/SerializeContext.h>
|
||||
#include <AzFramework/Asset/AssetSystemBus.h>
|
||||
#include <AzFramework/IO/LocalFileIO.h>
|
||||
#include <AzFramework/StringFunc/StringFunc.h>
|
||||
#include <AzToolsFramework/API/EditorAssetSystemAPI.h>
|
||||
#include <AzToolsFramework/AssetBrowser/AssetBrowserEntry.h>
|
||||
#include <Viewport/MaterialViewportComponent.h>
|
||||
|
||||
namespace MaterialEditor
|
||||
{
|
||||
using LoadImageAsyncCallback = AZStd::function<void(const QImage&)>;
|
||||
void LoadImageAsync(const AZStd::string& path, LoadImageAsyncCallback callback)
|
||||
{
|
||||
AZ::Job* job = AZ::CreateJobFunction([path, callback]() {
|
||||
ImageProcessingAtom::IImageObjectPtr imageObject;
|
||||
ImageProcessingAtom::ImageProcessingRequestBus::BroadcastResult(imageObject, &ImageProcessingAtom::ImageProcessingRequests::LoadImagePreview, path);
|
||||
|
||||
if (imageObject)
|
||||
{
|
||||
AZ::u8* imageBuf = nullptr;
|
||||
AZ::u32 pitch = 0;
|
||||
AZ::u32 mip = 0;
|
||||
imageObject->GetImagePointer(mip, imageBuf, pitch);
|
||||
const AZ::u32 width = imageObject->GetWidth(mip);
|
||||
const AZ::u32 height = imageObject->GetHeight(mip);
|
||||
|
||||
QImage image(imageBuf, width, height, pitch, QImage::Format_RGBA8888);
|
||||
|
||||
if (callback)
|
||||
{
|
||||
callback(image);
|
||||
}
|
||||
}
|
||||
}, true);
|
||||
job->Start();
|
||||
}
|
||||
|
||||
MaterialViewportComponent::MaterialViewportComponent()
|
||||
{
|
||||
}
|
||||
@@ -162,12 +127,6 @@ namespace MaterialEditor
|
||||
m_viewportSettings =
|
||||
AZ::UserSettings::CreateFind<MaterialViewportSettings>(AZ::Crc32("MaterialViewportSettings"), AZ::UserSettings::CT_GLOBAL);
|
||||
|
||||
m_lightingPresetPreviewImageDefault = QImage(180, 90, QImage::Format::Format_RGBA8888);
|
||||
m_lightingPresetPreviewImageDefault.fill(Qt::GlobalColor::black);
|
||||
|
||||
m_modelPresetPreviewImageDefault = QImage(90, 90, QImage::Format::Format_RGBA8888);
|
||||
m_modelPresetPreviewImageDefault.fill(Qt::GlobalColor::black);
|
||||
|
||||
MaterialViewportRequestBus::Handler::BusConnect();
|
||||
AzFramework::AssetCatalogEventBus::Handler::BusConnect();
|
||||
}
|
||||
@@ -177,12 +136,10 @@ namespace MaterialEditor
|
||||
AzFramework::AssetCatalogEventBus::Handler::BusDisconnect();
|
||||
MaterialViewportRequestBus::Handler::BusDisconnect();
|
||||
|
||||
m_lightingPresetPreviewImages.clear();
|
||||
m_lightingPresetVector.clear();
|
||||
m_lightingPresetLastSavePathMap.clear();
|
||||
m_lightingPresetSelection.reset();
|
||||
|
||||
m_modelPresetPreviewImages.clear();
|
||||
m_modelPresetVector.clear();
|
||||
m_modelPresetLastSavePathMap.clear();
|
||||
m_modelPresetSelection.reset();
|
||||
@@ -286,14 +243,6 @@ namespace MaterialEditor
|
||||
SelectLightingPreset(presetPtr);
|
||||
}
|
||||
|
||||
const auto& imagePath = AZ::RPI::AssetUtils::GetSourcePathByAssetId(presetPtr->m_skyboxImageAsset.GetId());
|
||||
LoadImageAsync(imagePath, [presetPtr](const QImage& image) {
|
||||
QImage imageScaled = image.scaled(180, 90, Qt::AspectRatioMode::KeepAspectRatio);
|
||||
AZ::TickBus::QueueFunction([presetPtr, imageScaled]() {
|
||||
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SetLightingPresetPreview, presetPtr, imageScaled);
|
||||
});
|
||||
});
|
||||
|
||||
return presetPtr;
|
||||
}
|
||||
|
||||
@@ -353,17 +302,6 @@ namespace MaterialEditor
|
||||
return names;
|
||||
}
|
||||
|
||||
void MaterialViewportComponent::SetLightingPresetPreview(AZ::Render::LightingPresetPtr preset, const QImage& image)
|
||||
{
|
||||
m_lightingPresetPreviewImages[preset] = image;
|
||||
}
|
||||
|
||||
QImage MaterialViewportComponent::GetLightingPresetPreview(AZ::Render::LightingPresetPtr preset) const
|
||||
{
|
||||
auto imageItr = m_lightingPresetPreviewImages.find(preset);
|
||||
return imageItr != m_lightingPresetPreviewImages.end() ? imageItr->second : m_lightingPresetPreviewImageDefault;
|
||||
}
|
||||
|
||||
AZStd::string MaterialViewportComponent::GetLightingPresetLastSavePath(AZ::Render::LightingPresetPtr preset) const
|
||||
{
|
||||
auto pathItr = m_lightingPresetLastSavePathMap.find(preset);
|
||||
@@ -382,14 +320,6 @@ namespace MaterialEditor
|
||||
SelectModelPreset(presetPtr);
|
||||
}
|
||||
|
||||
const auto& imagePath = AZ::RPI::AssetUtils::GetSourcePathByAssetId(presetPtr->m_previewImageAsset.GetId());
|
||||
LoadImageAsync(imagePath, [presetPtr](const QImage& image) {
|
||||
QImage imageScaled = image.scaled(90, 90, Qt::AspectRatioMode::KeepAspectRatio);
|
||||
AZ::TickBus::QueueFunction([presetPtr, imageScaled]() {
|
||||
MaterialViewportRequestBus::Broadcast(&MaterialViewportRequestBus::Events::SetModelPresetPreview, presetPtr, imageScaled);
|
||||
});
|
||||
});
|
||||
|
||||
return presetPtr;
|
||||
}
|
||||
|
||||
@@ -449,17 +379,6 @@ namespace MaterialEditor
|
||||
return names;
|
||||
}
|
||||
|
||||
void MaterialViewportComponent::SetModelPresetPreview(AZ::Render::ModelPresetPtr preset, const QImage& image)
|
||||
{
|
||||
m_modelPresetPreviewImages[preset] = image;
|
||||
}
|
||||
|
||||
QImage MaterialViewportComponent::GetModelPresetPreview(AZ::Render::ModelPresetPtr preset) const
|
||||
{
|
||||
auto imageItr = m_modelPresetPreviewImages.find(preset);
|
||||
return imageItr != m_modelPresetPreviewImages.end() ? imageItr->second : m_modelPresetPreviewImageDefault;
|
||||
}
|
||||
|
||||
AZStd::string MaterialViewportComponent::GetModelPresetLastSavePath(AZ::Render::ModelPresetPtr preset) const
|
||||
{
|
||||
auto pathItr = m_modelPresetLastSavePathMap.find(preset);
|
||||
|
||||
@@ -58,8 +58,6 @@ namespace MaterialEditor
|
||||
void SelectLightingPreset(AZ::Render::LightingPresetPtr preset) override;
|
||||
void SelectLightingPresetByName(const AZStd::string& name) override;
|
||||
MaterialViewportPresetNameSet GetLightingPresetNames() const override;
|
||||
void SetLightingPresetPreview(AZ::Render::LightingPresetPtr preset, const QImage& image) override;
|
||||
QImage GetLightingPresetPreview(AZ::Render::LightingPresetPtr preset) const override;
|
||||
AZStd::string GetLightingPresetLastSavePath(AZ::Render::LightingPresetPtr preset) const override;
|
||||
|
||||
AZ::Render::ModelPresetPtr AddModelPreset(const AZ::Render::ModelPreset& preset) override;
|
||||
@@ -70,8 +68,6 @@ namespace MaterialEditor
|
||||
void SelectModelPreset(AZ::Render::ModelPresetPtr preset) override;
|
||||
void SelectModelPresetByName(const AZStd::string& name) override;
|
||||
MaterialViewportPresetNameSet GetModelPresetNames() const override;
|
||||
void SetModelPresetPreview(AZ::Render::ModelPresetPtr preset, const QImage& image) override;
|
||||
QImage GetModelPresetPreview(AZ::Render::ModelPresetPtr preset) const override;
|
||||
AZStd::string GetModelPresetLastSavePath(AZ::Render::ModelPresetPtr preset) const override;
|
||||
|
||||
void SetShadowCatcherEnabled(bool enable) override;
|
||||
@@ -97,12 +93,6 @@ namespace MaterialEditor
|
||||
AZ::Render::ModelPresetPtrVector m_modelPresetVector;
|
||||
AZ::Render::ModelPresetPtr m_modelPresetSelection;
|
||||
|
||||
AZStd::map<AZ::Render::LightingPresetPtr, QImage> m_lightingPresetPreviewImages;
|
||||
AZStd::map<AZ::Render::ModelPresetPtr, QImage> m_modelPresetPreviewImages;
|
||||
|
||||
QImage m_lightingPresetPreviewImageDefault;
|
||||
QImage m_modelPresetPreviewImageDefault;
|
||||
|
||||
mutable AZStd::map<AZ::Render::LightingPresetPtr, AZStd::string> m_lightingPresetLastSavePathMap;
|
||||
mutable AZStd::map<AZ::Render::ModelPresetPtr, AZStd::string> m_modelPresetLastSavePathMap;
|
||||
|
||||
|
||||
+8
-4
@@ -7,6 +7,7 @@
|
||||
*/
|
||||
|
||||
#include <Atom/Feature/Utils/LightingPreset.h>
|
||||
#include <Atom/RPI.Edit/Common/AssetUtils.h>
|
||||
#include <Atom/Viewport/MaterialViewportRequestBus.h>
|
||||
#include <AtomToolsFramework/Util/Util.h>
|
||||
#include <AzFramework/Application/Application.h>
|
||||
@@ -27,13 +28,16 @@ namespace MaterialEditor
|
||||
MaterialViewportRequestBus::BroadcastResult(presets, &MaterialViewportRequestBus::Events::GetLightingPresets);
|
||||
AZStd::sort(presets.begin(), presets.end(), [](const auto& a, const auto& b) { return a->m_displayName < b->m_displayName; });
|
||||
|
||||
const int itemSize = aznumeric_cast<int>(
|
||||
AtomToolsFramework::GetSettingOrDefault<AZ::u64>("/O3DE/Atom/MaterialEditor/PresetBrowserDialog/LightingItemSize", 180));
|
||||
|
||||
QListWidgetItem* selectedItem = nullptr;
|
||||
for (const auto& preset : presets)
|
||||
{
|
||||
QImage image;
|
||||
MaterialViewportRequestBus::BroadcastResult(image, &MaterialViewportRequestBus::Events::GetLightingPresetPreview, preset);
|
||||
|
||||
QListWidgetItem* item = CreateListItem(preset->m_displayName.c_str(), image);
|
||||
AZStd::string path;
|
||||
MaterialViewportRequestBus::BroadcastResult(path, &MaterialViewportRequestBus::Events::GetLightingPresetLastSavePath, preset);
|
||||
QListWidgetItem* item = CreateListItem(
|
||||
preset->m_displayName.c_str(), AZ::RPI::AssetUtils::MakeAssetId(path, 0).GetValue(), QSize(itemSize, itemSize));
|
||||
|
||||
m_listItemToPresetMap[item] = preset;
|
||||
|
||||
|
||||
+4
-4
@@ -27,13 +27,13 @@ namespace MaterialEditor
|
||||
MaterialViewportRequestBus::BroadcastResult(presets, &MaterialViewportRequestBus::Events::GetModelPresets);
|
||||
AZStd::sort(presets.begin(), presets.end(), [](const auto& a, const auto& b) { return a->m_displayName < b->m_displayName; });
|
||||
|
||||
const int itemSize = aznumeric_cast<int>(
|
||||
AtomToolsFramework::GetSettingOrDefault<AZ::u64>("/O3DE/Atom/MaterialEditor/PresetBrowserDialog/ModelItemSize", 90));
|
||||
|
||||
QListWidgetItem* selectedItem = nullptr;
|
||||
for (const auto& preset : presets)
|
||||
{
|
||||
QImage image;
|
||||
MaterialViewportRequestBus::BroadcastResult(image, &MaterialViewportRequestBus::Events::GetModelPresetPreview, preset);
|
||||
|
||||
QListWidgetItem* item = CreateListItem(preset->m_displayName.c_str(), image);
|
||||
QListWidgetItem* item = CreateListItem(preset->m_displayName.c_str(), preset->m_modelAsset.GetId(), QSize(itemSize, itemSize));
|
||||
|
||||
m_listItemToPresetMap[item] = preset;
|
||||
|
||||
|
||||
+42
-21
@@ -12,11 +12,16 @@
|
||||
#include <AzQtComponents/Components/Widgets/ElidingLabel.h>
|
||||
#include <AzQtComponents/Components/Widgets/LineEdit.h>
|
||||
#include <AzQtComponents/Components/Widgets/Text.h>
|
||||
#include <AzToolsFramework/AssetBrowser/Thumbnails/ProductThumbnail.h>
|
||||
#include <AzToolsFramework/Thumbnails/ThumbnailContext.h>
|
||||
#include <AzToolsFramework/Thumbnails/ThumbnailWidget.h>
|
||||
#include <AzToolsFramework/Thumbnails/ThumbnailerBus.h>
|
||||
#include <Window/PresetBrowserDialogs/PresetBrowserDialog.h>
|
||||
|
||||
#include <QLabel>
|
||||
#include <QLineEdit>
|
||||
#include <QMenu>
|
||||
#include <QVBoxLayout>
|
||||
|
||||
namespace MaterialEditor
|
||||
{
|
||||
@@ -41,35 +46,51 @@ namespace MaterialEditor
|
||||
m_ui->m_presetList->setGridSize(QSize(0, 0));
|
||||
m_ui->m_presetList->setWrapping(true);
|
||||
|
||||
QObject::connect(m_ui->m_presetList, &QListWidget::currentItemChanged, [this]() { SelectCurrentPreset(); });
|
||||
QObject::connect(m_ui->m_presetList, &QListWidget::currentItemChanged, [this](){ SelectCurrentPreset(); });
|
||||
}
|
||||
|
||||
QListWidgetItem* PresetBrowserDialog::CreateListItem(const QString& title, const QImage& image)
|
||||
QListWidgetItem* PresetBrowserDialog::CreateListItem(const QString& title, const AZ::Data::AssetId& assetId, const QSize& size)
|
||||
{
|
||||
const int itemBorder = aznumeric_cast<int>(
|
||||
AtomToolsFramework::GetSettingOrDefault<AZ::u64>("/O3DE/Atom/MaterialEditor/PresetBrowserDialog/ItemBorder", 4));
|
||||
const int itemSpacing = aznumeric_cast<int>(
|
||||
AtomToolsFramework::GetSettingOrDefault<AZ::u64>("/O3DE/Atom/MaterialEditor/PresetBrowserDialog/ItemSpacing", 10));
|
||||
const int headerHeight = aznumeric_cast<int>(
|
||||
AtomToolsFramework::GetSettingOrDefault<AZ::u64>("/O3DE/Atom/MaterialEditor/PresetBrowserDialog/HeaderHeight", 15));
|
||||
|
||||
const QSize gridSize = m_ui->m_presetList->gridSize();
|
||||
m_ui->m_presetList->setGridSize(
|
||||
QSize(AZStd::max(gridSize.width(), image.width() + 10), AZStd::max(gridSize.height(), image.height() + 10)));
|
||||
m_ui->m_presetList->setGridSize(QSize(
|
||||
AZStd::max(gridSize.width(), size.width() + itemSpacing),
|
||||
AZStd::max(gridSize.height(), size.height() + itemSpacing + headerHeight)));
|
||||
|
||||
QListWidgetItem* item = new QListWidgetItem(m_ui->m_presetList);
|
||||
item->setData(Qt::UserRole, title);
|
||||
item->setSizeHint(image.size() + QSize(4, 4));
|
||||
item->setSizeHint(size + QSize(itemBorder, itemBorder + headerHeight));
|
||||
m_ui->m_presetList->addItem(item);
|
||||
|
||||
QLabel* previewImage = new QLabel(m_ui->m_presetList);
|
||||
previewImage->setFixedSize(image.size());
|
||||
previewImage->setMargin(0);
|
||||
previewImage->setPixmap(QPixmap::fromImage(image));
|
||||
previewImage->updateGeometry();
|
||||
QWidget* itemWidget = new QWidget(m_ui->m_presetList);
|
||||
itemWidget->setLayout(new QVBoxLayout(itemWidget));
|
||||
itemWidget->layout()->setSpacing(0);
|
||||
itemWidget->layout()->setMargin(0);
|
||||
|
||||
AzQtComponents::ElidingLabel* previewLabel = new AzQtComponents::ElidingLabel(previewImage);
|
||||
previewLabel->setText(title);
|
||||
previewLabel->setFixedSize(QSize(image.width(), 15));
|
||||
previewLabel->setMargin(0);
|
||||
previewLabel->setStyleSheet("background-color: rgb(35, 35, 35)");
|
||||
AzQtComponents::Text::addPrimaryStyle(previewLabel);
|
||||
AzQtComponents::Text::addLabelStyle(previewLabel);
|
||||
AzQtComponents::ElidingLabel* header = new AzQtComponents::ElidingLabel(itemWidget);
|
||||
header->setText(title);
|
||||
header->setFixedSize(QSize(size.width(), headerHeight));
|
||||
header->setMargin(0);
|
||||
header->setStyleSheet("background-color: rgb(35, 35, 35)");
|
||||
AzQtComponents::Text::addPrimaryStyle(header);
|
||||
AzQtComponents::Text::addLabelStyle(header);
|
||||
itemWidget->layout()->addWidget(header);
|
||||
|
||||
m_ui->m_presetList->setItemWidget(item, previewImage);
|
||||
AzToolsFramework::Thumbnailer::ThumbnailWidget* thumbnail = new AzToolsFramework::Thumbnailer::ThumbnailWidget(itemWidget);
|
||||
thumbnail->setFixedSize(size);
|
||||
thumbnail->SetThumbnailKey(
|
||||
MAKE_TKEY(AzToolsFramework::AssetBrowser::ProductThumbnailKey, assetId),
|
||||
AzToolsFramework::Thumbnailer::ThumbnailContext::DefaultContext);
|
||||
thumbnail->updateGeometry();
|
||||
itemWidget->layout()->addWidget(thumbnail);
|
||||
|
||||
m_ui->m_presetList->setItemWidget(item, itemWidget);
|
||||
|
||||
return item;
|
||||
}
|
||||
@@ -79,15 +100,15 @@ namespace MaterialEditor
|
||||
m_ui->m_searchWidget->setReadOnly(false);
|
||||
m_ui->m_searchWidget->setContextMenuPolicy(Qt::CustomContextMenu);
|
||||
AzQtComponents::LineEdit::applySearchStyle(m_ui->m_searchWidget);
|
||||
connect(m_ui->m_searchWidget, &QLineEdit::textChanged, this, [this]() { ApplySearchFilter(); });
|
||||
connect(m_ui->m_searchWidget, &QWidget::customContextMenuRequested, this, [this](const QPoint& pos) { ShowSearchMenu(pos); });
|
||||
connect(m_ui->m_searchWidget, &QLineEdit::textChanged, this, [this](){ ApplySearchFilter(); });
|
||||
connect(m_ui->m_searchWidget, &QWidget::customContextMenuRequested, this, [this](const QPoint& pos){ ShowSearchMenu(pos); });
|
||||
}
|
||||
|
||||
void PresetBrowserDialog::SetupDialogButtons()
|
||||
{
|
||||
connect(m_ui->m_buttonBox, &QDialogButtonBox::accepted, this, &QDialog::accept);
|
||||
connect(m_ui->m_buttonBox, &QDialogButtonBox::rejected, this, &QDialog::reject);
|
||||
connect(this, &QDialog::rejected, this, [this]() { SelectInitialPreset(); });
|
||||
connect(this, &QDialog::rejected, this, [this](){ SelectInitialPreset(); });
|
||||
}
|
||||
|
||||
void PresetBrowserDialog::ApplySearchFilter()
|
||||
|
||||
+3
-3
@@ -9,12 +9,12 @@
|
||||
#pragma once
|
||||
|
||||
#if !defined(Q_MOC_RUN)
|
||||
#include <AzCore/Asset/AssetCommon.h>
|
||||
#include <AzCore/std/containers/vector.h>
|
||||
|
||||
#include <QDialog>
|
||||
#endif
|
||||
|
||||
#include <Source/Window/PresetBrowserDialogs/ui_PresetBrowserDialog.h>
|
||||
#include <Window/PresetBrowserDialogs/ui_PresetBrowserDialog.h>
|
||||
|
||||
class QImage;
|
||||
class QListWidgetItem;
|
||||
@@ -32,7 +32,7 @@ namespace MaterialEditor
|
||||
|
||||
protected:
|
||||
void SetupPresetList();
|
||||
QListWidgetItem* CreateListItem(const QString& title, const QImage& image);
|
||||
QListWidgetItem* CreateListItem(const QString& title, const AZ::Data::AssetId& assetId, const QSize& size);
|
||||
|
||||
void SetupSearchWidget();
|
||||
void SetupDialogButtons();
|
||||
|
||||
Reference in New Issue
Block a user