/* * 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 #include #include #include #include #include #include #include #include #include #include namespace MaterialEditor { /** * MaterialDocument provides an API for modifying and saving material document properties. */ class MaterialDocument : public MaterialDocumentRequestBus::Handler , private AZ::TickBus::Handler , private AZ::Data::AssetBus::MultiHandler , private AzToolsFramework::AssetSystemBus::Handler { public: AZ_RTTI(MaterialDocument, "{DBA269AE-892B-415C-8FA1-166B94B0E045}"); AZ_CLASS_ALLOCATOR(MaterialDocument, AZ::SystemAllocator, 0); AZ_DISABLE_COPY(MaterialDocument); MaterialDocument(); virtual ~MaterialDocument(); const AZ::Uuid& GetId() const; //////////////////////////////////////////////////////////////////////// // MaterialDocumentRequestBus::Handler implementation AZStd::string_view GetAbsolutePath() const override; AZStd::string_view GetRelativePath() const override; AZ::Data::Asset GetAsset() const override; AZ::Data::Instance GetInstance() const override; const AZ::RPI::MaterialSourceData* GetMaterialSourceData() const override; const AZ::RPI::MaterialTypeSourceData* GetMaterialTypeSourceData() const override; const AZStd::any& GetPropertyValue(const AZ::Name& propertyFullName) const override; const AtomToolsFramework::DynamicProperty& GetProperty(const AZ::Name& propertyFullName) const override; void SetPropertyValue(const AZ::Name& propertyFullName, const AZStd::any& value) override; bool Open(AZStd::string_view loadPath) override; bool Rebuild() override; bool Save() override; bool SaveAsCopy(AZStd::string_view savePath) override; bool SaveAsChild(AZStd::string_view savePath) override; bool Close() override; bool IsOpen() const override; bool IsModified() const override; bool IsSavable() const override; bool CanUndo() const override; bool CanRedo() const override; bool Undo() override; bool Redo() override; bool BeginEdit() override; bool EndEdit() override; //////////////////////////////////////////////////////////////////////// private: // Predicate for evaluating properties using PropertyFilterFunction = AZStd::function; // Map of documenmt's property using PropertyMap = AZStd::unordered_map; // Map of raw property values for undo/redo comparison and storage using PropertyValueMap = AZStd::unordered_map; // Function to be bound for undo and redo using UndoRedoFunction = AZStd::function; // A pair of functions, where first is the undo operation and second is the redo operation using UndoRedoFunctionPair = AZStd::pair; // Container for all of the active undo and redo functions and state using UndoRedoHistory = AZStd::vector; //////////////////////////////////////////////////////////////////////// // AZ::TickBus interface implementation void OnTick(float deltaTime, AZ::ScriptTimePoint time) override; //////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////// // AzToolsFramework::AssetSystemBus::Handler overrides... void SourceFileChanged(AZStd::string relativePath, AZStd::string scanFolder, AZ::Uuid sourceUUID) override; ////////////////////////////////////////////////////////////////////////// ////////////////////////////////////////////////////////////////////////// // AZ::Data::AssetBus::Router overrides... void OnAssetReloaded(AZ::Data::Asset asset) override; ////////////////////////////////////////////////////////////////////////// bool SavePropertiesToSourceData(AZ::RPI::MaterialSourceData& sourceData, PropertyFilterFunction propertyFilter) const; bool OpenInternal(AZStd::string_view loadPath); void Recompile(); void Clear(); void RestorePropertyValues(const PropertyValueMap& propertyValues); // Run editor material functor to update editor metadata. // @param dirtyFlags indicates which properties have changed, and thus which MaterialFunctors need to be run. // @return names for the set of properties that have been changed or need update. AZStd::unordered_set RunEditorMaterialFunctors(AZ::RPI::MaterialPropertyFlags dirtyFlags); // Unique id of this material document AZ::Uuid m_id = AZ::Uuid::CreateRandom(); // Underlying material asset AZ::Data::Asset m_materialAsset; // Material instance being edited AZ::Data::Instance m_materialInstance; // Relative path to the material source file AZStd::string m_relativePath; // Absolute path to the material source file AZStd::string m_absolutePath; // Asset used to open document AZ::Data::AssetId m_sourceAssetId; // Set of assets that can trigger a document reload AZStd::unordered_set m_dependentAssetIds; // Track if document saved itself last to skip external modification notification bool m_saveTriggeredInternally = false; // If material instance value(s) were modified, do we need to recompile on next tick? bool m_compilePending = false; // Collection of all material's properties PropertyMap m_properties; // Material functors that run in editor. See MaterialFunctor.h for details. AZStd::vector> m_editorFunctors; // Source data for material type AZ::RPI::MaterialTypeSourceData m_materialTypeSourceData; // Source data for material AZ::RPI::MaterialSourceData m_materialSourceData; // Variables needed for tracking the undo and redo state of this document // State of property values prior to an edit, used for restoration during undo PropertyValueMap m_propertyValuesBeforeEdit; // Container of undo commands UndoRedoHistory m_undoHistory; // The current position in the undo redo history int m_undoHistoryIndex = 0; AZStd::any m_invalidValue; AtomToolsFramework::DynamicProperty m_invalidProperty; }; } // namespace MaterialEditor