core: Defer WebGPU dynamic texture wrapper creation (#4369)

This commit is contained in:
Sargun Vohra
2026-07-01 05:16:51 -07:00
committed by GitHub
parent 887e6021e6
commit 027b9340c3
4 changed files with 41 additions and 6 deletions

View File

@@ -65,8 +65,11 @@ public:
virtual bool removeTexture(const TextureHandle& texHandle);
protected:
DynamicTexture(Size size, TexturePixelType pixelType);
mapbox::ShelfPack shelfPack;
Texture2DPtr texture;
TexturePixelType pixelFormat;
int numTextures = 0;
std::mutex mutex;
};

View File

@@ -19,6 +19,9 @@ public:
std::unordered_map<gfx::TextureHandle, std::unique_ptr<uint8_t[]>, gfx::TextureHandle::Hasher>;
private:
Context& context;
Size size;
gfx::TexturePixelType pixelType;
bool deferredCreation = false;
ImagesToUpload imagesToUpload;
};

View File

@@ -5,11 +5,15 @@
namespace mbgl {
namespace gfx {
DynamicTexture::DynamicTexture(Context& context, Size size, TexturePixelType pixelType) {
DynamicTexture::DynamicTexture(Size size, TexturePixelType pixelType)
: pixelFormat(pixelType) {
mapbox::ShelfPack::ShelfPackOptions options;
options.autoResize = false;
shelfPack = mapbox::ShelfPack(size.width, size.height, options);
}
DynamicTexture::DynamicTexture(Context& context, Size size, TexturePixelType pixelType)
: DynamicTexture(size, pixelType) {
texture = context.createTexture2D();
texture->setSize(size);
texture->setFormat(pixelType, gfx::TextureChannelDataType::UnsignedByte);
@@ -24,7 +28,7 @@ const gfx::Texture2DPtr& DynamicTexture::getTexture() const {
}
TexturePixelType DynamicTexture::getPixelFormat() const {
return getTexture()->getFormat();
return pixelFormat;
}
bool DynamicTexture::isEmpty() const {

View File

@@ -6,18 +6,37 @@ namespace mbgl {
namespace webgpu {
DynamicTexture::DynamicTexture(Context& context, Size size, gfx::TexturePixelType pixelType)
: gfx::DynamicTexture(context, size, pixelType) {
: gfx::DynamicTexture(size, pixelType),
context(context),
size(size),
pixelType(pixelType) {
deferredCreation = true;
}
namespace {
size_t pixelStride(gfx::TexturePixelType pixelType) {
switch (pixelType) {
case gfx::TexturePixelType::Alpha:
case gfx::TexturePixelType::Luminance:
return 1;
case gfx::TexturePixelType::RGBA:
return 4;
case gfx::TexturePixelType::Stencil:
case gfx::TexturePixelType::Depth:
return 4;
}
return 4;
}
} // namespace
void DynamicTexture::uploadImage(const uint8_t* pixelData, gfx::TextureHandle& texHandle) {
std::scoped_lock lock(mutex);
const auto& rect = texHandle.getRectangle();
const auto imageSize = Size(rect.w, rect.h);
auto size = imageSize.area() * texture->getPixelStride();
auto imageData = std::make_unique<uint8_t[]>(size);
std::copy(pixelData, pixelData + size, imageData.get());
auto byteSize = imageSize.area() * pixelStride(pixelType);
auto imageData = std::make_unique<uint8_t[]>(byteSize);
std::copy(pixelData, pixelData + byteSize, imageData.get());
imagesToUpload.emplace(texHandle, std::move(imageData));
gfx::DynamicTexture::uploadImage(pixelData, texHandle);
@@ -26,6 +45,12 @@ void DynamicTexture::uploadImage(const uint8_t* pixelData, gfx::TextureHandle& t
void DynamicTexture::uploadDeferredImages(gfx::UploadPass&) {
std::scoped_lock lock(mutex);
if (deferredCreation) {
texture = context.createTexture2D();
texture->setSize(size);
texture->setFormat(pixelType, gfx::TextureChannelDataType::UnsignedByte);
texture->setSamplerConfiguration({.filter = gfx::TextureFilterType::Linear,
.wrapU = gfx::TextureWrapType::Clamp,
.wrapV = gfx::TextureWrapType::Clamp});
texture->create();
deferredCreation = false;
}