Added support for rendering fieldlines as textured view-aligned billboards

This commit is contained in:
Hans-Christian Helltegen
2014-11-24 17:18:55 +01:00
parent 815fc3b348
commit 337ce2dd92
6 changed files with 170 additions and 90 deletions

View File

@@ -33,6 +33,12 @@
#include <ghoul/opengl/programobject.h>
#include <ghoul/filesystem/file.h>
namespace ghoul {
namespace opengl {
class Texture;
}
}
namespace openspace {
struct LinePoint;
@@ -58,6 +64,10 @@ private:
std::vector<GLint> _lineStart;
std::vector<GLsizei> _lineCount;
//TEST
ghoul::opengl::Texture* _texture;
void loadTexture(std::string path);
};
} // namespace openspace

View File

@@ -24,15 +24,23 @@
#version __CONTEXT__
uniform vec3 cameraViewDir;
uniform sampler2D texture1;
in vec4 gs_color;
in vec4 gs_position;
in vec3 gs_normal;
in vec2 gs_texcoord;
#include "ABuffer/abufferStruct.hglsl"
#include "ABuffer/abufferAddToBuffer.hglsl"
#include "PowerScaling/powerScaling_fs.hglsl"
float EARTH_RADIUS = 6371000.0;
void main() {
vec4 fragColor = gs_color;
// vec4 fragColor = vec4(gs_texcoord.x, gs_texcoord.x , gs_texcoord.x, 1)*gs_color;
vec4 fragColor = texture(texture1, gs_texcoord)*gs_color;
float depth = pscDepth(gs_position);
ABufferStruct_t frag = createGeometryFragment(fragColor, gs_position, depth);

View File

@@ -1,90 +1,133 @@
/*****************************************************************************************
* *
* OpenSpace *
* *
* Copyright (c) 2014 *
* *
* Permission is hereby granted, free of charge, to any person obtaining a copy of this *
* software and associated documentation files (the "Software"), to deal in the Software *
* without restriction, including without limitation the rights to use, copy, modify, *
* merge, publish, distribute, sublicense, and/or sell copies of the Software, and to *
* permit persons to whom the Software is furnished to do so, subject to the following *
* conditions: *
* *
* The above copyright notice and this permission notice shall be included in all copies *
* or substantial portions of the Software. *
* *
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, *
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A *
* PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT *
* HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF *
* CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE *
* OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. *
****************************************************************************************/
#version __CONTEXT__
uniform mat4 modelViewProjection;
uniform mat4 modelTransform;
layout(lines) in;
layout(line_strip, max_vertices = 2) out;
uniform vec3 cameraViewDir;
in vec4 vs_color[];
in vec4 vs_position[];
out vec4 gs_color;
out vec4 gs_position;
out vec3 gs_normal;
out vec2 gs_texcoord;
#include "PowerScaling/powerScaling_vs.hglsl"
void main() {
gs_color = vs_color[0];
for(int i = 0; i < 2; i++) {
// gs_position = gl_in[i].gl_Position;
// gl_Position = gl_in[i].gl_Position;
layout(lines_adjacency) in;
layout(triangle_strip, max_vertices = 4) out;
// calculate psc position
vec4 tmp = gl_in[i].gl_Position;
vec4 position = pscTransform(tmp, modelTransform);
gs_position = tmp;
vec4 prismoid[4];
vec2 texcoords[4];
float EARTH_RADIUS = 6371000.0;
// project the position to view space
position = modelViewProjection * position;
gl_Position = z_normalization(position);
EmitVertex();
}
EndPrimitive();
// Calculate the correct powerscaled position and depth for the ABuffer
void ABufferEmitVertex(vec4 pos) {
// calculate psc position
vec4 tmp = pos;
vec4 position = pscTransform(tmp, modelTransform);
gs_position = tmp;
// project the position to view space
position = modelViewProjection*position;
gl_Position = position;
EmitVertex();
}
// uniform mat4 ModelviewProjection;
// layout(lines_adjacency) in;
// layout(location = 0) in vec3 vPosition[4]; // Four inputs since we're using GL_LINE_STRIP_ADJACENCY
// // layout(location = 2) in vec3 vNormal[4]; // Orientation vectors are necessary for consistent alignment
// layout(triangle_strip, max_vertices = 24) out;
void emitFace(int a, int b, int c, int d) {
gs_texcoord = texcoords[a];
ABufferEmitVertex(prismoid[a]);
gs_texcoord = texcoords[b];
ABufferEmitVertex(prismoid[b]);
gs_texcoord = texcoords[c];
ABufferEmitVertex(prismoid[c]);
gs_texcoord = texcoords[d];
ABufferEmitVertex(prismoid[d]);
EndPrimitive();
}
// out vec4 in_color;
// Original code from http://prideout.net/blog/?p=61
void main() {
gs_color = vs_color[0];
vec3 p0, p1, p2, p3;
p0 = gl_in[0].gl_Position.xyz; p1 = gl_in[1].gl_Position.xyz;
p2 = gl_in[2].gl_Position.xyz; p3 = gl_in[3].gl_Position.xyz;
vec3 n0 = normalize(p1-p0);
vec3 n1 = normalize(p2-p1);
vec3 n2 = normalize(p3-p2);
vec3 u = normalize(n0+n1);
vec3 v = normalize(n1+n2);
// vec4 prismoid[8]; // Scratch space for the eight corners of the prismoid
// Declare scratch variables for basis vectors:
float width = 0.15*EARTH_RADIUS;
vec3 normals[2];
normals[0] = normalize(cross(cameraViewDir,u));
normals[1] = normalize(cross(cameraViewDir,v));
// void emit(int a, int b, int c, int d) {
// gl_Position = prismoid[a]; EmitVertex();
// gl_Position = prismoid[b]; EmitVertex();
// gl_Position = prismoid[c]; EmitVertex();
// gl_Position = prismoid[d]; EmitVertex();
// EndPrimitive();
// }
texcoords[0] = vec2(1,1);
texcoords[1] = vec2(1,0);
texcoords[2] = vec2(0,0);
texcoords[3] = vec2(0,1);
// void main() {
// // Compute orientation vectors for the two connecting faces:
// vec3 vNormal = vec3(0, 0, 1);
prismoid[0] = vec4(p1 + normals[0]*width, 0);
prismoid[1] = vec4(p1 - normals[0]*width, 0);
prismoid[2] = vec4(p2 - normals[1]*width, 0);
prismoid[3] = vec4(p2 + normals[1]*width, 0);
// vec3 p0, p1, p2, p3;
// p0 = vPosition[0]; p1 = vPosition[1];
// p2 = vPosition[2]; p3 = vPosition[3];
// vec3 n0 = normalize(p1-p0);
// vec3 n1 = normalize(p2-p1);
// vec3 n2 = normalize(p3-p2);
// vec3 u = normalize(n0+n1);
// vec3 v = normalize(n1+n2);
gs_normal = n1;
gs_texcoord = texcoords[0];
ABufferEmitVertex(prismoid[0]);
// // Declare scratch variables for basis vectors:
// vec3 i,j,k; float r = 0.1;
gs_texcoord = texcoords[1];
ABufferEmitVertex(prismoid[1]);
// // Compute face 1 of 2:
// // j = u; i = vNormal[1]; k = cross(i, j); i *= r; k *= r;
// j = u; i = vNormal; k = cross(i, j); i *= r; k *= r;
// prismoid[0] = ModelviewProjection * vec4(p1 + i + k, 1);
// prismoid[1] = ModelviewProjection * vec4(p1 + i - k, 1);
// prismoid[2] = ModelviewProjection * vec4(p1 - i - k, 1);
// prismoid[3] = ModelviewProjection * vec4(p1 - i + k, 1);
gs_normal = n2;
gs_texcoord = texcoords[3];
ABufferEmitVertex(prismoid[3]);
// // Compute face 2 of 2:
// // j = v; i = vNormal[2]; k = cross(i, j); i *= r; k *= r;
// j = v; i = vNormal; k = cross(i, j); i *= r; k *= r;
// prismoid[4] = ModelviewProjection * vec4(p2 + i + k, 1);
// prismoid[5] = ModelviewProjection * vec4(p2 + i - k, 1);
// prismoid[6] = ModelviewProjection * vec4(p2 - i - k, 1);
// prismoid[7] = ModelviewProjection * vec4(p2 - i + k, 1);
gs_texcoord = texcoords[2];
ABufferEmitVertex(prismoid[2]);
EndPrimitive();
// // Emit the six faces of the prismoid:
// emit(0,1,3,2); emit(5,4,6,7);
// emit(4,5,0,1); emit(3,2,7,6);
// emit(0,3,4,7); emit(2,1,6,5);
// }
// vec3 i,j,k; float r = 0.05*EARTH_RADIUS;
// j = u; i = normal; k = cross(i, j); i *= r; k *= r;
// // Compute face 1 of 2:
// prismoid[0] = vec4(p1 + i + k, 0);
// prismoid[1] = vec4(p1 + i - k, 0);
// prismoid[2] = vec4(p1 - i - k, 0);
// prismoid[3] = vec4(p1 - i + k, 0);
// // Compute face 2 of 2:
// prismoid[4] = vec4(p2 + i + k, 0);
// prismoid[5] = vec4(p2 + i - k, 0);
// prismoid[6] = vec4(p2 - i - k, 0);
// prismoid[7] = vec4(p2 - i + k, 0);
// // Emit the six faces of the prismoid:
// emitFace(0,1,3,2); emitFace(5,4,6,7);
// emitFace(4,5,0,1); emitFace(3,2,7,6);
// emitFace(0,3,4,7); emitFace(2,1,6,5);
}

View File

@@ -31,21 +31,10 @@ layout(location = 0) in vec3 in_position;
layout(location = 1) in vec4 in_color;
out vec4 vs_color;
// out vec4 vs_position;
#include "PowerScaling/powerScaling_vs.hglsl"
void main() {
vs_color = in_color;
// // calculate psc position
// vec4 tmp = vec4(in_position, 0);
// vec4 position = pscTransform(tmp, modelTransform);
// // vs_position = tmp;
// // project the position to view space
// position = modelViewProjection * position;
// gl_Position = z_normalization(position);
gl_Position = vec4(in_position, 0);
}

View File

@@ -29,6 +29,10 @@
#include <openspace/util/constants.h>
#include <ghoul/opengl/texturereader.h>
#include <ghoul/opengl/textureunit.h>
#include <ghoul/opengl/texture.h>
namespace {
const std::string _loggerCat = "RenderableFieldlines";
@@ -43,6 +47,7 @@ RenderableFieldlines::RenderableFieldlines(const ghoul::Dictionary& dictionary)
: Renderable(dictionary)
, _fieldlineVAO(0)
, _shader(nullptr)
, _texture(nullptr)
{
std::string name;
bool success = dictionary.getValue(constants::scenegraphnode::keyName, name);
@@ -149,17 +154,13 @@ bool RenderableFieldlines::initialize() {
glVertexAttribPointer(colorLocation, 4, GL_FLOAT, GL_FALSE, sizeof(LinePoint), (void*)(sizeof(glm::vec3)));
glBindBuffer(GL_ARRAY_BUFFER, 0); //unbind buffer
glBindVertexArray(0); //unbind array
glPointSize(5); // size of seedpoints
//glEnable(GL_LINE_SMOOTH);
//glEnable(GL_POLYGON_SMOOTH);
//glHint(GL_LINE_SMOOTH_HINT, GL_NICEST);
//glHint(GL_POLYGON_SMOOTH_HINT, GL_NICEST);
glBindVertexArray(0); //unbind array
OsEng.ref().configurationManager().getValue("FieldlineProgram", _shader);
assert(_shader);
loadTexture("C:/openspace/openspace-data/test.png");
return true;
}
@@ -170,20 +171,29 @@ bool RenderableFieldlines::deinitialize() {
void RenderableFieldlines::render(const RenderData& data) {
if (!_shader)
return;
_shader->activate();
_shader->setUniform("modelViewProjection", data.camera.viewProjectionMatrix());
_shader->setUniform("modelTransform", glm::mat4(1.0));
_shader->setUniform("cameraViewDir", data.camera.viewDirection());
setPscUniforms(_shader, &data.camera, data.position);
ghoul::opengl::TextureUnit unit;
unit.activate();
_texture->bind();
_shader->setUniform("texture1", unit);
// ------ DRAW FIELDLINES -----------------
glEnable(GL_POLYGON_SMOOTH);
glHint(GL_POLYGON_SMOOTH_HINT, GL_NICEST);
glBindVertexArray(_fieldlineVAO);
glMultiDrawArrays(GL_LINE_STRIP, &_lineStart[0], &_lineCount[0], _lineStart.size());
glMultiDrawArrays(GL_LINE_STRIP_ADJACENCY, &_lineStart[0], &_lineCount[0], _lineStart.size());
// // ------ DRAW SEEDPOINTS -----------------
// glBindVertexArray(_seedpointVAO);
// glMultiDrawArrays(GL_POINTS, &_lineStart[0], &_lineCount[0], _seedPoints.size());
//// ------ DRAW SEEDPOINTS -----------------
//glBindVertexArray(_seedpointVAO);
//glMultiDrawArrays(GL_LINE_STRIP_ADJACENCY, &_lineStart[0], &_lineCount[0], _seedPoints.size());
glDisable(GL_POLYGON_SMOOTH);
glBindVertexArray(0);
_shader->deactivate();
}
@@ -268,4 +278,22 @@ std::vector<std::vector<LinePoint> > RenderableFieldlines::getFieldlinesData(std
return fieldlinesData;
}
// TEST
void RenderableFieldlines::loadTexture(std::string path) {
if (path != "") {
ghoul::opengl::Texture* texture = ghoul::opengl::loadTexture(path);
if (texture) {
LDEBUG("Loaded texture from '" << path << "'");
texture->uploadTexture();
// Textures of planets looks much smoother with AnisotropicMipMap rather than linear
texture->setFilter(ghoul::opengl::Texture::FilterMode::AnisotropicMipMap);
if (_texture)
delete _texture;
_texture = texture;
}
}
}
} // namespace openspace

View File

@@ -402,6 +402,7 @@ KameleonWrapper::Fieldlines KameleonWrapper::getClassifiedFieldLines(
fLine = traceCartesianFieldline(xVar, yVar, zVar, seedPoint, stepSize, TraceDirection::FORWARD, forwardEnd);
bLine = traceCartesianFieldline(xVar, yVar, zVar, seedPoint, stepSize, TraceDirection::BACK, backEnd);
bLine.erase(bLine.begin());
bLine.insert(bLine.begin(), fLine.rbegin(), fLine.rend());
// classify
@@ -442,7 +443,8 @@ KameleonWrapper::Fieldlines KameleonWrapper::getFieldLines(
fLine = traceCartesianFieldline(xVar, yVar, zVar, seedPoint, stepSize, TraceDirection::FORWARD, forwardEnd);
bLine = traceCartesianFieldline(xVar, yVar, zVar, seedPoint, stepSize, TraceDirection::BACK, backEnd);
bLine.insert(bLine.begin(), fLine.rbegin(), fLine.rend());
bLine.erase(bLine.begin());
bLine.insert(bLine.begin(), fLine.rbegin(), fLine.rend());
// write colors
std::vector<LinePoint> line;