lightpreview: use a placeholder texture for missing textures

This commit is contained in:
Eric Wasylishen 2023-06-06 20:58:05 -06:00
parent 9c6f6c2589
commit 062c458913
2 changed files with 54 additions and 10 deletions

View File

@ -60,11 +60,13 @@ GLView::~GLView()
delete m_program;
delete m_program_wireframe;
delete m_skybox_program;
m_vbo.destroy();
m_indexBuffer.destroy();
m_vao.destroy();
placeholder_texture.reset();
lightmap_texture.reset();
m_drawcalls.clear();
@ -548,6 +550,7 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
makeCurrent();
// clear old data
placeholder_texture.reset();
lightmap_texture.reset();
m_drawcalls.clear();
m_vbo.bind();
@ -580,6 +583,39 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
}
}
// upload placeholder texture
{
placeholder_texture = std::make_shared<QOpenGLTexture>(QOpenGLTexture::Target2D);
placeholder_texture->setSize(64, 64);
placeholder_texture->setFormat(QOpenGLTexture::TextureFormat::RGBA8_UNorm);
placeholder_texture->setAutoMipMapGenerationEnabled(true);
placeholder_texture->setMagnificationFilter(QOpenGLTexture::Linear);
placeholder_texture->setMinificationFilter(QOpenGLTexture::Linear);
placeholder_texture->allocateStorage();
uint8_t *data = new uint8_t[64 * 64 * 4];
for (int y = 0; y < 64; ++y) {
for (int x = 0; x < 64; ++x) {
int i = ((y * 64) + x) * 4;
int v;
if ((x > 32) == (y > 32)) {
v = 64;
} else {
v = 32;
}
data[i] = v; // R
data[i + 1] = v; // G
data[i + 2] = v; // B
data[i + 3] = 0xff; // A
}
}
placeholder_texture->setData(
0, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8, reinterpret_cast<const void *>(data));
delete[] data;
}
struct face_payload
{
const mface_t *face;
@ -716,13 +752,17 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
// upload texture
// FIXME: we should have a separate lightpreview_options
auto *texture = img::find(k.texname);
std::shared_ptr<QOpenGLTexture> qtexture;
if (!texture) {
logging::print("warning, couldn't locate {}", k.texname);
continue;
qtexture = placeholder_texture;
}
std::shared_ptr<QOpenGLTexture> qtexture;
if (!texture->width || !texture->height) {
logging::print("warning, empty texture {}", k.texname);
qtexture = placeholder_texture;
}
const size_t dc_first_index = indexBuffer.size();
@ -744,8 +784,13 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
qvec3f pos = Face_PointAtIndex(&bsp, f, j);
qvec2f uv = Face_WorldToTexCoord(&bsp, f, pos);
uv[0] *= (1.0 / texture->width);
uv[1] *= (1.0 / texture->height);
if (qtexture) {
uv[0] *= (1.0 / qtexture->width());
uv[1] *= (1.0 / qtexture->height());
} else {
uv[0] *= (1.0 / texture->width);
uv[1] *= (1.0 / texture->height);
}
qvec2f lightmap_uv = lm_uvs.at(j);
@ -784,8 +829,8 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
// ????
// FIXME: debug why this doesn't work, so we can remove the QImage garbage
qtexture->setData(QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
reinterpret_cast<const void *>(texture->pixels.data()));
qtexture->setData(
QOpenGLTexture::RGBA, QOpenGLTexture::UInt8, reinterpret_cast<const void *>(texture->pixels.data()));
qtexture->setMaximumAnisotropy(16);
qtexture->setAutoMipMapGenerationEnabled(true);
@ -796,10 +841,8 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
const size_t dc_index_count = indexBuffer.size() - dc_first_index;
drawcall_t dc = {.key = k,
.texture = std::move(qtexture),
.first_index = dc_first_index,
.index_count = dc_index_count};
drawcall_t dc = {
.key = k, .texture = std::move(qtexture), .first_index = dc_first_index, .index_count = dc_index_count};
m_drawcalls.push_back(std::move(dc));
}

View File

@ -99,6 +99,7 @@ private:
bool operator<(const material_key &other) const { return as_tuple() < other.as_tuple(); }
};
std::shared_ptr<QOpenGLTexture> placeholder_texture;
std::shared_ptr<QOpenGLTexture> lightmap_texture;
struct drawcall_t
{