diff --git a/modules/dsn/CMakeLists.txt b/modules/dsn/CMakeLists.txt index 7020e7f078..861653ef30 100644 --- a/modules/dsn/CMakeLists.txt +++ b/modules/dsn/CMakeLists.txt @@ -52,6 +52,8 @@ source_group("Source Files" FILES ${SOURCE_FILES}) set(SHADER_FILES ${CMAKE_CURRENT_SOURCE_DIR}/shaders/renderablesignals_fs.glsl ${CMAKE_CURRENT_SOURCE_DIR}/shaders/renderablesignals_vs.glsl + ${CMAKE_CURRENT_SOURCE_DIR}/shaders/renderablestationfov_fs.glsl + ${CMAKE_CURRENT_SOURCE_DIR}/shaders/renderablestationfov_vs.glsl ${CMAKE_CURRENT_SOURCE_DIR}/shaders/renderablecone_fs.glsl ${CMAKE_CURRENT_SOURCE_DIR}/shaders/renderablecone_vs.glsl ) diff --git a/modules/dsn/rendering/renderablecone.cpp b/modules/dsn/rendering/renderablecone.cpp index e12f5e1fa2..099959d7a7 100644 --- a/modules/dsn/rendering/renderablecone.cpp +++ b/modules/dsn/rendering/renderablecone.cpp @@ -217,7 +217,7 @@ RenderableCone::RenderableCone(const ghoul::Dictionary& dictionary) _color = dictionary.value(ColorInfo.identifier); _color.setViewOption(properties::Property::ViewOptions::Color); } - if (dictionary.hasKeyAndValue(ApexPositionInfo.identifier)) { + if (dictionary.hasKeyAndValue(ResolutionInfo.identifier)) { _resolution = dictionary.value(ResolutionInfo.identifier); } if (dictionary.hasKeyAndValue(OpacityInfo.identifier)) { @@ -234,16 +234,8 @@ RenderableCone::RenderableCone(const ghoul::Dictionary& dictionary) addProperty(_color); } void RenderableCone::initializeGL() { - _programObject = BaseModule::ProgramObjectManager.request( - ProgramName, - []() -> std::unique_ptr { - return global::renderEngine.buildRenderProgram( - ProgramName, - absPath("${MODULE_DSN}/shaders/renderablecone_vs.glsl"), - absPath("${MODULE_DSN}/shaders/renderablecone_fs.glsl") - ); - } - ); + + createShaderProgram(); ghoul::opengl::updateUniformLocations(*_programObject, _uniformCache, UniformNames); setRenderBin(Renderable::RenderBin::Overlay); @@ -295,6 +287,9 @@ void RenderableCone::updateVertexAttributes() { sizeof(ColorVBOLayout) + sizeof(PositionVBOLayout), (void*)(sizeof(PositionVBOLayout))); glEnableVertexAttribArray(_vaLocCol); + + // Update the number of lines to render, same for both vertex arrays + _count = static_cast(_vertexLateralSurfaceArray.size() / (_sizeThreeVal + _sizeFourVal)); }; void RenderableCone::render(const RenderData& data, RendererTasks&) { @@ -361,6 +356,20 @@ void RenderableCone::render(const RenderData& data, RendererTasks&) { _programObject->deactivate(); } +void RenderableCone::createShaderProgram() +{ + _programObject = BaseModule::ProgramObjectManager.request( + ProgramName, + []() -> std::unique_ptr { + return global::renderEngine.buildRenderProgram( + ProgramName, + absPath("${MODULE_DSN}/shaders/renderablecone_vs.glsl"), + absPath("${MODULE_DSN}/shaders/renderablecone_fs.glsl") + ); + } + ); +} + void RenderableCone::update(const UpdateData& data) { _vertexLateralSurfaceArray.clear(); _vertexBaseArray.clear(); @@ -386,8 +395,7 @@ void RenderableCone::update(const UpdateData& data) { _baseCenterDirection = glm::normalize(_apexPosition - nodePos); } - std::vector baseVertices; - glm::dvec3 baseCenterPosition; + _baseVertices.clear(); int numBaseVertices = _resolution; double height = _height * _unit; @@ -401,31 +409,27 @@ void RenderableCone::update(const UpdateData& data) { glm::dvec3 e1 = glm::normalize(glm::cross(_baseCenterDirection, e0)); if (_directionIsReversed) { - baseCenterPosition = _apexPosition + _baseCenterDirection * height; + _baseCenterPosition = _apexPosition + _baseCenterDirection * height; } else { - baseCenterPosition = _apexPosition - _baseCenterDirection * height; + _baseCenterPosition = _apexPosition - _baseCenterDirection * height; } for (int i = 0; i < numBaseVertices; ++i) { double rad = angleIncrement * i; - glm::dvec3 p = baseCenterPosition + (((e0 * glm::cos(rad)) + (e1 * glm::sin(rad))) * radius); + glm::dvec3 p = _baseCenterPosition + (((e0 * glm::cos(rad)) + (e1 * glm::sin(rad))) * radius); p = getCoordinatePosFromFocusNode(p); - baseVertices.push_back(p); + _baseVertices.push_back(p); } // work around for precision errors _focusNodePos = global::navigationHandler.focusNode()->worldPosition(); _localTransform = glm::translate(glm::dmat4(1.0), _focusNodePos); _apexPosition = getCoordinatePosFromFocusNode(_apexPosition); - baseCenterPosition = getCoordinatePosFromFocusNode(baseCenterPosition); + _baseCenterPosition = getCoordinatePosFromFocusNode(_baseCenterPosition); - // upload all positions to the vertex array - fillVertexArray(_vertexBaseArray, baseCenterPosition, baseVertices); - fillVertexArray(_vertexLateralSurfaceArray, _apexPosition, baseVertices); - - // Update the number of lines to render, same for both vertex arrays - _count = static_cast(_vertexLateralSurfaceArray.size() / (_sizeThreeVal + _sizeFourVal)); + // upload all positions to the vertex arrays + fillVertexArrays(); unbindGL(); } @@ -447,15 +451,25 @@ void RenderableCone::updateUniforms(const RenderData& data) { _programObject->setUniform(_uniformCache.projection, data.camera.sgctInternal.projectionMatrix()); } -void RenderableCone::fillVertexArray(std::vector &vertexArray, glm::dvec3 centerPoint, std::vector points) { +void RenderableCone::fillVertexArrays() { glm::vec3 color = _color; glm::vec4 colorAndOpacity = { color, _opacity }; - addVertexToVertexArray(vertexArray, centerPoint, colorAndOpacity); - - for (int i = 0; i < points.size(); ++i) { - addVertexToVertexArray(vertexArray,points[i], colorAndOpacity); + + // add base vertices + addVertexToVertexArray(_vertexBaseArray, _baseCenterPosition, colorAndOpacity); + + for (int i = 0; i < _baseVertices.size(); ++i) { + addVertexToVertexArray(_vertexBaseArray, _baseVertices[i], colorAndOpacity); } - addVertexToVertexArray(vertexArray,points[0], colorAndOpacity); + addVertexToVertexArray(_vertexBaseArray, _baseVertices[0], colorAndOpacity); + + //add lateral surface vertices + addVertexToVertexArray(_vertexLateralSurfaceArray, _apexPosition, colorAndOpacity); + + for (int i = 0; i < _baseVertices.size(); ++i) { + addVertexToVertexArray(_vertexLateralSurfaceArray, _baseVertices[i], colorAndOpacity); + } + addVertexToVertexArray(_vertexLateralSurfaceArray, _baseVertices[0], colorAndOpacity); } void RenderableCone::addVertexToVertexArray(std::vector &vertexArray,glm::dvec3 position, glm::vec4 color) diff --git a/modules/dsn/rendering/renderablecone.h b/modules/dsn/rendering/renderablecone.h index cf9658ca09..c536b5193f 100644 --- a/modules/dsn/rendering/renderablecone.h +++ b/modules/dsn/rendering/renderablecone.h @@ -58,17 +58,18 @@ namespace openspace { void initializeGL() override; void deinitializeGL() override; - void update(const UpdateData& data) override; + + virtual void update(const UpdateData& data) override; + virtual void createShaderProgram(); + virtual void fillVertexArrays(); + virtual void updateVertexAttributes(); void render(const RenderData& data, RendererTasks& rendererTask) override; - void fillVertexArray(std::vector &_vertexArray, glm::dvec3 centerPoint, std::vector points); - - void updateVertexAttributes(); + void addVertexToVertexArray(std::vector &_vertexArray, glm::dvec3 position, glm::vec4 color); bool isReady() const override; /// Number of variables in _uniformCache static const GLuint uniformCacheSize = 2; - /// Returns the documentation entries static documentation::Documentation Documentation(); @@ -100,6 +101,7 @@ namespace openspace { /// Specifies the number of components per generic vertex attribute const GLuint _sizeFourVal = 4; const GLuint _sizeThreeVal = 3; + const GLuint _sizeOneVal = 1; /// Local model matrix, used for rendering in camera space glm::dmat4 _localTransform = glm::dmat4(1.0); @@ -107,9 +109,11 @@ namespace openspace { GLint _first = 0; /// The number of values to be rendered GLsizei _count = 0; + /// Program object used to render the data stored in RenderInformation + ghoul::opengl::ProgramObject* _programObject = nullptr; + /// Cache for uniform variables, update _uniformCacheSize accordingly + UniformCache(modelView, projection) _uniformCache; - private: - void addVertexToVertexArray(std::vector &_vertexArray,glm::dvec3 position,glm::vec4 color); glm::dvec3 getCoordinatePosFromFocusNode(glm::dvec3 worldPos); void updateUniforms(const RenderData& data); @@ -124,6 +128,8 @@ namespace openspace { glm::dvec3 _apexPosition; glm::dvec3 _baseCenterDirection; + std::vector _baseVertices; + glm::dvec3 _baseCenterPosition; // lightdays in meters double _unit = 2.59E13; @@ -134,7 +140,7 @@ namespace openspace { properties::Vec3Property _color; properties::BoolProperty _wireframe; - bool _showbase = false; + bool _showbase = true; bool _apexIsNodeAttached = true; bool _baseCenterIsNodeAttached = true; bool _directionIsReversed = false; @@ -143,10 +149,6 @@ namespace openspace { std::string _apexNodeId, _baseDirNodeId = ""; glm::dvec3 _focusNodePos; - /// Program object used to render the data stored in RenderInformation - ghoul::opengl::ProgramObject* _programObject = nullptr; - /// Cache for uniform variables, update _uniformCacheSize accordingly - UniformCache(modelView, projection) _uniformCache; }; } // namespace openspace diff --git a/modules/dsn/rendering/renderablestationfov.cpp b/modules/dsn/rendering/renderablestationfov.cpp index 69b3772412..085f079ca9 100644 --- a/modules/dsn/rendering/renderablestationfov.cpp +++ b/modules/dsn/rendering/renderablestationfov.cpp @@ -25,9 +25,18 @@ #include #include +#include +#include +#include +#include namespace { + constexpr const char* ProgramName = "StationFovProgram"; constexpr const char* _loggerCat = "RenderableStationFov"; + + constexpr const std::array UniformNames = { + "modelView", "projectionTransform" }; + } // namespace namespace openspace { @@ -61,10 +70,82 @@ documentation::Documentation RenderableStationFov::Documentation() { return doc; } -RenderableStationFov::RenderableStationFov(const ghoul::Dictionary& dictionary) +RenderableStationFov::RenderableStationFov(const ghoul::Dictionary& dictionary) : RenderableCone(dictionary) { + _showbase = false; +} + +void RenderableStationFov::createShaderProgram() +{ + _programObject = BaseModule::ProgramObjectManager.request( + ProgramName, + []() -> std::unique_ptr { + return global::renderEngine.buildRenderProgram( + ProgramName, + absPath("${MODULE_DSN}/shaders/renderablestationfov_vs.glsl"), + absPath("${MODULE_DSN}/shaders/renderablestationfov_fs.glsl") + ); + } + ); +} + +void RenderableStationFov::updateVertexAttributes() +{ + // position attributes + glVertexAttribPointer(_vaLocVer, _sizeThreeVal, GL_FLOAT, GL_FALSE, + sizeof(ColorVBOLayout) + sizeof(PositionVBOLayout) + sizeof(float), + (void*)0); + glEnableVertexAttribArray(_vaLocVer); + // color attributes + glVertexAttribPointer(_vaLocCol, _sizeFourVal, GL_FLOAT, GL_FALSE, + sizeof(ColorVBOLayout) + sizeof(PositionVBOLayout) + sizeof(float), + (void*)(sizeof(PositionVBOLayout))); + glEnableVertexAttribArray(_vaLocCol); + + // distance from apex attribute + glVertexAttribPointer(_vaLocDist, _sizeOneVal, GL_FLOAT, GL_FALSE, + sizeof(ColorVBOLayout) + sizeof(PositionVBOLayout) + sizeof(float), + (void*)(sizeof(PositionVBOLayout) + sizeof(ColorVBOLayout))); + glEnableVertexAttribArray(_vaLocDist); + + // Update the number of lines to render, same for both vertex arrays + _count = static_cast(_vertexLateralSurfaceArray.size() / (_sizeThreeVal + _sizeFourVal + _sizeOneVal)); +} + +void RenderableStationFov::fillVertexArrays() +{ + glm::vec3 color = _color; + glm::vec4 colorAndOpacity = { color, _opacity }; + + // add base vertices + addVertexToVertexArray(_vertexBaseArray, _baseCenterPosition, colorAndOpacity, 1.0); + + for (int i = 0; i < _baseVertices.size(); ++i) { + addVertexToVertexArray(_vertexBaseArray, _baseVertices[i], colorAndOpacity, 0.0); + } + addVertexToVertexArray(_vertexBaseArray, _baseVertices[0], colorAndOpacity, 0.0); + + //add lateral surface vertices + addVertexToVertexArray(_vertexLateralSurfaceArray, _apexPosition, colorAndOpacity, 1.0); + + for (int i = 0; i < _baseVertices.size(); ++i) { + addVertexToVertexArray(_vertexLateralSurfaceArray, _baseVertices[i], colorAndOpacity, 0.0); + } + addVertexToVertexArray(_vertexLateralSurfaceArray, _baseVertices[0], colorAndOpacity, 0.0); } +void RenderableStationFov::addVertexToVertexArray(std::vector& vertexArray, glm::dvec3 position, glm::vec4 color, float distance) +{ + vertexArray.push_back(position.x); + vertexArray.push_back(position.y); + vertexArray.push_back(position.z); + vertexArray.push_back(color.r); + vertexArray.push_back(color.g); + vertexArray.push_back(color.b); + vertexArray.push_back(color.a); + vertexArray.push_back(distance); +} + } // namespace openspace diff --git a/modules/dsn/rendering/renderablestationfov.h b/modules/dsn/rendering/renderablestationfov.h index 119c05b9b4..e7e6cf0047 100644 --- a/modules/dsn/rendering/renderablestationfov.h +++ b/modules/dsn/rendering/renderablestationfov.h @@ -31,7 +31,10 @@ namespace openspace { namespace documentation { struct Documentation; } /** - * This is a class for rendering cones + * This is a class for rendering a station field of view. + * It is based off of RenderableCone but includes some extra + * functionality such as defining the base radius with an angle + * and having a distance fade from the apex point. **/ class RenderableStationFov : public RenderableCone{ @@ -39,6 +42,19 @@ namespace openspace { RenderableStationFov(const ghoul::Dictionary& dictionary); ~RenderableStationFov() = default; static documentation::Documentation Documentation(); + + void updateVertexAttributes() override; + void fillVertexArrays() override; + void createShaderProgram() override; + void addVertexToVertexArray(std::vector &vertexArray, glm::dvec3 position, + glm::vec4 color, float distance); + + + private: + /// The vertex attribute location for position + /// must correlate to layout location in vertex shader + const GLuint _vaLocDist = 2; + }; } // namespace openspace diff --git a/modules/dsn/shaders/renderablestationfov_fs.glsl b/modules/dsn/shaders/renderablestationfov_fs.glsl new file mode 100644 index 0000000000..6e394dc607 --- /dev/null +++ b/modules/dsn/shaders/renderablestationfov_fs.glsl @@ -0,0 +1,53 @@ +/***************************************************************************************** + * * + * OpenSpace * + * * + * Copyright (c) 2014-2018 * + * * + * 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. * + ****************************************************************************************/ + +#include "fragment.glsl" +#include "floatoperations.glsl" + +in vec4 vs_positionScreenSpace; +in vec4 vs_gPosition; +in vec4 vs_color; + +Fragment getFragment() { + + Fragment frag; + frag.depth = vs_positionScreenSpace.w; + //frag.blend = BLEND_MODE_ADDITIVE; + + frag.color = vs_color; + + // G-Buffer + // JCC: The depthCorrection here is a temporary tweak + // to fix precision problems. + + vec4 depthCorrection = vec4(0.0,0.0,100,0.0); + frag.gPosition = vs_gPosition + depthCorrection; + + // For rendering inside earth atmosphere we need to set a normal for our line + // Todo: calculate normal correctly + // currently normal is in object space + frag.gNormal= vec4(0.0, 0.0, -1.0, 1.0); + + return frag; +} diff --git a/modules/dsn/shaders/renderablestationfov_vs.glsl b/modules/dsn/shaders/renderablestationfov_vs.glsl new file mode 100644 index 0000000000..8e5750961c --- /dev/null +++ b/modules/dsn/shaders/renderablestationfov_vs.glsl @@ -0,0 +1,50 @@ +/***************************************************************************************** + * * + * OpenSpace * + * * + * Copyright (c) 2014-2018 * + * * + * 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__ + +// layout locations must correspond to va locations in renderablesignals.cpp +layout(location = 0) in vec3 in_point_position; +layout(location = 1) in vec4 in_color; +layout(location = 2) in float in_distance_from_apex; + + +out vec4 vs_positionScreenSpace; +out vec4 vs_gPosition; +out vec4 vs_color; + +uniform dmat4 modelView; +uniform mat4 projectionTransform; + +void main() { + vs_gPosition = vec4(modelView * dvec4(in_point_position, 1)); + vs_positionScreenSpace = projectionTransform * vs_gPosition; + gl_Position = vs_positionScreenSpace; + + // Set z to 0 to disable near and far plane, unique handling for perspective in space + gl_Position.z = 0.f; + + // pass variables with no calculations directly to fragment + vs_color = vec4(in_color.rgb, in_distance_from_apex); +}