gs-mipmapper: Formatting and refactoring

This commit is contained in:
Michael Fabian 'Xaymar' Dirks 2018-09-28 23:32:35 +02:00
parent bb5c1f80b5
commit 95018868dc
2 changed files with 33 additions and 34 deletions

View File

@ -18,6 +18,7 @@
*/ */
#include "gs-mipmapper.h" #include "gs-mipmapper.h"
#include "plugin.h"
extern "C" { extern "C" {
#pragma warning(push) #pragma warning(push)
@ -57,41 +58,41 @@ struct gs_d3d11_device {
gs::mipmapper::~mipmapper() gs::mipmapper::~mipmapper()
{ {
vertexBuffer.reset(); vertex_buffer.reset();
renderTarget.reset(); render_target.reset();
effect.reset(); effect.reset();
} }
gs::mipmapper::mipmapper() gs::mipmapper::mipmapper()
{ {
vertexBuffer = std::make_unique<gs::vertex_buffer>(6, 1); vertex_buffer = std::make_unique<gs::vertex_buffer>(6, 1);
auto v0 = vertexBuffer->at(0); auto v0 = vertex_buffer->at(0);
v0.position->x = 0; v0.position->x = 0;
v0.position->y = 0; v0.position->y = 0;
v0.uv[0]->x = 0; v0.uv[0]->x = 0;
v0.uv[0]->y = 0; v0.uv[0]->y = 0;
auto v1 = vertexBuffer->at(1); auto v1 = vertex_buffer->at(1);
auto v4 = vertexBuffer->at(4); auto v4 = vertex_buffer->at(4);
v4.position->x = v1.position->x = 1.0; v4.position->x = v1.position->x = 1.0;
v4.position->y = v1.position->y = 0; v4.position->y = v1.position->y = 0;
v4.uv[0]->x = v1.uv[0]->x = 1.0; v4.uv[0]->x = v1.uv[0]->x = 1.0;
v4.uv[0]->y = v1.uv[0]->y = 0; v4.uv[0]->y = v1.uv[0]->y = 0;
auto v2 = vertexBuffer->at(2); auto v2 = vertex_buffer->at(2);
auto v3 = vertexBuffer->at(3); auto v3 = vertex_buffer->at(3);
v3.position->x = v2.position->x = 0; v3.position->x = v2.position->x = 0;
v3.position->y = v2.position->y = 1.0; v3.position->y = v2.position->y = 1.0;
v3.uv[0]->x = v2.uv[0]->x = 0; v3.uv[0]->x = v2.uv[0]->x = 0;
v3.uv[0]->y = v2.uv[0]->y = 1.0; v3.uv[0]->y = v2.uv[0]->y = 1.0;
auto v5 = vertexBuffer->at(5); auto v5 = vertex_buffer->at(5);
v5.position->x = 1.0; v5.position->x = 1.0;
v5.position->y = 1.0; v5.position->y = 1.0;
v5.uv[0]->x = 1.0; v5.uv[0]->x = 1.0;
v5.uv[0]->y = 1.0; v5.uv[0]->y = 1.0;
vertexBuffer->update(); vertex_buffer->update();
char* effect_file = obs_module_file("effects/mipgen.effect"); char* effect_file = obs_module_file("effects/mipgen.effect");
effect = std::make_unique<gs::effect>(effect_file); effect = std::make_unique<gs::effect>(effect_file);
@ -136,19 +137,11 @@ void gs::mipmapper::rebuild(std::shared_ptr<gs::texture> source, std::shared_ptr
obs_enter_graphics(); obs_enter_graphics();
// Copy original texture // Copy original texture
gs_copy_texture(target->get_object(), source->get_object()); //gs_copy_texture(target->get_object(), source->get_object());
// Test if we actually need to recreate the render target for a different format. // Test if we actually need to recreate the render target for a different format or at all.
bool recreate = false; if ((!render_target) || (source->get_color_format() != render_target->get_color_format())) {
if (renderTarget) { render_target = std::make_unique<gs::rendertarget>(source->get_color_format(), GS_ZS_NONE);
recreate = (source->get_color_format() != renderTarget->get_color_format());
} else {
recreate = true;
}
// Re-create the render target if necessary.
if (recreate) {
renderTarget = std::make_unique<gs::rendertarget>(source->get_color_format(), GS_ZS_NONE);
} }
// Render // Render
@ -180,7 +173,7 @@ void gs::mipmapper::rebuild(std::shared_ptr<gs::texture> source, std::shared_ptr
break; break;
} }
gs_load_vertexbuffer(vertexBuffer->update()); gs_load_vertexbuffer(vertex_buffer->update());
gs_load_indexbuffer(nullptr); gs_load_indexbuffer(nullptr);
if (source->get_type() == gs::texture::type::Normal) { if (source->get_type() == gs::texture::type::Normal) {
@ -198,36 +191,41 @@ void gs::mipmapper::rebuild(std::shared_ptr<gs::texture> source, std::shared_ptr
target_t2->GetDesc(&target_t2desc); target_t2->GetDesc(&target_t2desc);
dev->context->CopySubresourceRegion(target_t2, 0, 0, 0, 0, source_t2, 0, nullptr);
// If we do not have any miplevels, just stop now. // If we do not have any miplevels, just stop now.
if (target_t2desc.MipLevels == 1) { if (target_t2desc.MipLevels == 1) {
obs_leave_graphics(); obs_leave_graphics();
return; return;
} }
for (size_t mip = 1; mip < target_t2desc.MipLevels; mip++) { for (size_t mip = 1; mip <= target_t2desc.MipLevels; mip++) {
texture_width /= 2; texture_width /= 2;
texture_height /= 2; texture_height /= 2;
texel_width *= 2; texel_width *= 2;
texel_height *= 2; texel_height *= 2;
// Draw mipmap layer // Draw mipmap layer
{ try {
auto op = renderTarget->render(texture_width, texture_height); auto op = render_target->render(texture_width, texture_height);
effect->get_parameter("image").set_texture(target); effect->get_parameter("image").set_texture(target);
effect->get_parameter("level").set_int(mip - 1); effect->get_parameter("level").set_int(mip);
effect->get_parameter("imageTexel").set_float2(texel_width, texel_height); effect->get_parameter("imageTexel").set_float2(texel_width, texel_height);
effect->get_parameter("strength").set_float(strength); effect->get_parameter("strength").set_float(strength);
while (gs_effect_loop(effect->get_object(), technique.c_str())) { while (gs_effect_loop(effect->get_object(), technique.c_str())) {
gs_draw(gs_draw_mode::GS_TRIS, 0, vertexBuffer->size()); gs_draw(gs_draw_mode::GS_TRIS, 0, vertex_buffer->size());
} }
} catch (...) {
P_LOG_ERROR("Failed to render mipmap layer.");
} }
// Copy // Copy
ID3D11Texture2D* rt = ID3D11Texture2D* rt =
reinterpret_cast<ID3D11Texture2D*>(gs_texture_get_obj(renderTarget->get_object())); reinterpret_cast<ID3D11Texture2D*>(gs_texture_get_obj(render_target->get_object()));
dev->context->CopySubresourceRegion(target_t2, mip, 0, 0, 0, rt, 0, nullptr); uint32_t level = D3D11CalcSubresource(mip, 0, target_t2desc.MipLevels);
dev->context->CopySubresourceRegion(target_t2, level, 0, 0, 0, rt, 0, NULL);
} }
} }
#endif #endif

View File

@ -32,8 +32,8 @@ extern "C" {
namespace gs { namespace gs {
class mipmapper { class mipmapper {
std::unique_ptr<gs::vertex_buffer> vertexBuffer; std::unique_ptr<gs::vertex_buffer> vertex_buffer;
std::unique_ptr<gs::rendertarget> renderTarget; std::unique_ptr<gs::rendertarget> render_target;
std::unique_ptr<gs::effect> effect; std::unique_ptr<gs::effect> effect;
public: public:
@ -50,6 +50,7 @@ namespace gs {
~mipmapper(); ~mipmapper();
mipmapper(); mipmapper();
void rebuild(std::shared_ptr<gs::texture> source, std::shared_ptr<gs::texture> target, gs::mipmapper::generator generator, float_t strength); void rebuild(std::shared_ptr<gs::texture> source, std::shared_ptr<gs::texture> target,
gs::mipmapper::generator generator, float_t strength);
}; };
} // namespace gs } // namespace gs