#pragma once #include "Core/Geometry.hpp" #include "Core/Shader.hpp" #include "Core/Texture.hpp" #include "Core/Pix.hpp" #include #include namespace Aya { namespace Graphics { class RasterizerState; class BlendState; class DepthState; class SamplerState; class Framebuffer; class DeviceContext { public: enum BufferMask { Buffer_Color = 1 << 0, Buffer_Depth = 1 << 1, Buffer_Stencil = 1 << 2 }; virtual ~DeviceContext(); virtual void setDefaultAnisotropy(unsigned int value) = 0; virtual void updateGlobalConstants(const void* data, size_t dataSize) = 0; virtual void bindFramebuffer(Framebuffer* buffer) = 0; virtual void clearFramebuffer(unsigned int mask, const float color[4], float depth, unsigned int stencil) = 0; virtual void copyFramebuffer(Framebuffer* buffer, Texture* texture, int xOffset, int yOffset) = 0; virtual void resolveFramebuffer(Framebuffer* msaaBuffer, Framebuffer* buffer, unsigned int mask) = 0; virtual void discardFramebuffer(Framebuffer* buffer, unsigned int mask) = 0; virtual void bindProgram(ShaderProgram* program) = 0; virtual void setWorldTransforms4x3(const float* data, size_t matrixCount) = 0; virtual void setConstant(int handle, const float* data, size_t vectorCount) = 0; virtual void bindTexture(unsigned int stage, Texture* texture, const SamplerState& state) = 0; virtual void setRasterizerState(const RasterizerState& state) = 0; virtual void setBlendState(const BlendState& state) = 0; virtual void setDepthState(const DepthState& state) = 0; void draw(Geometry* geometry, Geometry::Primitive primitive, unsigned int offset, unsigned int count, unsigned int indexRangeBegin, unsigned int indexRangeEnd); void draw(const GeometryBatch& geometryBatch); virtual void pushDebugMarkerGroup(const char* text) = 0; virtual void popDebugMarkerGroup() = 0; virtual void setDebugMarker(const char* text) = 0; protected: DeviceContext(); virtual void drawImpl(Geometry* geometry, Geometry::Primitive primitive, unsigned int offset, unsigned int count, unsigned int indexRangeBegin, unsigned int indexRangeEnd) = 0; }; struct DeviceCaps { bool supportsFramebuffer; bool supportsShaders; bool supportsFFP; bool supportsStencil; bool supportsIndex32; bool supportsTextureDXT; bool supportsTexturePVR; bool supportsTextureHalfFloat; bool supportsTexture3D; bool supportsTextureNPOT; bool supportsTextureETC1; bool supportsTexturePartialMipChain; unsigned int maxDrawBuffers; unsigned int maxSamples; unsigned int maxTextureSize; unsigned int maxTextureUnits; bool colorOrderBGR; bool needsHalfPixelOffset; bool requiresRenderTargetFlipping; bool retina; void dumpToFLog(int channel) const; }; struct DeviceStats { float gpuFrameTime; }; typedef boost::function DeviceFrameDataCallback; class Device { friend class Resource; public: enum API { API_BGFX, API_OpenGL }; static Device* create(API api, void* windowHandle, void* display, int w, int h); virtual ~Device(); virtual bool validate() = 0; virtual void resize(int w, int h) = 0; virtual DeviceContext* beginFrame() = 0; virtual void endFrame() = 0; virtual Framebuffer* getMainFramebuffer() = 0; virtual void defineGlobalConstants(size_t dataSize, const std::vector& constants) = 0; virtual std::string getAPIName() = 0; virtual std::string getFeatureLevel() = 0; virtual std::string getShadingLanguage() = 0; virtual std::string createShaderSource( const std::string& path, const std::string& defines, boost::function fileCallback) = 0; virtual std::vector createShaderBytecode(const std::string& source, const std::string& target, const std::string& entrypoint) = 0; virtual shared_ptr createVertexShader(const std::vector& bytecode) = 0; virtual shared_ptr createFragmentShader(const std::vector& bytecode) = 0; virtual shared_ptr createShaderProgram( const shared_ptr& vertexShader, const shared_ptr& fragmentShader) = 0; virtual shared_ptr createShaderProgramFFP() = 0; virtual shared_ptr createVertexBuffer(size_t elementSize, size_t elementCount, GeometryBuffer::Usage usage) = 0; virtual shared_ptr createIndexBuffer(size_t elementSize, size_t elementCount, GeometryBuffer::Usage usage) = 0; virtual shared_ptr createVertexLayout(const std::vector& elements) = 0; shared_ptr createGeometry(const shared_ptr& layout, const shared_ptr& vertexBuffer, const shared_ptr& indexBuffer, unsigned int baseVertexIndex = 0); shared_ptr createGeometry(const shared_ptr& layout, const std::vector>& vertexBuffers, const shared_ptr& indexBuffer, unsigned int baseVertexIndex = 0); virtual shared_ptr createTexture(Texture::Type type, Texture::Format format, unsigned int width, unsigned int height, unsigned int depth, unsigned int mipLevels, Texture::Usage usage) = 0; virtual shared_ptr createRenderbuffer(Texture::Format format, unsigned int width, unsigned int height, unsigned int samples) = 0; shared_ptr createFramebuffer( const shared_ptr& color, const shared_ptr& depth = shared_ptr()); shared_ptr createFramebuffer( const std::vector>& color, const shared_ptr& depth = shared_ptr()); virtual const DeviceCaps& getCaps() const = 0; virtual DeviceStats getStatistics() const = 0; virtual void suspend() { AYAASSERT(false); /* only DX11-Durango*/ } virtual void resume() { AYAASSERT(false); /* only DX11-Durango*/ } protected: Resource* resourceListHead; Resource* resourceListTail; Device(); virtual shared_ptr createGeometryImpl(const shared_ptr& layout, const std::vector>& vertexBuffers, const shared_ptr& indexBuffer, unsigned int baseVertexIndex) = 0; virtual shared_ptr createFramebufferImpl( const std::vector>& color, const shared_ptr& depth) = 0; void fireDeviceLost(); void fireDeviceRestored(); }; } // namespace Graphics } // namespace Aya