mirror of
https://github.com/wheremyfoodat/Panda3DS.git
synced 2025-04-16 18:59:48 +12:00
implement textures
This commit is contained in:
parent
bac3a8e040
commit
b62a14d3ff
3 changed files with 63 additions and 3 deletions
|
@ -54,4 +54,7 @@ class RendererMTL final : public Renderer {
|
||||||
commandBuffer = commandQueue->commandBuffer();
|
commandBuffer = commandQueue->commandBuffer();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MTL::Texture* getTexture(Metal::Texture& tex);
|
||||||
|
void bindTexturesToSlots();
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,3 +1,4 @@
|
||||||
|
#include "PICA/gpu.hpp"
|
||||||
#include "renderer_mtl/renderer_mtl.hpp"
|
#include "renderer_mtl/renderer_mtl.hpp"
|
||||||
|
|
||||||
#include <cmrc/cmrc.hpp>
|
#include <cmrc/cmrc.hpp>
|
||||||
|
@ -209,6 +210,9 @@ void RendererMTL::drawVertices(PICA::PrimType primType, std::span<const PICA::Ve
|
||||||
renderCommandEncoder->setRenderPipelineState(drawPipeline);
|
renderCommandEncoder->setRenderPipelineState(drawPipeline);
|
||||||
renderCommandEncoder->setVertexBytes(vertices.data(), vertices.size_bytes(), VERTEX_BUFFER_BINDING_INDEX);
|
renderCommandEncoder->setVertexBytes(vertices.data(), vertices.size_bytes(), VERTEX_BUFFER_BINDING_INDEX);
|
||||||
|
|
||||||
|
// Bind resources
|
||||||
|
bindTexturesToSlots();
|
||||||
|
|
||||||
// TODO: respect primitive type
|
// TODO: respect primitive type
|
||||||
renderCommandEncoder->drawPrimitives(MTL::PrimitiveTypeTriangle, NS::UInteger(0), NS::UInteger(vertices.size()));
|
renderCommandEncoder->drawPrimitives(MTL::PrimitiveTypeTriangle, NS::UInteger(0), NS::UInteger(vertices.size()));
|
||||||
|
|
||||||
|
@ -226,3 +230,49 @@ void RendererMTL::deinitGraphicsContext() {
|
||||||
// TODO: implement
|
// TODO: implement
|
||||||
Helpers::warn("RendererMTL::deinitGraphicsContext not implemented");
|
Helpers::warn("RendererMTL::deinitGraphicsContext not implemented");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MTL::Texture* RendererMTL::getTexture(Metal::Texture& tex) {
|
||||||
|
auto buffer = textureCache.find(tex);
|
||||||
|
|
||||||
|
if (buffer.has_value()) {
|
||||||
|
return buffer.value().get().texture;
|
||||||
|
} else {
|
||||||
|
const auto textureData = std::span{gpu.getPointerPhys<u8>(tex.location), tex.sizeInBytes()}; // Get pointer to the texture data in 3DS memory
|
||||||
|
Metal::Texture& newTex = textureCache.add(tex);
|
||||||
|
newTex.decodeTexture(textureData);
|
||||||
|
|
||||||
|
return newTex.texture;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void RendererMTL::bindTexturesToSlots() {
|
||||||
|
static constexpr std::array<u32, 3> ioBases = {
|
||||||
|
PICA::InternalRegs::Tex0BorderColor,
|
||||||
|
PICA::InternalRegs::Tex1BorderColor,
|
||||||
|
PICA::InternalRegs::Tex2BorderColor,
|
||||||
|
};
|
||||||
|
|
||||||
|
for (int i = 0; i < 3; i++) {
|
||||||
|
if ((regs[PICA::InternalRegs::TexUnitCfg] & (1 << i)) == 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
const size_t ioBase = ioBases[i];
|
||||||
|
|
||||||
|
const u32 dim = regs[ioBase + 1];
|
||||||
|
const u32 config = regs[ioBase + 2];
|
||||||
|
const u32 height = dim & 0x7ff;
|
||||||
|
const u32 width = Helpers::getBits<16, 11>(dim);
|
||||||
|
const u32 addr = (regs[ioBase + 4] & 0x0FFFFFFF) << 3;
|
||||||
|
u32 format = regs[ioBase + (i == 0 ? 13 : 5)] & 0xF;
|
||||||
|
|
||||||
|
if (addr != 0) [[likely]] {
|
||||||
|
Metal::Texture targetTex(device, addr, static_cast<PICA::TextureFmt>(format), width, height, config);
|
||||||
|
MTL::Texture* tex = getTexture(targetTex);
|
||||||
|
// TODO: bind the texture
|
||||||
|
Helpers::warn("Wanted to bind texture %p at index %i", tex, i);
|
||||||
|
} else {
|
||||||
|
// TODO: bind a dummy texture?
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
|
@ -228,8 +228,14 @@ u32 Texture::decodeTexel(u32 u, u32 v, PICA::TextureFmt fmt, std::span<const u8>
|
||||||
return (alpha << 24) | (intensity << 16) | (intensity << 8) | intensity;
|
return (alpha << 24) | (intensity << 16) | (intensity << 8) | intensity;
|
||||||
}
|
}
|
||||||
|
|
||||||
case PICA::TextureFmt::ETC1: return getTexelETC(false, u, v, size.u(), data);
|
case PICA::TextureFmt::ETC1: {
|
||||||
case PICA::TextureFmt::ETC1A4: return getTexelETC(true, u, v, size.u(), data);
|
//return getTexelETC(false, u, v, size.u(), data);
|
||||||
|
Helpers::panic("[Texture::DecodeTexel] Unimplemented format = %d", static_cast<int>(fmt));
|
||||||
|
}
|
||||||
|
case PICA::TextureFmt::ETC1A4: {
|
||||||
|
//return getTexelETC(true, u, v, size.u(), data);
|
||||||
|
Helpers::panic("[Texture::DecodeTexel] Unimplemented format = %d", static_cast<int>(fmt));
|
||||||
|
}
|
||||||
|
|
||||||
default:
|
default:
|
||||||
Helpers::panic("[Texture::DecodeTexel] Unimplemented format = %d", static_cast<int>(fmt));
|
Helpers::panic("[Texture::DecodeTexel] Unimplemented format = %d", static_cast<int>(fmt));
|
||||||
|
@ -248,7 +254,8 @@ void Texture::decodeTexture(std::span<const u8> data) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
u32 bytesPerRow = sizeInBytes() / size.v();
|
// TODO: is this correct?
|
||||||
|
u32 bytesPerRow = 4 * size.u();//sizeInBytes() / size.v();
|
||||||
texture->replaceRegion(MTL::Region(0, 0, size.u(), size.v()), 0, 0, decoded.data(), bytesPerRow, 0);
|
texture->replaceRegion(MTL::Region(0, 0, size.u(), size.v()), 0, 0, decoded.data(), bytesPerRow, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue