sky rendering (still needs work)
wireframe slightly easier to work with
This commit is contained in:
parent
66815aed40
commit
6c2b4f6f04
|
|
@ -325,16 +325,17 @@ qvec3b calculate_average(const std::vector<qvec4b> &pixels)
|
|||
}
|
||||
|
||||
std::tuple<std::optional<img::texture>, fs::resolve_result, fs::data> load_texture(
|
||||
const std::string_view &name, bool meta_only, const gamedef_t *game, const settings::common_settings &options)
|
||||
const std::string_view &name, bool meta_only, const gamedef_t *game, const settings::common_settings &options,
|
||||
bool no_prefix)
|
||||
{
|
||||
fs::path prefix;
|
||||
fs::path prefix {};
|
||||
|
||||
if (game->id == GAME_QUAKE_II) {
|
||||
if (!no_prefix && game->id == GAME_QUAKE_II) {
|
||||
prefix = "textures";
|
||||
}
|
||||
|
||||
for (auto &ext : img::extension_list) {
|
||||
fs::path p = (prefix / name) += ext.suffix;
|
||||
fs::path p = (no_prefix ? fs::path(name) : (prefix / name)) += ext.suffix;
|
||||
|
||||
if (auto pos = fs::where(p, options.filepriority.value() == settings::search_priority_t::LOOSE)) {
|
||||
if (auto data = fs::load(pos)) {
|
||||
|
|
|
|||
|
|
@ -114,7 +114,7 @@ constexpr struct
|
|||
|
||||
// Attempt to load a texture from the specified name.
|
||||
std::tuple<std::optional<texture>, fs::resolve_result, fs::data> load_texture(
|
||||
const std::string_view &name, bool meta_only, const gamedef_t *game, const settings::common_settings &options);
|
||||
const std::string_view &name, bool meta_only, const gamedef_t *game, const settings::common_settings &options, bool no_prefix = false);
|
||||
|
||||
enum class meta_ext
|
||||
{
|
||||
|
|
|
|||
|
|
@ -171,8 +171,90 @@ void main() {
|
|||
}
|
||||
)";
|
||||
|
||||
static const char *s_skyboxFragShader = R"(
|
||||
#version 330 core
|
||||
|
||||
in vec3 uv;
|
||||
in vec2 lightmap_uv;
|
||||
in vec3 normal;
|
||||
flat in vec3 flat_color;
|
||||
flat in uint styles;
|
||||
|
||||
out vec4 color;
|
||||
|
||||
uniform samplerCube texture_sampler;
|
||||
uniform sampler2DArray lightmap_sampler;
|
||||
uniform bool lightmap_only;
|
||||
uniform bool fullbright;
|
||||
uniform bool drawnormals;
|
||||
uniform bool drawflat;
|
||||
uniform float style_scalars[256];
|
||||
|
||||
void main() {
|
||||
if (drawnormals) {
|
||||
// remap -1..+1 to 0..1
|
||||
color = vec4((normal + vec3(1.0)) / vec3(2.0), 1.0);
|
||||
} else if (drawflat) {
|
||||
color = vec4(flat_color, 1.0);
|
||||
} else {
|
||||
if (!fullbright && lightmap_only)
|
||||
{
|
||||
vec3 lmcolor = vec3(0.5);
|
||||
|
||||
for (uint i = 0u; i < 32u; i += 8u)
|
||||
{
|
||||
uint style = (styles >> i) & 0xFFu;
|
||||
|
||||
if (style == 0xFFu)
|
||||
break;
|
||||
|
||||
lmcolor += texture(lightmap_sampler, vec3(lightmap_uv, (float) style)).rgb * style_scalars[style];
|
||||
}
|
||||
|
||||
// 2.0 for overbright
|
||||
color = vec4(lmcolor * 2.0, 1.0);
|
||||
}
|
||||
else
|
||||
color = vec4(texture(texture_sampler, uv).rgb, 1.0);
|
||||
}
|
||||
}
|
||||
)";
|
||||
|
||||
static const char *s_skyboxVertShader = R"(
|
||||
#version 330 core
|
||||
|
||||
layout (location = 0) in vec3 position;
|
||||
layout (location = 1) in vec2 vertex_uv;
|
||||
layout (location = 2) in vec2 vertex_lightmap_uv;
|
||||
layout (location = 3) in vec3 vertex_normal;
|
||||
layout (location = 4) in vec3 vertex_flat_color;
|
||||
layout (location = 5) in uint vertex_styles;
|
||||
|
||||
smooth out vec3 uv;
|
||||
out vec2 lightmap_uv;
|
||||
out vec3 normal;
|
||||
flat out vec3 flat_color;
|
||||
flat out uint styles;
|
||||
|
||||
uniform mat4 MVP;
|
||||
uniform vec3 eye_origin;
|
||||
|
||||
void main() {
|
||||
gl_Position = MVP * vec4(position.x, position.y, position.z, 1.0);
|
||||
|
||||
uv = normalize(position - eye_origin);
|
||||
lightmap_uv = vertex_lightmap_uv;
|
||||
normal = vertex_normal;
|
||||
flat_color = vertex_flat_color;
|
||||
styles = vertex_styles;
|
||||
}
|
||||
)";
|
||||
|
||||
void GLView::handleLoggedMessage(const QOpenGLDebugMessage &debugMessage)
|
||||
{
|
||||
if (debugMessage.type() == QOpenGLDebugMessage::ErrorType)
|
||||
__debugbreak();
|
||||
|
||||
qDebug() << debugMessage.message();
|
||||
}
|
||||
|
||||
|
|
@ -186,7 +268,7 @@ void GLView::initializeGL()
|
|||
logger->initialize(); // initializes in the current context, i.e. ctx
|
||||
|
||||
connect(logger, &QOpenGLDebugLogger::messageLogged, this, &GLView::handleLoggedMessage);
|
||||
logger->startLogging();
|
||||
logger->startLogging(QOpenGLDebugLogger::SynchronousLogging);
|
||||
|
||||
// set up shader
|
||||
|
||||
|
|
@ -195,6 +277,11 @@ void GLView::initializeGL()
|
|||
m_program->addShaderFromSourceCode(QOpenGLShader::Fragment, s_fragShader);
|
||||
assert(m_program->link());
|
||||
|
||||
m_skybox_program = new QOpenGLShaderProgram();
|
||||
m_skybox_program->addShaderFromSourceCode(QOpenGLShader::Vertex, s_skyboxVertShader);
|
||||
m_skybox_program->addShaderFromSourceCode(QOpenGLShader::Fragment, s_skyboxFragShader);
|
||||
assert(m_skybox_program->link());
|
||||
|
||||
m_program_wireframe = new QOpenGLShaderProgram();
|
||||
m_program_wireframe->addShaderFromSourceCode(QOpenGLShader::Vertex, s_vertShader_Wireframe);
|
||||
m_program_wireframe->addShaderFromSourceCode(QOpenGLShader::Fragment, s_fragShader_Wireframe);
|
||||
|
|
@ -212,6 +299,19 @@ void GLView::initializeGL()
|
|||
m_program_style_scalars_location = m_program->uniformLocation("style_scalars");
|
||||
m_program->release();
|
||||
|
||||
m_skybox_program->bind();
|
||||
m_skybox_program_mvp_location = m_skybox_program->uniformLocation("MVP");
|
||||
m_skybox_program_eye_direction_location = m_skybox_program->uniformLocation("eye_origin");
|
||||
m_skybox_program_texture_sampler_location = m_skybox_program->uniformLocation("texture_sampler");
|
||||
m_skybox_program_lightmap_sampler_location = m_skybox_program->uniformLocation("lightmap_sampler");
|
||||
m_skybox_program_opacity_location = m_skybox_program->uniformLocation("opacity");
|
||||
m_skybox_program_lightmap_only_location = m_skybox_program->uniformLocation("lightmap_only");
|
||||
m_skybox_program_fullbright_location = m_skybox_program->uniformLocation("fullbright");
|
||||
m_skybox_program_drawnormals_location = m_skybox_program->uniformLocation("drawnormals");
|
||||
m_skybox_program_drawflat_location = m_skybox_program->uniformLocation("drawflat");
|
||||
m_skybox_program_style_scalars_location = m_skybox_program->uniformLocation("style_scalars");
|
||||
m_skybox_program->release();
|
||||
|
||||
m_program_wireframe->bind();
|
||||
m_program_wireframe_mvp_location = m_program_wireframe->uniformLocation("MVP");
|
||||
m_program_wireframe->release();
|
||||
|
|
@ -257,6 +357,10 @@ void GLView::paintGL()
|
|||
m_program_wireframe->bind();
|
||||
m_program_wireframe->setUniformValue(m_program_wireframe_mvp_location, MVP);
|
||||
|
||||
glEnable(GL_POLYGON_OFFSET_FILL);
|
||||
glEnable(GL_POLYGON_OFFSET_LINE);
|
||||
glPolygonOffset(-0.8, 1.0);
|
||||
|
||||
glPolygonMode(GL_FRONT_AND_BACK, GL_LINE);
|
||||
QOpenGLVertexArrayObject::Binder vaoBinder(&m_vao);
|
||||
|
||||
|
|
@ -265,10 +369,14 @@ void GLView::paintGL()
|
|||
reinterpret_cast<void *>(draw.first_index * sizeof(uint32_t)));
|
||||
}
|
||||
glPolygonMode(GL_FRONT_AND_BACK, GL_FILL);
|
||||
glDisable(GL_POLYGON_OFFSET_FILL);
|
||||
glDisable(GL_POLYGON_OFFSET_LINE);
|
||||
|
||||
m_program_wireframe->release();
|
||||
}
|
||||
|
||||
QOpenGLShaderProgram *active_program = nullptr;
|
||||
|
||||
m_program->bind();
|
||||
m_program->setUniformValue(m_program_mvp_location, MVP);
|
||||
m_program->setUniformValue(m_program_texture_sampler_location, 0 /* texture unit */);
|
||||
|
|
@ -279,11 +387,27 @@ void GLView::paintGL()
|
|||
m_program->setUniformValue(m_program_drawnormals_location, m_drawNormals);
|
||||
m_program->setUniformValue(m_program_drawflat_location, m_drawFlat);
|
||||
|
||||
m_skybox_program->bind();
|
||||
m_skybox_program->setUniformValue(m_skybox_program_mvp_location, MVP);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_eye_direction_location, m_cameraOrigin);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_texture_sampler_location, 0 /* texture unit */);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_lightmap_sampler_location, 1 /* texture unit */);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_opacity_location, 1.0f);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_lightmap_only_location, m_lighmapOnly);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_fullbright_location, m_fullbright);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_drawnormals_location, m_drawNormals);
|
||||
m_skybox_program->setUniformValue(m_skybox_program_drawflat_location, m_drawFlat);
|
||||
|
||||
// opaque draws
|
||||
for (auto &draw : m_drawcalls) {
|
||||
if (draw.opacity != 1.0f)
|
||||
if (draw.key.opacity != 1.0f)
|
||||
continue;
|
||||
|
||||
if (active_program != draw.key.program) {
|
||||
active_program = draw.key.program;
|
||||
active_program->bind();
|
||||
}
|
||||
|
||||
draw.texture->bind(0 /* texture unit */);
|
||||
lightmap_texture->bind(1 /* texture unit */);
|
||||
|
||||
|
|
@ -299,13 +423,22 @@ void GLView::paintGL()
|
|||
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
|
||||
|
||||
for (auto &draw : m_drawcalls) {
|
||||
if (draw.opacity == 1.0f)
|
||||
if (draw.key.opacity == 1.0f)
|
||||
continue;
|
||||
|
||||
if (active_program != draw.key.program) {
|
||||
active_program = draw.key.program;
|
||||
active_program->bind();
|
||||
}
|
||||
|
||||
draw.texture->bind(0 /* texture unit */);
|
||||
lightmap_texture->bind(1 /* texture unit */);
|
||||
|
||||
m_program->setUniformValue(m_program_opacity_location, draw.opacity);
|
||||
if (active_program == m_program) {
|
||||
m_program->setUniformValue(m_program_opacity_location, draw.key.opacity);
|
||||
} else {
|
||||
m_skybox_program->setUniformValue(m_skybox_program_opacity_location, draw.key.opacity);
|
||||
}
|
||||
|
||||
QOpenGLVertexArrayObject::Binder vaoBinder(&m_vao);
|
||||
|
||||
|
|
@ -417,7 +550,9 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
// clear old data
|
||||
lightmap_texture.reset();
|
||||
m_drawcalls.clear();
|
||||
m_vbo.bind();
|
||||
m_vbo.allocate(0);
|
||||
m_indexBuffer.bind();
|
||||
m_indexBuffer.allocate(0);
|
||||
|
||||
int32_t highest_depth = 0;
|
||||
|
|
@ -430,16 +565,13 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
{
|
||||
const auto &lm_tex = lightmap.style_to_lightmap_atlas.begin()->second;
|
||||
|
||||
lightmap_texture = std::make_unique<QOpenGLTexture>(QOpenGLTexture::Target2DArray);
|
||||
lightmap_texture = std::make_shared<QOpenGLTexture>(QOpenGLTexture::Target2DArray);
|
||||
lightmap_texture->setSize(lm_tex.width, lm_tex.height);
|
||||
lightmap_texture->setLayers(highest_depth + 1);
|
||||
|
||||
lightmap_texture->setFormat(QOpenGLTexture::TextureFormat::RGBA8_UNorm);
|
||||
lightmap_texture->setAutoMipMapGenerationEnabled(false);
|
||||
lightmap_texture->setMagnificationFilter(QOpenGLTexture::Linear);
|
||||
lightmap_texture->setMinificationFilter(QOpenGLTexture::Linear);
|
||||
|
||||
lightmap_texture->setFormat(QOpenGLTexture::TextureFormat::RGBAFormat);
|
||||
|
||||
lightmap_texture->allocateStorage();
|
||||
|
||||
for (auto &style : lightmap.style_to_lightmap_atlas) {
|
||||
|
|
@ -448,17 +580,6 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
}
|
||||
}
|
||||
|
||||
// this determines what can be batched together in a draw call
|
||||
struct material_key
|
||||
{
|
||||
std::string texname;
|
||||
float opacity;
|
||||
|
||||
auto as_tuple() const { return std::make_tuple(texname, opacity); }
|
||||
|
||||
bool operator<(const material_key &other) const { return as_tuple() < other.as_tuple(); }
|
||||
};
|
||||
|
||||
struct face_payload
|
||||
{
|
||||
const mface_t *face;
|
||||
|
|
@ -468,6 +589,8 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
// collect faces grouped by material_key
|
||||
std::map<material_key, std::vector<face_payload>> faces_by_material_key;
|
||||
|
||||
bool needs_skybox = false;
|
||||
|
||||
// collect entity bmodels
|
||||
for (int mi = 0; mi < bsp.dmodels.size(); mi++) {
|
||||
qvec3d origin{};
|
||||
|
|
@ -504,27 +627,78 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
if (!texinfo)
|
||||
continue; // FIXME: render as checkerboard?
|
||||
|
||||
QOpenGLShaderProgram *program = m_program;
|
||||
|
||||
// determine opacity
|
||||
float opacity = 1.0f;
|
||||
|
||||
if (bsp.loadversion->game->id == GAME_QUAKE_II) {
|
||||
|
||||
if (texinfo->flags.native & (Q2_SURF_NODRAW | Q2_SURF_SKY)) {
|
||||
if (texinfo->flags.native & Q2_SURF_NODRAW) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if (texinfo->flags.native & Q2_SURF_TRANS33) {
|
||||
opacity = 0.33f;
|
||||
}
|
||||
if (texinfo->flags.native & Q2_SURF_TRANS66) {
|
||||
opacity = 0.66f;
|
||||
if (texinfo->flags.native & Q2_SURF_SKY) {
|
||||
program = m_skybox_program;
|
||||
needs_skybox = true;
|
||||
} else {
|
||||
if (texinfo->flags.native & Q2_SURF_TRANS33) {
|
||||
opacity = 0.33f;
|
||||
}
|
||||
if (texinfo->flags.native & Q2_SURF_TRANS66) {
|
||||
opacity = 0.66f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
material_key k = {.texname = t, .opacity = opacity};
|
||||
material_key k = {.program = program, .texname = t, .opacity = opacity};
|
||||
faces_by_material_key[k].push_back({.face = &f, .model_offset = origin});
|
||||
}
|
||||
}
|
||||
|
||||
std::shared_ptr<QOpenGLTexture> skybox_texture;
|
||||
|
||||
if (needs_skybox) {
|
||||
// load skybox
|
||||
std::string skybox = "unit1_"; // TODO: game-specific defaults
|
||||
|
||||
if (entities[0].has("sky")) {
|
||||
skybox = entities[0].get("sky");
|
||||
}
|
||||
|
||||
auto up = img::load_texture(fmt::format("env/{}up", skybox), false, bsp.loadversion->game, settings, true);
|
||||
auto down = img::load_texture(fmt::format("env/{}dn", skybox), false, bsp.loadversion->game, settings, true);
|
||||
auto left = img::load_texture(fmt::format("env/{}lf", skybox), false, bsp.loadversion->game, settings, true);
|
||||
auto right = img::load_texture(fmt::format("env/{}rt", skybox), false, bsp.loadversion->game, settings, true);
|
||||
auto front = img::load_texture(fmt::format("env/{}ft", skybox), false, bsp.loadversion->game, settings, true);
|
||||
auto back = img::load_texture(fmt::format("env/{}bk", skybox), false, bsp.loadversion->game, settings, true);
|
||||
|
||||
skybox_texture = std::make_shared<QOpenGLTexture>(QOpenGLTexture::TargetCubeMap);
|
||||
|
||||
skybox_texture->setSize(std::get<0>(up)->width, std::get<0>(up)->height);
|
||||
skybox_texture->setFormat(QOpenGLTexture::TextureFormat::RGBA8_UNorm);
|
||||
skybox_texture->setAutoMipMapGenerationEnabled(true);
|
||||
skybox_texture->setMagnificationFilter(QOpenGLTexture::Linear);
|
||||
skybox_texture->setMinificationFilter(QOpenGLTexture::LinearMipMapLinear);
|
||||
skybox_texture->setMaximumAnisotropy(16);
|
||||
skybox_texture->allocateStorage();
|
||||
|
||||
skybox_texture->setWrapMode(QOpenGLTexture::ClampToEdge);
|
||||
|
||||
skybox_texture->setData(0, 0, QOpenGLTexture::CubeMapNegativeZ, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
|
||||
std::get<0>(up)->pixels.data(), nullptr);
|
||||
skybox_texture->setData(0, 0, QOpenGLTexture::CubeMapPositiveZ, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
|
||||
std::get<0>(down)->pixels.data(), nullptr);
|
||||
skybox_texture->setData(0, 0, QOpenGLTexture::CubeMapNegativeY, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
|
||||
std::get<0>(left)->pixels.data(), nullptr);
|
||||
skybox_texture->setData(0, 0, QOpenGLTexture::CubeMapPositiveY, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
|
||||
std::get<0>(right)->pixels.data(), nullptr);
|
||||
skybox_texture->setData(0, 0, QOpenGLTexture::CubeMapNegativeX, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
|
||||
std::get<0>(front)->pixels.data(), nullptr);
|
||||
skybox_texture->setData(0, 0, QOpenGLTexture::CubeMapPositiveX, QOpenGLTexture::RGBA, QOpenGLTexture::UInt8,
|
||||
std::get<0>(back)->pixels.data(), nullptr);
|
||||
}
|
||||
|
||||
// populate the vertex/index buffers
|
||||
struct vertex_t
|
||||
{
|
||||
|
|
@ -548,15 +722,14 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
continue;
|
||||
}
|
||||
|
||||
std::unique_ptr<QOpenGLTexture> qtexture =
|
||||
std::make_unique<QOpenGLTexture>(QImage(reinterpret_cast<const uint8_t *>(texture->pixels.data()),
|
||||
texture->width, texture->height, QImage::Format_RGBA8888));
|
||||
|
||||
qtexture->setMaximumAnisotropy(16);
|
||||
qtexture->setAutoMipMapGenerationEnabled(true);
|
||||
std::shared_ptr<QOpenGLTexture> qtexture;
|
||||
|
||||
const size_t dc_first_index = indexBuffer.size();
|
||||
|
||||
if (k.program == m_skybox_program) {
|
||||
qtexture = skybox_texture;
|
||||
}
|
||||
|
||||
for (const auto &[f, model_offset] : faces) {
|
||||
const int fnum = Face_GetNum(&bsp, f);
|
||||
const auto plane_normal = Face_Normal(&bsp, f);
|
||||
|
|
@ -601,9 +774,29 @@ void GLView::renderBSP(const QString &file, const mbsp_t &bsp, const bspxentries
|
|||
}
|
||||
}
|
||||
|
||||
if (!qtexture) {
|
||||
qtexture = std::make_shared<QOpenGLTexture>(QOpenGLTexture::Target2D);
|
||||
|
||||
qtexture->setSize(texture->width, texture->height);
|
||||
qtexture->setFormat(QOpenGLTexture::TextureFormat::RGBA8_UNorm);
|
||||
|
||||
qtexture->allocateStorage();
|
||||
|
||||
// ????
|
||||
// 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->setMaximumAnisotropy(16);
|
||||
qtexture->setAutoMipMapGenerationEnabled(true);
|
||||
|
||||
qtexture->setMagnificationFilter(QOpenGLTexture::Linear);
|
||||
qtexture->setMinificationFilter(QOpenGLTexture::LinearMipMapLinear);
|
||||
}
|
||||
|
||||
const size_t dc_index_count = indexBuffer.size() - dc_first_index;
|
||||
|
||||
drawcall_t dc = {.opacity = k.opacity,
|
||||
drawcall_t dc = {.key = k,
|
||||
.texture = std::move(qtexture),
|
||||
.first_index = dc_first_index,
|
||||
.index_count = dc_index_count};
|
||||
|
|
|
|||
|
|
@ -85,17 +85,29 @@ private:
|
|||
QOpenGLBuffer m_vbo;
|
||||
QOpenGLBuffer m_indexBuffer;
|
||||
|
||||
std::unique_ptr<QOpenGLTexture> lightmap_texture;
|
||||
// this determines what can be batched together in a draw call
|
||||
struct material_key
|
||||
{
|
||||
QOpenGLShaderProgram *program;
|
||||
std::string texname;
|
||||
float opacity = 1.f;
|
||||
|
||||
auto as_tuple() const { return std::make_tuple(program, texname, opacity); }
|
||||
|
||||
bool operator<(const material_key &other) const { return as_tuple() < other.as_tuple(); }
|
||||
};
|
||||
|
||||
std::shared_ptr<QOpenGLTexture> lightmap_texture;
|
||||
struct drawcall_t
|
||||
{
|
||||
float opacity = 1.0f;
|
||||
std::unique_ptr<QOpenGLTexture> texture;
|
||||
material_key key;
|
||||
std::shared_ptr<QOpenGLTexture> texture;
|
||||
size_t first_index = 0;
|
||||
size_t index_count = 0;
|
||||
};
|
||||
std::vector<drawcall_t> m_drawcalls;
|
||||
|
||||
QOpenGLShaderProgram *m_program = nullptr;
|
||||
QOpenGLShaderProgram *m_program = nullptr, *m_skybox_program = nullptr;
|
||||
QOpenGLShaderProgram *m_program_wireframe = nullptr;
|
||||
|
||||
// uniform locations
|
||||
|
|
@ -109,6 +121,18 @@ private:
|
|||
int m_program_drawflat_location = 0;
|
||||
int m_program_style_scalars_location = 0;
|
||||
|
||||
// uniform locations
|
||||
int m_skybox_program_mvp_location = 0;
|
||||
int m_skybox_program_eye_direction_location = 0;
|
||||
int m_skybox_program_texture_sampler_location = 0;
|
||||
int m_skybox_program_lightmap_sampler_location = 0;
|
||||
int m_skybox_program_opacity_location = 0;
|
||||
int m_skybox_program_lightmap_only_location = 0;
|
||||
int m_skybox_program_fullbright_location = 0;
|
||||
int m_skybox_program_drawnormals_location = 0;
|
||||
int m_skybox_program_drawflat_location = 0;
|
||||
int m_skybox_program_style_scalars_location = 0;
|
||||
|
||||
// uniform locations (wireframe program)
|
||||
int m_program_wireframe_mvp_location = 0;
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue