This commit is contained in:
Isuru Samarathunga
2025-11-14 09:43:09 +05:30
parent 9ff39d7245
commit a2b80ef600
32 changed files with 928 additions and 295 deletions

View File

@ -50,9 +50,11 @@ namespace ia::iae
INT32 RDC::s_primitiveInstanceCount{};
GeometryVertex RDC::s_primitiveInstances[RDC::MAX_PRIMITIVE_COUNT];
Vector<RDC_Texture*> g_managedBakedTextures;
VOID RDC::Initialize(IN IVec2 viewportExtent, IN SDL_Window *windowHandle, IN BOOL isDebugMode)
{
if(s_windowHandle)
if (s_windowHandle)
return;
EmbeddedResources::Initialize();
@ -77,6 +79,9 @@ namespace ia::iae
RDC_Device::DestroyGeometry(s_quadGeometry);
for (const auto &t : g_managedBakedTextures)
delete t;
SDL_ReleaseGPUSampler(RDC_Device::GetHandle(), s_linearClampSampler);
SDL_ReleaseGPUSampler(RDC_Device::GetHandle(), s_linearRepeatSampler);
@ -190,29 +195,26 @@ namespace ia::iae
RDC_Device::WaitForIdle();
}
Vec2 RDC::DrawSpriteTopLeft(IN Handle _image, IN INT32 tileIndexX, IN INT32 tileIndexY, IN Vec2 position,
Vec2 RDC::DrawSpriteTopLeft(IN ImageView *imageView, IN INT32 tileIndexX, IN INT32 tileIndexY, IN Vec2 position,
IN Vec2 scale, IN FLOAT32 rotation, IN BOOL flipH, IN BOOL flipV, IN Vec2 uvOffset)
{
const auto image = (ImageData *) _image;
const auto _s = Vec2{scale.x * image->TileWidth, scale.y * image->TileHeight};
const auto _s = Vec2{scale.x * imageView->TileWidth, scale.y * imageView->TileHeight};
Mat4 transform = glm::translate(glm::mat4(1.0f), glm::vec3{position.x, position.y, 0});
transform = glm::rotate(transform, rotation, glm::vec3(0.0f, 0.0f, 1.0f));
transform = glm::scale(transform, glm::vec3(_s, 1.0f));
s_spriteInstances[s_spriteInstanceCount++] = {
.Transform = transform,
.TexCoords = s_dynamicSpriteAtlas ? s_dynamicSpriteAtlas->GetTextureCoordinates(
_image, tileIndexX, tileIndexY, flipH, flipV, uvOffset)
imageView, tileIndexX, tileIndexY, flipH, flipV, uvOffset)
: Vec4{0.0f, 0.0f, 1.0f, 1.0f},
.Color = {1.0f, 1.0f, 1.0f, 1.0f}};
return _s;
}
Vec2 RDC::DrawSpriteCentered(IN Handle _image, IN INT32 tileIndexX, IN INT32 tileIndexY, IN Vec2 position,
Vec2 RDC::DrawSpriteCentered(IN ImageView *imageView, IN INT32 tileIndexX, IN INT32 tileIndexY, IN Vec2 position,
IN Vec2 scale, IN FLOAT32 rotation, IN BOOL flipH, IN BOOL flipV, IN Vec2 uvOffset)
{
const auto image = (ImageData *) _image;
const auto _s = Vec2{scale.x * image->TileWidth, scale.y * image->TileHeight};
const auto _s = Vec2{scale.x * imageView->TileWidth, scale.y * imageView->TileHeight};
Mat4 transform =
glm::translate(glm::mat4(1.0f), glm::vec3{position.x - _s.x / 2.0f, position.y - _s.y / 2.0f, 0});
transform = glm::rotate(transform, rotation, glm::vec3(0.0f, 0.0f, 1.0f));
@ -220,7 +222,7 @@ namespace ia::iae
s_spriteInstances[s_spriteInstanceCount++] = {
.Transform = transform,
.TexCoords = s_dynamicSpriteAtlas ? s_dynamicSpriteAtlas->GetTextureCoordinates(
_image, tileIndexX, tileIndexY, flipH, flipV, uvOffset)
imageView, tileIndexX, tileIndexY, flipH, flipV, uvOffset)
: Vec4{0.0f, 0.0f, 1.0f, 1.0f},
.Color = {1.0f, 1.0f, 1.0f, 1.0f}};
return _s;
@ -263,34 +265,50 @@ namespace ia::iae
s_viewMatrix = glm::lookAtLH(glm::vec3{s_cameraPosition, -1.0f}, {s_cameraPosition, 0.0f}, {0.0f, 1.0f, 0.0f});
}
Handle RDC::CreateImage(IN PCUINT8 rgbaData, IN INT32 width, IN INT32 height, IN INT32 tileCountX,
IN INT32 tileCountY)
Image *RDC::CreateImage(IN PCUINT8 rgbaData, IN INT32 width, IN INT32 height)
{
const auto pixelDataSize = width * height * 4;
const auto image = new ImageData{
.Pixels = new UINT8[pixelDataSize],
.Width = width,
.Height = height,
.TileWidth = width / tileCountX,
.TileHeight = height / tileCountY,
const auto image = new Image{.Pixels = new UINT8[pixelDataSize], .Width = width, .Height = height};
ia_memcpy(image->Pixels, rgbaData, pixelDataSize);
return image;
}
ImageView *RDC::CreateImageView(IN Image *image, IN INT32 tileCountX, IN INT32 tileCountY)
{
const auto imageView = new ImageView{
.ImagePtr = image,
.TileWidth = image->Width / tileCountX,
.TileHeight = image->Height / tileCountY,
.TileCountX = tileCountX,
.TileCountY = tileCountY,
};
ia_memcpy(image->Pixels, rgbaData, pixelDataSize);
return (Handle) image;
return imageView;
}
VOID RDC::DestroyImage(IN Handle _image)
VOID RDC::DestroyImage(IN Image *image)
{
const auto image = (ImageData *) _image;
delete[] image->Pixels;
delete image;
}
VOID RDC::CompileTextures(IN CONST Vector<Handle> &images)
VOID RDC::DestroyImageView(IN ImageView *imageView)
{
delete imageView;
}
Handle RDC::BakeTexture(IN Image *image)
{
const auto texture = new RDC_Texture(RDC_Texture::EType::SAMPLED, image->Width, image->Height);
texture->SetImageData(image->Pixels);
g_managedBakedTextures.pushBack(texture);
return (Handle)texture->GetHandle();
}
VOID RDC::CompileTextures(IN CONST Vector<Image *> &images)
{
if (!images.size())
return;

View File

@ -18,19 +18,18 @@
namespace ia::iae
{
RDC_TextureAtlas::RDC_TextureAtlas(IN CONST Vector<Handle> &images)
RDC_TextureAtlas::RDC_TextureAtlas(IN CONST Vector<Image*> &images)
{
if (images.empty())
return;
m_atlasSize.x = 0;
m_atlasSize.y = 0;
for (const auto &_image : images)
for (const auto &image : images)
{
const auto d = (ImageData *) _image;
m_atlasSize.x += d->Width;
if (d->Height > m_atlasSize.y)
m_atlasSize.y = d->Height;
m_atlasSize.x += image->Width;
if (image->Height > m_atlasSize.y)
m_atlasSize.y = image->Height;
}
m_inverseAtlasSize = {1.0f / ((FLOAT32) m_atlasSize.x), 1.0f / ((FLOAT32) m_atlasSize.y)};
@ -38,13 +37,12 @@ namespace ia::iae
const auto pixels = new UINT8[m_atlasSize.x * m_atlasSize.y * 4];
INT32 atlasCursor{0};
for (const auto &_image : images)
for (const auto &image : images)
{
const auto d = (ImageData *) _image;
for (INT32 y = 0; y < d->Height; y++)
ia_memcpy(&pixels[(atlasCursor + (y * m_atlasSize.x)) * 4], &d->Pixels[y * d->Width * 4], d->Width * 4);
m_texCoordMap[_image] = Vec2(((FLOAT32) atlasCursor) / ((FLOAT32) m_atlasSize.x), 0.0f);
atlasCursor += d->Width;
for (INT32 y = 0; y < image->Height; y++)
ia_memcpy(&pixels[(atlasCursor + (y * m_atlasSize.x)) * 4], &image->Pixels[y * image->Width * 4], image->Width * 4);
m_texCoordMap[(Handle)(image)] = Vec2(((FLOAT32) atlasCursor) / ((FLOAT32) m_atlasSize.x), 0.0f);
atlasCursor += image->Width;
}
m_texture = new RDC_Texture(RDC_Texture::EType::SAMPLED, m_atlasSize.x, m_atlasSize.y);
@ -58,15 +56,14 @@ namespace ia::iae
delete m_texture;
}
Vec4 RDC_TextureAtlas::GetTextureCoordinates(IN Handle _image, IN INT32 tileIndexX, IN INT32 tileIndexY, IN BOOL flipH,
Vec4 RDC_TextureAtlas::GetTextureCoordinates(IN ImageView* imageView, IN INT32 tileIndexX, IN INT32 tileIndexY, IN BOOL flipH,
IN BOOL flipV, IN Vec2 uvOffset)
{
const auto d = (ImageData *) _image;
const auto &t = m_texCoordMap[_image];
const auto pX = ((tileIndexX + uvOffset.x) * ((FLOAT32) d->TileWidth)) * m_inverseAtlasSize.x;
const auto pY = ((tileIndexY + uvOffset.y) * ((FLOAT32) d->TileHeight)) * m_inverseAtlasSize.y;
auto texCoords = Vec4(t.x + pX, t.y + pY, d->TileWidth * m_inverseAtlasSize.x,
d->TileHeight * m_inverseAtlasSize.y);
const auto &t = m_texCoordMap[(Handle)(imageView->ImagePtr)];
const auto pX = ((tileIndexX + uvOffset.x) * ((FLOAT32) imageView->TileWidth)) * m_inverseAtlasSize.x;
const auto pY = ((tileIndexY + uvOffset.y) * ((FLOAT32) imageView->TileHeight)) * m_inverseAtlasSize.y;
auto texCoords = Vec4(t.x + pX, t.y + pY, imageView->TileWidth * m_inverseAtlasSize.x,
imageView->TileHeight * m_inverseAtlasSize.y);
if (flipH)
{
texCoords.x += texCoords.z;

View File

@ -27,11 +27,16 @@
namespace ia::iae
{
struct ImageData
struct Image
{
PUINT8 Pixels{};
INT32 Width{};
INT32 Height{};
};
struct ImageView
{
Image* ImagePtr{};
INT32 TileWidth{};
INT32 TileHeight{};
INT32 TileCountX{};

View File

@ -17,10 +17,11 @@
#pragma once
#include <RenderCore/Buffer.hpp>
#include <RenderCore/Texture.hpp>
#include <RenderCore/Pipeline.hpp>
#include <RenderCore/Texture.hpp>
#include <RenderCore/TextureAtlas.hpp>
namespace ia::iae
{
#pragma pack(push, 1)
@ -47,25 +48,30 @@ namespace ia::iae
STATIC VOID ResizeScreen(IN IVec2 newExtent);
STATIC VOID RenderToWindow();
STATIC VOID RenderToTexture(IN SDL_GPUTexture* texture);
STATIC VOID RenderToTexture(IN SDL_GPUTexture *texture);
public:
STATIC Vec2 GetCameraPosition();
STATIC VOID SetCameraPosition(IN Vec2 position);
STATIC Vec2 DrawSpriteTopLeft(IN Handle image, IN INT32 tileIndexX, IN INT32 tileIndexY,
IN Vec2 position, IN Vec2 scale, IN FLOAT32 rotation, IN BOOL flipH = false, IN BOOL flipV = false, IN Vec2 uvOffset = {});
STATIC Vec2 DrawSpriteCentered(IN Handle image, IN INT32 tileIndexX, IN INT32 tileIndexY,
IN Vec2 position, IN Vec2 scale, IN FLOAT32 rotation, IN BOOL flipH = false, IN BOOL flipV = false, IN Vec2 uvOffset = {});
STATIC Vec2 DrawSpriteTopLeft(IN ImageView* imageView, IN INT32 tileIndexX, IN INT32 tileIndexY, IN Vec2 position,
IN Vec2 scale, IN FLOAT32 rotation, IN BOOL flipH = false, IN BOOL flipV = false,
IN Vec2 uvOffset = {});
STATIC Vec2 DrawSpriteCentered(IN ImageView* imageView, IN INT32 tileIndexX, IN INT32 tileIndexY, IN Vec2 position,
IN Vec2 scale, IN FLOAT32 rotation, IN BOOL flipH = false, IN BOOL flipV = false,
IN Vec2 uvOffset = {});
STATIC VOID DrawLine(IN Vec2 start, IN Vec2 end, IN Vec4 color);
STATIC VOID DrawRect(IN Vec2 start, IN Vec2 end, IN Vec4 color);
STATIC Handle CreateImage(IN PCUINT8 rgbaData, IN INT32 width, IN INT32 height, IN INT32 tileCountX = 1,
IN INT32 tileCountY = 1);
STATIC VOID DestroyImage(IN Handle image);
STATIC Image* CreateImage(IN PCUINT8 rgbaData, IN INT32 width, IN INT32 height);
STATIC ImageView* CreateImageView(IN Image* image, IN INT32 tileCountX = 1, IN INT32 tileCountY = 1);
STATIC VOID DestroyImage(IN Image* image);
STATIC VOID DestroyImageView(IN ImageView* imageView);
STATIC VOID CompileTextures(IN CONST Vector<Handle>& images);
STATIC Handle BakeTexture(IN Image* image);
STATIC VOID CompileTextures(IN CONST Vector<Image*> &images);
private:
STATIC VOID InitializeSamplers();
@ -74,7 +80,7 @@ namespace ia::iae
STATIC VOID InitializePipelines();
STATIC VOID InitializeGeometries();
STATIC VOID Render(IN SDL_GPURenderPass* renderPass, IN SDL_GPUCommandBuffer* commandBuffer);
STATIC VOID Render(IN SDL_GPURenderPass *renderPass, IN SDL_GPUCommandBuffer *commandBuffer);
private:
STATIC Mat4 s_viewMatrix;
@ -83,7 +89,7 @@ namespace ia::iae
STATIC IVec2 s_viewportExtent;
STATIC Mat4 s_projectionMatrix;
STATIC SDL_Window *s_windowHandle;
STATIC RDC_Texture* s_defaultTexture;
STATIC RDC_Texture *s_defaultTexture;
STATIC RDC_Pipeline *s_primitiveDrawPipeline;
STATIC RDC_Pipeline *s_dynamicSpritePipeline;
@ -93,9 +99,9 @@ namespace ia::iae
STATIC RDC_TextureAtlas *s_staticSpriteAtlas;
STATIC RDC_TextureAtlas *s_dynamicSpriteAtlas;
STATIC RDC_HostVisibleBuffer* s_primitiveInstanceBuffer;
STATIC RDC_HostVisibleBuffer* s_staticSpriteInstanceBuffer;
STATIC RDC_HostVisibleBuffer* s_dynamicSpriteInstanceBuffer;
STATIC RDC_HostVisibleBuffer *s_primitiveInstanceBuffer;
STATIC RDC_HostVisibleBuffer *s_staticSpriteInstanceBuffer;
STATIC RDC_HostVisibleBuffer *s_dynamicSpriteInstanceBuffer;
STATIC INT32 s_spriteInstanceCount;
STATIC RDC_SpriteInstanceData s_spriteInstances[MAX_SPRITE_COUNT];

View File

@ -23,10 +23,10 @@ namespace ia::iae
class RDC_TextureAtlas
{
public:
RDC_TextureAtlas(IN CONST Vector<Handle> &images);
RDC_TextureAtlas(IN CONST Vector<Image*> &images);
~RDC_TextureAtlas();
Vec4 GetTextureCoordinates(IN Handle image, IN INT32 tileIndexX, IN INT32 tileIndexY, IN BOOL flipH,
Vec4 GetTextureCoordinates(IN ImageView* imageView, IN INT32 tileIndexX, IN INT32 tileIndexY, IN BOOL flipH,
IN BOOL flipV, IN Vec2 uvOffset);
public: