#pragma once #include "editor/EditorAuthority.h" #include "editor/EditorProperty.h" #include "editing/EditableTarget.h" #include "spritestack/SpriteStack.h" #include #include #include #include namespace eve::graphics { class Graphics; } namespace eve::image { class ImageData; } namespace eve::model3d { class ModelData; } namespace eve::spritestack { class SpriteStack2D; } namespace eve::editor { /** @brief Complete authored sprite-stack bake and presentation preset. */ struct SpriteStackAssetValue { std::string sourceKind = "primitive"; std::string source = "box"; spritestack::SliceOptions bake; float displayWidth = 64.f; float displayHeight = 64.f; float layerOffset = 1.f; bool shadow = true; float shadowOpacity = .3f; float outlineWidth = 0.f; }; /** @brief Revisioned SpriteStack bake preset with reusable Inspector metadata. */ class SpriteStackDocumentTarget final : public virtual IEditableTarget, public IDomainOperationTarget, public IDomainOperationTargetStaging, public IPropertyProvider { public: explicit SpriteStackDocumentTarget(std::string id); const std::string& targetId() const override { return id_; } unsigned long long revision() const override { return revision_; } EditRegion dirtyRegion() const override { return dirty_; } void clearDirtyRegion() override { dirty_.clear(); } TargetDescriptor describe() const override; /** @brief Query an optional target capability. @return Borrowed pointer owned by this target, or null. @lifetime Valid until this target is destroyed or mutated. */ void* queryCapability(const CapabilityId& capability) override; EditorResult applyDomainOperation(const DomainOperation& operation) override; std::unique_ptr cloneDomainState() const override; EditorResult commitDomainState(std::unique_ptr candidate) override; eve::Result currentRevision(const SelectionSnapshot& selection) const override; PropertySchema schema(const SelectionSnapshot& selection) const override; PropertyReadResult read(const SelectionSnapshot& selection, const PropertyPath& path) const override; EditorResult makeSet(const SelectionSnapshot& selection, const PropertyPath& path, const EditorValue& value, PropertySetMode mode) const override; EditorResult makeReset(const SelectionSnapshot& selection, const PropertyPath& path) const override; const SpriteStackAssetValue& value() const { return value_; } /** @brief Validate source, sampling limits, output memory and presentation values. */ std::vector validate() const; EditorValue snapshotValue() const; EditorResult loadSnapshot(const EditorValue& snapshot); private: bool matches(const SelectionSnapshot& selection) const; EditorValue contentValue() const; EditorResult replacement(EditorValue content, std::string property) const; std::string id_; Revision revision_=1; EditRegion dirty_; SpriteStackAssetValue value_; }; /** @brief Metadata for one immutable baked layer. */ struct SpriteStackLayerArtifact { int index=0,width=0,height=0; std::uint64_t checksum=0; double alphaCoverage=0; }; /** @brief Resolves model assets without coupling the document to AssetDB ownership. */ class ISpriteStackModelResolver { public: virtual ~ISpriteStackModelResolver() = default; /** @brief Resolve a ready, borrowed ModelData for the duration of bake(). */ virtual EditorResult resolveModel(const std::string& assetId) const = 0; }; /** @brief Candidate-first CPU baker and optional live SpriteStack2D publisher. */ class SpriteStackBakeRuntime { public: SpriteStackBakeRuntime(); ~SpriteStackBakeRuntime(); /** @brief Bake all layers in temporary ownership before replacing the generation. */ EditorResult> bake(const SpriteStackDocumentTarget& document, const ISpriteStackModelResolver* resolver=nullptr); /** @brief Create and populate a live stack from the current baked generation. */ EditorResult publish(graphics::Graphics* graphics, Revision expectedRevision); const std::vector>& layers() const { return layers_; } Revision revision() const { return revision_; } private: std::vector> layers_; std::unique_ptr stack_; SpriteStackAssetValue value_; Revision revision_=0; }; } // namespace eve::editor