Currently job artifacts in CI/CD pipelines on LRZ GitLab never expire. Starting from Wed 26.1.2022 the default expiration time will be 30 days (GitLab default). Currently existing artifacts in already completed jobs will not be affected by the change. The latest artifacts for all jobs in the latest successful pipelines will be kept. More information: https://gitlab.lrz.de/help/user/admin_area/settings/continuous_integration.html#default-artifacts-expiration

Commit e2128a34 authored by Christian Schulte zu Berge's avatar Christian Schulte zu Berge
Browse files

* Fixed GLReduction computing wrong values due to missing texture clamping

* Updated DepthDarkening to use GlReduction to compute min/max depth
parent 8fa3a1ab
......@@ -195,7 +195,7 @@ namespace campvis {
}
_texture->uploadTexture();
_texture->setWrapping(tgt::Texture::CLAMP);
_texture->setWrapping(tgt::Texture::CLAMP_TO_EDGE);
if (isInteger && isSigned) {
// restore default
......
......@@ -33,17 +33,15 @@ out vec4 out_Color;
#include "tools/texture2d.frag"
uniform sampler2D _texture;
uniform TextureParameters2D _textureParams;
uniform vec2 _texCoordsMultiplier;
uniform vec2 _texCoordsShift;
void main() {
vec2 tmp = ex_TexCoord.xy * _texCoordsMultiplier * 2.0;
ivec2 texel = ivec2((tmp * _textureParams._size));
vec2 tmp = ex_TexCoord.xy - _texCoordsShift;
vec4 a = texelFetch(_texture, texel, 0);
vec4 b = texelFetch(_texture, texel + ivec2(1, 0), 0);
vec4 c = texelFetch(_texture, texel + ivec2(0, 1), 0);
vec4 d = texelFetch(_texture, texel + ivec2(1, 1), 0);
vec4 a = texture(_texture, tmp);
vec4 b = textureOffset(_texture, tmp, ivec2(1, 0));
vec4 c = textureOffset(_texture, tmp, ivec2(0, 1));
vec4 d = textureOffset(_texture, tmp, ivec2(1, 1));
out_Color = REDUCTION_OP(a, b, c, d);
}
......@@ -108,6 +108,7 @@ namespace campvis {
break;
#ifdef GL_DEPTH_COMPONENT32F
case GL_DEPTH_COMPONENT32F:
tex = new tgt::Texture(0, getRenderTargetSize(), GL_DEPTH_COMPONENT, GL_DEPTH_COMPONENT32F, GL_FLOAT, tgt::Texture::LINEAR);
break;
#endif
......
......@@ -102,11 +102,11 @@ namespace campvis {
tgtAssert(texture->getDimensions().z == 1, "Reduction of 3D images not yet implemented! Somebody was too lazy (or stressed - deadline was close) to do that...");
std::vector<float> readBackBuffer;
const tgt::ivec3& size = texture->getDimensions();
tgt::vec2 texCoordMultiplier(1.f);
tgt::vec2 texCoordShift = tgt::vec2(.5f) / tgt::vec2(size.xy());
tgt::ivec2 currentSize = size.xy();
reduceSizes(currentSize, texCoordMultiplier);
reduceSizes(currentSize, texCoordShift);
tgt::ivec2 startSize = currentSize;
// Set OpenGL pixel alignment to 1 to avoid problems with NPOT textures
glPixelStorei(GL_UNPACK_ALIGNMENT, 1);
......@@ -119,7 +119,7 @@ namespace campvis {
for (size_t i = 0; i < 2; ++i) {
tempTextures[i] = new tgt::Texture(0, tgt::ivec3(currentSize, 1), GL_RGBA, GL_RGBA32F, GL_FLOAT, tgt::Texture::NEAREST);
tempTextures[i]->uploadTexture();
tempTextures[i]->setWrapping(tgt::Texture::CLAMP);
tempTextures[i]->setWrapping(tgt::Texture::CLAMP_TO_EDGE);
}
size_t readTex = 0;
size_t writeTex = 1;
......@@ -133,33 +133,27 @@ namespace campvis {
_shader->activate();
_fbo->attachTexture(tempTextures[readTex]);
_shader->setIgnoreUniformLocationError(true);
inputUnit.activate();
texture->bind();
_shader->setUniform("_texture", inputUnit.getUnitNumber());
_shader->setUniform("_textureParams._size", tgt::vec2(size.xy()));
_shader->setUniform("_textureParams._sizeRCP", tgt::vec2(1.f) / tgt::vec2(size.xy()));
_shader->setUniform("_textureParams._numChannels", static_cast<int>(texture->getNumChannels()));
_shader->setIgnoreUniformLocationError(false);
glViewport(0, 0, currentSize.x, currentSize.y);
_shader->setUniform("_texCoordsMultiplier", texCoordMultiplier);
_shader->setUniform("_texCoordsShift", texCoordShift);
glViewport(startSize.x - currentSize.x, startSize.y - currentSize.y, currentSize.x, currentSize.y);
QuadRdr.renderQuad();
LGL_ERROR;
reduceSizes(currentSize, texCoordShift);
glViewport(startSize.x - currentSize.x, startSize.y - currentSize.y, currentSize.x, currentSize.y);
// perform reduction until 1x1 texture remains
while (currentSize.x > 1 || currentSize.y > 1) {
reduceSizes(currentSize, texCoordMultiplier);
_fbo->attachTexture(tempTextures[writeTex]);
tempTextures[readTex]->bind();
glViewport(0, 0, currentSize.x, currentSize.y);
_shader->setUniform("_texCoordsMultiplier", texCoordMultiplier);
_shader->setUniform("_texCoordsShift", texCoordShift);
QuadRdr.renderQuad();
LGL_ERROR;
//_fbo->detachTexture(GL_COLOR_ATTACHMENT0);
reduceSizes(currentSize, texCoordShift);
std::swap(writeTex, readTex);
}
......@@ -171,7 +165,7 @@ namespace campvis {
size_t channels = tempTextures[readTex]->getNumChannels();
toReturn.resize(currentSize.x * currentSize.y * channels);
glReadBuffer(GL_COLOR_ATTACHMENT0);
glReadPixels(0, 0, currentSize.x, currentSize.y, readBackFormat, GL_FLOAT, &toReturn.front());
glReadPixels(startSize.x - currentSize.x, startSize.y - currentSize.y, currentSize.x, currentSize.y, readBackFormat, GL_FLOAT, &toReturn.front());
LGL_ERROR;
// clean up...
......@@ -187,14 +181,16 @@ namespace campvis {
return toReturn;
}
void GlReduction::reduceSizes(tgt::ivec2& currentSize, tgt::vec2& texCoordMultiplier) {
void GlReduction::reduceSizes(tgt::ivec2& currentSize, tgt::vec2& texCoordShift) {
if (currentSize.x > 1) {
currentSize.x = DIV_CEIL(currentSize.x, 2);
texCoordMultiplier.x /= 2.f;
if (currentSize.x == 1)
texCoordShift.x *= -1.f;
}
if (currentSize.y > 1) {
currentSize.y = DIV_CEIL(currentSize.y, 2);
texCoordMultiplier.y /= 2.f;
if (currentSize.y == 1)
texCoordShift.y *= -1.f;
}
}
......@@ -213,6 +209,9 @@ namespace campvis {
case MULTIPLICATION:
return "#define REDUCTION_OP(a, b, c, d) a*b*c*d";
break;
case MIN_MAX:
return "#define REDUCTION_OP(a, b, c, d) vec4(min(a.r, min(b.r, min(c.r, d.r))), max(a.g, max(b.g, max(c.g, d.g))), 0.0, 0.0)";
break;
default:
tgtAssert(false, "Should not reach this, wrong enum value?");
return "";
......
......@@ -58,7 +58,8 @@ namespace campvis {
MIN, ///< Minimum
MAX, ///< Maximum
PLUS, ///< Sum (plus)
MULTIPLICATION ///< Product (multiplication)
MULTIPLICATION, ///< Product (multiplication)
MIN_MAX ///< Minimum/Maximum (WORKS ONLY with single channel images!)
};
/**
......
......@@ -35,7 +35,7 @@
#include "core/datastructures/imagedata.h"
#include "core/datastructures/imagerepresentationgl.h"
#include "core/datastructures/renderdata.h"
#include "core/tools/glreduction.h"
#include "core/classification/simpletransferfunction.h"
......@@ -50,10 +50,11 @@ namespace campvis {
, p_outputImage("OutputImage", "Output Image", "dd.output", DataNameProperty::WRITE)
, p_sigma("Sigma", "Sigma of Gaussian Filter", 2.f, 0.f, 10.f, 0.1f)
, p_lambda("Lambda", "Strength of Depth Darkening Effect", 10.f, 0.f, 50.f, 0.1f)
, p_useColorCoding("UseColorCoding", "Cold/Warm Color Coding", false, AbstractProcessor::INVALID_SHADER)
, p_useColorCoding("UseColorCoding", "Cold/Warm Color Coding", false, AbstractProcessor::INVALID_RESULT | AbstractProcessor::INVALID_SHADER)
, p_coldColor("ColdColor", "Cold Color (Far Objects)", tgt::vec3(0.f, 0.f, 1.f), tgt::vec3(0.f), tgt::vec3(1.f))
, p_warmColor("WarmColor", "Warm Color (Near Objects)", tgt::vec3(1.f, 0.f, 0.f), tgt::vec3(0.f), tgt::vec3(1.f))
, _shader(0)
, _glReduction(0)
{
addProperty(&p_inputImage);
addProperty(&p_outputImage);
......@@ -73,11 +74,14 @@ namespace campvis {
_shader = ShdrMgr.loadSeparate("core/glsl/passthrough.vert", "modules/vis/glsl/depthdarkening.frag", generateHeader(), false);
_shader->setAttributeLocation(0, "in_Position");
_shader->setAttributeLocation(1, "in_TexCoord");
_glReduction = new GlReduction(GlReduction::MIN_MAX);
}
void DepthDarkening::deinit() {
VisualizationProcessor::deinit();
ShdrMgr.dispose(_shader);
delete _glReduction;
VisualizationProcessor::deinit();
}
void DepthDarkening::process(DataContainer& data) {
......@@ -90,19 +94,10 @@ namespace campvis {
validate(INVALID_SHADER);
}
// TODO: const cast is ugly...
const tgt::Texture* tex = inputImage->getDepthTexture()->getRepresentation<ImageRepresentationGL>()->getTexture();
const_cast<tgt::Texture*>(tex)->downloadTexture();
const float* pixels = reinterpret_cast<const float*>(tex->getPixelData());
float curDepth = *(pixels);
float minDepth = curDepth;
float maxDepth = curDepth;
size_t numPixels = inputImage->getDepthTexture()->getNumElements();
for (size_t i = 1; i < numPixels; ++i) {
curDepth = pixels[i];
minDepth = std::min(minDepth, curDepth);
maxDepth = std::max(maxDepth, curDepth);
}
std::vector<float> tmp = _glReduction->reduce(tex);
float minDepth = tmp[0];
float maxDepth = tmp[1];
FramebufferActivationGuard fag(this);
glEnable(GL_DEPTH_TEST);
......
......@@ -42,6 +42,7 @@ namespace tgt {
namespace campvis {
class ImageData;
class GlReduction;
/**
* Extracts a slice from a 3D image and renders it into a rendertarget.
......@@ -93,6 +94,7 @@ namespace campvis {
std::string generateHeader() const;
tgt::Shader* _shader; ///< Shader for slice rendering
GlReduction* _glReduction;
static const std::string loggerCat_;
};
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment