From ae8a9e68c8229c48645dd96f5a9424b217526dd1 Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Wed, 25 Oct 2017 11:58:16 +0200 Subject: [PATCH 01/34] Added debug tool to view shadow & view frustums --- .gitignore | 3 + libraries/gpu/src/gpu/DrawColor.slf | 19 ++++ libraries/gpu/src/gpu/StandardShaderLib.cpp | 9 ++ libraries/gpu/src/gpu/StandardShaderLib.h | 2 + .../render-utils/src/RenderDeferredTask.cpp | 86 +++++++++++++++++++ .../render-utils/src/RenderDeferredTask.h | 34 ++++++++ .../developer/utilities/render/debugShadow.js | 20 +++++ scripts/developer/utilities/render/shadow.qml | 46 ++++++++++ 8 files changed, 219 insertions(+) create mode 100644 libraries/gpu/src/gpu/DrawColor.slf create mode 100644 scripts/developer/utilities/render/debugShadow.js create mode 100644 scripts/developer/utilities/render/shadow.qml diff --git a/.gitignore b/.gitignore index 072e6001da..f085b676e4 100644 --- a/.gitignore +++ b/.gitignore @@ -65,6 +65,9 @@ gvr-interface/libs/* TAGS *.sw[po] +# ignore QML compilation output +*.qmlc + # ignore node files for the console node_modules npm-debug.log diff --git a/libraries/gpu/src/gpu/DrawColor.slf b/libraries/gpu/src/gpu/DrawColor.slf new file mode 100644 index 0000000000..c24d69d29f --- /dev/null +++ b/libraries/gpu/src/gpu/DrawColor.slf @@ -0,0 +1,19 @@ +<@include gpu/Config.slh@> +<$VERSION_HEADER$> +// Generated on <$_SCRIBE_DATE$> +// +// Draw with color uniform +// +// Created by Olivier Prat on 25/10/2017 +// Copyright 2017 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// +uniform vec4 color; + +out vec4 outFragColor; + +void main(void) { + outFragColor = color; +} diff --git a/libraries/gpu/src/gpu/StandardShaderLib.cpp b/libraries/gpu/src/gpu/StandardShaderLib.cpp index 7143242618..0d8d131e0b 100755 --- a/libraries/gpu/src/gpu/StandardShaderLib.cpp +++ b/libraries/gpu/src/gpu/StandardShaderLib.cpp @@ -22,6 +22,7 @@ const char DrawNada_frag[] = "void main(void) {}"; // DrawNada is really simple... #include "DrawWhite_frag.h" +#include "DrawColor_frag.h" #include "DrawTexture_frag.h" #include "DrawTextureMirroredX_frag.h" #include "DrawTextureOpaque_frag.h" @@ -37,6 +38,7 @@ ShaderPointer StandardShaderLib::_drawVertexPositionVS; ShaderPointer StandardShaderLib::_drawTransformVertexPositionVS; ShaderPointer StandardShaderLib::_drawNadaPS; ShaderPointer StandardShaderLib::_drawWhitePS; +ShaderPointer StandardShaderLib::_drawColorPS; ShaderPointer StandardShaderLib::_drawTexturePS; ShaderPointer StandardShaderLib::_drawTextureMirroredXPS; ShaderPointer StandardShaderLib::_drawTextureOpaquePS; @@ -125,6 +127,13 @@ ShaderPointer StandardShaderLib::getDrawWhitePS() { return _drawWhitePS; } +ShaderPointer StandardShaderLib::getDrawColorPS() { + if (!_drawColorPS) { + _drawColorPS = gpu::Shader::createPixel(std::string(DrawColor_frag)); + } + return _drawColorPS; +} + ShaderPointer StandardShaderLib::getDrawTexturePS() { if (!_drawTexturePS) { _drawTexturePS = gpu::Shader::createPixel(std::string(DrawTexture_frag)); diff --git a/libraries/gpu/src/gpu/StandardShaderLib.h b/libraries/gpu/src/gpu/StandardShaderLib.h index 94885b8ca0..9c11f6cc3a 100755 --- a/libraries/gpu/src/gpu/StandardShaderLib.h +++ b/libraries/gpu/src/gpu/StandardShaderLib.h @@ -46,6 +46,7 @@ public: static ShaderPointer getDrawNadaPS(); static ShaderPointer getDrawWhitePS(); + static ShaderPointer getDrawColorPS(); static ShaderPointer getDrawTexturePS(); static ShaderPointer getDrawTextureMirroredXPS(); static ShaderPointer getDrawTextureOpaquePS(); @@ -67,6 +68,7 @@ protected: static ShaderPointer _drawNadaPS; static ShaderPointer _drawWhitePS; + static ShaderPointer _drawColorPS; static ShaderPointer _drawTexturePS; static ShaderPointer _drawTextureMirroredXPS; static ShaderPointer _drawTextureOpaquePS; diff --git a/libraries/render-utils/src/RenderDeferredTask.cpp b/libraries/render-utils/src/RenderDeferredTask.cpp index 6a3b560167..75af8506a2 100644 --- a/libraries/render-utils/src/RenderDeferredTask.cpp +++ b/libraries/render-utils/src/RenderDeferredTask.cpp @@ -190,6 +190,7 @@ void RenderDeferredTask::build(JobModel& task, const render::Varying& input, ren task.addJob("DrawLightBounds", lights); task.addJob("DrawZones", zones); + task.addJob("DrawFrustums"); } // Layered Overlays @@ -516,3 +517,88 @@ void Blit::run(const RenderContextPointer& renderContext, const gpu::Framebuffer }); } +void DrawFrustums::configure(const Config& configuration) { + _updateFrustums = !configuration.isFrozen; +} + +void DrawFrustums::run(const render::RenderContextPointer& renderContext) { + assert(renderContext->args); + assert(renderContext->args->_context); + + RenderArgs* args = renderContext->args; + static uint8_t indexData[] = { 0, 1, 2, 3, 0, 4, 5, 6, 7, 4, 5, 1, 2, 6, 7, 3 }; + + if (!_frustumMeshIndices._buffer) { + auto indices = std::make_shared(sizeof(indexData), indexData); + _frustumMeshIndices = gpu::BufferView(indices, gpu::Element(gpu::SCALAR, gpu::UINT8, gpu::INDEX)); + _viewFrustumMeshVertices = gpu::BufferView(std::make_shared(sizeof(glm::vec3) * 8, nullptr), gpu::Element::VEC3F_XYZ); + _viewFrustumMeshStream.addBuffer(_viewFrustumMeshVertices._buffer, _viewFrustumMeshVertices._offset, _viewFrustumMeshVertices._stride); + _shadowFrustumMeshVertices = gpu::BufferView(std::make_shared(sizeof(glm::vec3) * 8, nullptr), gpu::Element::VEC3F_XYZ); + _shadowFrustumMeshStream.addBuffer(_shadowFrustumMeshVertices._buffer, _shadowFrustumMeshVertices._offset, _shadowFrustumMeshVertices._stride); + } + + if (_updateFrustums) { + updateFrustum(args->getViewFrustum(), _viewFrustumMeshVertices); + + auto lightStage = renderContext->_scene->getStage(); + assert(lightStage); + + const auto globalShadow = lightStage->getCurrentKeyShadow(); + if (globalShadow) { + updateFrustum(*globalShadow->getFrustum(), _shadowFrustumMeshVertices); + } + } + + if (!_pipeline) { + auto vs = gpu::StandardShaderLib::getDrawTransformVertexPositionVS(); + auto ps = gpu::StandardShaderLib::getDrawColorPS(); + gpu::ShaderPointer program = gpu::Shader::createProgram(vs, ps); + + gpu::Shader::BindingSet slotBindings; + slotBindings.insert(gpu::Shader::Binding("color", 0)); + gpu::Shader::makeProgram(*program, slotBindings); + + gpu::StatePointer state = gpu::StatePointer(new gpu::State()); + state->setDepthTest(gpu::State::DepthTest(true, false)); + _pipeline = gpu::Pipeline::create(program, state); + } + + // Render the frustums in wireframe + gpu::doInBatch(args->_context, [&](gpu::Batch& batch) { + args->_batch = &batch; + batch.setViewportTransform(args->_viewport); + batch.setStateScissorRect(args->_viewport); + + glm::mat4 projMat; + Transform viewMat; + args->getViewFrustum().evalProjectionMatrix(projMat); + args->getViewFrustum().evalViewTransform(viewMat); + + batch.setProjectionTransform(projMat); + batch.setViewTransform(viewMat); + batch.setPipeline(_pipeline); + batch.setIndexBuffer(_frustumMeshIndices); + + batch._glUniform4f(0, 1.0f, 1.0f, 0.0f, 1.0f); + batch.setInputStream(0, _viewFrustumMeshStream); + batch.drawIndexed(gpu::LINE_STRIP, sizeof(indexData) / sizeof(indexData[0]), 0U); + + batch._glUniform4f(0, 1.0f, 0.0f, 0.0f, 1.0f); + batch.setInputStream(0, _shadowFrustumMeshStream); + batch.drawIndexed(gpu::LINE_STRIP, sizeof(indexData) / sizeof(indexData[0]), 0U); + + args->_batch = nullptr; + }); +} + +void DrawFrustums::updateFrustum(const ViewFrustum& frustum, gpu::BufferView& vertexBuffer) { + auto& vertices = vertexBuffer.edit >(); + vertices[0] = frustum.getNearTopLeft(); + vertices[1] = frustum.getNearTopRight(); + vertices[2] = frustum.getNearBottomRight(); + vertices[3] = frustum.getNearBottomLeft(); + vertices[4] = frustum.getFarTopLeft(); + vertices[5] = frustum.getFarTopRight(); + vertices[6] = frustum.getFarBottomRight(); + vertices[7] = frustum.getFarBottomLeft(); +} diff --git a/libraries/render-utils/src/RenderDeferredTask.h b/libraries/render-utils/src/RenderDeferredTask.h index 452420589b..e8dd22359d 100644 --- a/libraries/render-utils/src/RenderDeferredTask.h +++ b/libraries/render-utils/src/RenderDeferredTask.h @@ -170,6 +170,40 @@ public: void run(const render::RenderContextPointer& renderContext, const gpu::FramebufferPointer& srcFramebuffer); }; +class DrawFrustumsConfig : public render::Job::Config { + Q_OBJECT + Q_PROPERTY(bool isFrozen MEMBER isFrozen NOTIFY dirty) +public: + + DrawFrustumsConfig(bool enabled = false) : JobConfig(enabled) {} + + bool isFrozen{ false }; +signals: + void dirty(); + +}; + +class DrawFrustums { +public: + using Config = DrawFrustumsConfig; + using JobModel = render::Job::Model; + + void configure(const Config& configuration); + void run(const render::RenderContextPointer& renderContext); + +private: + + bool _updateFrustums{ true }; + gpu::PipelinePointer _pipeline; + gpu::BufferView _frustumMeshIndices; + gpu::BufferView _viewFrustumMeshVertices; + gpu::BufferView _shadowFrustumMeshVertices; + gpu::BufferStream _viewFrustumMeshStream; + gpu::BufferStream _shadowFrustumMeshStream; + + static void updateFrustum(const ViewFrustum& frustum, gpu::BufferView& vertexBuffer); +}; + class RenderDeferredTaskConfig : public render::Task::Config { Q_OBJECT Q_PROPERTY(float fadeScale MEMBER fadeScale NOTIFY dirty) diff --git a/scripts/developer/utilities/render/debugShadow.js b/scripts/developer/utilities/render/debugShadow.js new file mode 100644 index 0000000000..a0d2142258 --- /dev/null +++ b/scripts/developer/utilities/render/debugShadow.js @@ -0,0 +1,20 @@ +// +// debugShadow.js +// developer/utilities/render +// +// Olivier Prat, created on 10/25/2017. +// Copyright 2017 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html +// + +// Set up the qml ui +var qml = Script.resolvePath('shadow.qml'); +var window = new OverlayWindow({ + title: 'Shadow Debug', + source: qml, + width: 200, + height: 90 +}); +window.closed.connect(function() { Script.stop(); }); \ No newline at end of file diff --git a/scripts/developer/utilities/render/shadow.qml b/scripts/developer/utilities/render/shadow.qml new file mode 100644 index 0000000000..1b4e647c77 --- /dev/null +++ b/scripts/developer/utilities/render/shadow.qml @@ -0,0 +1,46 @@ +// +// shadow.qml +// developer/utilities/render +// +// Olivier Prat, created on 10/25/2017. +// Copyright 2017 High Fidelity, Inc. +// +// Distributed under the Apache License, Version 2.0. +// See the accompanying file LICENSE or https://www.apache.org/licenses/LICENSE-2.0.html +// +import QtQuick 2.5 +import QtQuick.Controls 1.4 + +Column { + id: root + spacing: 8 + property var config: Render.getConfig("RenderMainView.DrawFrustums"); + + Component.onCompleted: { + config.enabled = true; + } + Component.onDestruction: { + config.enabled = false; + } + + CheckBox { + text: "Freeze Frustums" + checked: false + onCheckedChanged: { + config.isFrozen = checked; + } + } + Row { + spacing: 8 + Label { + text: "View" + color: "yellow" + font.italic: true + } + Label { + text: "Shadow" + color: "red" + font.italic: true + } + } +} From 6cf689a3853679c5661eb9e48f1a1b23948029cc Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Thu, 26 Oct 2017 12:42:36 +0200 Subject: [PATCH 02/34] First draft version of tighter shadow frustum --- libraries/render-utils/src/LightStage.cpp | 21 ++- libraries/render-utils/src/LightStage.h | 3 +- .../render-utils/src/RenderShadowTask.cpp | 129 +++++++++++++++-- libraries/render-utils/src/RenderShadowTask.h | 6 +- libraries/render/src/render/SortTask.cpp | 36 ++++- libraries/render/src/render/SortTask.h | 13 +- libraries/shared/src/AABox.h | 3 +- libraries/shared/src/GeometryUtil.cpp | 130 ++++++++++++++++++ libraries/shared/src/GeometryUtil.h | 4 + libraries/shared/src/Plane.h | 4 +- libraries/shared/src/Transform.h | 8 ++ 11 files changed, 335 insertions(+), 22 deletions(-) diff --git a/libraries/render-utils/src/LightStage.cpp b/libraries/render-utils/src/LightStage.cpp index 079c63f367..945bb3b9e6 100644 --- a/libraries/render-utils/src/LightStage.cpp +++ b/libraries/render-utils/src/LightStage.cpp @@ -25,7 +25,10 @@ LightStage::Shadow::Shadow(model::LightPointer light) : _light{ light}, _frustum _schemaBuffer = std::make_shared(sizeof(Schema), (const gpu::Byte*) &schema); } -void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, float nearDepth, float farDepth) { +void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, + float viewMinShadowDistance, float viewMaxShadowDistance, + float nearDepth, float farDepth) { + assert(viewMinShadowDistance < viewMaxShadowDistance); assert(nearDepth < farDepth); // Orient the keylight frustum @@ -48,8 +51,8 @@ void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, floa const Transform view{ _frustum->getView()}; const Transform viewInverse{ view.getInverseMatrix() }; - auto nearCorners = viewFrustum.getCorners(nearDepth); - auto farCorners = viewFrustum.getCorners(farDepth); + auto nearCorners = viewFrustum.getCorners(viewMinShadowDistance); + auto farCorners = viewFrustum.getCorners(viewMaxShadowDistance); vec3 min{ viewInverse.transform(nearCorners.bottomLeft) }; vec3 max{ min }; @@ -73,6 +76,8 @@ void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, floa fitFrustum(farCorners.topLeft); fitFrustum(farCorners.topRight); + // Re-adjust near shadow distance to + max.z = glm::max(max.z, -nearDepth); glm::mat4 ortho = glm::ortho(min.x, max.x, min.y, max.y, -max.z, -min.z); _frustum->setProjection(ortho); @@ -84,6 +89,16 @@ void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, floa _schemaBuffer.edit().viewInverse = viewInverse.getMatrix(); } +void LightStage::Shadow::setFrustum(const ViewFrustum& shadowFrustum) { + const Transform view{ shadowFrustum.getView() }; + const Transform viewInverse{ view.getInverseMatrix() }; + + *_frustum = shadowFrustum; + // Update the buffer + _schemaBuffer.edit().projection = shadowFrustum.getProjection(); + _schemaBuffer.edit().viewInverse = viewInverse.getMatrix(); +} + const glm::mat4& LightStage::Shadow::getView() const { return _frustum->getView(); } diff --git a/libraries/render-utils/src/LightStage.h b/libraries/render-utils/src/LightStage.h index 66d73c9a6e..a6e369c2f4 100644 --- a/libraries/render-utils/src/LightStage.h +++ b/libraries/render-utils/src/LightStage.h @@ -48,8 +48,9 @@ public: Shadow(model::LightPointer light); - void setKeylightFrustum(const ViewFrustum& viewFrustum, float nearDepth, float farDepth); + void setKeylightFrustum(const ViewFrustum& viewFrustum, float viewMinShadowDistance, float viewMaxShadowDistance, float nearDepth = 1.0f, float farDepth = 1000.0f); + void setFrustum(const ViewFrustum& shadowFrustum); const std::shared_ptr getFrustum() const { return _frustum; } const glm::mat4& getView() const; diff --git a/libraries/render-utils/src/RenderShadowTask.cpp b/libraries/render-utils/src/RenderShadowTask.cpp index 7171543abc..80b988d055 100644 --- a/libraries/render-utils/src/RenderShadowTask.cpp +++ b/libraries/render-utils/src/RenderShadowTask.cpp @@ -22,25 +22,131 @@ #include "DeferredLightingEffect.h" #include "FramebufferCache.h" +#define SHADOW_FRUSTUM_NEAR 1.0f +#define SHADOW_FRUSTUM_FAR 100.0f + using namespace render; extern void initZPassPipelines(ShapePlumber& plumber, gpu::StatePointer state); -void RenderShadowMap::run(const render::RenderContextPointer& renderContext, - const render::ShapeBounds& inShapes) { +static void computeNearFar(const Triangle& triangle, const Plane shadowClipPlanes[4], float& near, float& far) { + static const int MAX_TRIANGLE_COUNT = 16; + Triangle clippedTriangles[MAX_TRIANGLE_COUNT]; + auto clippedTriangleCount = clipTriangleWithPlanes(triangle, shadowClipPlanes, 4, clippedTriangles, MAX_TRIANGLE_COUNT); + + for (auto i = 0; i < clippedTriangleCount; i++) { + const auto& clippedTriangle = clippedTriangles[i]; + + near = glm::min(near, -clippedTriangle.v0.z); + near = glm::min(near, -clippedTriangle.v1.z); + near = glm::min(near, -clippedTriangle.v2.z); + + far = glm::max(far, -clippedTriangle.v0.z); + far = glm::max(far, -clippedTriangle.v1.z); + far = glm::max(far, -clippedTriangle.v2.z); + } +} + +static void computeNearFar(const glm::vec3 sceneBoundVertices[8], const Plane shadowClipPlanes[4], float& near, float& far) { + // This code is inspired from Microsoft's CascadedShadowMaps11 sample which is under MIT licence. + // See https://code.msdn.microsoft.com/windowsdesktop/Direct3D-Shadow-Win32-2d72a4f2/sourcecode?fileId=121915&pathId=1645833187 + // Basically it decomposes the object bounding box in triangles and clips each triangle with the shadow + // frustum planes. Finally it computes the minimum and maximum depth of the clipped triangle vertices + // in shadow space to extract the near and far distances of the shadow frustum. + static const std::array boxQuadVertexIndices = { { + { TOP_LEFT_FAR, BOTTOM_LEFT_FAR, BOTTOM_RIGHT_FAR, TOP_RIGHT_FAR }, + { TOP_LEFT_NEAR, BOTTOM_LEFT_NEAR, BOTTOM_RIGHT_NEAR, TOP_RIGHT_NEAR }, + { TOP_RIGHT_FAR, BOTTOM_RIGHT_FAR, BOTTOM_RIGHT_NEAR, TOP_RIGHT_NEAR }, + { TOP_LEFT_FAR, BOTTOM_LEFT_FAR, BOTTOM_LEFT_NEAR, TOP_LEFT_NEAR }, + { BOTTOM_LEFT_FAR, BOTTOM_RIGHT_FAR, BOTTOM_RIGHT_NEAR, BOTTOM_LEFT_NEAR }, + { TOP_LEFT_FAR, TOP_RIGHT_FAR, TOP_RIGHT_NEAR, TOP_LEFT_NEAR } + } }; + Triangle triangle; + + for (auto quadVertexIndices : boxQuadVertexIndices) { + triangle.v0 = sceneBoundVertices[quadVertexIndices[0]]; + triangle.v1 = sceneBoundVertices[quadVertexIndices[1]]; + triangle.v2 = sceneBoundVertices[quadVertexIndices[2]]; + computeNearFar(triangle, shadowClipPlanes, near, far); + triangle.v1 = sceneBoundVertices[quadVertexIndices[3]]; + computeNearFar(triangle, shadowClipPlanes, near, far); + } +} + +static void adjustNearFar(const AABox& inShapeBounds, ViewFrustum& shadowFrustum) { + const Transform shadowView{ shadowFrustum.getView() }; + const Transform shadowViewInverse{ shadowView.getInverseMatrix() }; + + glm::vec3 sceneBoundVertices[8]; + // Keep only the left, right, top and bottom shadow frustum planes as we wish to determine + // the near and far + Plane shadowClipPlanes[4]; + int i; + + // The vertices of the scene bounding box are expressed in the shadow frustum's local space + for (i = 0; i < 8; i++) { + sceneBoundVertices[i] = shadowViewInverse.transform(inShapeBounds.getVertex(static_cast(i))); + } + // This indirection array is just a protection in case the ViewFrustum::PlaneIndex enum + // changes order especially as we don't need to test the NEAR and FAR planes. + static const ViewFrustum::PlaneIndex planeIndices[4] = { + ViewFrustum::TOP_PLANE, + ViewFrustum::BOTTOM_PLANE, + ViewFrustum::LEFT_PLANE, + ViewFrustum::RIGHT_PLANE + }; + // Same goes for the shadow frustum planes. + for (i = 0; i < 4; i++) { + const auto& worldPlane = shadowFrustum.getPlanes()[planeIndices[i]]; + // We assume the transform doesn't have a non uniform scale component to apply the + // transform to the normal without using the correct transpose of inverse, which should be the + // case for a view matrix. + auto planeNormal = shadowViewInverse.transformDirection(worldPlane.getNormal()); + auto planePoint = shadowViewInverse.transform(worldPlane.getPoint()); + shadowClipPlanes[i].setNormalAndPoint(planeNormal, planePoint); + } + + float near = std::numeric_limits::max(); + float far = 0.0f; + + computeNearFar(sceneBoundVertices, shadowClipPlanes, near, far); + + const auto depthEpsilon = 0.25f; + auto projMatrix = glm::ortho(-1.0f, 1.0f, -1.0f, 1.0f, near - depthEpsilon, far + depthEpsilon); + auto shadowProjection = shadowFrustum.getProjection(); + + shadowProjection[2][2] = projMatrix[2][2]; + shadowProjection[3][2] = projMatrix[3][2]; + shadowFrustum.setProjection(shadowProjection); + shadowFrustum.calculate(); +} + +void RenderShadowMap::run(const render::RenderContextPointer& renderContext, const Inputs& inputs) { assert(renderContext->args); assert(renderContext->args->hasViewFrustum()); + const auto& inShapes = inputs.get0(); + const auto& inShapeBounds = inputs.get1(); + auto lightStage = renderContext->_scene->getStage(); assert(lightStage); - const auto shadow = lightStage->getCurrentKeyShadow(); + auto shadow = lightStage->getCurrentKeyShadow(); if (!shadow) return; const auto& fbo = shadow->framebuffer; RenderArgs* args = renderContext->args; ShapeKey::Builder defaultKeyBuilder; + auto adjustedShadowFrustum = args->getViewFrustum(); + + // Adjust the frustum near and far depths based on the rendered items bounding box to have + // the minimal Z range. + adjustNearFar(inShapeBounds, adjustedShadowFrustum); + // Reapply the frustum as it has been adjusted + shadow->setFrustum(adjustedShadowFrustum); + args->popViewFrustum(); + args->pushViewFrustum(adjustedShadowFrustum); gpu::doInBatch(args->_context, [&](gpu::Batch& batch) { args->_batch = &batch; @@ -55,8 +161,13 @@ void RenderShadowMap::run(const render::RenderContextPointer& renderContext, gpu::Framebuffer::BUFFER_COLOR0 | gpu::Framebuffer::BUFFER_DEPTH, vec4(vec3(1.0, 1.0, 1.0), 0.0), 1.0, 0, true); - batch.setProjectionTransform(shadow->getProjection()); - batch.setViewTransform(shadow->getView(), false); + glm::mat4 projMat; + Transform viewMat; + args->getViewFrustum().evalProjectionMatrix(projMat); + args->getViewFrustum().evalViewTransform(viewMat); + + batch.setProjectionTransform(projMat); + batch.setViewTransform(viewMat, false); auto shadowPipeline = _shapePlumber->pickPipeline(args, defaultKeyBuilder); auto shadowSkinnedPipeline = _shapePlumber->pickPipeline(args, defaultKeyBuilder.withSkinned()); @@ -109,10 +220,10 @@ void RenderShadowTask::build(JobModel& task, const render::Varying& input, rende // Sort const auto sortedPipelines = task.addJob("PipelineSortShadowSort", culledShadowSelection); - const auto sortedShapes = task.addJob("DepthSortShadowMap", sortedPipelines); + const auto sortedShapesAndBounds = task.addJob("DepthSortShadowMap", sortedPipelines, true); // GPU jobs: Render to shadow map - task.addJob("RenderShadowMap", sortedShapes, shapePlumber); + task.addJob("RenderShadowMap", sortedShapesAndBounds, shapePlumber); task.addJob("ShadowTeardown", cachedMode); } @@ -135,8 +246,8 @@ void RenderShadowSetup::run(const render::RenderContextPointer& renderContext, O auto nearClip = args->getViewFrustum().getNearClip(); float nearDepth = -args->_boomOffset.z; - const int SHADOW_FAR_DEPTH = 20; - globalShadow->setKeylightFrustum(args->getViewFrustum(), nearDepth, nearClip + SHADOW_FAR_DEPTH); + const float SHADOW_MAX_DISTANCE = 20.0f; + globalShadow->setKeylightFrustum(args->getViewFrustum(), nearDepth, nearClip + SHADOW_MAX_DISTANCE, SHADOW_FRUSTUM_NEAR, SHADOW_FRUSTUM_FAR); // Set the keylight render args args->pushViewFrustum(*(globalShadow->getFrustum())); diff --git a/libraries/render-utils/src/RenderShadowTask.h b/libraries/render-utils/src/RenderShadowTask.h index 031f44a42d..7b2bbeb306 100644 --- a/libraries/render-utils/src/RenderShadowTask.h +++ b/libraries/render-utils/src/RenderShadowTask.h @@ -21,11 +21,11 @@ class ViewFrustum; class RenderShadowMap { public: - using JobModel = render::Job::ModelI; + using Inputs = render::VaryingSet2; + using JobModel = render::Job::ModelI; RenderShadowMap(render::ShapePlumberPointer shapePlumber) : _shapePlumber{ shapePlumber } {} - void run(const render::RenderContextPointer& renderContext, - const render::ShapeBounds& inShapes); + void run(const render::RenderContextPointer& renderContext, const Inputs& inputs); protected: render::ShapePlumberPointer _shapePlumber; diff --git a/libraries/render/src/render/SortTask.cpp b/libraries/render/src/render/SortTask.cpp index 5b7ead4b6a..f789f8c5c6 100644 --- a/libraries/render/src/render/SortTask.cpp +++ b/libraries/render/src/render/SortTask.cpp @@ -40,7 +40,8 @@ struct BackToFrontSort { } }; -void render::depthSortItems(const RenderContextPointer& renderContext, bool frontToBack, const ItemBounds& inItems, ItemBounds& outItems) { +void render::depthSortItems(const RenderContextPointer& renderContext, bool frontToBack, + const ItemBounds& inItems, ItemBounds& outItems, AABox* bounds) { assert(renderContext->args); assert(renderContext->args->hasViewFrustum()); @@ -75,8 +76,18 @@ void render::depthSortItems(const RenderContextPointer& renderContext, bool fron } // Finally once sorted result to a list of itemID - for (auto& item : itemBoundSorts) { - outItems.emplace_back(ItemBound(item._id, item._bounds)); + if (!bounds) { + for (auto& item : itemBoundSorts) { + outItems.emplace_back(ItemBound(item._id, item._bounds)); + } + } else if (!itemBoundSorts.empty()) { + if (bounds->isNull()) { + *bounds = itemBoundSorts.front()._bounds; + } + for (auto& item : itemBoundSorts) { + *bounds += item._bounds; + outItems.emplace_back(ItemBound(item._id, item._bounds)); + } } } @@ -115,6 +126,25 @@ void DepthSortShapes::run(const RenderContextPointer& renderContext, const Shape } } +void DepthSortShapesAndComputeBounds::run(const RenderContextPointer& renderContext, const ShapeBounds& inShapes, Outputs& outputs) { + auto& outShapes = outputs.edit0(); + auto& outBounds = outputs.edit1(); + + outShapes.clear(); + outShapes.reserve(inShapes.size()); + outBounds = AABox(); + + for (auto& pipeline : inShapes) { + auto& inItems = pipeline.second; + auto outItems = outShapes.find(pipeline.first); + if (outItems == outShapes.end()) { + outItems = outShapes.insert(std::make_pair(pipeline.first, ItemBounds{})).first; + } + + depthSortItems(renderContext, _frontToBack, inItems, outItems->second, &outBounds); + } +} + void DepthSortItems::run(const RenderContextPointer& renderContext, const ItemBounds& inItems, ItemBounds& outItems) { depthSortItems(renderContext, _frontToBack, inItems, outItems); } diff --git a/libraries/render/src/render/SortTask.h b/libraries/render/src/render/SortTask.h index dfeb22d540..de670b1676 100644 --- a/libraries/render/src/render/SortTask.h +++ b/libraries/render/src/render/SortTask.h @@ -15,7 +15,7 @@ #include "Engine.h" namespace render { - void depthSortItems(const RenderContextPointer& renderContext, bool frontToBack, const ItemBounds& inItems, ItemBounds& outItems); + void depthSortItems(const RenderContextPointer& renderContext, bool frontToBack, const ItemBounds& inItems, ItemBounds& outItems, AABox* bounds = nullptr); class PipelineSortShapes { public: @@ -33,6 +33,17 @@ namespace render { void run(const RenderContextPointer& renderContext, const ShapeBounds& inShapes, ShapeBounds& outShapes); }; + class DepthSortShapesAndComputeBounds { + public: + using Outputs = VaryingSet2; + using JobModel = Job::ModelIO; + + bool _frontToBack; + DepthSortShapesAndComputeBounds(bool frontToBack = true) : _frontToBack(frontToBack) {} + + void run(const RenderContextPointer& renderContext, const ShapeBounds& inShapes, Outputs& outputs); + }; + class DepthSortItems { public: using JobModel = Job::ModelIO; diff --git a/libraries/shared/src/AABox.h b/libraries/shared/src/AABox.h index eef83974ea..24485eaad6 100644 --- a/libraries/shared/src/AABox.h +++ b/libraries/shared/src/AABox.h @@ -127,10 +127,11 @@ public: AABox getOctreeChild(OctreeChild child) const; // returns the AABox of the would be octree child of this AABox + glm::vec4 getPlane(BoxFace face) const; + private: glm::vec3 getClosestPointOnFace(const glm::vec3& point, BoxFace face) const; glm::vec3 getClosestPointOnFace(const glm::vec4& origin, const glm::vec4& direction, BoxFace face) const; - glm::vec4 getPlane(BoxFace face) const; static BoxFace getOppositeFace(BoxFace face); diff --git a/libraries/shared/src/GeometryUtil.cpp b/libraries/shared/src/GeometryUtil.cpp index 6b9718fbb8..e502d44a08 100644 --- a/libraries/shared/src/GeometryUtil.cpp +++ b/libraries/shared/src/GeometryUtil.cpp @@ -14,10 +14,12 @@ #include #include #include +#include #include #include "NumericalConstants.h" #include "GLMHelpers.h" +#include "Plane.h" glm::vec3 computeVectorFromPointToSegment(const glm::vec3& point, const glm::vec3& start, const glm::vec3& end) { // compute the projection of the point vector onto the segment vector @@ -314,6 +316,134 @@ bool findRayTriangleIntersection(const glm::vec3& origin, const glm::vec3& direc return false; } +static void getTrianglePlaneIntersectionPoints(const glm::vec3 trianglePoints[3], const float pointPlaneDistances[3], + const int clippedPointIndex, const int keptPointIndices[2], + glm::vec3 points[2]) { + assert(clippedPointIndex >= 0 && clippedPointIndex < 3); + const auto& clippedPoint = trianglePoints[clippedPointIndex]; + const float clippedPointPlaneDistance = pointPlaneDistances[clippedPointIndex]; + for (auto i = 0; i < 2; i++) { + assert(keptPointIndices[i] >= 0 && keptPointIndices[i] < 3); + const auto& keptPoint = trianglePoints[keptPointIndices[i]]; + const float keptPointPlaneDistance = pointPlaneDistances[keptPointIndices[i]]; + auto intersectionEdgeRatio = clippedPointPlaneDistance / (clippedPointPlaneDistance - keptPointPlaneDistance); + points[i] = clippedPoint + (keptPoint - clippedPoint) * intersectionEdgeRatio; + } +} + +int clipTriangleWithPlane(const Triangle& triangle, const Plane& plane, Triangle* clippedTriangles, int maxClippedTriangleCount) { + float pointDistanceToPlane[3]; + std::bitset<3> arePointsClipped; + glm::vec3 triangleVertices[3] = { triangle.v0, triangle.v1, triangle.v2 }; + int clippedTriangleCount = 0; + int i; + + assert(clippedTriangleCount > 0); + + for (i = 0; i < 3; i++) { + pointDistanceToPlane[i] = plane.distance(triangleVertices[i]); + arePointsClipped.set(i, pointDistanceToPlane[i] < 0.0f); + } + + switch (arePointsClipped.count()) { + case 0: + // Easy, the entire triangle is kept as is. + *clippedTriangles = triangle; + clippedTriangleCount = 1; + break; + + case 1: + { + int clippedPointIndex = 2; + int keptPointIndices[2] = { 0, 1 }; + glm::vec3 newVertices[2]; + + // Determine which point was clipped. + if (arePointsClipped.test(0)) { + clippedPointIndex = 0; + keptPointIndices[0] = 2; + } else if (arePointsClipped.test(1)) { + clippedPointIndex = 1; + keptPointIndices[1] = 2; + } + // We have a quad now, so we need to create two triangles. + getTrianglePlaneIntersectionPoints(triangleVertices, pointDistanceToPlane, clippedPointIndex, keptPointIndices, newVertices); + clippedTriangles->v0 = triangleVertices[keptPointIndices[0]]; + clippedTriangles->v1 = triangleVertices[keptPointIndices[1]]; + clippedTriangles->v2 = newVertices[1]; + clippedTriangles++; + clippedTriangleCount++; + + if (clippedTriangleCount < maxClippedTriangleCount) { + clippedTriangles->v0 = triangleVertices[keptPointIndices[0]]; + clippedTriangles->v1 = newVertices[0]; + clippedTriangles->v2 = newVertices[1]; + clippedTriangles++; + clippedTriangleCount++; + } + } + break; + + case 2: + { + int keptPointIndex = 2; + int clippedPointIndices[2] = { 0, 1 }; + glm::vec3 newVertices[2]; + + // Determine which point was NOT clipped. + if (!arePointsClipped.test(0)) { + keptPointIndex = 0; + clippedPointIndices[0] = 2; + } else if (!arePointsClipped.test(1)) { + keptPointIndex = 1; + clippedPointIndices[1] = 2; + } + // We have a single triangle + getTrianglePlaneIntersectionPoints(triangleVertices, pointDistanceToPlane, keptPointIndex, clippedPointIndices, newVertices); + clippedTriangles->v0 = triangleVertices[keptPointIndex]; + clippedTriangles->v1 = newVertices[0]; + clippedTriangles->v2 = newVertices[1]; + clippedTriangleCount = 1; + } + break; + + default: + // Entire triangle is clipped. + break; + } + + return clippedTriangleCount; +} + +int clipTriangleWithPlanes(const Triangle& triangle, const Plane* planes, int planeCount, Triangle* clippedTriangles, int maxClippedTriangleCount) { + auto planesEnd = planes + planeCount; + int triangleCount = 1; + std::vector trianglesToTest; + + assert(maxClippedTriangleCount > 0); + + *clippedTriangles = triangle; + + while (planes < planesEnd) { + int clippedSubTriangleCount; + + trianglesToTest.clear(); + trianglesToTest.insert(trianglesToTest.begin(), clippedTriangles, clippedTriangles + triangleCount); + triangleCount = 0; + + for (const auto& triangleToTest : trianglesToTest) { + clippedSubTriangleCount = clipTriangleWithPlane(triangleToTest, *planes, + clippedTriangles + triangleCount, maxClippedTriangleCount - triangleCount); + triangleCount += clippedSubTriangleCount; + if (triangleCount >= maxClippedTriangleCount) { + return triangleCount; + } + } + ++planes; + } + return triangleCount; +} + // Do line segments (r1p1.x, r1p1.y)--(r1p2.x, r1p2.y) and (r2p1.x, r2p1.y)--(r2p2.x, r2p2.y) intersect? // from: http://ptspts.blogspot.com/2010/06/how-to-determine-if-two-line-segments.html bool doLineSegmentsIntersect(glm::vec2 r1p1, glm::vec2 r1p2, glm::vec2 r2p1, glm::vec2 r2p2) { diff --git a/libraries/shared/src/GeometryUtil.h b/libraries/shared/src/GeometryUtil.h index eb9424d938..dcb90643b6 100644 --- a/libraries/shared/src/GeometryUtil.h +++ b/libraries/shared/src/GeometryUtil.h @@ -15,6 +15,8 @@ #include #include +class Plane; + glm::vec3 computeVectorFromPointToSegment(const glm::vec3& point, const glm::vec3& start, const glm::vec3& end); /// Computes the penetration between a point and a sphere (centered at the origin) @@ -109,6 +111,8 @@ inline bool findRayTriangleIntersection(const glm::vec3& origin, const glm::vec3 return findRayTriangleIntersection(origin, direction, triangle.v0, triangle.v1, triangle.v2, distance, allowBackface); } +int clipTriangleWithPlane(const Triangle& triangle, const Plane& plane, Triangle* clippedTriangles, int maxClippedTriangleCount); +int clipTriangleWithPlanes(const Triangle& triangle, const Plane* planes, int planeCount, Triangle* clippedTriangles, int maxClippedTriangleCount); bool doLineSegmentsIntersect(glm::vec2 r1p1, glm::vec2 r1p2, glm::vec2 r2p1, glm::vec2 r2p2); bool isOnSegment(float xi, float yi, float xj, float yj, float xk, float yk); diff --git a/libraries/shared/src/Plane.h b/libraries/shared/src/Plane.h index c903ad9db7..cf17ca7201 100644 --- a/libraries/shared/src/Plane.h +++ b/libraries/shared/src/Plane.h @@ -19,7 +19,9 @@ class Plane { public: - Plane(const glm::vec3 &v1, const glm::vec3 &v2, const glm::vec3 &v3) { set3Points(v1,v2,v3); } + Plane(const glm::vec3 &v1, const glm::vec3 &v2, const glm::vec3 &v3) { set3Points(v1, v2, v3); } + Plane(const glm::vec3 &normal, const glm::vec3 &point) { setNormalAndPoint(normal, point); } + Plane(float a, float b, float c, float d) { setCoefficients(a, b, c, d); } Plane() : _normal(0.0f), _point(0.0f), _dCoefficient(0.0f) {}; ~Plane() {} ; diff --git a/libraries/shared/src/Transform.h b/libraries/shared/src/Transform.h index 316fcb2f04..71d8b6c915 100644 --- a/libraries/shared/src/Transform.h +++ b/libraries/shared/src/Transform.h @@ -149,6 +149,7 @@ public: Vec4 transform(const Vec4& pos) const; Vec3 transform(const Vec3& pos) const; + Vec3 transformDirection(const Vec3& pos) const; bool containsNaN() const { return isNaN(_rotation) || isNaN(glm::dot(_scale, _translation)); } @@ -541,6 +542,13 @@ inline Transform::Vec3 Transform::transform(const Vec3& pos) const { return Vec3(result.x / result.w, result.y / result.w, result.z / result.w); } +inline Transform::Vec3 Transform::transformDirection(const Vec3& pos) const { + Mat4 m; + getMatrix(m); + Vec4 result = m * Vec4(pos, 0.0f); + return Vec3(result.x, result.y, result.z); +} + inline Transform::Mat4& Transform::getCachedMatrix(Transform::Mat4& result) const { updateCache(); result = (*_matrix); From 9eed69d7ef39c0a8475dbbeae4037519993eed65 Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Thu, 26 Oct 2017 15:11:42 +0200 Subject: [PATCH 03/34] Trying to pin point a zone bug --- .../src/RenderableZoneEntityItem.cpp | 6 +++- .../src/DeferredLightingEffect.cpp | 8 ++--- libraries/render-utils/src/DrawHaze.cpp | 6 ++-- libraries/render-utils/src/LightStage.cpp | 32 +++++++++++++++++++ libraries/render-utils/src/LightStage.h | 28 +++------------- .../render-utils/src/RenderShadowTask.cpp | 9 ++++-- 6 files changed, 56 insertions(+), 33 deletions(-) diff --git a/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp b/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp index 0235f1b7a3..7a30414360 100644 --- a/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp +++ b/libraries/entities-renderer/src/RenderableZoneEntityItem.cpp @@ -40,22 +40,26 @@ void ZoneEntityRenderer::onRemoveFromSceneTyped(const TypedEntityPointer& entity if (_stage) { if (!LightStage::isIndexInvalid(_sunIndex)) { _stage->removeLight(_sunIndex); + _sunIndex = INVALID_INDEX; + _shadowIndex = INVALID_INDEX; } if (!LightStage::isIndexInvalid(_ambientIndex)) { _stage->removeLight(_ambientIndex); - + _ambientIndex = INVALID_INDEX; } } if (_backgroundStage) { if (!BackgroundStage::isIndexInvalid(_backgroundIndex)) { _backgroundStage->removeBackground(_backgroundIndex); + _backgroundIndex = INVALID_INDEX; } } if (_hazeStage) { if (!HazeStage::isIndexInvalid(_hazeIndex)) { _hazeStage->removeHaze(_hazeIndex); + _hazeIndex = INVALID_INDEX; } } } diff --git a/libraries/render-utils/src/DeferredLightingEffect.cpp b/libraries/render-utils/src/DeferredLightingEffect.cpp index b6a91888a1..5068047d20 100644 --- a/libraries/render-utils/src/DeferredLightingEffect.cpp +++ b/libraries/render-utils/src/DeferredLightingEffect.cpp @@ -105,13 +105,13 @@ void DeferredLightingEffect::setupKeyLightBatch(const RenderArgs* args, gpu::Bat PerformanceTimer perfTimer("DLE->setupBatch()"); model::LightPointer keySunLight; auto lightStage = args->_scene->getStage(); - if (lightStage && lightStage->_currentFrame._sunLights.size()) { - keySunLight = lightStage->getLight(lightStage->_currentFrame._sunLights.front()); + if (lightStage) { + keySunLight = lightStage->getCurrentKeyLight(); } model::LightPointer keyAmbiLight; - if (lightStage && lightStage->_currentFrame._ambientLights.size()) { - keyAmbiLight = lightStage->getLight(lightStage->_currentFrame._ambientLights.front()); + if (lightStage) { + keyAmbiLight = lightStage->getCurrentAmbientLight(); } if (keySunLight) { diff --git a/libraries/render-utils/src/DrawHaze.cpp b/libraries/render-utils/src/DrawHaze.cpp index bf254ce80e..fc751e9dc1 100644 --- a/libraries/render-utils/src/DrawHaze.cpp +++ b/libraries/render-utils/src/DrawHaze.cpp @@ -191,9 +191,9 @@ void DrawHaze::run(const render::RenderContextPointer& renderContext, const Inpu batch.setUniformBuffer(HazeEffect_TransformBufferSlot, transformBuffer->getFrameTransformBuffer()); auto lightStage = args->_scene->getStage(); - if (lightStage && lightStage->_currentFrame._sunLights.size() > 0) { - model::LightPointer keyLight; - keyLight = lightStage->getLight(lightStage->_currentFrame._sunLights.front()); + if (lightStage) { + model::LightPointer keyLight; + keyLight = lightStage->getCurrentKeyLight(); if (keyLight != nullptr) { batch.setUniformBuffer(HazeEffect_LightingMapSlot, keyLight->getLightSchemaBuffer()); } diff --git a/libraries/render-utils/src/LightStage.cpp b/libraries/render-utils/src/LightStage.cpp index 945bb3b9e6..0a18c19698 100644 --- a/libraries/render-utils/src/LightStage.cpp +++ b/libraries/render-utils/src/LightStage.cpp @@ -168,6 +168,38 @@ LightStage::LightPointer LightStage::removeLight(Index index) { return removed; } +LightStage::LightPointer LightStage::getCurrentKeyLight() const { + Index keyLightId{ 0 }; + if (!_currentFrame._sunLights.empty()) { + keyLightId = _currentFrame._sunLights.front(); + } + return _lights.get(keyLightId); +} + +LightStage::LightPointer LightStage::getCurrentAmbientLight() const { + Index keyLightId{ 0 }; + if (!_currentFrame._ambientLights.empty()) { + keyLightId = _currentFrame._ambientLights.front(); + } + return _lights.get(keyLightId); +} + +LightStage::ShadowPointer LightStage::getCurrentKeyShadow() const { + Index keyLightId{ 0 }; + if (!_currentFrame._sunLights.empty()) { + keyLightId = _currentFrame._sunLights.front(); + } + return getShadow(keyLightId); +} + +LightStage::LightAndShadow LightStage::getCurrentKeyLightAndShadow() const { + Index keyLightId{ 0 }; + if (!_currentFrame._sunLights.empty()) { + keyLightId = _currentFrame._sunLights.front(); + } + return LightAndShadow(getLight(keyLightId), getShadow(keyLightId)); +} + void LightStage::updateLightArrayBuffer(Index lightId) { auto lightSize = sizeof(model::Light::LightSchema); if (!_lightArrayBuffer) { diff --git a/libraries/render-utils/src/LightStage.h b/libraries/render-utils/src/LightStage.h index a6e369c2f4..cb310ce54d 100644 --- a/libraries/render-utils/src/LightStage.h +++ b/libraries/render-utils/src/LightStage.h @@ -117,31 +117,13 @@ public: return LightAndShadow(getLight(lightId), getShadow(lightId)); } - LightPointer getCurrentKeyLight() const { - Index keyLightId{ 0 }; - if (!_currentFrame._sunLights.empty()) { - keyLightId = _currentFrame._sunLights.front(); - } - return _lights.get(keyLightId); - } - - ShadowPointer getCurrentKeyShadow() const { - Index keyLightId{ 0 }; - if (!_currentFrame._sunLights.empty()) { - keyLightId = _currentFrame._sunLights.front(); - } - return getShadow(keyLightId); - } - - LightAndShadow getCurrentKeyLightAndShadow() const { - Index keyLightId{ 0 }; - if (!_currentFrame._sunLights.empty()) { - keyLightId = _currentFrame._sunLights.front(); - } - return LightAndShadow(getLight(keyLightId), getShadow(keyLightId)); - } + LightPointer getCurrentKeyLight() const; + LightPointer getCurrentAmbientLight() const; + ShadowPointer getCurrentKeyShadow() const; + LightAndShadow getCurrentKeyLightAndShadow() const; LightStage(); + Lights _lights; LightMap _lightMap; Descs _descs; diff --git a/libraries/render-utils/src/RenderShadowTask.cpp b/libraries/render-utils/src/RenderShadowTask.cpp index 80b988d055..9bf915b33e 100644 --- a/libraries/render-utils/src/RenderShadowTask.cpp +++ b/libraries/render-utils/src/RenderShadowTask.cpp @@ -22,8 +22,10 @@ #include "DeferredLightingEffect.h" #include "FramebufferCache.h" +// These values are used for culling the objects rendered in the shadow map +// but are readjusted afterwards #define SHADOW_FRUSTUM_NEAR 1.0f -#define SHADOW_FRUSTUM_FAR 100.0f +#define SHADOW_FRUSTUM_FAR 500.0f using namespace render; @@ -110,8 +112,11 @@ static void adjustNearFar(const AABox& inShapeBounds, ViewFrustum& shadowFrustum float far = 0.0f; computeNearFar(sceneBoundVertices, shadowClipPlanes, near, far); + // Limit the far range to the one used originally. There's no point in rendering objects + // that are not in the view frustum. + far = glm::min(far, shadowFrustum.getFarClip()); - const auto depthEpsilon = 0.25f; + const auto depthEpsilon = 0.1f; auto projMatrix = glm::ortho(-1.0f, 1.0f, -1.0f, 1.0f, near - depthEpsilon, far + depthEpsilon); auto shadowProjection = shadowFrustum.getProjection(); From 5d83284ac59ae680408285ae05c0cc1f67999772 Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Thu, 26 Oct 2017 16:47:20 +0200 Subject: [PATCH 04/34] Fixed small bug in shadow bounds computation --- libraries/render/src/render/SortTask.cpp | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/libraries/render/src/render/SortTask.cpp b/libraries/render/src/render/SortTask.cpp index f789f8c5c6..987b25358a 100644 --- a/libraries/render/src/render/SortTask.cpp +++ b/libraries/render/src/render/SortTask.cpp @@ -140,8 +140,14 @@ void DepthSortShapesAndComputeBounds::run(const RenderContextPointer& renderCont if (outItems == outShapes.end()) { outItems = outShapes.insert(std::make_pair(pipeline.first, ItemBounds{})).first; } + AABox bounds; - depthSortItems(renderContext, _frontToBack, inItems, outItems->second, &outBounds); + depthSortItems(renderContext, _frontToBack, inItems, outItems->second, &bounds); + if (!outBounds.isNull()) { + outBounds += bounds; + } else { + outBounds = bounds; + } } } From 44393f12d9409f9ed556ba934d4cf105ca6241cf Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Thu, 26 Oct 2017 17:41:54 +0200 Subject: [PATCH 05/34] Adjusted bias --- libraries/render-utils/src/LightStage.cpp | 7 ++++--- libraries/render-utils/src/LightStage.h | 2 +- libraries/render-utils/src/RenderShadowTask.cpp | 2 +- 3 files changed, 6 insertions(+), 5 deletions(-) diff --git a/libraries/render-utils/src/LightStage.cpp b/libraries/render-utils/src/LightStage.cpp index 0a18c19698..b13e46788d 100644 --- a/libraries/render-utils/src/LightStage.cpp +++ b/libraries/render-utils/src/LightStage.cpp @@ -76,9 +76,10 @@ void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, fitFrustum(farCorners.topLeft); fitFrustum(farCorners.topRight); - // Re-adjust near shadow distance to - max.z = glm::max(max.z, -nearDepth); - glm::mat4 ortho = glm::ortho(min.x, max.x, min.y, max.y, -max.z, -min.z); + // Re-adjust near shadow distance + auto near = glm::max(max.z, -nearDepth); + auto far = -min.z; + glm::mat4 ortho = glm::ortho(min.x, max.x, min.y, max.y, near, far); _frustum->setProjection(ortho); // Calculate the frustum's internal state diff --git a/libraries/render-utils/src/LightStage.h b/libraries/render-utils/src/LightStage.h index cb310ce54d..706caec9d6 100644 --- a/libraries/render-utils/src/LightStage.h +++ b/libraries/render-utils/src/LightStage.h @@ -69,7 +69,7 @@ public: glm::mat4 projection; glm::mat4 viewInverse; - glm::float32 bias = 0.005f; + glm::float32 bias = 0.003f; glm::float32 scale = 1 / MAP_SIZE; }; UniformBufferView _schemaBuffer = nullptr; diff --git a/libraries/render-utils/src/RenderShadowTask.cpp b/libraries/render-utils/src/RenderShadowTask.cpp index 9bf915b33e..7a6e3dc74f 100644 --- a/libraries/render-utils/src/RenderShadowTask.cpp +++ b/libraries/render-utils/src/RenderShadowTask.cpp @@ -203,7 +203,7 @@ void RenderShadowMap::run(const render::RenderContextPointer& renderContext, con } void RenderShadowTask::build(JobModel& task, const render::Varying& input, render::Varying& output, CullFunctor cullFunctor) { - cullFunctor = cullFunctor ? cullFunctor : [](const RenderArgs*, const AABox&){ return true; }; + cullFunctor = cullFunctor ? cullFunctor : [](const RenderArgs*, const AABox&) { return true; }; // Prepare the ShapePipeline ShapePlumberPointer shapePlumber = std::make_shared(); From 0044759196656a08ffadfeae09ffe3b4e3a9e3d5 Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Thu, 26 Oct 2017 18:29:29 +0200 Subject: [PATCH 06/34] Disabled broken PCF and reset back to previous bias --- libraries/render-utils/src/LightStage.cpp | 6 ++++++ libraries/render-utils/src/LightStage.h | 8 ++++++-- libraries/render-utils/src/Shadow.slh | 5 +++++ 3 files changed, 17 insertions(+), 2 deletions(-) diff --git a/libraries/render-utils/src/LightStage.cpp b/libraries/render-utils/src/LightStage.cpp index b13e46788d..411f179d49 100644 --- a/libraries/render-utils/src/LightStage.cpp +++ b/libraries/render-utils/src/LightStage.cpp @@ -18,6 +18,12 @@ std::string LightStage::_stageName { "LIGHT_STAGE"}; LightStage::LightStage() { } +LightStage::Shadow::Schema::Schema() : + bias{ 0.005f }, + scale{ 1.0f / MAP_SIZE } { + +} + LightStage::Shadow::Shadow(model::LightPointer light) : _light{ light}, _frustum{ std::make_shared() } { framebuffer = gpu::FramebufferPointer(gpu::Framebuffer::createShadowmap(MAP_SIZE)); map = framebuffer->getDepthStencilBuffer(); diff --git a/libraries/render-utils/src/LightStage.h b/libraries/render-utils/src/LightStage.h index 706caec9d6..3a2a77055f 100644 --- a/libraries/render-utils/src/LightStage.h +++ b/libraries/render-utils/src/LightStage.h @@ -60,17 +60,21 @@ public: gpu::FramebufferPointer framebuffer; gpu::TexturePointer map; + protected: model::LightPointer _light; std::shared_ptr _frustum; class Schema { public: + + Schema(); + glm::mat4 projection; glm::mat4 viewInverse; - glm::float32 bias = 0.003f; - glm::float32 scale = 1 / MAP_SIZE; + glm::float32 bias; + glm::float32 scale; }; UniformBufferView _schemaBuffer = nullptr; diff --git a/libraries/render-utils/src/Shadow.slh b/libraries/render-utils/src/Shadow.slh index 7b86b9b660..e844db43dd 100644 --- a/libraries/render-utils/src/Shadow.slh +++ b/libraries/render-utils/src/Shadow.slh @@ -68,6 +68,8 @@ vec2 PCFkernel[4] = vec2[4]( ); float evalShadowAttenuationPCF(vec4 position, vec4 shadowTexcoord) { + // PCF is buggy so disable it for the time being +#if 0 float pcfRadius = 3.0; float shadowScale = getShadowScale(); @@ -80,6 +82,9 @@ float evalShadowAttenuationPCF(vec4 position, vec4 shadowTexcoord) { fetchShadow(shadowTexcoord.xyz + shadowScale * vec3(offset + PCFkernel[2], 0.0)) + fetchShadow(shadowTexcoord.xyz + shadowScale * vec3(offset + PCFkernel[3], 0.0)) )); +#else + float shadowAttenuation = fetchShadow(shadowTexcoord.xyz); +#endif return shadowAttenuation; } From 79c2da3dcb4841f4a5c17f4cfc82643a1e4e560e Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Fri, 3 Nov 2017 16:52:29 +0100 Subject: [PATCH 07/34] Removed cull functor from shadow render task as it is inadapted for the shadow's orthographic projection --- libraries/render-utils/src/RenderViewTask.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/libraries/render-utils/src/RenderViewTask.cpp b/libraries/render-utils/src/RenderViewTask.cpp index fceaf7b5b9..1085a1148c 100644 --- a/libraries/render-utils/src/RenderViewTask.cpp +++ b/libraries/render-utils/src/RenderViewTask.cpp @@ -19,7 +19,10 @@ void RenderViewTask::build(JobModel& task, const render::Varying& input, render::Varying& output, render::CullFunctor cullFunctor, bool isDeferred) { // auto items = input.get(); - task.addJob("RenderShadowTask", cullFunctor); + // Shadows use an orthographic projection because they are linked to sunlights + // but the cullFunctor passed is probably tailored for perspective projection and culls too much. + // TODO : create a special cull functor for this. + task.addJob("RenderShadowTask", nullptr); const auto items = task.addJob("FetchCullSort", cullFunctor); assert(items.canCast()); From 332cb48a41e0db4eaed996b0ab0a73162bc008ee Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Tue, 7 Nov 2017 16:57:55 -0700 Subject: [PATCH 08/34] Lasers and teleport scale with avatar --- interface/src/raypick/LaserPointer.cpp | 16 +++++++++++++--- interface/src/raypick/LaserPointer.h | 3 ++- interface/src/raypick/LaserPointerManager.cpp | 4 ++-- interface/src/raypick/LaserPointerManager.h | 2 +- .../raypick/LaserPointerScriptingInterface.cpp | 9 +++++++-- interface/src/ui/overlays/Line3DOverlay.cpp | 10 +++++++++- interface/src/ui/overlays/Line3DOverlay.h | 3 +++ libraries/render-utils/src/GeometryCache.cpp | 5 +++-- libraries/render-utils/src/GeometryCache.h | 6 +++--- libraries/render-utils/src/glowLine.slf | 5 +++-- libraries/render-utils/src/glowLine.slv | 3 +++ .../controllerModules/farActionGrabEntity.js | 1 + .../controllers/controllerModules/farTrigger.js | 1 + .../controllers/controllerModules/inEditMode.js | 1 + .../controllerModules/overlayLaserInput.js | 1 + .../controllers/controllerModules/teleport.js | 4 ++++ .../controllerModules/webEntityLaserInput.js | 2 +- .../marketplace/shapes/modules/laser.js | 1 + 18 files changed, 59 insertions(+), 18 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index 75b43a251b..50479a77dd 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -7,7 +7,7 @@ // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// +//// #include "LaserPointer.h" #include "Application.h" @@ -15,7 +15,7 @@ #include "RayPickScriptingInterface.h" LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, - const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled) : + const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : _renderingEnabled(enabled), _renderStates(renderStates), _defaultRenderStates(defaultRenderStates), @@ -23,6 +23,7 @@ LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& rende _centerEndY(centerEndY), _lockEnd(lockEnd), _distanceScaleEnd(distanceScaleEnd), + _scaleWithAvatar(scaleWithAvatar), _rayPickUID(DependencyManager::get()->createRayPick(rayProps)) { @@ -151,6 +152,9 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter } } } + + float avatarScale = DependencyManager::get()->getMyAvatar()->getAvatarScale(); + QVariant end = vec3toVariant(endVec); if (!renderState.getPathID().isNull()) { QVariantMap pathProps; @@ -158,6 +162,11 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter pathProps.insert("end", end); pathProps.insert("visible", true); pathProps.insert("ignoreRayIntersection", renderState.doesPathIgnoreRays()); + if (_scaleWithAvatar) { + auto glowScaleProp = qApp->getOverlays().getProperty(renderState.getPathID(), "glowScale").value; + float glowScale = glowScaleProp.isValid() ? avatarScale * glowScaleProp.toFloat() : avatarScale; + pathProps.insert("glowScale", glowScale); + } qApp->getOverlays().editOverlay(renderState.getPathID(), pathProps); } if (!renderState.getEndID().isNull()) { @@ -165,7 +174,7 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter glm::quat faceAvatarRotation = DependencyManager::get()->getMyAvatar()->getOrientation() * glm::quat(glm::radians(glm::vec3(0.0f, 180.0f, 0.0f))); glm::vec3 dim = vec3FromVariant(qApp->getOverlays().getProperty(renderState.getEndID(), "dimensions").value); if (_distanceScaleEnd) { - dim = renderState.getEndDim() * glm::distance(pickRay.origin, endVec) * DependencyManager::get()->getMyAvatar()->getSensorToWorldScale(); + dim = renderState.getEndDim() * glm::distance(pickRay.origin, endVec); endProps.insert("dimensions", vec3toVariant(dim)); } if (_centerEndY) { @@ -211,6 +220,7 @@ void LaserPointer::update() { if (_renderingEnabled && !_currentRenderState.empty() && _renderStates.find(_currentRenderState) != _renderStates.end() && (prevRayPickResult.type != IntersectionType::NONE || _laserLength > 0.0f || !_objectLockEnd.first.isNull())) { float distance = _laserLength > 0.0f ? _laserLength : prevRayPickResult.distance; + qDebug() << &_currentRenderState; updateRenderState(_renderStates[_currentRenderState], prevRayPickResult.type, distance, prevRayPickResult.objectID, prevRayPickResult.searchRay, false); disableRenderState(_defaultRenderStates[_currentRenderState].second); } else if (_renderingEnabled && !_currentRenderState.empty() && _defaultRenderStates.find(_currentRenderState) != _defaultRenderStates.end()) { diff --git a/interface/src/raypick/LaserPointer.h b/interface/src/raypick/LaserPointer.h index f2350c7199..592ba978df 100644 --- a/interface/src/raypick/LaserPointer.h +++ b/interface/src/raypick/LaserPointer.h @@ -60,7 +60,7 @@ public: typedef std::unordered_map> DefaultRenderStateMap; LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, - const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled); + const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled); ~LaserPointer(); QUuid getRayUID() { return _rayPickUID; } @@ -91,6 +91,7 @@ private: bool _centerEndY; bool _lockEnd; bool _distanceScaleEnd; + bool _scaleWithAvatar; std::pair _objectLockEnd { std::pair(QUuid(), false)}; const QUuid _rayPickUID; diff --git a/interface/src/raypick/LaserPointerManager.cpp b/interface/src/raypick/LaserPointerManager.cpp index 9d58cc2587..868491f166 100644 --- a/interface/src/raypick/LaserPointerManager.cpp +++ b/interface/src/raypick/LaserPointerManager.cpp @@ -11,9 +11,9 @@ #include "LaserPointerManager.h" QUuid LaserPointerManager::createLaserPointer(const QVariant& rayProps, const LaserPointer::RenderStateMap& renderStates, const LaserPointer::DefaultRenderStateMap& defaultRenderStates, - const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled) { + const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) { QUuid result; - std::shared_ptr laserPointer = std::make_shared(rayProps, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, distanceScaleEnd, enabled); + std::shared_ptr laserPointer = std::make_shared(rayProps, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, distanceScaleEnd, scaleWithAvatar, enabled); if (!laserPointer->getRayUID().isNull()) { result = QUuid::createUuid(); withWriteLock([&] { _laserPointers[result] = laserPointer; }); diff --git a/interface/src/raypick/LaserPointerManager.h b/interface/src/raypick/LaserPointerManager.h index e302318483..9283b7ac89 100644 --- a/interface/src/raypick/LaserPointerManager.h +++ b/interface/src/raypick/LaserPointerManager.h @@ -25,7 +25,7 @@ class LaserPointerManager : protected ReadWriteLockable { public: QUuid createLaserPointer(const QVariant& rayProps, const LaserPointer::RenderStateMap& renderStates, const LaserPointer::DefaultRenderStateMap& defaultRenderStates, - const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool enabled); + const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled); void removeLaserPointer(const QUuid& uid); void enableLaserPointer(const QUuid& uid) const; diff --git a/interface/src/raypick/LaserPointerScriptingInterface.cpp b/interface/src/raypick/LaserPointerScriptingInterface.cpp index e8d28bfab2..a47605fa1f 100644 --- a/interface/src/raypick/LaserPointerScriptingInterface.cpp +++ b/interface/src/raypick/LaserPointerScriptingInterface.cpp @@ -7,7 +7,7 @@ // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// +//// #include "LaserPointerScriptingInterface.h" @@ -51,6 +51,11 @@ QUuid LaserPointerScriptingInterface::createLaserPointer(const QVariant& propert enabled = propertyMap["enabled"].toBool(); } + bool scaleWithAvatar = false; + if (propertyMap["scaleWithAvatar"].isValid()) { + scaleWithAvatar = propertyMap["scaleWithAvatar"].toBool(); + } + LaserPointer::RenderStateMap renderStates; if (propertyMap["renderStates"].isValid()) { QList renderStateVariants = propertyMap["renderStates"].toList(); @@ -80,7 +85,7 @@ QUuid LaserPointerScriptingInterface::createLaserPointer(const QVariant& propert } } - return qApp->getLaserPointerManager().createLaserPointer(properties, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, distanceScaleEnd, enabled); + return qApp->getLaserPointerManager().createLaserPointer(properties, renderStates, defaultRenderStates, faceAvatar, centerEndY, lockEnd, distanceScaleEnd, scaleWithAvatar, enabled); } void LaserPointerScriptingInterface::editRenderState(const QUuid& uid, const QString& renderState, const QVariant& properties) const { diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index bdb35d4f49..7ac79f081a 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -12,6 +12,7 @@ #include #include +#include #include "AbstractViewStateInterface.h" @@ -35,6 +36,7 @@ Line3DOverlay::Line3DOverlay(const Line3DOverlay* line3DOverlay) : _endParentJointIndex = line3DOverlay->getEndJointIndex(); _glow = line3DOverlay->getGlow(); _glowWidth = line3DOverlay->getGlowWidth(); + _glowScale = line3DOverlay->getGlowScale(); } Line3DOverlay::~Line3DOverlay() { @@ -145,7 +147,7 @@ void Line3DOverlay::render(RenderArgs* args) { geometryCache->renderDashedLine(*batch, start, end, colorv4, _geometryCacheID); } else { // renderGlowLine handles both glow = 0 and glow > 0 cases - geometryCache->renderGlowLine(*batch, start, end, colorv4, _glow, _glowWidth, _geometryCacheID); + geometryCache->renderGlowLine(*batch, start, end, colorv4, _glow, _glowWidth, _glowScale, _geometryCacheID); } } } @@ -244,6 +246,12 @@ void Line3DOverlay::setProperties(const QVariantMap& originalProperties) { setGlowWidth(glowWidth.toFloat()); } + auto glowScale = properties["glowScale"]; + if (glowScale.isValid()) { + float gscale = glowScale.toFloat(); + setGlowScale(gscale); + } + } QVariant Line3DOverlay::getProperty(const QString& property) { diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index bcb65b1f1e..250d823598 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -33,6 +33,7 @@ public: glm::vec3 getEnd() const; const float& getGlow() const { return _glow; } const float& getGlowWidth() const { return _glowWidth; } + const float& getGlowScale() const { return _glowScale; } // setters void setStart(const glm::vec3& start); @@ -43,6 +44,7 @@ public: void setGlow(const float& glow) { _glow = glow; } void setGlowWidth(const float& glowWidth) { _glowWidth = glowWidth; } + void setGlowScale(const float& glowScale) { _glowScale = glowScale; } void setProperties(const QVariantMap& properties) override; QVariant getProperty(const QString& property) override; @@ -72,6 +74,7 @@ private: float _glow { 0.0 }; float _glowWidth { 0.0 }; + float _glowScale{ 1.0 }; int _geometryCacheID; }; diff --git a/libraries/render-utils/src/GeometryCache.cpp b/libraries/render-utils/src/GeometryCache.cpp index fa00737e3c..90b3ca402d 100644 --- a/libraries/render-utils/src/GeometryCache.cpp +++ b/libraries/render-utils/src/GeometryCache.cpp @@ -1868,7 +1868,7 @@ void GeometryCache::renderLine(gpu::Batch& batch, const glm::vec2& p1, const glm void GeometryCache::renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const glm::vec3& p2, - const glm::vec4& color, float glowIntensity, float glowWidth, int id) { + const glm::vec4& color, float glowIntensity, float glowWidth, float glowScale, int id) { // Disable glow lines on OSX #ifndef Q_OS_WIN @@ -1931,9 +1931,10 @@ void GeometryCache::renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const vec4 p1; vec4 p2; vec4 color; + float scale; }; - LineData lineData { vec4(p1, 1.0f), vec4(p2, 1.0f), color }; + LineData lineData { vec4(p1, 1.0f), vec4(p2, 1.0f), color, glowScale }; details.uniformBuffer->resize(sizeof(LineData)); details.uniformBuffer->setSubData(0, lineData); } diff --git a/libraries/render-utils/src/GeometryCache.h b/libraries/render-utils/src/GeometryCache.h index cd8c43f1df..862331b743 100644 --- a/libraries/render-utils/src/GeometryCache.h +++ b/libraries/render-utils/src/GeometryCache.h @@ -248,7 +248,7 @@ public: renderWireCubeInstance(args, batch, glm::vec4(color, 1.0f), pipeline); } - // Dynamic geometry + // //Dynamic geometry void renderShape(gpu::Batch& batch, Shape shape); void renderWireShape(gpu::Batch& batch, Shape shape); size_t getShapeTriangleCount(Shape shape); @@ -314,10 +314,10 @@ public: const glm::vec4& color1, const glm::vec4& color2, int id); void renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const glm::vec3& p2, - const glm::vec4& color, float glowIntensity, float glowWidth, int id); + const glm::vec4& color, float glowIntensity, float glowWidth, float glowScale, int id); void renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const glm::vec3& p2, const glm::vec4& color, int id) - { renderGlowLine(batch, p1, p2, color, 1.0f, 0.05f, id); } + { renderGlowLine(batch, p1, p2, color, 1.0f, 0.05f, 1.0f, id); } void renderDashedLine(gpu::Batch& batch, const glm::vec3& start, const glm::vec3& end, const glm::vec4& color, int id) { renderDashedLine(batch, start, end, color, 0.05f, 0.025f, id); } diff --git a/libraries/render-utils/src/glowLine.slf b/libraries/render-utils/src/glowLine.slf index 73e14bd319..be1c6842e3 100644 --- a/libraries/render-utils/src/glowLine.slf +++ b/libraries/render-utils/src/glowLine.slf @@ -10,8 +10,9 @@ // in vec4 _color; -in float distanceFromCenter; +in float _scale; +in float distanceFromCenter; out vec4 _fragColor; void main(void) { @@ -21,7 +22,7 @@ void main(void) { float alpha = 1.0 - abs(distanceFromCenter); // Convert from a linear alpha curve to a sharp peaked one - alpha = _color.a * pow(alpha, 10.0); + alpha = _color.a * pow(alpha, 10.0/_scale); // Drop everything where the curve falls off to nearly nothing if (alpha <= 0.05) { diff --git a/libraries/render-utils/src/glowLine.slv b/libraries/render-utils/src/glowLine.slv index fd3a85d254..7b69943b7a 100644 --- a/libraries/render-utils/src/glowLine.slv +++ b/libraries/render-utils/src/glowLine.slv @@ -16,14 +16,17 @@ layout(std140) uniform lineData { vec4 p1; vec4 p2; vec4 color; + float scale; }; out vec4 _color; +out float _scale; // the distance from the center in 'quad space' out float distanceFromCenter; void main(void) { _color = color; + _scale = scale; TransformCamera cam = getTransformCamera(); TransformObject obj = getTransformObject(); diff --git a/scripts/system/controllers/controllerModules/farActionGrabEntity.js b/scripts/system/controllers/controllerModules/farActionGrabEntity.js index e34855d521..2ee308ddb4 100644 --- a/scripts/system/controllers/controllerModules/farActionGrabEntity.js +++ b/scripts/system/controllers/controllerModules/farActionGrabEntity.js @@ -584,6 +584,7 @@ Script.include("/~/system/libraries/controllers.js"); renderStates: renderStates, faceAvatar: true, distanceScaleEnd: true, + scaleWithAvatar: true, defaultRenderStates: defaultRenderStates }); } diff --git a/scripts/system/controllers/controllerModules/farTrigger.js b/scripts/system/controllers/controllerModules/farTrigger.js index de60e2e227..ab950cbbdf 100644 --- a/scripts/system/controllers/controllerModules/farTrigger.js +++ b/scripts/system/controllers/controllerModules/farTrigger.js @@ -190,6 +190,7 @@ Script.include("/~/system/libraries/controllers.js"); renderStates: renderStates, faceAvatar: true, distanceScaleEnd: true, + scaleWithAvatar: true, defaultRenderStates: defaultRenderStates }); diff --git a/scripts/system/controllers/controllerModules/inEditMode.js b/scripts/system/controllers/controllerModules/inEditMode.js index f9ec38d22a..4520a91d74 100644 --- a/scripts/system/controllers/controllerModules/inEditMode.js +++ b/scripts/system/controllers/controllerModules/inEditMode.js @@ -237,6 +237,7 @@ Script.include("/~/system/libraries/utils.js"); posOffset: getGrabPointSphereOffset(this.handToController(), true), renderStates: renderStates, faceAvatar: true, + scaleWithAvatar: true, defaultRenderStates: defaultRenderStates }); diff --git a/scripts/system/controllers/controllerModules/overlayLaserInput.js b/scripts/system/controllers/controllerModules/overlayLaserInput.js index 1c83f38d9b..e87e6e000a 100644 --- a/scripts/system/controllers/controllerModules/overlayLaserInput.js +++ b/scripts/system/controllers/controllerModules/overlayLaserInput.js @@ -371,6 +371,7 @@ Script.include("/~/system/libraries/controllers.js"); posOffset: getGrabPointSphereOffset(this.handToController(), true), renderStates: renderStates, faceAvatar: true, + scaleWithAvatar: true, defaultRenderStates: defaultRenderStates }); diff --git a/scripts/system/controllers/controllerModules/teleport.js b/scripts/system/controllers/controllerModules/teleport.js index 0364e4f9b4..c4fbe781b9 100644 --- a/scripts/system/controllers/controllerModules/teleport.js +++ b/scripts/system/controllers/controllerModules/teleport.js @@ -153,6 +153,7 @@ Script.include("/~/system/libraries/controllers.js"); joint: (_this.hand === RIGHT_HAND) ? "RightHand" : "LeftHand", filter: RayPick.PICK_ENTITIES, faceAvatar: true, + scaleWithAvatar: true, centerEndY: false, renderStates: teleportRenderStates, defaultRenderStates: teleportDefaultRenderStates @@ -161,6 +162,7 @@ Script.include("/~/system/libraries/controllers.js"); joint: (_this.hand === RIGHT_HAND) ? "RightHand" : "LeftHand", filter: RayPick.PICK_ENTITIES | RayPick.PICK_INCLUDE_INVISIBLE, faceAvatar: true, + scaleWithAvatar: true, centerEndY: false, renderStates: teleportRenderStates }); @@ -168,6 +170,7 @@ Script.include("/~/system/libraries/controllers.js"); joint: "Avatar", filter: RayPick.PICK_ENTITIES, faceAvatar: true, + scaleWithAvatar: true, centerEndY: false, renderStates: teleportRenderStates, defaultRenderStates: teleportDefaultRenderStates @@ -176,6 +179,7 @@ Script.include("/~/system/libraries/controllers.js"); joint: "Avatar", filter: RayPick.PICK_ENTITIES | RayPick.PICK_INCLUDE_INVISIBLE, faceAvatar: true, + scaleWithAvatar: true, centerEndY: false, renderStates: teleportRenderStates }); diff --git a/scripts/system/controllers/controllerModules/webEntityLaserInput.js b/scripts/system/controllers/controllerModules/webEntityLaserInput.js index 39969df614..eafe7c3462 100644 --- a/scripts/system/controllers/controllerModules/webEntityLaserInput.js +++ b/scripts/system/controllers/controllerModules/webEntityLaserInput.js @@ -88,7 +88,6 @@ Script.include("/~/system/libraries/controllers.js"); {name: "hold", distance: DEFAULT_SEARCH_SPHERE_DISTANCE, path: holdPath} ]; - // triggered when stylus presses a web overlay/entity var HAPTIC_STYLUS_STRENGTH = 1.0; var HAPTIC_STYLUS_DURATION = 20.0; @@ -452,6 +451,7 @@ Script.include("/~/system/libraries/controllers.js"); posOffset: getGrabPointSphereOffset(this.handToController(), true), renderStates: renderStates, faceAvatar: true, + scaleWithAvatar: true, defaultRenderStates: defaultRenderStates }); } diff --git a/unpublishedScripts/marketplace/shapes/modules/laser.js b/unpublishedScripts/marketplace/shapes/modules/laser.js index 1efc38b65a..beefa8a2f4 100644 --- a/unpublishedScripts/marketplace/shapes/modules/laser.js +++ b/unpublishedScripts/marketplace/shapes/modules/laser.js @@ -150,6 +150,7 @@ Laser = function (side) { } function update(hand) { + return; var handPosition, handOrientation, deltaOrigin, From ee3900be4f7104841244222be95af1f9a7f22b04 Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Tue, 7 Nov 2017 18:26:41 -0700 Subject: [PATCH 09/34] Corrections --- interface/src/raypick/LaserPointer.cpp | 31 ++++++++++++------- interface/src/raypick/LaserPointer.h | 10 +++--- interface/src/raypick/LaserPointerManager.cpp | 4 +-- interface/src/raypick/LaserPointerManager.h | 2 +- .../LaserPointerScriptingInterface.cpp | 2 +- interface/src/ui/overlays/Line3DOverlay.h | 2 +- libraries/render-utils/src/GeometryCache.h | 2 +- .../marketplace/shapes/modules/laser.js | 1 - 8 files changed, 30 insertions(+), 24 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index af09e50cb6..ee0336438c 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -7,7 +7,7 @@ // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -//// +// #include "LaserPointer.h" #include "Application.h" @@ -15,7 +15,7 @@ #include "RayPickScriptingInterface.h" LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, - const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : + const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : _renderingEnabled(enabled), _renderStates(renderStates), _defaultRenderStates(defaultRenderStates), @@ -121,7 +121,8 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter glm::vec3 endVec; if (((defaultState || !_lockEnd) && _lockEndObject.id.isNull()) || type == IntersectionType::HUD) { endVec = pickRay.origin + pickRay.direction * distance; - } else { + } + else { if (!_lockEndObject.id.isNull()) { glm::vec3 pos; glm::quat rot; @@ -132,7 +133,8 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter rot = quatFromVariant(qApp->getOverlays().getProperty(_lockEndObject.id, "rotation").value); dim = vec3FromVariant(qApp->getOverlays().getProperty(_lockEndObject.id, "dimensions").value); registrationPoint = glm::vec3(0.5f); - } else { + } + else { EntityItemProperties props = DependencyManager::get()->getEntityProperties(_lockEndObject.id); glm::mat4 entityMat = createMatFromQuatAndPos(props.getRotation(), props.getPosition()); glm::mat4 finalPosAndRotMat = entityMat * _lockEndObject.offsetMat; @@ -143,17 +145,20 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter } const glm::vec3 DEFAULT_REGISTRATION_POINT = glm::vec3(0.5f); endVec = pos + rot * (dim * (DEFAULT_REGISTRATION_POINT - registrationPoint)); - } else { + } + else { if (type == IntersectionType::ENTITY) { endVec = DependencyManager::get()->getEntityTransform(objectID)[3]; - } else if (type == IntersectionType::OVERLAY) { + } + else if (type == IntersectionType::OVERLAY) { endVec = vec3FromVariant(qApp->getOverlays().getProperty(objectID, "position").value); - } else if (type == IntersectionType::AVATAR) { + } + else if (type == IntersectionType::AVATAR) { endVec = DependencyManager::get()->getAvatar(objectID)->getPosition(); } } } - + float avatarScale = DependencyManager::get()->getMyAvatar()->getAvatarScale(); QVariant end = vec3toVariant(endVec); @@ -180,7 +185,8 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter } if (_centerEndY) { endProps.insert("position", end); - } else { + } + else { glm::vec3 currentUpVector = faceAvatarRotation * Vectors::UP; endProps.insert("position", vec3toVariant(endVec + glm::vec3(currentUpVector.x * 0.5f * dim.y, currentUpVector.y * 0.5f * dim.y, currentUpVector.z * 0.5f * dim.y))); } @@ -221,13 +227,14 @@ void LaserPointer::update() { if (_renderingEnabled && !_currentRenderState.empty() && _renderStates.find(_currentRenderState) != _renderStates.end() && (prevRayPickResult.type != IntersectionType::NONE || _laserLength > 0.0f || !_lockEndObject.id.isNull())) { float distance = _laserLength > 0.0f ? _laserLength : prevRayPickResult.distance; - qDebug() << &_currentRenderState; updateRenderState(_renderStates[_currentRenderState], prevRayPickResult.type, distance, prevRayPickResult.objectID, prevRayPickResult.searchRay, false); disableRenderState(_defaultRenderStates[_currentRenderState].second); - } else if (_renderingEnabled && !_currentRenderState.empty() && _defaultRenderStates.find(_currentRenderState) != _defaultRenderStates.end()) { + } + else if (_renderingEnabled && !_currentRenderState.empty() && _defaultRenderStates.find(_currentRenderState) != _defaultRenderStates.end()) { disableRenderState(_renderStates[_currentRenderState]); updateRenderState(_defaultRenderStates[_currentRenderState].second, IntersectionType::NONE, _defaultRenderStates[_currentRenderState].first, QUuid(), prevRayPickResult.searchRay, true); - } else if (!_currentRenderState.empty()) { + } + else if (!_currentRenderState.empty()) { disableRenderState(_renderStates[_currentRenderState]); disableRenderState(_defaultRenderStates[_currentRenderState].second); } diff --git a/interface/src/raypick/LaserPointer.h b/interface/src/raypick/LaserPointer.h index e0c6f631c0..7d44194be4 100644 --- a/interface/src/raypick/LaserPointer.h +++ b/interface/src/raypick/LaserPointer.h @@ -22,9 +22,9 @@ class RayPickResult; struct LockEndObject { - QUuid id { QUuid() }; - bool isOverlay { false }; - glm::mat4 offsetMat { glm::mat4() }; + QUuid id{ QUuid() }; + bool isOverlay{ false }; + glm::mat4 offsetMat{ glm::mat4() }; }; class RenderState { @@ -89,8 +89,8 @@ public: private: bool _renderingEnabled; - float _laserLength { 0.0f }; - std::string _currentRenderState { "" }; + float _laserLength{ 0.0f }; + std::string _currentRenderState{ "" }; RenderStateMap _renderStates; DefaultRenderStateMap _defaultRenderStates; bool _faceAvatar; diff --git a/interface/src/raypick/LaserPointerManager.cpp b/interface/src/raypick/LaserPointerManager.cpp index 143451d0d3..868491f166 100644 --- a/interface/src/raypick/LaserPointerManager.cpp +++ b/interface/src/raypick/LaserPointerManager.cpp @@ -113,9 +113,9 @@ void LaserPointerManager::setIncludeItems(const QUuid& uid, const QVector } } -void LaserPointerManager::setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay, const glm::mat4& offsetMat) const { +void LaserPointerManager::setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay) const { auto laserPointer = find(uid); if (laserPointer) { - laserPointer->setLockEndUUID(objectID, isOverlay, offsetMat); + laserPointer->setLockEndUUID(objectID, isOverlay); } } diff --git a/interface/src/raypick/LaserPointerManager.h b/interface/src/raypick/LaserPointerManager.h index 3f8f962679..9283b7ac89 100644 --- a/interface/src/raypick/LaserPointerManager.h +++ b/interface/src/raypick/LaserPointerManager.h @@ -39,7 +39,7 @@ public: void setIgnoreItems(const QUuid& uid, const QVector& ignoreEntities) const; void setIncludeItems(const QUuid& uid, const QVector& includeEntities) const; - void setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay, const glm::mat4& offsetMat = glm::mat4()) const; + void setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay) const; void update(); diff --git a/interface/src/raypick/LaserPointerScriptingInterface.cpp b/interface/src/raypick/LaserPointerScriptingInterface.cpp index a47605fa1f..eb69d610ad 100644 --- a/interface/src/raypick/LaserPointerScriptingInterface.cpp +++ b/interface/src/raypick/LaserPointerScriptingInterface.cpp @@ -7,7 +7,7 @@ // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -//// +// #include "LaserPointerScriptingInterface.h" diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index 250d823598..39e6436683 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -74,7 +74,7 @@ private: float _glow { 0.0 }; float _glowWidth { 0.0 }; - float _glowScale{ 1.0 }; + float _glowScale { 1.0 }; int _geometryCacheID; }; diff --git a/libraries/render-utils/src/GeometryCache.h b/libraries/render-utils/src/GeometryCache.h index 862331b743..a325026914 100644 --- a/libraries/render-utils/src/GeometryCache.h +++ b/libraries/render-utils/src/GeometryCache.h @@ -248,7 +248,7 @@ public: renderWireCubeInstance(args, batch, glm::vec4(color, 1.0f), pipeline); } - // //Dynamic geometry + // Dynamic geometry void renderShape(gpu::Batch& batch, Shape shape); void renderWireShape(gpu::Batch& batch, Shape shape); size_t getShapeTriangleCount(Shape shape); diff --git a/unpublishedScripts/marketplace/shapes/modules/laser.js b/unpublishedScripts/marketplace/shapes/modules/laser.js index beefa8a2f4..1efc38b65a 100644 --- a/unpublishedScripts/marketplace/shapes/modules/laser.js +++ b/unpublishedScripts/marketplace/shapes/modules/laser.js @@ -150,7 +150,6 @@ Laser = function (side) { } function update(hand) { - return; var handPosition, handOrientation, deltaOrigin, From 536bf6f81d5e763cd4bde37bf08ec4571a655fdb Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Tue, 7 Nov 2017 18:34:33 -0700 Subject: [PATCH 10/34] Corrections --- interface/src/raypick/LaserPointer.cpp | 26 +++++++++----------------- interface/src/raypick/LaserPointer.h | 10 +++++----- 2 files changed, 14 insertions(+), 22 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index ee0336438c..5f2549deea 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -15,7 +15,7 @@ #include "RayPickScriptingInterface.h" LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, - const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : + const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : _renderingEnabled(enabled), _renderStates(renderStates), _defaultRenderStates(defaultRenderStates), @@ -121,8 +121,7 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter glm::vec3 endVec; if (((defaultState || !_lockEnd) && _lockEndObject.id.isNull()) || type == IntersectionType::HUD) { endVec = pickRay.origin + pickRay.direction * distance; - } - else { + } else { if (!_lockEndObject.id.isNull()) { glm::vec3 pos; glm::quat rot; @@ -133,8 +132,7 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter rot = quatFromVariant(qApp->getOverlays().getProperty(_lockEndObject.id, "rotation").value); dim = vec3FromVariant(qApp->getOverlays().getProperty(_lockEndObject.id, "dimensions").value); registrationPoint = glm::vec3(0.5f); - } - else { + } else { EntityItemProperties props = DependencyManager::get()->getEntityProperties(_lockEndObject.id); glm::mat4 entityMat = createMatFromQuatAndPos(props.getRotation(), props.getPosition()); glm::mat4 finalPosAndRotMat = entityMat * _lockEndObject.offsetMat; @@ -145,15 +143,12 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter } const glm::vec3 DEFAULT_REGISTRATION_POINT = glm::vec3(0.5f); endVec = pos + rot * (dim * (DEFAULT_REGISTRATION_POINT - registrationPoint)); - } - else { + } else { if (type == IntersectionType::ENTITY) { endVec = DependencyManager::get()->getEntityTransform(objectID)[3]; - } - else if (type == IntersectionType::OVERLAY) { + } else if (type == IntersectionType::OVERLAY) { endVec = vec3FromVariant(qApp->getOverlays().getProperty(objectID, "position").value); - } - else if (type == IntersectionType::AVATAR) { + } else if (type == IntersectionType::AVATAR) { endVec = DependencyManager::get()->getAvatar(objectID)->getPosition(); } } @@ -185,8 +180,7 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter } if (_centerEndY) { endProps.insert("position", end); - } - else { + } else { glm::vec3 currentUpVector = faceAvatarRotation * Vectors::UP; endProps.insert("position", vec3toVariant(endVec + glm::vec3(currentUpVector.x * 0.5f * dim.y, currentUpVector.y * 0.5f * dim.y, currentUpVector.z * 0.5f * dim.y))); } @@ -229,12 +223,10 @@ void LaserPointer::update() { float distance = _laserLength > 0.0f ? _laserLength : prevRayPickResult.distance; updateRenderState(_renderStates[_currentRenderState], prevRayPickResult.type, distance, prevRayPickResult.objectID, prevRayPickResult.searchRay, false); disableRenderState(_defaultRenderStates[_currentRenderState].second); - } - else if (_renderingEnabled && !_currentRenderState.empty() && _defaultRenderStates.find(_currentRenderState) != _defaultRenderStates.end()) { + } else if (_renderingEnabled && !_currentRenderState.empty() && _defaultRenderStates.find(_currentRenderState) != _defaultRenderStates.end()) { disableRenderState(_renderStates[_currentRenderState]); updateRenderState(_defaultRenderStates[_currentRenderState].second, IntersectionType::NONE, _defaultRenderStates[_currentRenderState].first, QUuid(), prevRayPickResult.searchRay, true); - } - else if (!_currentRenderState.empty()) { + } else if (!_currentRenderState.empty()) { disableRenderState(_renderStates[_currentRenderState]); disableRenderState(_defaultRenderStates[_currentRenderState].second); } diff --git a/interface/src/raypick/LaserPointer.h b/interface/src/raypick/LaserPointer.h index 7d44194be4..e0c6f631c0 100644 --- a/interface/src/raypick/LaserPointer.h +++ b/interface/src/raypick/LaserPointer.h @@ -22,9 +22,9 @@ class RayPickResult; struct LockEndObject { - QUuid id{ QUuid() }; - bool isOverlay{ false }; - glm::mat4 offsetMat{ glm::mat4() }; + QUuid id { QUuid() }; + bool isOverlay { false }; + glm::mat4 offsetMat { glm::mat4() }; }; class RenderState { @@ -89,8 +89,8 @@ public: private: bool _renderingEnabled; - float _laserLength{ 0.0f }; - std::string _currentRenderState{ "" }; + float _laserLength { 0.0f }; + std::string _currentRenderState { "" }; RenderStateMap _renderStates; DefaultRenderStateMap _defaultRenderStates; bool _faceAvatar; From 8c5f97f3d10d4af6d86fb1d9c550c797eb2e03ea Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Tue, 7 Nov 2017 20:25:24 -0700 Subject: [PATCH 11/34] More corrections --- interface/src/raypick/LaserPointerManager.cpp | 4 ++-- interface/src/raypick/LaserPointerManager.h | 2 +- interface/src/ui/overlays/Line3DOverlay.cpp | 1 - 3 files changed, 3 insertions(+), 4 deletions(-) diff --git a/interface/src/raypick/LaserPointerManager.cpp b/interface/src/raypick/LaserPointerManager.cpp index 868491f166..143451d0d3 100644 --- a/interface/src/raypick/LaserPointerManager.cpp +++ b/interface/src/raypick/LaserPointerManager.cpp @@ -113,9 +113,9 @@ void LaserPointerManager::setIncludeItems(const QUuid& uid, const QVector } } -void LaserPointerManager::setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay) const { +void LaserPointerManager::setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay, const glm::mat4& offsetMat) const { auto laserPointer = find(uid); if (laserPointer) { - laserPointer->setLockEndUUID(objectID, isOverlay); + laserPointer->setLockEndUUID(objectID, isOverlay, offsetMat); } } diff --git a/interface/src/raypick/LaserPointerManager.h b/interface/src/raypick/LaserPointerManager.h index 9283b7ac89..3f8f962679 100644 --- a/interface/src/raypick/LaserPointerManager.h +++ b/interface/src/raypick/LaserPointerManager.h @@ -39,7 +39,7 @@ public: void setIgnoreItems(const QUuid& uid, const QVector& ignoreEntities) const; void setIncludeItems(const QUuid& uid, const QVector& includeEntities) const; - void setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay) const; + void setLockEndUUID(const QUuid& uid, const QUuid& objectID, const bool isOverlay, const glm::mat4& offsetMat = glm::mat4()) const; void update(); diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index 7ac79f081a..0dc8fddd04 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -12,7 +12,6 @@ #include #include -#include #include "AbstractViewStateInterface.h" From 1791ed01ca050d9c9ff505610a12c7b8871c9d07 Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Wed, 8 Nov 2017 18:35:26 -0700 Subject: [PATCH 12/34] add width param to vertex shader --- interface/src/raypick/LaserPointer.cpp | 11 ++++++----- interface/src/ui/overlays/Line3DOverlay.cpp | 10 +--------- interface/src/ui/overlays/Line3DOverlay.h | 3 --- libraries/render-utils/src/GeometryCache.cpp | 6 +++--- libraries/render-utils/src/GeometryCache.h | 4 ++-- libraries/render-utils/src/glowLine.slf | 3 +-- libraries/render-utils/src/glowLine.slv | 6 ++---- 7 files changed, 15 insertions(+), 28 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index 5f2549deea..14af9b336f 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -14,6 +14,8 @@ #include "avatar/AvatarManager.h" #include "RayPickScriptingInterface.h" +static const float DEFAULT_LASER_POINTER_SIZE = 0.02f; + LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : _renderingEnabled(enabled), @@ -163,11 +165,10 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter pathProps.insert("end", end); pathProps.insert("visible", true); pathProps.insert("ignoreRayIntersection", renderState.doesPathIgnoreRays()); - if (_scaleWithAvatar) { - auto glowScaleProp = qApp->getOverlays().getProperty(renderState.getPathID(), "glowScale").value; - float glowScale = glowScaleProp.isValid() ? avatarScale * glowScaleProp.toFloat() : avatarScale; - pathProps.insert("glowScale", glowScale); - } + + float glowWidth = _scaleWithAvatar ? DEFAULT_LASER_POINTER_SIZE * avatarScale : DEFAULT_LASER_POINTER_SIZE; + pathProps.insert("glowWidth", glowWidth); + qApp->getOverlays().editOverlay(renderState.getPathID(), pathProps); } if (!renderState.getEndID().isNull()) { diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index 0dc8fddd04..82a3c46727 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -35,7 +35,6 @@ Line3DOverlay::Line3DOverlay(const Line3DOverlay* line3DOverlay) : _endParentJointIndex = line3DOverlay->getEndJointIndex(); _glow = line3DOverlay->getGlow(); _glowWidth = line3DOverlay->getGlowWidth(); - _glowScale = line3DOverlay->getGlowScale(); } Line3DOverlay::~Line3DOverlay() { @@ -146,7 +145,7 @@ void Line3DOverlay::render(RenderArgs* args) { geometryCache->renderDashedLine(*batch, start, end, colorv4, _geometryCacheID); } else { // renderGlowLine handles both glow = 0 and glow > 0 cases - geometryCache->renderGlowLine(*batch, start, end, colorv4, _glow, _glowWidth, _glowScale, _geometryCacheID); + geometryCache->renderGlowLine(*batch, start, end, colorv4, _glow, _glowWidth, _geometryCacheID); } } } @@ -244,13 +243,6 @@ void Line3DOverlay::setProperties(const QVariantMap& originalProperties) { if (glowWidth.isValid()) { setGlowWidth(glowWidth.toFloat()); } - - auto glowScale = properties["glowScale"]; - if (glowScale.isValid()) { - float gscale = glowScale.toFloat(); - setGlowScale(gscale); - } - } QVariant Line3DOverlay::getProperty(const QString& property) { diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index 39e6436683..bcb65b1f1e 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -33,7 +33,6 @@ public: glm::vec3 getEnd() const; const float& getGlow() const { return _glow; } const float& getGlowWidth() const { return _glowWidth; } - const float& getGlowScale() const { return _glowScale; } // setters void setStart(const glm::vec3& start); @@ -44,7 +43,6 @@ public: void setGlow(const float& glow) { _glow = glow; } void setGlowWidth(const float& glowWidth) { _glowWidth = glowWidth; } - void setGlowScale(const float& glowScale) { _glowScale = glowScale; } void setProperties(const QVariantMap& properties) override; QVariant getProperty(const QString& property) override; @@ -74,7 +72,6 @@ private: float _glow { 0.0 }; float _glowWidth { 0.0 }; - float _glowScale { 1.0 }; int _geometryCacheID; }; diff --git a/libraries/render-utils/src/GeometryCache.cpp b/libraries/render-utils/src/GeometryCache.cpp index 90b3ca402d..ebf0f13d97 100644 --- a/libraries/render-utils/src/GeometryCache.cpp +++ b/libraries/render-utils/src/GeometryCache.cpp @@ -1868,7 +1868,7 @@ void GeometryCache::renderLine(gpu::Batch& batch, const glm::vec2& p1, const glm void GeometryCache::renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const glm::vec3& p2, - const glm::vec4& color, float glowIntensity, float glowWidth, float glowScale, int id) { + const glm::vec4& color, float glowIntensity, float glowWidth, int id) { // Disable glow lines on OSX #ifndef Q_OS_WIN @@ -1931,10 +1931,10 @@ void GeometryCache::renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const vec4 p1; vec4 p2; vec4 color; - float scale; + float width; }; - LineData lineData { vec4(p1, 1.0f), vec4(p2, 1.0f), color, glowScale }; + LineData lineData { vec4(p1, 1.0f), vec4(p2, 1.0f), color, glowWidth }; details.uniformBuffer->resize(sizeof(LineData)); details.uniformBuffer->setSubData(0, lineData); } diff --git a/libraries/render-utils/src/GeometryCache.h b/libraries/render-utils/src/GeometryCache.h index a325026914..cd8c43f1df 100644 --- a/libraries/render-utils/src/GeometryCache.h +++ b/libraries/render-utils/src/GeometryCache.h @@ -314,10 +314,10 @@ public: const glm::vec4& color1, const glm::vec4& color2, int id); void renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const glm::vec3& p2, - const glm::vec4& color, float glowIntensity, float glowWidth, float glowScale, int id); + const glm::vec4& color, float glowIntensity, float glowWidth, int id); void renderGlowLine(gpu::Batch& batch, const glm::vec3& p1, const glm::vec3& p2, const glm::vec4& color, int id) - { renderGlowLine(batch, p1, p2, color, 1.0f, 0.05f, 1.0f, id); } + { renderGlowLine(batch, p1, p2, color, 1.0f, 0.05f, id); } void renderDashedLine(gpu::Batch& batch, const glm::vec3& start, const glm::vec3& end, const glm::vec4& color, int id) { renderDashedLine(batch, start, end, color, 0.05f, 0.025f, id); } diff --git a/libraries/render-utils/src/glowLine.slf b/libraries/render-utils/src/glowLine.slf index be1c6842e3..6a7a6157a4 100644 --- a/libraries/render-utils/src/glowLine.slf +++ b/libraries/render-utils/src/glowLine.slf @@ -10,7 +10,6 @@ // in vec4 _color; -in float _scale; in float distanceFromCenter; out vec4 _fragColor; @@ -22,7 +21,7 @@ void main(void) { float alpha = 1.0 - abs(distanceFromCenter); // Convert from a linear alpha curve to a sharp peaked one - alpha = _color.a * pow(alpha, 10.0/_scale); + alpha = _color.a * pow(alpha, 10.0); // Drop everything where the curve falls off to nearly nothing if (alpha <= 0.05) { diff --git a/libraries/render-utils/src/glowLine.slv b/libraries/render-utils/src/glowLine.slv index 7b69943b7a..4532ed7b9f 100644 --- a/libraries/render-utils/src/glowLine.slv +++ b/libraries/render-utils/src/glowLine.slv @@ -16,17 +16,15 @@ layout(std140) uniform lineData { vec4 p1; vec4 p2; vec4 color; - float scale; + float width; }; out vec4 _color; -out float _scale; // the distance from the center in 'quad space' out float distanceFromCenter; void main(void) { _color = color; - _scale = scale; TransformCamera cam = getTransformCamera(); TransformObject obj = getTransformObject(); @@ -42,7 +40,7 @@ void main(void) { // Find the vector from the eye to one of the points vec3 v2 = normalize(p1eye.xyz); // The orthogonal vector is the cross product of these two - vec3 orthogonal = cross(v1, v2) * 0.02; + vec3 orthogonal = cross(v1, v2) * width; // Deteremine which end to emit based on the vertex id (even / odd) vec4 eye = (0 == gl_VertexID % 2) ? p1eye : p2eye; From 7dfdc8da59fc80f006dd0dfba683259d2a0c03fd Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Thu, 9 Nov 2017 17:50:38 -0700 Subject: [PATCH 13/34] Redesign and clean of unused lineWidths --- interface/src/raypick/LaserPointer.cpp | 12 ++++++++---- interface/src/raypick/LaserPointer.h | 4 ++++ interface/src/ui/overlays/Base3DOverlay.cpp | 12 ------------ interface/src/ui/overlays/Base3DOverlay.h | 3 --- interface/src/ui/overlays/Line3DOverlay.cpp | 15 +++++++++------ interface/src/ui/overlays/Line3DOverlay.h | 8 +++++--- .../tests/performance/rayPickPerformance.js | 1 - scripts/system/chat.js | 3 +-- .../controllerModules/farActionGrabEntity.js | 3 --- .../controllerModules/farTrigger.js | 3 --- .../controllerModules/hudOverlayPointer.js | 3 --- .../controllerModules/inEditMode.js | 3 --- .../controllerModules/overlayLaserInput.js | 3 --- .../controllerModules/webEntityLaserInput.js | 3 --- .../system/libraries/entitySelectionTool.js | 19 ++----------------- scripts/system/pal.js | 1 - scripts/tutorials/entity_scripts/pistol.js | 3 +-- .../DomainContent/Toybox/bow/bow.js | 2 -- .../DomainContent/Toybox/bow/createBow.js | 1 - .../DomainContent/Toybox/hiddenEntityReset.js | 1 - .../DomainContent/Toybox/masterReset.js | 1 - .../DomainContent/Toybox/pistol/pistol.js | 3 +-- unpublishedScripts/marketplace/bow/bow.js | 2 -- .../marketplace/laser/laserPointerApp.js | 1 - .../marketplace/shapes/modules/laser.js | 1 - .../marketplace/shortbow/bow/bow.js | 2 -- 26 files changed, 31 insertions(+), 82 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index 14af9b336f..4ef5613b79 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -97,6 +97,10 @@ void LaserPointer::editRenderState(const std::string& state, const QVariant& sta if (endDim.isValid()) { _renderStates[state].setEndDim(vec3FromVariant(endDim)); } + QVariant lineWidth = pathProps.toMap()["lineWidth"]; + if (lineWidth.isValid()) { + _renderStates[state].setLineWidth(lineWidth.toFloat()); + } }); } @@ -165,10 +169,9 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter pathProps.insert("end", end); pathProps.insert("visible", true); pathProps.insert("ignoreRayIntersection", renderState.doesPathIgnoreRays()); - - float glowWidth = _scaleWithAvatar ? DEFAULT_LASER_POINTER_SIZE * avatarScale : DEFAULT_LASER_POINTER_SIZE; - pathProps.insert("glowWidth", glowWidth); - + if (_scaleWithAvatar) { + pathProps.insert("lineWidth", renderState.getLineWidth() * avatarScale); + } qApp->getOverlays().editOverlay(renderState.getPathID(), pathProps); } if (!renderState.getEndID().isNull()) { @@ -268,6 +271,7 @@ RenderState::RenderState(const OverlayID& startID, const OverlayID& pathID, cons } if (!_pathID.isNull()) { _pathIgnoreRays = qApp->getOverlays().getProperty(_pathID, "ignoreRayIntersection").value.toBool(); + _lineWidth = qApp->getOverlays().getProperty(_pathID, "lineWidth").value.toFloat(); } if (!_endID.isNull()) { _endDim = vec3FromVariant(qApp->getOverlays().getProperty(_endID, "dimensions").value); diff --git a/interface/src/raypick/LaserPointer.h b/interface/src/raypick/LaserPointer.h index e0c6f631c0..d38070c05c 100644 --- a/interface/src/raypick/LaserPointer.h +++ b/interface/src/raypick/LaserPointer.h @@ -43,6 +43,9 @@ public: void setEndDim(const glm::vec3& endDim) { _endDim = endDim; } const glm::vec3& getEndDim() const { return _endDim; } + void setLineWidth(const float& lineWidth) { _lineWidth = lineWidth; } + const float& getLineWidth() const { return _lineWidth; } + void deleteOverlays(); private: @@ -54,6 +57,7 @@ private: bool _endIgnoreRays; glm::vec3 _endDim; + float _lineWidth; }; diff --git a/interface/src/ui/overlays/Base3DOverlay.cpp b/interface/src/ui/overlays/Base3DOverlay.cpp index 42425932df..a2f400900e 100644 --- a/interface/src/ui/overlays/Base3DOverlay.cpp +++ b/interface/src/ui/overlays/Base3DOverlay.cpp @@ -16,13 +16,11 @@ #include "Application.h" -const float DEFAULT_LINE_WIDTH = 1.0f; const bool DEFAULT_IS_SOLID = false; const bool DEFAULT_IS_DASHED_LINE = false; Base3DOverlay::Base3DOverlay() : SpatiallyNestable(NestableType::Overlay, QUuid::createUuid()), - _lineWidth(DEFAULT_LINE_WIDTH), _isSolid(DEFAULT_IS_SOLID), _isDashedLine(DEFAULT_IS_DASHED_LINE), _ignoreRayIntersection(false), @@ -34,7 +32,6 @@ Base3DOverlay::Base3DOverlay() : Base3DOverlay::Base3DOverlay(const Base3DOverlay* base3DOverlay) : Overlay(base3DOverlay), SpatiallyNestable(NestableType::Overlay, QUuid::createUuid()), - _lineWidth(base3DOverlay->_lineWidth), _isSolid(base3DOverlay->_isSolid), _isDashedLine(base3DOverlay->_isDashedLine), _ignoreRayIntersection(base3DOverlay->_ignoreRayIntersection), @@ -153,12 +150,6 @@ void Base3DOverlay::setProperties(const QVariantMap& originalProperties) { setLocalOrientation(quatFromVariant(properties["orientation"])); needRenderItemUpdate = true; } - - if (properties["lineWidth"].isValid()) { - setLineWidth(properties["lineWidth"].toFloat()); - needRenderItemUpdate = true; - } - if (properties["isSolid"].isValid()) { setIsSolid(properties["isSolid"].toBool()); } @@ -225,9 +216,6 @@ QVariant Base3DOverlay::getProperty(const QString& property) { if (property == "localRotation" || property == "localOrientation") { return quatToVariant(getLocalOrientation()); } - if (property == "lineWidth") { - return _lineWidth; - } if (property == "isSolid" || property == "isFilled" || property == "solid" || property == "filed") { return _isSolid; } diff --git a/interface/src/ui/overlays/Base3DOverlay.h b/interface/src/ui/overlays/Base3DOverlay.h index 436cfbf97b..0c73214259 100644 --- a/interface/src/ui/overlays/Base3DOverlay.h +++ b/interface/src/ui/overlays/Base3DOverlay.h @@ -35,7 +35,6 @@ public: // TODO: consider implementing registration points in this class glm::vec3 getCenter() const { return getPosition(); } - float getLineWidth() const { return _lineWidth; } bool getIsSolid() const { return _isSolid; } bool getIsDashedLine() const { return _isDashedLine; } bool getIsSolidLine() const { return !_isDashedLine; } @@ -44,7 +43,6 @@ public: bool getDrawHUDLayer() const { return _drawHUDLayer; } bool getIsGrabbable() const { return _isGrabbable; } - void setLineWidth(float lineWidth) { _lineWidth = lineWidth; } void setIsSolid(bool isSolid) { _isSolid = isSolid; } void setIsDashedLine(bool isDashedLine) { _isDashedLine = isDashedLine; } void setIgnoreRayIntersection(bool value) { _ignoreRayIntersection = value; } @@ -80,7 +78,6 @@ protected: virtual void setRenderTransform(const Transform& transform); const Transform& getRenderTransform() const { return _renderTransform; } - float _lineWidth; bool _isSolid; bool _isDashedLine; bool _ignoreRayIntersection; diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index 82a3c46727..c3d9de859c 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -6,7 +6,7 @@ // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -// +//// #include "Line3DOverlay.h" @@ -33,8 +33,8 @@ Line3DOverlay::Line3DOverlay(const Line3DOverlay* line3DOverlay) : _length = line3DOverlay->getLength(); _endParentID = line3DOverlay->getEndParentID(); _endParentJointIndex = line3DOverlay->getEndJointIndex(); + _lineWidth = line3DOverlay->getLineWidth(); _glow = line3DOverlay->getGlow(); - _glowWidth = line3DOverlay->getGlowWidth(); } Line3DOverlay::~Line3DOverlay() { @@ -145,7 +145,7 @@ void Line3DOverlay::render(RenderArgs* args) { geometryCache->renderDashedLine(*batch, start, end, colorv4, _geometryCacheID); } else { // renderGlowLine handles both glow = 0 and glow > 0 cases - geometryCache->renderGlowLine(*batch, start, end, colorv4, _glow, _glowWidth, _geometryCacheID); + geometryCache->renderGlowLine(*batch, start, end, colorv4, _glow, _lineWidth, _geometryCacheID); } } } @@ -239,9 +239,9 @@ void Line3DOverlay::setProperties(const QVariantMap& originalProperties) { } } - auto glowWidth = properties["glowWidth"]; - if (glowWidth.isValid()) { - setGlowWidth(glowWidth.toFloat()); + auto lineWidth = properties["lineWidth"]; + if (lineWidth.isValid()) { + setLineWidth(lineWidth.toFloat()); } } @@ -261,6 +261,9 @@ QVariant Line3DOverlay::getProperty(const QString& property) { if (property == "length") { return QVariant(getLength()); } + if (property == "lineWidth") { + return _lineWidth; + } return Base3DOverlay::getProperty(property); } diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index bcb65b1f1e..2a3c7caa99 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -13,6 +13,8 @@ #include "Base3DOverlay.h" +static const float DEFAULT_LINE_WIDTH = 0.02f; + class Line3DOverlay : public Base3DOverlay { Q_OBJECT using Parent = Base3DOverlay; @@ -31,8 +33,8 @@ public: // getters glm::vec3 getStart() const; glm::vec3 getEnd() const; + const float& getLineWidth() const { return _lineWidth; } const float& getGlow() const { return _glow; } - const float& getGlowWidth() const { return _glowWidth; } // setters void setStart(const glm::vec3& start); @@ -41,8 +43,8 @@ public: void setLocalStart(const glm::vec3& localStart) { setLocalPosition(localStart); } void setLocalEnd(const glm::vec3& localEnd); + void setLineWidth(const float& lineWidth) { _lineWidth = lineWidth; } void setGlow(const float& glow) { _glow = glow; } - void setGlowWidth(const float& glowWidth) { _glowWidth = glowWidth; } void setProperties(const QVariantMap& properties) override; QVariant getProperty(const QString& property) override; @@ -70,8 +72,8 @@ private: glm::vec3 _direction; // in parent frame float _length { 1.0 }; // in parent frame + float _lineWidth { DEFAULT_LINE_WIDTH }; float _glow { 0.0 }; - float _glowWidth { 0.0 }; int _geometryCacheID; }; diff --git a/scripts/developer/tests/performance/rayPickPerformance.js b/scripts/developer/tests/performance/rayPickPerformance.js index b4faf4c1be..92d12c0e71 100644 --- a/scripts/developer/tests/performance/rayPickPerformance.js +++ b/scripts/developer/tests/performance/rayPickPerformance.js @@ -96,7 +96,6 @@ function rayCastTest() { color: color, alpha: 1, visible: visible, - lineWidth: 2, start: origin, end: Vec3.sum(origin,Vec3.multiply(5,direction)) }); diff --git a/scripts/system/chat.js b/scripts/system/chat.js index fa997e20cc..0cb414e23c 100644 --- a/scripts/system/chat.js +++ b/scripts/system/chat.js @@ -284,8 +284,7 @@ endParentJointIndex: yourJointIndex, end: yourJointPosition, color: identifyAvatarLineColor, - alpha: 1, - lineWidth: 1 + alpha: 1 }; avatarIdentifiers[yourAvatarID] = identifierParams; diff --git a/scripts/system/controllers/controllerModules/farActionGrabEntity.js b/scripts/system/controllers/controllerModules/farActionGrabEntity.js index 0b00cfa303..8139302dfe 100644 --- a/scripts/system/controllers/controllerModules/farActionGrabEntity.js +++ b/scripts/system/controllers/controllerModules/farActionGrabEntity.js @@ -33,7 +33,6 @@ Script.include("/~/system/libraries/Xform.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -55,7 +54,6 @@ Script.include("/~/system/libraries/Xform.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -77,7 +75,6 @@ Script.include("/~/system/libraries/Xform.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID diff --git a/scripts/system/controllers/controllerModules/farTrigger.js b/scripts/system/controllers/controllerModules/farTrigger.js index ab950cbbdf..9c72c3df4d 100644 --- a/scripts/system/controllers/controllerModules/farTrigger.js +++ b/scripts/system/controllers/controllerModules/farTrigger.js @@ -25,7 +25,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -47,7 +46,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -69,7 +67,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID diff --git a/scripts/system/controllers/controllerModules/hudOverlayPointer.js b/scripts/system/controllers/controllerModules/hudOverlayPointer.js index 23802893a8..acddcaf246 100644 --- a/scripts/system/controllers/controllerModules/hudOverlayPointer.js +++ b/scripts/system/controllers/controllerModules/hudOverlayPointer.js @@ -31,7 +31,6 @@ alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawHUDLayer: true, parentID: MyAvatar.SELF_ID @@ -53,7 +52,6 @@ alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawHUDLayer: true, parentID: MyAvatar.SELF_ID @@ -75,7 +73,6 @@ alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawHUDLayer: true, parentID: MyAvatar.SELF_ID diff --git a/scripts/system/controllers/controllerModules/inEditMode.js b/scripts/system/controllers/controllerModules/inEditMode.js index 4520a91d74..94233376c7 100644 --- a/scripts/system/controllers/controllerModules/inEditMode.js +++ b/scripts/system/controllers/controllerModules/inEditMode.js @@ -27,7 +27,6 @@ Script.include("/~/system/libraries/utils.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -49,7 +48,6 @@ Script.include("/~/system/libraries/utils.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -71,7 +69,6 @@ Script.include("/~/system/libraries/utils.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID diff --git a/scripts/system/controllers/controllerModules/overlayLaserInput.js b/scripts/system/controllers/controllerModules/overlayLaserInput.js index e87e6e000a..2d27f160c1 100644 --- a/scripts/system/controllers/controllerModules/overlayLaserInput.js +++ b/scripts/system/controllers/controllerModules/overlayLaserInput.js @@ -26,7 +26,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -48,7 +47,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -70,7 +68,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID diff --git a/scripts/system/controllers/controllerModules/webEntityLaserInput.js b/scripts/system/controllers/controllerModules/webEntityLaserInput.js index eafe7c3462..36a36d38f3 100644 --- a/scripts/system/controllers/controllerModules/webEntityLaserInput.js +++ b/scripts/system/controllers/controllerModules/webEntityLaserInput.js @@ -26,7 +26,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -48,7 +47,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID @@ -70,7 +68,6 @@ Script.include("/~/system/libraries/controllers.js"); alpha: 1, solid: true, glow: 1.0, - lineWidth: 5, ignoreRayIntersection: true, // always ignore this drawInFront: true, // Even when burried inside of something, show it. parentID: MyAvatar.SELF_ID diff --git a/scripts/system/libraries/entitySelectionTool.js b/scripts/system/libraries/entitySelectionTool.js index 3a422bcb8a..d947a1d397 100644 --- a/scripts/system/libraries/entitySelectionTool.js +++ b/scripts/system/libraries/entitySelectionTool.js @@ -339,7 +339,6 @@ SelectionDisplay = (function() { solid: grabberSolid, visible: false, dashed: false, - lineWidth: grabberLineWidth, drawInFront: true, borderSize: 1.4 }; @@ -352,7 +351,6 @@ SelectionDisplay = (function() { solid: grabberSolid, visible: false, dashed: false, - lineWidth: grabberLineWidth, drawInFront: true, borderSize: 1.4 }; @@ -365,7 +363,6 @@ SelectionDisplay = (function() { solid: grabberSolid, visible: false, dashed: false, - lineWidth: grabberLineWidth, drawInFront: true, borderSize: 1.4 }; @@ -378,14 +375,12 @@ SelectionDisplay = (function() { solid: grabberSolid, visible: false, dashed: false, - lineWidth: grabberLineWidth, drawInFront: true, borderSize: 1.4 }; var spotLightLineProperties = { - color: lightOverlayColor, - lineWidth: 1.5 + color: lightOverlayColor }; var highlightBox = Overlays.addOverlay("cube", { @@ -400,7 +395,6 @@ SelectionDisplay = (function() { solid: false, visible: false, dashed: true, - lineWidth: 2.0, ignoreRayIntersection: true, // this never ray intersects drawInFront: true }); @@ -416,8 +410,7 @@ SelectionDisplay = (function() { alpha: 1, solid: false, visible: false, - dashed: false, - lineWidth: 1.0 + dashed: false }); var selectionBoxes = []; @@ -466,7 +459,6 @@ SelectionDisplay = (function() { // var normalLine = Overlays.addOverlay("line3d", { // visible: true, - // lineWidth: 2.0, // start: { x: 0, y: 0, z: 0 }, // end: { x: 0, y: 0, z: 0 }, // color: { red: 255, green: 255, blue: 0 }, @@ -656,7 +648,6 @@ SelectionDisplay = (function() { var xRailOverlay = Overlays.addOverlay("line3d", { visible: false, - lineWidth: 1.0, start: Vec3.ZERO, end: Vec3.ZERO, color: { @@ -668,7 +659,6 @@ SelectionDisplay = (function() { }); var yRailOverlay = Overlays.addOverlay("line3d", { visible: false, - lineWidth: 1.0, start: Vec3.ZERO, end: Vec3.ZERO, color: { @@ -680,7 +670,6 @@ SelectionDisplay = (function() { }); var zRailOverlay = Overlays.addOverlay("line3d", { visible: false, - lineWidth: 1.0, start: Vec3.ZERO, end: Vec3.ZERO, color: { @@ -693,7 +682,6 @@ SelectionDisplay = (function() { var rotateZeroOverlay = Overlays.addOverlay("line3d", { visible: false, - lineWidth: 2.0, start: Vec3.ZERO, end: Vec3.ZERO, color: { @@ -706,7 +694,6 @@ SelectionDisplay = (function() { var rotateCurrentOverlay = Overlays.addOverlay("line3d", { visible: false, - lineWidth: 2.0, start: Vec3.ZERO, end: Vec3.ZERO, color: { @@ -1788,7 +1775,6 @@ SelectionDisplay = (function() { y: distance, z: 1 }, - lineWidth: 1.5, rotation: rotation, visible: true }); @@ -1994,7 +1980,6 @@ SelectionDisplay = (function() { solid: false, visible: false, dashed: false, - lineWidth: 1.0, ignoreRayIntersection: true })); } diff --git a/scripts/system/pal.js b/scripts/system/pal.js index 44ff7c2acd..b5551cf596 100644 --- a/scripts/system/pal.js +++ b/scripts/system/pal.js @@ -189,7 +189,6 @@ function HighlightedEntity(id, entityProperties) { green: 0x91, blue: 0x29 }, - lineWidth: 1.0, ignoreRayIntersection: true, drawInFront: false // Arguable. For now, let's not distract with mysterious wires around the scene. }); diff --git a/scripts/tutorials/entity_scripts/pistol.js b/scripts/tutorials/entity_scripts/pistol.js index 1a570cc80f..62517f486d 100644 --- a/scripts/tutorials/entity_scripts/pistol.js +++ b/scripts/tutorials/entity_scripts/pistol.js @@ -350,8 +350,7 @@ end: ZERO_VECTOR, color: { red: 255, green: 0, blue: 0}, alpha: 1, - visible: true, - lineWidth: 2 + visible: true }); }, }; diff --git a/unpublishedScripts/DomainContent/Toybox/bow/bow.js b/unpublishedScripts/DomainContent/Toybox/bow/bow.js index 0c16bcbc7b..47335bcb6d 100644 --- a/unpublishedScripts/DomainContent/Toybox/bow/bow.js +++ b/unpublishedScripts/DomainContent/Toybox/bow/bow.js @@ -329,7 +329,6 @@ y: 0, z: 0 }, lineVectors[0]], - lineWidth: 5, color: this.stringData.currentColor }); @@ -339,7 +338,6 @@ y: 0, z: 0 }, lineVectors[1]], - lineWidth: 5, color: this.stringData.currentColor }); diff --git a/unpublishedScripts/DomainContent/Toybox/bow/createBow.js b/unpublishedScripts/DomainContent/Toybox/bow/createBow.js index f1ed9eb263..5a4275d96a 100644 --- a/unpublishedScripts/DomainContent/Toybox/bow/createBow.js +++ b/unpublishedScripts/DomainContent/Toybox/bow/createBow.js @@ -125,7 +125,6 @@ function createPreNotchString() { y: 0, z: 0 }, downOffset)], - lineWidth: 5, color: { red: 255, green: 255, diff --git a/unpublishedScripts/DomainContent/Toybox/hiddenEntityReset.js b/unpublishedScripts/DomainContent/Toybox/hiddenEntityReset.js index e2deec75ed..fe514f6dfc 100644 --- a/unpublishedScripts/DomainContent/Toybox/hiddenEntityReset.js +++ b/unpublishedScripts/DomainContent/Toybox/hiddenEntityReset.js @@ -450,7 +450,6 @@ y: 0, z: 0 }, downOffset)], - lineWidth: 5, color: { red: 255, green: 255, diff --git a/unpublishedScripts/DomainContent/Toybox/masterReset.js b/unpublishedScripts/DomainContent/Toybox/masterReset.js index 4ad9cce401..b621544621 100644 --- a/unpublishedScripts/DomainContent/Toybox/masterReset.js +++ b/unpublishedScripts/DomainContent/Toybox/masterReset.js @@ -427,7 +427,6 @@ MasterReset = function() { y: 0, z: 0 }, downOffset)], - lineWidth: 5, color: { red: 255, green: 255, diff --git a/unpublishedScripts/DomainContent/Toybox/pistol/pistol.js b/unpublishedScripts/DomainContent/Toybox/pistol/pistol.js index 5f57c6fc17..b408e4f464 100644 --- a/unpublishedScripts/DomainContent/Toybox/pistol/pistol.js +++ b/unpublishedScripts/DomainContent/Toybox/pistol/pistol.js @@ -346,8 +346,7 @@ end: { x: 0, y: 0, z: 0 }, color: COLORS.RED, alpha: 1, - visible: true, - lineWidth: 2 + visible: true }); }, }; diff --git a/unpublishedScripts/marketplace/bow/bow.js b/unpublishedScripts/marketplace/bow/bow.js index 818960e335..883eff113c 100644 --- a/unpublishedScripts/marketplace/bow/bow.js +++ b/unpublishedScripts/marketplace/bow/bow.js @@ -266,7 +266,6 @@ dimensions: { "x": 5, "y": 5, "z": 5 }, ignoreForCollisions: 1, linePoints: [ { "x": 0, "y": 0, "z": 0 }, { "x": 0, "y": -1.2, "z": 0 } ], - lineWidth: 5, name: STRING_NAME, parentID: this.entityID, localPosition: { "x": 0, "y": 0.6, "z": 0.1 }, @@ -287,7 +286,6 @@ resetStringToIdlePosition: function() { Entities.editEntity(this.stringID, { linePoints: [ { "x": 0, "y": 0, "z": 0 }, { "x": 0, "y": -1.2, "z": 0 } ], - lineWidth: 5, localPosition: { "x": 0, "y": 0.6, "z": 0.1 }, localRotation: { "w": 1, "x": 0, "y": 0, "z": 0 }, }); diff --git a/unpublishedScripts/marketplace/laser/laserPointerApp.js b/unpublishedScripts/marketplace/laser/laserPointerApp.js index 515a2c3a76..aa049ea470 100644 --- a/unpublishedScripts/marketplace/laser/laserPointerApp.js +++ b/unpublishedScripts/marketplace/laser/laserPointerApp.js @@ -99,7 +99,6 @@ lifetime: 360, type: 'Line', glow: 1.0, - lineWidth: 5, alpha: 0.5, ignoreRayIntersection: true, drawInFront: true, diff --git a/unpublishedScripts/marketplace/shapes/modules/laser.js b/unpublishedScripts/marketplace/shapes/modules/laser.js index 1efc38b65a..d5feda0e1f 100644 --- a/unpublishedScripts/marketplace/shapes/modules/laser.js +++ b/unpublishedScripts/marketplace/shapes/modules/laser.js @@ -72,7 +72,6 @@ Laser = function (side) { } laserLine = Overlays.addOverlay("line3d", { - lineWidth: 5, alpha: 1.0, glow: 1.0, ignoreRayIntersection: true, diff --git a/unpublishedScripts/marketplace/shortbow/bow/bow.js b/unpublishedScripts/marketplace/shortbow/bow/bow.js index a8e76f76fd..5134fb6fd8 100644 --- a/unpublishedScripts/marketplace/shortbow/bow/bow.js +++ b/unpublishedScripts/marketplace/shortbow/bow/bow.js @@ -408,7 +408,6 @@ function getControllerLocation(controllerHand) { dimensions: { "x": 5, "y": 5, "z": 5 }, ignoreForCollisions: 1, linePoints: [ { "x": 0, "y": 0, "z": 0 }, { "x": 0, "y": -1.2, "z": 0 } ], - lineWidth: 5, color: { red: 153, green: 102, blue: 51 }, name: STRING_NAME, parentID: this.entityID, @@ -430,7 +429,6 @@ function getControllerLocation(controllerHand) { resetStringToIdlePosition: function() { Entities.editEntity(this.stringID, { linePoints: [ { "x": 0, "y": 0, "z": 0 }, { "x": 0, "y": -1.2, "z": 0 } ], - lineWidth: 5, localPosition: { "x": 0, "y": 0.6, "z": 0.1 }, localRotation: { "w": 1, "x": 0, "y": 0, "z": 0 }, }); From 255a40ce3139868333d4b30a8c882e3f563f4b82 Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Thu, 9 Nov 2017 18:38:04 -0700 Subject: [PATCH 14/34] Corrections --- interface/src/raypick/LaserPointer.cpp | 2 -- interface/src/ui/overlays/Line3DOverlay.cpp | 2 +- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index 4ef5613b79..6d29154be0 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -14,8 +14,6 @@ #include "avatar/AvatarManager.h" #include "RayPickScriptingInterface.h" -static const float DEFAULT_LASER_POINTER_SIZE = 0.02f; - LaserPointer::LaserPointer(const QVariant& rayProps, const RenderStateMap& renderStates, const DefaultRenderStateMap& defaultRenderStates, const bool faceAvatar, const bool centerEndY, const bool lockEnd, const bool distanceScaleEnd, const bool scaleWithAvatar, const bool enabled) : _renderingEnabled(enabled), diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index c3d9de859c..a6b7242df2 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -6,7 +6,7 @@ // // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html -//// +// #include "Line3DOverlay.h" From a9fe3596cf4a8ab025e31a60e92faf49acabf6a3 Mon Sep 17 00:00:00 2001 From: beholder Date: Fri, 27 Oct 2017 20:39:43 +0300 Subject: [PATCH 15/34] 4684 Add collapse button on the virtual keyboard --- interface/resources/images/lowerKeyboard.png | Bin 0 -> 1053 bytes interface/resources/qml/controls-uit/Key.qml | 12 +- .../resources/qml/controls-uit/Keyboard.qml | 121 ++++++++++++++++-- libraries/ui/src/ui/OffscreenQmlSurface.cpp | 12 ++ libraries/ui/src/ui/OffscreenQmlSurface.h | 1 + 5 files changed, 125 insertions(+), 21 deletions(-) create mode 100644 interface/resources/images/lowerKeyboard.png diff --git a/interface/resources/images/lowerKeyboard.png b/interface/resources/images/lowerKeyboard.png new file mode 100644 index 0000000000000000000000000000000000000000..d379b028abf829efd35f3e78a7fb90db40636d5d GIT binary patch literal 1053 zcmV+&1mgRNP)tFHbFs&rYpO%1FH^loSdkut1DSVGXCX3uuo4szP~rIhvcBwXLM21Wip% zI668)XJ@A#85zO)`Z^8|4;43)fPcva1pD~-NM#Wj8L3lJQczo4i-LjzarMT=20T1G zpbQJTva%A{+1W@>PZyTP#>PMbW@l%yy1J@vZf=CR-%J4S%^4UNsEH#dCkGTYDJcoN zySw7(@$qrNb#QQ?l)t~fs2ULwp))cvke8Q-;^Jb2g@s{dWd$=cGeQLC>FKG#{=0I3 zV4agp&?97O<`eS0q5uEifhHiK|w)M%9cgU1|1z8 zEt~7=>cj;X7Z=#v+!XM=y}ejlTT@)mQutegmv?t}*96Mi)0#;w@f z+f(=V_d<@nW1oRr0IX180x}d55)x2fUoWBH=H^D$Fh4(!*49>Wg9$@9nByl)!9JO3 z=ZcC75r$w{v$QksM1}YF_eI_JGU^p@dj%~U5wP_!1_eLH|8{nE(9zL>fq?;rA=oAu zEZ-G~_9FQB_~@9J7&J6ApscJ+!iybtHhRMlETwh;*ScG?hzqGMsFXljXb+yo(}{@*QHRQK-&+Lm92XZC zn4YWi^YevBs?7hmpDl<9ZHQF2x3{l?%8`Km67ZJ5($90COFad1+}0?d|R25WXZCmL!hnefRiQ;P#iZ!iMQjRr!)?Y-|)& z=?q$)Dl(aA=a!ZhEH5uVx5uA;DE%1lw>kn-J~1&-*VNSTR{+!grY%Yv{A@CR#RY!= XNdg&R^>QXW00000NkvXXu0mjff;Z>0 literal 0 HcmV?d00001 diff --git a/interface/resources/qml/controls-uit/Key.qml b/interface/resources/qml/controls-uit/Key.qml index e54250c872..586a9c0225 100644 --- a/interface/resources/qml/controls-uit/Key.qml +++ b/interface/resources/qml/controls-uit/Key.qml @@ -5,6 +5,8 @@ Item { id: keyItem width: 45 height: 50 + + property int contentPadding: 4 property string glyph: "a" property bool toggle: false // does this button have the toggle behaivor? property bool toggled: false // is this button currently toggled? @@ -105,14 +107,8 @@ Item { color: "#121212" radius: 2 border.color: "#00000000" - anchors.right: parent.right - anchors.rightMargin: 4 - anchors.left: parent.left - anchors.leftMargin: 4 - anchors.bottom: parent.bottom - anchors.bottomMargin: 4 - anchors.top: parent.top - anchors.topMargin: 4 + anchors.fill: parent + anchors.margins: contentPadding } Text { diff --git a/interface/resources/qml/controls-uit/Keyboard.qml b/interface/resources/qml/controls-uit/Keyboard.qml index 66a61742c9..7f73538c19 100644 --- a/interface/resources/qml/controls-uit/Keyboard.qml +++ b/interface/resources/qml/controls-uit/Keyboard.qml @@ -8,7 +8,8 @@ // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // -import QtQuick 2.0 +import QtQuick 2.7 +import QtGraphicalEffects 1.0 import "." Rectangle { @@ -112,8 +113,6 @@ Rectangle { } Rectangle { - y: 0 - x: 0 height: showMirrorText ? mirrorTextHeight : 0 width: keyboardWidth color: "#252525" @@ -122,13 +121,18 @@ Rectangle { TextInput { id: mirrorText visible: showMirrorText - FontLoader { id: ralewaySemiBold; source: "../../fonts/Raleway-SemiBold.ttf"; } - font.family: ralewaySemiBold.name - font.pointSize: 13.5 + FontLoader { id: font; source: "../../fonts/FiraSans-Regular.ttf"; } + font.family: font.name + font.pixelSize: 20 verticalAlignment: Text.AlignVCenter - horizontalAlignment: Text.AlignHCenter - color: "#FFFFFF"; - anchors.fill: parent + horizontalAlignment: Text.AlignLeft + color: "#00B4EF"; + anchors.left: parent.left + anchors.leftMargin: 10 + anchors.right: lowerKeyboard.left + anchors.top: parent.top + anchors.bottom: parent.bottom + wrapMode: Text.WordWrap readOnly: false // we need this to allow control to accept QKeyEvent selectByMouse: false @@ -140,16 +144,107 @@ Rectangle { event.accepted = true; } } + + MouseArea { // ... and we need this mouse area to prevent mirrorText from getting mouse events to ensure it will never get focus + anchors.fill: parent + } } - MouseArea { // ... and we need this mouse area to prevent mirrorText from getting mouse events to ensure it will never get focus - anchors.fill: parent + Item { + id: lowerKeyboard + anchors.right: parent.right + anchors.rightMargin: keyboardRect.width - (key_Backspace.x + key_Backspace.width + key_Backspace.contentPadding) + width: key_Backspace.width * 2 + height: parent.height + + Rectangle { + id: roundedRect + color: "#121212" + radius: 6 + border.color: "#00000000" + anchors.fill: parent + anchors.margins: 4 + + MouseArea { + id: mouseArea + anchors.fill: parent + hoverEnabled: true + + onClicked: { + webEntity.lowerKeyboard(); + } + + onEntered: { + roundedRect.state = "mouseOver"; + } + + onExited: { + roundedRect.state = ""; + } + + onPressed: { + roundedRect.state = "mouseClicked"; + } + + onReleased: { + if (containsMouse) { + roundedRect.state = "mouseOver"; + } else { + roundedRect.state = ""; + } + } + } + + states: [ + State { + name: "mouseOver" + PropertyChanges { + target: roundedRect + color: "#121212" + border.width: 2 + border.color: "#00b4ef" + } + }, + State { + name: "mouseClicked" + PropertyChanges { + target: roundedRect + border.width: 2 + border.color: "#00b4ef" + } + PropertyChanges { + target: colorOverlay + color: '#00B4EF' + } + }, + State { + name: "mouseDepressed" + PropertyChanges { + target: roundedRect + color: "#0578b1" + border.width: 0 + } + } + ] + + Image { + id: buttonImage + anchors.centerIn: parent + source: "../../images/lowerKeyboard.png" // "file:///D:/AI/hifi-elderorb-vs2/interface/resources/images/lowerKeyboard.png"; + } + + ColorOverlay { + id: colorOverlay + anchors.fill: buttonImage + source: buttonImage + color: 'white' + } + } } } Rectangle { id: keyboardRect - x: 0 y: showMirrorText ? mirrorTextHeight : 0 width: keyboardWidth height: raisedHeight @@ -180,7 +275,7 @@ Rectangle { Key { width: 43; glyph: "i"; } Key { width: 43; glyph: "o"; } Key { width: 43; glyph: "p"; } - Key { width: 43; glyph: "←"; } + Key { width: 43; glyph: "←"; id: key_Backspace } } Row { diff --git a/libraries/ui/src/ui/OffscreenQmlSurface.cpp b/libraries/ui/src/ui/OffscreenQmlSurface.cpp index ecd07a5874..8333e87799 100644 --- a/libraries/ui/src/ui/OffscreenQmlSurface.cpp +++ b/libraries/ui/src/ui/OffscreenQmlSurface.cpp @@ -1082,7 +1082,19 @@ void OffscreenQmlSurface::synthesizeKeyPress(QString key, QObject* targetOverrid } } +void OffscreenQmlSurface::lowerKeyboard() { + + QSignalBlocker blocker(_quickWindow); + + if (_currentFocusItem) { + _currentFocusItem->setFocus(false); + setKeyboardRaised(_currentFocusItem, false); + } +} + void OffscreenQmlSurface::setKeyboardRaised(QObject* object, bool raised, bool numeric, bool passwordField) { + qCDebug(uiLogging) << "setKeyboardRaised: " << object << ", raised: " << raised << ", numeric: " << numeric << ", password: " << passwordField; + #if Q_OS_ANDROID return; #endif diff --git a/libraries/ui/src/ui/OffscreenQmlSurface.h b/libraries/ui/src/ui/OffscreenQmlSurface.h index 12ee9e59a1..5acdeb4f40 100644 --- a/libraries/ui/src/ui/OffscreenQmlSurface.h +++ b/libraries/ui/src/ui/OffscreenQmlSurface.h @@ -84,6 +84,7 @@ public: void setKeyboardRaised(QObject* object, bool raised, bool numeric = false, bool passwordField = false); Q_INVOKABLE void synthesizeKeyPress(QString key, QObject* targetOverride = nullptr); + Q_INVOKABLE void lowerKeyboard(); using TextureAndFence = std::pair; // Checks to see if a new texture is available. If one is, the function returns true and From fb14e4dc4d32db910efe383e4031602a8fb55b2e Mon Sep 17 00:00:00 2001 From: beholder Date: Sun, 29 Oct 2017 19:00:03 +0300 Subject: [PATCH 16/34] Fixed programmatical lowering of 'TabletAddressDialog' --- interface/resources/qml/hifi/tablet/TabletAddressDialog.qml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml b/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml index 4d9a83817a..649a8e6259 100644 --- a/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml +++ b/interface/resources/qml/hifi/tablet/TabletAddressDialog.qml @@ -366,7 +366,7 @@ StackView { HifiControls.Keyboard { id: keyboard - raised: parent.keyboardEnabled + raised: parent.keyboardEnabled && parent.keyboardRaised numeric: parent.punctuationMode anchors { bottom: parent.bottom From eb4214fb4c840bb74fb1dec56e9b8f18b3b94370 Mon Sep 17 00:00:00 2001 From: beholder Date: Thu, 2 Nov 2017 03:35:32 +0300 Subject: [PATCH 17/34] add API for unfocusing input fields in HTML, unfocus WebEngine-based QML items on lowering keyboard --- interface/resources/qml/controls/FlickableWebViewCore.qml | 6 ++++++ interface/resources/qml/controls/TabletWebScreen.qml | 5 +++++ interface/resources/qml/controls/TabletWebView.qml | 5 +++++ interface/resources/qml/controls/WebView.qml | 5 +++++ 4 files changed, 21 insertions(+) diff --git a/interface/resources/qml/controls/FlickableWebViewCore.qml b/interface/resources/qml/controls/FlickableWebViewCore.qml index cbc4d19334..29944781c1 100644 --- a/interface/resources/qml/controls/FlickableWebViewCore.qml +++ b/interface/resources/qml/controls/FlickableWebViewCore.qml @@ -27,6 +27,12 @@ Item { id: hifi } + function unfocus() { + webViewCore.runJavaScript("if (document.activeElement) document.activeElement.blur();", function(result) { + console.log('unfocus completed: ', result); + }); + } + function onLoadingChanged(loadRequest) { if (WebEngineView.LoadStartedStatus === loadRequest.status) { diff --git a/interface/resources/qml/controls/TabletWebScreen.qml b/interface/resources/qml/controls/TabletWebScreen.qml index e06ff51569..501e321f0d 100644 --- a/interface/resources/qml/controls/TabletWebScreen.qml +++ b/interface/resources/qml/controls/TabletWebScreen.qml @@ -10,6 +10,11 @@ Item { property alias urlTag: webroot.urlTag property bool keyboardEnabled: true // FIXME - Keyboard HMD only: Default to false property bool keyboardRaised: false + onKeyboardRaisedChanged: { + if(!keyboardRaised) { + webroot.unfocus(); + } + } property bool punctuationMode: false // FIXME - Keyboard HMD only: Make Interface either set keyboardRaised property directly in OffscreenQmlSurface diff --git a/interface/resources/qml/controls/TabletWebView.qml b/interface/resources/qml/controls/TabletWebView.qml index 8cd61bc90b..477422cfa1 100644 --- a/interface/resources/qml/controls/TabletWebView.qml +++ b/interface/resources/qml/controls/TabletWebView.qml @@ -15,6 +15,11 @@ Item { property string scriptURL property bool keyboardEnabled: false property bool keyboardRaised: false + onKeyboardRaisedChanged: { + if(!keyboardRaised) { + webroot.unfocus(); + } + } property bool punctuationMode: false property bool passwordField: false property bool isDesktop: false diff --git a/interface/resources/qml/controls/WebView.qml b/interface/resources/qml/controls/WebView.qml index 923c8f3fa1..931c64e1ef 100644 --- a/interface/resources/qml/controls/WebView.qml +++ b/interface/resources/qml/controls/WebView.qml @@ -12,6 +12,11 @@ Item { property alias urlTag: webroot.urlTag property bool keyboardEnabled: true // FIXME - Keyboard HMD only: Default to false property bool keyboardRaised: false + onKeyboardRaisedChanged: { + if(!keyboardRaised) { + webroot.unfocus(); + } + } property bool punctuationMode: false property bool passwordField: false property alias flickable: webroot.interactive From db3ed81513f0cbe14cb24fe479de297b26cca6ec Mon Sep 17 00:00:00 2001 From: beholder Date: Tue, 7 Nov 2017 13:45:27 +0300 Subject: [PATCH 18/34] adjust to changed requirements: 1. The keyboard collapse button is moved to the lower right, replacing the keys there 2. The button next to m is a hyphen instead of a underscore, it turns to a underscore when the user clicks on shift 3. The input text at the top occupies the full width and is center aligned, when you start typing the text moves in both directions the left and the right --- interface/resources/fonts/hifi-glyphs.ttf | Bin 30784 -> 31232 bytes interface/resources/qml/controls-uit/Key.qml | 1 + .../resources/qml/controls-uit/Keyboard.qml | 120 +++--------------- libraries/ui/src/ui/OffscreenQmlSurface.cpp | 4 + 4 files changed, 24 insertions(+), 101 deletions(-) diff --git a/interface/resources/fonts/hifi-glyphs.ttf b/interface/resources/fonts/hifi-glyphs.ttf index 3db48602b1eb845238497d2f3750fa7d281ccfbc..4cc5a0fe4f098a287c1df067c8bff37695f96d34 100644 GIT binary patch delta 802 zcmYjPO-vI}5dNk=lmNR(TfuH?y6rZQ(hzJ5t)>v;U-eJ~fe_RvE~V1Y)-Ducn~31S zXcQB}swWP5@J5ZMUQ9Tk(VIpNN(}MPgE8PmWAp$qt?5FvlQ-{uGjF~xGs!IfpxIwE z0|LNc7HaeagZ*9UTZM-}<_iGJ@uSCrc!3Ha^BMr(-Ph{rUJ6M74FVVlCq$`#_~T78`Ub5Y_&1FvHhyD8}rnuoujj`$cO1PxpE8Sr9J^D z&7rtOkpYcBtso0DbOJyXDxpG2@oL_gcNL3@wk?l;82kl=QHfVTj#GQon)Wpy7pmAj zcE|z&C+P!4p@t6CsD%LyFvEr>xX=nO{0QJ6g6P6IBruLCWH60uxQ;o@J0LVPRF%x=XM(dq_x=_JE_g*wR!6IQoa0L=bUNqdUh&|0kV=`pec?M z%w~t#>?i|yJ;Ue=TXhUm_s42&wpyJ$->e)b&#(ReB);&*WVf3rV6u}?SY(U_mIAE7 zz#idwr^0k?)2!AlJ;My_h@SGa$2Lvn#&KLzSX)*7fNL{`np&oGn^DBMq0wj acwCfH5qa}6Pq$?*&DE?nX4iK%Wc@Fk$FR}> delta 432 zcmYL^%`0pH7{-6^oHGX*-PHKVoqT11ntaA6w{&AHeAd0bA{-2p3@2yGna!oUWTShm z#D6e~&W5tEw6L&Xqq~@HT}demHd3QGl(*jAr=GW8&$IC)XOFUu0C{YnFc=R1?6YzX ztHG)Q0^OZmVUE$jQi1Y;A9albr@hM{qrmWNOgG~DSG(Z31kcQZZW`${3aq^X*$YdF z`P=;8ouKu?qCXnZ=Y045L%?64B^r&a>uSBEK>R>eG#0nYj*1>Y4naznR%Z2*sa79& zn?Z_Wx@B-DlOUl?pk+N4d2GEH24fn;F;>j@`Hr;@tA6nQcgqP(Z;xzGeQAFt*F$Em zZ?)w6^=QdI^3A&?<9xNh%b3(Sd(tF58CUt(fQvyUP+S#2m5xk5vU%tIO4X#(F1aGb zhr<2UICCnMM#UM`3KpHb)m+JHAViQhyUeUr8$!W0yU*N_E$5$ED9%g#K($X2<+5qt LBuadrIkn^)$9!hA diff --git a/interface/resources/qml/controls-uit/Key.qml b/interface/resources/qml/controls-uit/Key.qml index 586a9c0225..ebdfff36c0 100644 --- a/interface/resources/qml/controls-uit/Key.qml +++ b/interface/resources/qml/controls-uit/Key.qml @@ -11,6 +11,7 @@ Item { property bool toggle: false // does this button have the toggle behaivor? property bool toggled: false // is this button currently toggled? property alias mouseArea: mouseArea1 + property alias fontFamily: letter.font.family; function resetToggledMode(mode) { toggled = mode; diff --git a/interface/resources/qml/controls-uit/Keyboard.qml b/interface/resources/qml/controls-uit/Keyboard.qml index 7f73538c19..5974ffe7bc 100644 --- a/interface/resources/qml/controls-uit/Keyboard.qml +++ b/interface/resources/qml/controls-uit/Keyboard.qml @@ -56,6 +56,8 @@ Rectangle { return ">"; } else if (str === "/") { return "?"; + } else if (str === "-") { + return "_"; } else { return str.toUpperCase(str); } @@ -68,6 +70,8 @@ Rectangle { return "."; } else if (str === "?") { return "/"; + } else if (str === "_") { + return "-"; } else { return str.toLowerCase(str); } @@ -86,7 +90,7 @@ Rectangle { onShiftModeChanged: { forEachKey(function (key) { - if (/[a-z]/i.test(key.glyph)) { + if (/[a-z-_]/i.test(key.glyph)) { if (shiftMode) { key.glyph = keyboardBase.toUpper(key.glyph); } else { @@ -125,11 +129,11 @@ Rectangle { font.family: font.name font.pixelSize: 20 verticalAlignment: Text.AlignVCenter - horizontalAlignment: Text.AlignLeft + horizontalAlignment: Text.AlignHCenter color: "#00B4EF"; anchors.left: parent.left anchors.leftMargin: 10 - anchors.right: lowerKeyboard.left + anchors.right: parent.right anchors.top: parent.top anchors.bottom: parent.bottom @@ -149,98 +153,6 @@ Rectangle { anchors.fill: parent } } - - Item { - id: lowerKeyboard - anchors.right: parent.right - anchors.rightMargin: keyboardRect.width - (key_Backspace.x + key_Backspace.width + key_Backspace.contentPadding) - width: key_Backspace.width * 2 - height: parent.height - - Rectangle { - id: roundedRect - color: "#121212" - radius: 6 - border.color: "#00000000" - anchors.fill: parent - anchors.margins: 4 - - MouseArea { - id: mouseArea - anchors.fill: parent - hoverEnabled: true - - onClicked: { - webEntity.lowerKeyboard(); - } - - onEntered: { - roundedRect.state = "mouseOver"; - } - - onExited: { - roundedRect.state = ""; - } - - onPressed: { - roundedRect.state = "mouseClicked"; - } - - onReleased: { - if (containsMouse) { - roundedRect.state = "mouseOver"; - } else { - roundedRect.state = ""; - } - } - } - - states: [ - State { - name: "mouseOver" - PropertyChanges { - target: roundedRect - color: "#121212" - border.width: 2 - border.color: "#00b4ef" - } - }, - State { - name: "mouseClicked" - PropertyChanges { - target: roundedRect - border.width: 2 - border.color: "#00b4ef" - } - PropertyChanges { - target: colorOverlay - color: '#00B4EF' - } - }, - State { - name: "mouseDepressed" - PropertyChanges { - target: roundedRect - color: "#0578b1" - border.width: 0 - } - } - ] - - Image { - id: buttonImage - anchors.centerIn: parent - source: "../../images/lowerKeyboard.png" // "file:///D:/AI/hifi-elderorb-vs2/interface/resources/images/lowerKeyboard.png"; - } - - ColorOverlay { - id: colorOverlay - anchors.fill: buttonImage - source: buttonImage - color: 'white' - } - } - } } Rectangle { @@ -253,6 +165,8 @@ Rectangle { anchors.bottom: parent.bottom anchors.bottomMargin: 0 + FontLoader { id: hiFiGlyphs; source: pathToFonts + "fonts/hifi-glyphs.ttf"; } + Column { id: columnAlpha width: keyboardWidth @@ -275,7 +189,7 @@ Rectangle { Key { width: 43; glyph: "i"; } Key { width: 43; glyph: "o"; } Key { width: 43; glyph: "p"; } - Key { width: 43; glyph: "←"; id: key_Backspace } + Key { width: 43; glyph: "←"; } } Row { @@ -316,7 +230,7 @@ Rectangle { Key { width: 43; glyph: "b"; } Key { width: 43; glyph: "n"; } Key { width: 43; glyph: "m"; } - Key { width: 43; glyph: "_"; } + Key { width: 43; glyph: "-"; } Key { width: 43; glyph: "/"; } Key { width: 43; glyph: "?"; } } @@ -335,8 +249,10 @@ Rectangle { Key { width: 231; glyph: " "; } Key { width: 43; glyph: ","; } Key { width: 43; glyph: "."; } - Key { width: 43; glyph: "\u276C"; } - Key { width: 43; glyph: "\u276D"; } + Key { + fontFamily: hiFiGlyphs.name; + width: 86; glyph: "\ue02b"; + } } } @@ -423,8 +339,10 @@ Rectangle { Key { width: 231; glyph: " "; } Key { width: 43; glyph: ","; } Key { width: 43; glyph: "."; } - Key { width: 43; glyph: "\u276C"; } - Key { width: 43; glyph: "\u276D"; } + Key { + fontFamily: hiFiGlyphs.name; + width: 86; glyph: "\ue02b"; + } } } } diff --git a/libraries/ui/src/ui/OffscreenQmlSurface.cpp b/libraries/ui/src/ui/OffscreenQmlSurface.cpp index 8333e87799..24e1006083 100644 --- a/libraries/ui/src/ui/OffscreenQmlSurface.cpp +++ b/libraries/ui/src/ui/OffscreenQmlSurface.cpp @@ -1038,6 +1038,7 @@ static const uint8_t BACKSPACE_SYMBOL[] = { 0xE2, 0x86, 0x90, 0x00 }; static const uint8_t LEFT_ARROW[] = { 0xE2, 0x9D, 0xAC, 0x00 }; static const uint8_t RIGHT_ARROW[] = { 0xE2, 0x9D, 0xAD, 0x00 }; static const uint8_t RETURN_SYMBOL[] = { 0xE2, 0x8F, 0x8E, 0x00 }; +static const uint8_t COLLAPSE_KEYBOARD[] = { 0xEE, 0x80, 0xAB, 0x00 }; static const char PUNCTUATION_STRING[] = "123"; static const char ALPHABET_STRING[] = "abc"; @@ -1061,6 +1062,9 @@ void OffscreenQmlSurface::synthesizeKeyPress(QString key, QObject* targetOverrid if (equals(utf8Key, SHIFT_ARROW) || equals(utf8Key, NUMERIC_SHIFT_ARROW) || equals(utf8Key, (uint8_t*)PUNCTUATION_STRING) || equals(utf8Key, (uint8_t*)ALPHABET_STRING)) { return; // ignore + } else if (equals(utf8Key, COLLAPSE_KEYBOARD)) { + lowerKeyboard(); + return; } else if (equals(utf8Key, BACKSPACE_SYMBOL)) { scanCode = Qt::Key_Backspace; keyString = "\x08"; From 4d11f9a434eb2530f3a5d3e413d256d779bdfea2 Mon Sep 17 00:00:00 2001 From: beholder Date: Tue, 7 Nov 2017 23:13:29 +0300 Subject: [PATCH 19/34] increase font pixel size for 'collapse keyboard' to 34px --- interface/resources/qml/controls-uit/Key.qml | 1 + interface/resources/qml/controls-uit/Keyboard.qml | 2 ++ 2 files changed, 3 insertions(+) diff --git a/interface/resources/qml/controls-uit/Key.qml b/interface/resources/qml/controls-uit/Key.qml index ebdfff36c0..314149ca6e 100644 --- a/interface/resources/qml/controls-uit/Key.qml +++ b/interface/resources/qml/controls-uit/Key.qml @@ -12,6 +12,7 @@ Item { property bool toggled: false // is this button currently toggled? property alias mouseArea: mouseArea1 property alias fontFamily: letter.font.family; + property alias fontPixelSize: letter.font.pixelSize function resetToggledMode(mode) { toggled = mode; diff --git a/interface/resources/qml/controls-uit/Keyboard.qml b/interface/resources/qml/controls-uit/Keyboard.qml index 5974ffe7bc..1865e437e5 100644 --- a/interface/resources/qml/controls-uit/Keyboard.qml +++ b/interface/resources/qml/controls-uit/Keyboard.qml @@ -251,6 +251,7 @@ Rectangle { Key { width: 43; glyph: "."; } Key { fontFamily: hiFiGlyphs.name; + fontPixelSize: 34; width: 86; glyph: "\ue02b"; } } @@ -341,6 +342,7 @@ Rectangle { Key { width: 43; glyph: "."; } Key { fontFamily: hiFiGlyphs.name; + fontPixelSize: 34; width: 86; glyph: "\ue02b"; } } From 0bc95998c498dcd1de8fdb766fe97392c8f7e2ee Mon Sep 17 00:00:00 2001 From: beholder Date: Wed, 8 Nov 2017 02:05:58 +0300 Subject: [PATCH 20/34] a few more adjustments based on discussion with Mukul --- interface/resources/qml/controls-uit/Key.qml | 2 ++ interface/resources/qml/controls-uit/Keyboard.qml | 8 ++++++-- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/interface/resources/qml/controls-uit/Key.qml b/interface/resources/qml/controls-uit/Key.qml index 314149ca6e..b0e965e79f 100644 --- a/interface/resources/qml/controls-uit/Key.qml +++ b/interface/resources/qml/controls-uit/Key.qml @@ -13,6 +13,8 @@ Item { property alias mouseArea: mouseArea1 property alias fontFamily: letter.font.family; property alias fontPixelSize: letter.font.pixelSize + property alias verticalAlignment: letter.verticalAlignment + property alias letterAnchors: letter.anchors function resetToggledMode(mode) { toggled = mode; diff --git a/interface/resources/qml/controls-uit/Keyboard.qml b/interface/resources/qml/controls-uit/Keyboard.qml index 1865e437e5..76b66178d4 100644 --- a/interface/resources/qml/controls-uit/Keyboard.qml +++ b/interface/resources/qml/controls-uit/Keyboard.qml @@ -251,7 +251,9 @@ Rectangle { Key { width: 43; glyph: "."; } Key { fontFamily: hiFiGlyphs.name; - fontPixelSize: 34; + fontPixelSize: 48; + letterAnchors.topMargin: -4; + verticalAlignment: Text.AlignVCenter; width: 86; glyph: "\ue02b"; } } @@ -342,7 +344,9 @@ Rectangle { Key { width: 43; glyph: "."; } Key { fontFamily: hiFiGlyphs.name; - fontPixelSize: 34; + fontPixelSize: 48; + letterAnchors.topMargin: -4; + verticalAlignment: Text.AlignVCenter; width: 86; glyph: "\ue02b"; } } From d1969d649a0e7f8a22791181a48e1d87fe77b460 Mon Sep 17 00:00:00 2001 From: beholder Date: Thu, 9 Nov 2017 22:33:16 +0300 Subject: [PATCH 21/34] fix not collapsing keyboard --- .../resources/qml/hifi/dialogs/TabletRunningScripts.qml | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/interface/resources/qml/hifi/dialogs/TabletRunningScripts.qml b/interface/resources/qml/hifi/dialogs/TabletRunningScripts.qml index 80c1b58444..83f91c78c5 100644 --- a/interface/resources/qml/hifi/dialogs/TabletRunningScripts.qml +++ b/interface/resources/qml/hifi/dialogs/TabletRunningScripts.qml @@ -32,6 +32,8 @@ Rectangle { color: hifi.colors.baseGray + property bool keyboardEnabled: HMD.active + property bool keyboardRaised: false LetterboxMessage { id: letterBoxMessage @@ -380,7 +382,7 @@ Rectangle { Component.onCompleted: scriptsModel.filterRegExp = new RegExp("^.*$", "i") onActiveFocusChanged: { // raise the keyboard - keyboard.raised = activeFocus; + root.keyboardRaised = activeFocus; // scroll to the bottom of the content area. if (activeFocus) { @@ -481,7 +483,7 @@ Rectangle { HifiControls.Keyboard { id: keyboard - raised: false + raised: parent.keyboardEnabled && parent.keyboardRaised numeric: false anchors { bottom: parent.bottom From 5fcde1186afb2dd3cb48dbb1b9e05c8f7771ce12 Mon Sep 17 00:00:00 2001 From: beholder Date: Fri, 10 Nov 2017 03:54:03 +0300 Subject: [PATCH 22/34] hide keyboard before showing to solve clearing 'mirrorText' on jumping between input fields without hiding keyboard --- libraries/ui/src/ui/OffscreenQmlSurface.cpp | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/libraries/ui/src/ui/OffscreenQmlSurface.cpp b/libraries/ui/src/ui/OffscreenQmlSurface.cpp index 24e1006083..01f8f4580a 100644 --- a/libraries/ui/src/ui/OffscreenQmlSurface.cpp +++ b/libraries/ui/src/ui/OffscreenQmlSurface.cpp @@ -1133,6 +1133,10 @@ void OffscreenQmlSurface::setKeyboardRaised(QObject* object, bool raised, bool n item->setProperty("passwordField", QVariant(passwordField)); } + if (raised) { + item->setProperty("keyboardRaised", QVariant(!raised)); + } + item->setProperty("keyboardRaised", QVariant(raised)); return; } From bf576e63fe49b91e0056c5ea97a2dffe4172bd91 Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Fri, 10 Nov 2017 11:54:53 -0700 Subject: [PATCH 23/34] move constant to class definition --- interface/src/ui/overlays/Line3DOverlay.cpp | 4 +++- interface/src/ui/overlays/Line3DOverlay.h | 4 +--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index a6b7242df2..eb19617bfc 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -16,9 +16,11 @@ #include "AbstractViewStateInterface.h" QString const Line3DOverlay::TYPE = "line3d"; +static const float DEFAULT_LINE_WIDTH = 0.02f; Line3DOverlay::Line3DOverlay() : - _geometryCacheID(DependencyManager::get()->allocateID()) + _geometryCacheID(DependencyManager::get()->allocateID()), + _lineWidth(DEFAULT_LINE_WIDTH) { } diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index 2a3c7caa99..2995363ad7 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -13,8 +13,6 @@ #include "Base3DOverlay.h" -static const float DEFAULT_LINE_WIDTH = 0.02f; - class Line3DOverlay : public Base3DOverlay { Q_OBJECT using Parent = Base3DOverlay; @@ -72,7 +70,7 @@ private: glm::vec3 _direction; // in parent frame float _length { 1.0 }; // in parent frame - float _lineWidth { DEFAULT_LINE_WIDTH }; + float _lineWidth { 0.0 }; float _glow { 0.0 }; int _geometryCacheID; }; From d53a29b958d40e752b1c342a2e1e2808c8727803 Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Fri, 10 Nov 2017 12:24:19 -0700 Subject: [PATCH 24/34] correction --- interface/src/ui/overlays/Line3DOverlay.cpp | 4 +--- interface/src/ui/overlays/Line3DOverlay.h | 3 ++- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/interface/src/ui/overlays/Line3DOverlay.cpp b/interface/src/ui/overlays/Line3DOverlay.cpp index eb19617bfc..a6b7242df2 100644 --- a/interface/src/ui/overlays/Line3DOverlay.cpp +++ b/interface/src/ui/overlays/Line3DOverlay.cpp @@ -16,11 +16,9 @@ #include "AbstractViewStateInterface.h" QString const Line3DOverlay::TYPE = "line3d"; -static const float DEFAULT_LINE_WIDTH = 0.02f; Line3DOverlay::Line3DOverlay() : - _geometryCacheID(DependencyManager::get()->allocateID()), - _lineWidth(DEFAULT_LINE_WIDTH) + _geometryCacheID(DependencyManager::get()->allocateID()) { } diff --git a/interface/src/ui/overlays/Line3DOverlay.h b/interface/src/ui/overlays/Line3DOverlay.h index 2995363ad7..79af937f23 100644 --- a/interface/src/ui/overlays/Line3DOverlay.h +++ b/interface/src/ui/overlays/Line3DOverlay.h @@ -70,7 +70,8 @@ private: glm::vec3 _direction; // in parent frame float _length { 1.0 }; // in parent frame - float _lineWidth { 0.0 }; + const float DEFAULT_LINE_WIDTH = 0.02f; + float _lineWidth { DEFAULT_LINE_WIDTH }; float _glow { 0.0 }; int _geometryCacheID; }; From 163de649bf2b5fa5b11b2bc4da34afd813a7c242 Mon Sep 17 00:00:00 2001 From: David Back Date: Fri, 10 Nov 2017 17:44:09 -0800 Subject: [PATCH 25/34] prevent rendering HUD elements in secondary camera --- libraries/render-utils/src/RenderDeferredTask.cpp | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/libraries/render-utils/src/RenderDeferredTask.cpp b/libraries/render-utils/src/RenderDeferredTask.cpp index ac4e717d60..79428979b9 100644 --- a/libraries/render-utils/src/RenderDeferredTask.cpp +++ b/libraries/render-utils/src/RenderDeferredTask.cpp @@ -438,6 +438,11 @@ void CompositeHUD::run(const RenderContextPointer& renderContext) { assert(renderContext->args); assert(renderContext->args->_context); + // We do not want to render HUD elements in secondary camera + if (renderContext->args->_renderMode == RenderArgs::RenderMode::SECONDARY_CAMERA_RENDER_MODE) { + return; + } + // Grab the HUD texture gpu::doInBatch(renderContext->args->_context, [&](gpu::Batch& batch) { if (renderContext->args->_hudOperator) { From 94b925d9d5fd22388357758f537ee590b6dcdbb5 Mon Sep 17 00:00:00 2001 From: Liv Date: Mon, 13 Nov 2017 15:53:33 -0800 Subject: [PATCH 26/34] Update .eslintrc.js --- .eslintrc.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.eslintrc.js b/.eslintrc.js index 54ff0a1268..5667a04984 100644 --- a/.eslintrc.js +++ b/.eslintrc.js @@ -68,7 +68,7 @@ module.exports = { "eqeqeq": ["error", "always"], "indent": ["error", 4, { "SwitchCase": 1 }], "keyword-spacing": ["error", { "before": true, "after": true }], - "max-len": ["error", 192, 4], + "max-len": ["error", 128, 4], "new-cap": ["error"], "no-floating-decimal": ["error"], //"no-magic-numbers": ["error", { "ignore": [0, 1], "ignoreArrayIndexes": true }], From b4b148367e959bb6ced05705663186574d206528 Mon Sep 17 00:00:00 2001 From: Nissim Hadar Date: Sat, 11 Nov 2017 18:58:12 -0800 Subject: [PATCH 27/34] Removed Keylight attenuation from .js (as well as .html). --- libraries/model/src/model/Haze.cpp | 2 +- scripts/system/html/entityProperties.html | 4 ++-- scripts/system/html/js/entityProperties.js | 12 ++++++------ 3 files changed, 9 insertions(+), 9 deletions(-) diff --git a/libraries/model/src/model/Haze.cpp b/libraries/model/src/model/Haze.cpp index c9c73bcee9..b56932e131 100644 --- a/libraries/model/src/model/Haze.cpp +++ b/libraries/model/src/model/Haze.cpp @@ -8,8 +8,8 @@ // Distributed under the Apache License, Version 2.0. // See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html // -#include +#include #include "Haze.h" using namespace model; diff --git a/scripts/system/html/entityProperties.html b/scripts/system/html/entityProperties.html index 9453b476ee..8b2a088d83 100644 --- a/scripts/system/html/entityProperties.html +++ b/scripts/system/html/entityProperties.html @@ -623,7 +623,7 @@ -
+
diff --git a/scripts/system/html/js/entityProperties.js b/scripts/system/html/js/entityProperties.js index 0463ac4172..f54394a353 100644 --- a/scripts/system/html/js/entityProperties.js +++ b/scripts/system/html/js/entityProperties.js @@ -1069,9 +1069,9 @@ function loaded() { elZoneHazeBackgroundBlend.value = properties.haze.hazeBackgroundBlend.toFixed(2); - elZoneHazeAttenuateKeyLight.checked = properties.haze.hazeAttenuateKeyLight; - elZoneHazeKeyLightRange.value = properties.haze.hazeKeyLightRange.toFixed(0); - elZoneHazeKeyLightAltitude.value = properties.haze.hazeKeyLightAltitude.toFixed(0); +// elZoneHazeAttenuateKeyLight.checked = properties.haze.hazeAttenuateKeyLight; +// elZoneHazeKeyLightRange.value = properties.haze.hazeKeyLightRange.toFixed(0); +// elZoneHazeKeyLightAltitude.value = properties.haze.hazeKeyLightAltitude.toFixed(0); elZoneStageLatitude.value = properties.stage.latitude.toFixed(2); elZoneStageLongitude.value = properties.stage.longitude.toFixed(2); @@ -1533,9 +1533,9 @@ function loaded() { elZoneHazeBackgroundBlend.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('haze', 'hazeBackgroundBlend')); - elZoneHazeAttenuateKeyLight.addEventListener('change', createEmitGroupCheckedPropertyUpdateFunction('haze', 'hazeAttenuateKeyLight')); - elZoneHazeKeyLightRange.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('haze', 'hazeKeyLightRange')); - elZoneHazeKeyLightAltitude.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('haze', 'hazeKeyLightAltitude')); +// elZoneHazeAttenuateKeyLight.addEventListener('change', createEmitGroupCheckedPropertyUpdateFunction('haze', 'hazeAttenuateKeyLight')); +// elZoneHazeKeyLightRange.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('haze', 'hazeKeyLightRange')); +// elZoneHazeKeyLightAltitude.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('haze', 'hazeKeyLightAltitude')); elZoneStageLatitude.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('stage', 'latitude')); elZoneStageLongitude.addEventListener('change', createEmitGroupNumberPropertyUpdateFunction('stage', 'longitude')); From 489e244342db3006c231e3cf18453cbb301f7894 Mon Sep 17 00:00:00 2001 From: luiscuenca Date: Tue, 14 Nov 2017 09:56:23 -0700 Subject: [PATCH 28/34] More accurate scale from SensorToWorldScale --- interface/src/raypick/LaserPointer.cpp | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/interface/src/raypick/LaserPointer.cpp b/interface/src/raypick/LaserPointer.cpp index 6d29154be0..71a547533b 100644 --- a/interface/src/raypick/LaserPointer.cpp +++ b/interface/src/raypick/LaserPointer.cpp @@ -158,8 +158,6 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter } } - float avatarScale = DependencyManager::get()->getMyAvatar()->getAvatarScale(); - QVariant end = vec3toVariant(endVec); if (!renderState.getPathID().isNull()) { QVariantMap pathProps; @@ -168,7 +166,7 @@ void LaserPointer::updateRenderState(const RenderState& renderState, const Inter pathProps.insert("visible", true); pathProps.insert("ignoreRayIntersection", renderState.doesPathIgnoreRays()); if (_scaleWithAvatar) { - pathProps.insert("lineWidth", renderState.getLineWidth() * avatarScale); + pathProps.insert("lineWidth", renderState.getLineWidth() * DependencyManager::get()->getMyAvatar()->getSensorToWorldScale()); } qApp->getOverlays().editOverlay(renderState.getPathID(), pathProps); } From e201e203b849367255e2653d97c994cca1e0277f Mon Sep 17 00:00:00 2001 From: Alexander Ivash Date: Tue, 14 Nov 2017 22:18:48 +0300 Subject: [PATCH 29/34] 8984 Opening tablet with "Enter" key displays the audio menu --- interface/resources/qml/hifi/tablet/Tablet.qml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/interface/resources/qml/hifi/tablet/Tablet.qml b/interface/resources/qml/hifi/tablet/Tablet.qml index 66e3dfdbbb..2a086bae94 100644 --- a/interface/resources/qml/hifi/tablet/Tablet.qml +++ b/interface/resources/qml/hifi/tablet/Tablet.qml @@ -8,8 +8,8 @@ import "../audio" as HifiAudio Item { id: tablet objectName: "tablet" - property int rowIndex: 0 - property int columnIndex: 0 + property int rowIndex: 6 // by default + property int columnIndex: 1 // point to 'go to location' property int count: (flowMain.children.length - 1) // used to look up a button by its uuid From f5994375cf8cf8d640812d7c5e573cc3771396cf Mon Sep 17 00:00:00 2001 From: Zach Fox Date: Tue, 14 Nov 2017 14:24:03 -0800 Subject: [PATCH 30/34] Remove Marketplace's dependency on Edit.js for rez --- .../qml/hifi/commerce/checkout/Checkout.qml | 4 +- .../hifi/commerce/purchases/PurchasedItem.qml | 4 +- .../qml/hifi/commerce/purchases/Purchases.qml | 2 + scripts/system/marketplaces/marketplaces.js | 111 ++++++++++++++++++ 4 files changed, 115 insertions(+), 6 deletions(-) diff --git a/interface/resources/qml/hifi/commerce/checkout/Checkout.qml b/interface/resources/qml/hifi/commerce/checkout/Checkout.qml index dfe0c319e5..3e7c23f2dd 100644 --- a/interface/resources/qml/hifi/commerce/checkout/Checkout.qml +++ b/interface/resources/qml/hifi/commerce/checkout/Checkout.qml @@ -476,9 +476,7 @@ Rectangle { commerce.buy(itemId, itemPrice, true); } } else { - if (urlHandler.canHandleUrl(itemHref)) { - urlHandler.handleUrl(itemHref); - } + sendToScript({method: 'checkout_rezClicked', itemHref: root.itemHref, isWearable: root.isWearable}); } } } diff --git a/interface/resources/qml/hifi/commerce/purchases/PurchasedItem.qml b/interface/resources/qml/hifi/commerce/purchases/PurchasedItem.qml index fb42865ba4..15ebada0c4 100644 --- a/interface/resources/qml/hifi/commerce/purchases/PurchasedItem.qml +++ b/interface/resources/qml/hifi/commerce/purchases/PurchasedItem.qml @@ -346,9 +346,7 @@ Item { enabled: (root.canRezCertifiedItems || root.isWearable) && root.purchaseStatus !== "invalidated"; onClicked: { - if (urlHandler.canHandleUrl(root.itemHref)) { - urlHandler.handleUrl(root.itemHref); - } + sendToPurchases({method: 'purchases_rezClicked', itemHref: root.itemHref, isWearable: root.isWearable}); rezzedNotifContainer.visible = true; rezzedNotifContainerTimer.start(); } diff --git a/interface/resources/qml/hifi/commerce/purchases/Purchases.qml b/interface/resources/qml/hifi/commerce/purchases/Purchases.qml index f292f9603e..1ea488ac98 100644 --- a/interface/resources/qml/hifi/commerce/purchases/Purchases.qml +++ b/interface/resources/qml/hifi/commerce/purchases/Purchases.qml @@ -442,6 +442,8 @@ Rectangle { onSendToPurchases: { if (msg.method === 'purchases_itemInfoClicked') { sendToScript({method: 'purchases_itemInfoClicked', itemId: itemId}); + } else if (msg.method === "purchases_rezClicked") { + sendToScript({method: 'purchases_rezClicked', itemHref: itemHref, isWearable: isWearable}); } else if (msg.method === 'purchases_itemCertificateClicked') { inspectionCertificate.visible = true; inspectionCertificate.isLightbox = true; diff --git a/scripts/system/marketplaces/marketplaces.js b/scripts/system/marketplaces/marketplaces.js index efe5812ecb..83566fd207 100644 --- a/scripts/system/marketplaces/marketplaces.js +++ b/scripts/system/marketplaces/marketplaces.js @@ -168,6 +168,113 @@ })); } + var HALF_TREE_SCALE = 16384; + function getPositionToCreateEntity(extra) { + var CREATE_DISTANCE = 2; + var position; + var delta = extra !== undefined ? extra : 0; + if (Camera.mode === "entity" || Camera.mode === "independent") { + position = Vec3.sum(Camera.position, Vec3.multiply(Quat.getForward(Camera.orientation), CREATE_DISTANCE + delta)); + } else { + position = Vec3.sum(MyAvatar.position, Vec3.multiply(Quat.getForward(MyAvatar.orientation), CREATE_DISTANCE + delta)); + position.y += 0.5; + } + + if (position.x > HALF_TREE_SCALE || position.y > HALF_TREE_SCALE || position.z > HALF_TREE_SCALE) { + return null; + } + return position; + } + + function rezEntity(itemHref, isWearable) { + if (!isWearable && + (!Entities.canRez() && !Entities.canRezTmp() && + !Entities.canRezCertified() && !Entities.canRezTmpCertified())) { + Window.notifyEditError("You do not have the necessary permissions to place items on this domain."); + return; + } + + var success = Clipboard.importEntities(itemHref); + + if (success) { + var VERY_LARGE = 10000; + var isLargeImport = Clipboard.getClipboardContentsLargestDimension() >= VERY_LARGE; + var position = Vec3.ZERO; + if (!isLargeImport) { + position = getPositionToCreateEntity(Clipboard.getClipboardContentsLargestDimension() / 2); + } + if (position !== null && position !== undefined) { + var pastedEntityIDs = Clipboard.pasteEntities(position); + if (!isLargeImport) { + // The first entity in Clipboard gets the specified position with the rest being relative to it. Therefore, move + // entities after they're imported so that they're all the correct distance in front of and with geometric mean + // centered on the avatar/camera direction. + var deltaPosition = Vec3.ZERO; + var entityPositions = []; + var entityParentIDs = []; + + var propType = Entities.getEntityProperties(pastedEntityIDs[0], ["type"]).type; + var NO_ADJUST_ENTITY_TYPES = ["Zone", "Light", "ParticleEffect"]; + if (NO_ADJUST_ENTITY_TYPES.indexOf(propType) === -1) { + var targetDirection; + if (Camera.mode === "entity" || Camera.mode === "independent") { + targetDirection = Camera.orientation; + } else { + targetDirection = MyAvatar.orientation; + } + targetDirection = Vec3.multiplyQbyV(targetDirection, Vec3.UNIT_Z); + + var targetPosition = getPositionToCreateEntity(); + var deltaParallel = HALF_TREE_SCALE; // Distance to move entities parallel to targetDirection. + var deltaPerpendicular = Vec3.ZERO; // Distance to move entities perpendicular to targetDirection. + for (var i = 0, length = pastedEntityIDs.length; i < length; i++) { + var curLoopEntityProps = Entities.getEntityProperties(pastedEntityIDs[i], ["position", "dimensions", + "registrationPoint", "rotation", "parentID"]); + var adjustedPosition = adjustPositionPerBoundingBox(targetPosition, targetDirection, + curLoopEntityProps.registrationPoint, curLoopEntityProps.dimensions, curLoopEntityProps.rotation); + var delta = Vec3.subtract(adjustedPosition, curLoopEntityProps.position); + var distance = Vec3.dot(delta, targetDirection); + deltaParallel = Math.min(distance, deltaParallel); + deltaPerpendicular = Vec3.sum(Vec3.subtract(delta, Vec3.multiply(distance, targetDirection)), + deltaPerpendicular); + entityPositions[i] = curLoopEntityProps.position; + entityParentIDs[i] = curLoopEntityProps.parentID; + } + deltaPerpendicular = Vec3.multiply(1 / pastedEntityIDs.length, deltaPerpendicular); + deltaPosition = Vec3.sum(Vec3.multiply(deltaParallel, targetDirection), deltaPerpendicular); + } + + if (grid.getSnapToGrid()) { + var firstEntityProps = Entities.getEntityProperties(pastedEntityIDs[0], ["position", "dimensions", + "registrationPoint"]); + var positionPreSnap = Vec3.sum(deltaPosition, firstEntityProps.position); + position = grid.snapToSurface(grid.snapToGrid(positionPreSnap, false, firstEntityProps.dimensions, + firstEntityProps.registrationPoint), firstEntityProps.dimensions, firstEntityProps.registrationPoint); + deltaPosition = Vec3.subtract(position, firstEntityProps.position); + } + + if (!Vec3.equal(deltaPosition, Vec3.ZERO)) { + for (var editEntityIndex = 0, numEntities = pastedEntityIDs.length; editEntityIndex < numEntities; editEntityIndex++) { + if (Uuid.isNull(entityParentIDs[editEntityIndex])) { + Entities.editEntity(pastedEntityIDs[editEntityIndex], { + position: Vec3.sum(deltaPosition, entityPositions[editEntityIndex]) + }); + } + } + } + } + + if (isActive) { + selectionManager.setSelections(pastedEntityIDs); + } + } else { + Window.notifyEditError("Can't import entities: entities would be out of bounds."); + } + } else { + Window.notifyEditError("There was an error importing the entity file."); + } + } + marketplaceButton.clicked.connect(onClick); tablet.screenChanged.connect(onScreenChanged); Entities.canWriteAssetsChanged.connect(onCanWriteAssetsChanged); @@ -330,6 +437,10 @@ tablet.gotoWebScreen(MARKETPLACE_URL + '/items/' + itemId, MARKETPLACES_INJECT_SCRIPT_URL); } break; + case 'checkout_rezClicked': + case 'purchases_rezClicked': + rezEntity(message.itemHref, message.isWearable); + break; case 'header_marketplaceImageClicked': case 'purchases_backClicked': tablet.gotoWebScreen(message.referrerURL, MARKETPLACES_INJECT_SCRIPT_URL); From d6c244d1d5690e07288e0cc9b7125bed14ac4461 Mon Sep 17 00:00:00 2001 From: Zach Fox Date: Tue, 14 Nov 2017 14:54:03 -0800 Subject: [PATCH 31/34] Remove incorrect logic --- scripts/system/marketplaces/marketplaces.js | 7 ------- 1 file changed, 7 deletions(-) diff --git a/scripts/system/marketplaces/marketplaces.js b/scripts/system/marketplaces/marketplaces.js index 83566fd207..80990402d7 100644 --- a/scripts/system/marketplaces/marketplaces.js +++ b/scripts/system/marketplaces/marketplaces.js @@ -187,13 +187,6 @@ } function rezEntity(itemHref, isWearable) { - if (!isWearable && - (!Entities.canRez() && !Entities.canRezTmp() && - !Entities.canRezCertified() && !Entities.canRezTmpCertified())) { - Window.notifyEditError("You do not have the necessary permissions to place items on this domain."); - return; - } - var success = Clipboard.importEntities(itemHref); if (success) { From f47a3e7d2ced239fdf16b259112b7ee23e228a74 Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Wed, 15 Nov 2017 09:42:57 +0100 Subject: [PATCH 32/34] Moved draw frustum job to render DrawTask and made generic. A couple of fixes as requested by @samcake --- .../render-utils/src/RenderDeferredTask.cpp | 100 ++++-------------- .../render-utils/src/RenderDeferredTask.h | 36 ++----- libraries/render/src/render/DrawTask.cpp | 84 ++++++++++++++- libraries/render/src/render/DrawTask.h | 37 +++++++ libraries/render/src/render/SortTask.cpp | 6 +- libraries/shared/src/Transform.h | 6 +- scripts/developer/utilities/render/shadow.qml | 14 ++- 7 files changed, 165 insertions(+), 118 deletions(-) diff --git a/libraries/render-utils/src/RenderDeferredTask.cpp b/libraries/render-utils/src/RenderDeferredTask.cpp index 3dccef4a54..4261b14a9b 100644 --- a/libraries/render-utils/src/RenderDeferredTask.cpp +++ b/libraries/render-utils/src/RenderDeferredTask.cpp @@ -44,8 +44,6 @@ #include "DrawHaze.h" #include "HighlightEffect.h" -#include - #include using namespace render; @@ -193,14 +191,18 @@ void RenderDeferredTask::build(JobModel& task, const render::Varying& input, ren task.addJob("HighlightRangeTimer", outlineRangeTimer); - { // DEbug the bounds of the rendered items, still look at the zbuffer + { // Debug the bounds of the rendered items, still look at the zbuffer task.addJob("DrawMetaBounds", metas); task.addJob("DrawOpaqueBounds", opaques); task.addJob("DrawTransparentBounds", transparents); task.addJob("DrawLightBounds", lights); task.addJob("DrawZones", zones); - task.addJob("DrawFrustums"); + const auto frustums = task.addJob("ExtractFrustums"); + const auto viewFrustum = frustums.getN(ExtractFrustums::VIEW_FRUSTUM); + const auto shadowFrustum = frustums.getN(ExtractFrustums::SHADOW_FRUSTUM); + task.addJob("DrawViewFrustum", viewFrustum, glm::vec3(1.0f, 1.0f, 0.0f)); + task.addJob("DrawShadowFrustum", shadowFrustum, glm::vec3(0.0f, 0.0f, 1.0f)); // Render.getConfig("RenderMainView.DrawSelectionBounds").enabled = true task.addJob("DrawSelectionBounds", selectedItems); @@ -533,88 +535,32 @@ void Blit::run(const RenderContextPointer& renderContext, const gpu::Framebuffer }); } -void DrawFrustums::configure(const Config& configuration) { - _updateFrustums = !configuration.isFrozen; -} - -void DrawFrustums::run(const render::RenderContextPointer& renderContext) { +void ExtractFrustums::run(const render::RenderContextPointer& renderContext, Output& output) { assert(renderContext->args); assert(renderContext->args->_context); RenderArgs* args = renderContext->args; - static uint8_t indexData[] = { 0, 1, 2, 3, 0, 4, 5, 6, 7, 4, 5, 1, 2, 6, 7, 3 }; - if (!_frustumMeshIndices._buffer) { - auto indices = std::make_shared(sizeof(indexData), indexData); - _frustumMeshIndices = gpu::BufferView(indices, gpu::Element(gpu::SCALAR, gpu::UINT8, gpu::INDEX)); - _viewFrustumMeshVertices = gpu::BufferView(std::make_shared(sizeof(glm::vec3) * 8, nullptr), gpu::Element::VEC3F_XYZ); - _viewFrustumMeshStream.addBuffer(_viewFrustumMeshVertices._buffer, _viewFrustumMeshVertices._offset, _viewFrustumMeshVertices._stride); - _shadowFrustumMeshVertices = gpu::BufferView(std::make_shared(sizeof(glm::vec3) * 8, nullptr), gpu::Element::VEC3F_XYZ); - _shadowFrustumMeshStream.addBuffer(_shadowFrustumMeshVertices._buffer, _shadowFrustumMeshVertices._offset, _shadowFrustumMeshVertices._stride); + // Return view frustum + auto& viewFrustum = output[VIEW_FRUSTUM].edit(); + if (!viewFrustum) { + viewFrustum = std::make_shared(args->getViewFrustum()); + } else { + *viewFrustum = args->getViewFrustum(); } - if (_updateFrustums) { - updateFrustum(args->getViewFrustum(), _viewFrustumMeshVertices); + // Return shadow frustum + auto& shadowFrustum = output[SHADOW_FRUSTUM].edit(); + auto lightStage = args->_scene->getStage(LightStage::getName()); + if (lightStage) { + auto globalShadow = lightStage->getCurrentKeyShadow(); - auto lightStage = renderContext->_scene->getStage(); - assert(lightStage); - - const auto globalShadow = lightStage->getCurrentKeyShadow(); if (globalShadow) { - updateFrustum(*globalShadow->getFrustum(), _shadowFrustumMeshVertices); + shadowFrustum = globalShadow->getFrustum(); + } else { + shadowFrustum.reset(); } + } else { + shadowFrustum.reset(); } - - if (!_pipeline) { - auto vs = gpu::StandardShaderLib::getDrawTransformVertexPositionVS(); - auto ps = gpu::StandardShaderLib::getDrawColorPS(); - gpu::ShaderPointer program = gpu::Shader::createProgram(vs, ps); - - gpu::Shader::BindingSet slotBindings; - slotBindings.insert(gpu::Shader::Binding("color", 0)); - gpu::Shader::makeProgram(*program, slotBindings); - - gpu::StatePointer state = gpu::StatePointer(new gpu::State()); - state->setDepthTest(gpu::State::DepthTest(true, false)); - _pipeline = gpu::Pipeline::create(program, state); - } - - // Render the frustums in wireframe - gpu::doInBatch(args->_context, [&](gpu::Batch& batch) { - args->_batch = &batch; - batch.setViewportTransform(args->_viewport); - batch.setStateScissorRect(args->_viewport); - - glm::mat4 projMat; - Transform viewMat; - args->getViewFrustum().evalProjectionMatrix(projMat); - args->getViewFrustum().evalViewTransform(viewMat); - - batch.setProjectionTransform(projMat); - batch.setViewTransform(viewMat); - batch.setPipeline(_pipeline); - batch.setIndexBuffer(_frustumMeshIndices); - - batch._glUniform4f(0, 1.0f, 1.0f, 0.0f, 1.0f); - batch.setInputStream(0, _viewFrustumMeshStream); - batch.drawIndexed(gpu::LINE_STRIP, sizeof(indexData) / sizeof(indexData[0]), 0U); - - batch._glUniform4f(0, 1.0f, 0.0f, 0.0f, 1.0f); - batch.setInputStream(0, _shadowFrustumMeshStream); - batch.drawIndexed(gpu::LINE_STRIP, sizeof(indexData) / sizeof(indexData[0]), 0U); - - args->_batch = nullptr; - }); -} - -void DrawFrustums::updateFrustum(const ViewFrustum& frustum, gpu::BufferView& vertexBuffer) { - auto& vertices = vertexBuffer.edit >(); - vertices[0] = frustum.getNearTopLeft(); - vertices[1] = frustum.getNearTopRight(); - vertices[2] = frustum.getNearBottomRight(); - vertices[3] = frustum.getNearBottomLeft(); - vertices[4] = frustum.getFarTopLeft(); - vertices[5] = frustum.getFarTopRight(); - vertices[6] = frustum.getFarBottomRight(); - vertices[7] = frustum.getFarBottomLeft(); } diff --git a/libraries/render-utils/src/RenderDeferredTask.h b/libraries/render-utils/src/RenderDeferredTask.h index bf457d7fcb..40ae503fb7 100644 --- a/libraries/render-utils/src/RenderDeferredTask.h +++ b/libraries/render-utils/src/RenderDeferredTask.h @@ -170,38 +170,20 @@ public: void run(const render::RenderContextPointer& renderContext, const gpu::FramebufferPointer& srcFramebuffer); }; -class DrawFrustumsConfig : public render::Job::Config { - Q_OBJECT - Q_PROPERTY(bool isFrozen MEMBER isFrozen NOTIFY dirty) +class ExtractFrustums { public: - DrawFrustumsConfig(bool enabled = false) : JobConfig(enabled) {} + enum Frustum { + VIEW_FRUSTUM, + SHADOW_FRUSTUM, - bool isFrozen{ false }; -signals: - void dirty(); + FRUSTUM_COUNT + }; -}; + using Output = render::VaryingArray; + using JobModel = render::Job::ModelO; -class DrawFrustums { -public: - using Config = DrawFrustumsConfig; - using JobModel = render::Job::Model; - - void configure(const Config& configuration); - void run(const render::RenderContextPointer& renderContext); - -private: - - bool _updateFrustums{ true }; - gpu::PipelinePointer _pipeline; - gpu::BufferView _frustumMeshIndices; - gpu::BufferView _viewFrustumMeshVertices; - gpu::BufferView _shadowFrustumMeshVertices; - gpu::BufferStream _viewFrustumMeshStream; - gpu::BufferStream _shadowFrustumMeshStream; - - static void updateFrustum(const ViewFrustum& frustum, gpu::BufferView& vertexBuffer); + void run(const render::RenderContextPointer& renderContext, Output& output); }; class RenderDeferredTaskConfig : public render::Task::Config { diff --git a/libraries/render/src/render/DrawTask.cpp b/libraries/render/src/render/DrawTask.cpp index 710507bd79..0f4137e38d 100755 --- a/libraries/render/src/render/DrawTask.cpp +++ b/libraries/render/src/render/DrawTask.cpp @@ -20,7 +20,7 @@ #include #include #include - +#include #include #include @@ -215,3 +215,85 @@ void DrawBounds::run(const RenderContextPointer& renderContext, }); } +gpu::PipelinePointer DrawFrustum::_pipeline; +gpu::BufferView DrawFrustum::_frustumMeshIndices; + +DrawFrustum::DrawFrustum(const glm::vec3& color) : + _color{ color } { + _frustumMeshVertices = gpu::BufferView(std::make_shared(sizeof(glm::vec3) * 8, nullptr), gpu::Element::VEC3F_XYZ); + _frustumMeshStream.addBuffer(_frustumMeshVertices._buffer, _frustumMeshVertices._offset, _frustumMeshVertices._stride); +} + +void DrawFrustum::configure(const Config& configuration) { + _updateFrustum = !configuration.isFrozen; +} + +void DrawFrustum::run(const render::RenderContextPointer& renderContext, const Input& input) { + assert(renderContext->args); + assert(renderContext->args->_context); + + RenderArgs* args = renderContext->args; + if (input) { + const auto& frustum = *input; + + static uint8_t indexData[] = { 0, 1, 2, 3, 0, 4, 5, 6, 7, 4, 5, 1, 2, 6, 7, 3 }; + + if (!_frustumMeshIndices._buffer) { + auto indices = std::make_shared(sizeof(indexData), indexData); + _frustumMeshIndices = gpu::BufferView(indices, gpu::Element(gpu::SCALAR, gpu::UINT8, gpu::INDEX)); + } + + if (!_pipeline) { + auto vs = gpu::StandardShaderLib::getDrawTransformVertexPositionVS(); + auto ps = gpu::StandardShaderLib::getDrawColorPS(); + gpu::ShaderPointer program = gpu::Shader::createProgram(vs, ps); + + gpu::Shader::BindingSet slotBindings; + slotBindings.insert(gpu::Shader::Binding("color", 0)); + gpu::Shader::makeProgram(*program, slotBindings); + + gpu::StatePointer state = gpu::StatePointer(new gpu::State()); + state->setDepthTest(gpu::State::DepthTest(true, false)); + _pipeline = gpu::Pipeline::create(program, state); + } + + if (_updateFrustum) { + updateFrustum(frustum); + } + + // Render the frustums in wireframe + gpu::doInBatch(args->_context, [&](gpu::Batch& batch) { + args->_batch = &batch; + batch.setViewportTransform(args->_viewport); + batch.setStateScissorRect(args->_viewport); + + glm::mat4 projMat; + Transform viewMat; + args->getViewFrustum().evalProjectionMatrix(projMat); + args->getViewFrustum().evalViewTransform(viewMat); + + batch.setProjectionTransform(projMat); + batch.setViewTransform(viewMat); + batch.setPipeline(_pipeline); + batch.setIndexBuffer(_frustumMeshIndices); + + batch._glUniform4f(0, _color.x, _color.y, _color.z, 1.0f); + batch.setInputStream(0, _frustumMeshStream); + batch.drawIndexed(gpu::LINE_STRIP, sizeof(indexData) / sizeof(indexData[0]), 0U); + + args->_batch = nullptr; + }); + } +} + +void DrawFrustum::updateFrustum(const ViewFrustum& frustum) { + auto& vertices = _frustumMeshVertices.edit >(); + vertices[0] = frustum.getNearTopLeft(); + vertices[1] = frustum.getNearTopRight(); + vertices[2] = frustum.getNearBottomRight(); + vertices[3] = frustum.getNearBottomLeft(); + vertices[4] = frustum.getFarTopLeft(); + vertices[5] = frustum.getFarTopRight(); + vertices[6] = frustum.getFarBottomRight(); + vertices[7] = frustum.getFarBottomLeft(); +} diff --git a/libraries/render/src/render/DrawTask.h b/libraries/render/src/render/DrawTask.h index 896ccef842..5d98c37c21 100755 --- a/libraries/render/src/render/DrawTask.h +++ b/libraries/render/src/render/DrawTask.h @@ -70,6 +70,43 @@ private: int _colorLocation { -1 }; }; +class DrawFrustumConfig : public render::JobConfig { + Q_OBJECT + Q_PROPERTY(bool isFrozen MEMBER isFrozen NOTIFY dirty) +public: + + DrawFrustumConfig(bool enabled = false) : JobConfig(enabled) {} + + bool isFrozen{ false }; +signals: + void dirty(); + +}; + +class DrawFrustum { +public: + using Config = DrawFrustumConfig; + using Input = ViewFrustumPointer; + using JobModel = render::Job::ModelI; + + DrawFrustum(const glm::vec3& color = glm::vec3(1.0f, 1.0f, 1.0f)); + + void configure(const Config& configuration); + void run(const render::RenderContextPointer& renderContext, const Input& input); + +private: + + static gpu::PipelinePointer _pipeline; + static gpu::BufferView _frustumMeshIndices; + + bool _updateFrustum{ true }; + gpu::BufferView _frustumMeshVertices; + gpu::BufferStream _frustumMeshStream; + glm::vec3 _color; + + void updateFrustum(const ViewFrustum& frustum); +}; + } #endif // hifi_render_DrawTask_h diff --git a/libraries/render/src/render/SortTask.cpp b/libraries/render/src/render/SortTask.cpp index a97d795736..63673a71a5 100644 --- a/libraries/render/src/render/SortTask.cpp +++ b/libraries/render/src/render/SortTask.cpp @@ -151,11 +151,7 @@ void DepthSortShapesAndComputeBounds::run(const RenderContextPointer& renderCont AABox bounds; depthSortItems(renderContext, _frontToBack, inItems, outItems->second, &bounds); - if (!outBounds.isNull()) { - outBounds += bounds; - } else { - outBounds = bounds; - } + outBounds += bounds; } } diff --git a/libraries/shared/src/Transform.h b/libraries/shared/src/Transform.h index 71d8b6c915..7a39314f4d 100644 --- a/libraries/shared/src/Transform.h +++ b/libraries/shared/src/Transform.h @@ -149,7 +149,7 @@ public: Vec4 transform(const Vec4& pos) const; Vec3 transform(const Vec3& pos) const; - Vec3 transformDirection(const Vec3& pos) const; + Vec3 transformDirection(const Vec3& dir) const; bool containsNaN() const { return isNaN(_rotation) || isNaN(glm::dot(_scale, _translation)); } @@ -542,10 +542,10 @@ inline Transform::Vec3 Transform::transform(const Vec3& pos) const { return Vec3(result.x / result.w, result.y / result.w, result.z / result.w); } -inline Transform::Vec3 Transform::transformDirection(const Vec3& pos) const { +inline Transform::Vec3 Transform::transformDirection(const Vec3& dir) const { Mat4 m; getMatrix(m); - Vec4 result = m * Vec4(pos, 0.0f); + Vec4 result = m * Vec4(dir, 0.0f); return Vec3(result.x, result.y, result.z); } diff --git a/scripts/developer/utilities/render/shadow.qml b/scripts/developer/utilities/render/shadow.qml index 1b4e647c77..8548ba4119 100644 --- a/scripts/developer/utilities/render/shadow.qml +++ b/scripts/developer/utilities/render/shadow.qml @@ -14,20 +14,24 @@ import QtQuick.Controls 1.4 Column { id: root spacing: 8 - property var config: Render.getConfig("RenderMainView.DrawFrustums"); + property var viewConfig: Render.getConfig("RenderMainView.DrawViewFrustum"); + property var shadowConfig: Render.getConfig("RenderMainView.DrawShadowFrustum"); Component.onCompleted: { - config.enabled = true; + viewConfig.enabled = true; + shadowConfig.enabled = true; } Component.onDestruction: { - config.enabled = false; + viewConfig.enabled = false; + shadowConfig.enabled = false; } CheckBox { text: "Freeze Frustums" checked: false onCheckedChanged: { - config.isFrozen = checked; + viewConfig.isFrozen = checked; + shadowConfig.isFrozen = checked; } } Row { @@ -39,7 +43,7 @@ Column { } Label { text: "Shadow" - color: "red" + color: "blue" font.italic: true } } From 14275b1cf31090cb8e9a759202527e6efda43b2e Mon Sep 17 00:00:00 2001 From: Olivier Prat Date: Wed, 15 Nov 2017 15:42:04 +0100 Subject: [PATCH 33/34] Added asserts in LightStage to catch shadow disappearance when domain is automatically reloaded --- .../src/DeferredLightingEffect.cpp | 2 +- libraries/render-utils/src/LightClusters.cpp | 2 +- libraries/render-utils/src/LightStage.cpp | 45 ++++++++++++----- libraries/render-utils/src/LightStage.h | 50 +++++++++++-------- 4 files changed, 63 insertions(+), 36 deletions(-) diff --git a/libraries/render-utils/src/DeferredLightingEffect.cpp b/libraries/render-utils/src/DeferredLightingEffect.cpp index dcb16c08f8..646b19198b 100644 --- a/libraries/render-utils/src/DeferredLightingEffect.cpp +++ b/libraries/render-utils/src/DeferredLightingEffect.cpp @@ -620,7 +620,7 @@ void RenderDeferredLocals::run(const render::RenderContextPointer& renderContext auto& lightIndices = lightClusters->_visibleLightIndices; if (!lightIndices.empty() && lightIndices[0] > 0) { // Bind the global list of lights and the visible lights this frame - batch.setUniformBuffer(deferredLightingEffect->_localLightLocations->lightBufferUnit, lightClusters->_lightStage->_lightArrayBuffer); + batch.setUniformBuffer(deferredLightingEffect->_localLightLocations->lightBufferUnit, lightClusters->_lightStage->getLightArrayBuffer()); batch.setUniformBuffer(LIGHT_CLUSTER_GRID_FRUSTUM_GRID_SLOT, lightClusters->_frustumGridBuffer); batch.setUniformBuffer(LIGHT_CLUSTER_GRID_CLUSTER_GRID_SLOT, lightClusters->_clusterGridBuffer); diff --git a/libraries/render-utils/src/LightClusters.cpp b/libraries/render-utils/src/LightClusters.cpp index ab1e194498..eedb9053c7 100644 --- a/libraries/render-utils/src/LightClusters.cpp +++ b/libraries/render-utils/src/LightClusters.cpp @@ -727,7 +727,7 @@ void DebugLightClusters::run(const render::RenderContextPointer& renderContext, batch.setModelTransform(Transform()); // Bind the Light CLuster data strucutre - batch.setUniformBuffer(LIGHT_GPU_SLOT, lightClusters->_lightStage->_lightArrayBuffer); + batch.setUniformBuffer(LIGHT_GPU_SLOT, lightClusters->_lightStage->getLightArrayBuffer()); batch.setUniformBuffer(LIGHT_CLUSTER_GRID_FRUSTUM_GRID_SLOT, lightClusters->_frustumGridBuffer); batch.setUniformBuffer(LIGHT_CLUSTER_GRID_CLUSTER_GRID_SLOT, lightClusters->_clusterGridBuffer); batch.setUniformBuffer(LIGHT_CLUSTER_GRID_CLUSTER_CONTENT_SLOT, lightClusters->_clusterContentBuffer); diff --git a/libraries/render-utils/src/LightStage.cpp b/libraries/render-utils/src/LightStage.cpp index 160fa2deea..ba705e56cb 100644 --- a/libraries/render-utils/src/LightStage.cpp +++ b/libraries/render-utils/src/LightStage.cpp @@ -25,11 +25,17 @@ LightStage::Shadow::Schema::Schema() : } +gpu::FramebufferPointer LightStage::Shadow::framebuffer; +gpu::TexturePointer LightStage::Shadow::map; + LightStage::Shadow::Shadow(model::LightPointer light) : _light{ light}, _frustum{ std::make_shared() } { - framebuffer = gpu::FramebufferPointer(gpu::Framebuffer::createShadowmap(MAP_SIZE)); - map = framebuffer->getDepthStencilBuffer(); Schema schema; _schemaBuffer = std::make_shared(sizeof(Schema), (const gpu::Byte*) &schema); + + if (!framebuffer) { + framebuffer = gpu::FramebufferPointer(gpu::Framebuffer::createShadowmap(MAP_SIZE)); + map = framebuffer->getDepthStencilBuffer(); + } } void LightStage::Shadow::setKeylightFrustum(const ViewFrustum& viewFrustum, @@ -122,11 +128,9 @@ LightStage::Index LightStage::findLight(const LightPointer& light) const { } else { return (*found).second; } - } LightStage::Index LightStage::addLight(const LightPointer& light) { - auto found = _lightMap.find(light); if (found == _lightMap.end()) { auto lightId = _lights.newElement(light); @@ -137,6 +141,7 @@ LightStage::Index LightStage::addLight(const LightPointer& light) { if (lightId >= (Index) _descs.size()) { _descs.emplace_back(Desc()); } else { + assert(_descs[lightId].shadowId == INVALID_INDEX); _descs.emplace(_descs.begin() + lightId, Desc()); } @@ -155,6 +160,7 @@ LightStage::Index LightStage::addShadow(Index lightIndex) { auto light = getLight(lightIndex); Index shadowId = INVALID_INDEX; if (light) { + assert(_descs[lightIndex].shadowId == INVALID_INDEX); shadowId = _shadows.newElement(std::make_shared(light)); _descs[lightIndex].shadowId = shadowId; } @@ -162,18 +168,20 @@ LightStage::Index LightStage::addShadow(Index lightIndex) { } LightStage::LightPointer LightStage::removeLight(Index index) { - LightPointer removed = _lights.freeElement(index); - - if (removed) { + LightPointer removedLight = _lights.freeElement(index); + if (removedLight) { auto shadowId = _descs[index].shadowId; // Remove shadow if one exists for this light if (shadowId != INVALID_INDEX) { - _shadows.freeElement(shadowId); + auto removedShadow = _shadows.freeElement(shadowId); + assert(removedShadow); + assert(removedShadow->getLight() == removedLight); } - _lightMap.erase(removed); + _lightMap.erase(removedLight); _descs[index] = Desc(); } - return removed; + assert(_descs.size() <= index || _descs[index].shadowId == INVALID_INDEX); + return removedLight; } LightStage::LightPointer LightStage::getCurrentKeyLight() const { @@ -197,7 +205,9 @@ LightStage::ShadowPointer LightStage::getCurrentKeyShadow() const { if (!_currentFrame._sunLights.empty()) { keyLightId = _currentFrame._sunLights.front(); } - return getShadow(keyLightId); + auto shadow = getShadow(keyLightId); + assert(shadow == nullptr || shadow->getLight() == getLight(keyLightId)); + return shadow; } LightStage::LightAndShadow LightStage::getCurrentKeyLightAndShadow() const { @@ -205,7 +215,18 @@ LightStage::LightAndShadow LightStage::getCurrentKeyLightAndShadow() const { if (!_currentFrame._sunLights.empty()) { keyLightId = _currentFrame._sunLights.front(); } - return LightAndShadow(getLight(keyLightId), getShadow(keyLightId)); + auto shadow = getShadow(keyLightId); + auto light = getLight(keyLightId); + assert(shadow == nullptr || shadow->getLight() == light); + return LightAndShadow(light, shadow); +} + +LightStage::Index LightStage::getShadowId(Index lightId) const { + if (checkLightId(lightId)) { + return _descs[lightId].shadowId; + } else { + return INVALID_INDEX; + } } void LightStage::updateLightArrayBuffer(Index lightId) { diff --git a/libraries/render-utils/src/LightStage.h b/libraries/render-utils/src/LightStage.h index 052c8dd222..fa581c8315 100644 --- a/libraries/render-utils/src/LightStage.h +++ b/libraries/render-utils/src/LightStage.h @@ -58,10 +58,15 @@ public: const UniformBufferView& getBuffer() const { return _schemaBuffer; } - gpu::FramebufferPointer framebuffer; - gpu::TexturePointer map; + // Shadow maps are shared among all lights for the moment as only one key light + // is used. + static gpu::FramebufferPointer framebuffer; + static gpu::TexturePointer map; + + const model::LightPointer& getLight() const { return _light; } protected: + model::LightPointer _light; std::shared_ptr _frustum; @@ -78,16 +83,11 @@ public: }; UniformBufferView _schemaBuffer = nullptr; - friend class Light; }; + using ShadowPointer = std::shared_ptr; using Shadows = render::indexed_container::IndexedPointerVector; - struct Desc { - Index shadowId { INVALID_INDEX }; - }; - using Descs = std::vector; - Index findLight(const LightPointer& light) const; Index addLight(const LightPointer& light); @@ -105,20 +105,18 @@ public: return _lights.get(lightId); } - Index getShadowId(Index lightId) const { - if (checkLightId(lightId)) { - return _descs[lightId].shadowId; - } else { - return INVALID_INDEX; - } - } + Index getShadowId(Index lightId) const; + ShadowPointer getShadow(Index lightId) const { return _shadows.get(getShadowId(lightId)); } using LightAndShadow = std::pair; LightAndShadow getLightAndShadow(Index lightId) const { - return LightAndShadow(getLight(lightId), getShadow(lightId)); + auto light = getLight(lightId); + auto shadow = getShadow(lightId); + assert(shadow == nullptr || shadow->getLight() == light); + return LightAndShadow(light, shadow); } LightPointer getCurrentKeyLight() const; @@ -128,9 +126,8 @@ public: LightStage(); - Lights _lights; - LightMap _lightMap; - Descs _descs; + gpu::BufferPointer getLightArrayBuffer() const { return _lightArrayBuffer; } + void updateLightArrayBuffer(Index lightId); class Frame { public: @@ -159,15 +156,24 @@ public: Frame _currentFrame; - gpu::BufferPointer _lightArrayBuffer; - void updateLightArrayBuffer(Index lightId); +protected: + struct Desc { + Index shadowId{ INVALID_INDEX }; + }; + using Descs = std::vector; + + gpu::BufferPointer _lightArrayBuffer; + + Lights _lights; Shadows _shadows; + Descs _descs; + LightMap _lightMap; + }; using LightStagePointer = std::shared_ptr; - class LightStageSetup { public: using JobModel = render::Job::Model; From b49891c0f868caab7c99e58011994e4e470fdd6c Mon Sep 17 00:00:00 2001 From: "Anthony J. Thibault" Date: Wed, 15 Nov 2017 11:27:42 -0800 Subject: [PATCH 34/34] Bug fix for MyAvatar.getEyeHeight() --- libraries/avatars-renderer/src/avatars-renderer/Avatar.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/avatars-renderer/src/avatars-renderer/Avatar.cpp b/libraries/avatars-renderer/src/avatars-renderer/Avatar.cpp index 49d2431098..6bf9cc1666 100644 --- a/libraries/avatars-renderer/src/avatars-renderer/Avatar.cpp +++ b/libraries/avatars-renderer/src/avatars-renderer/Avatar.cpp @@ -1579,7 +1579,7 @@ float Avatar::getEyeHeight() const { if (QThread::currentThread() != thread()) { float result = DEFAULT_AVATAR_EYE_HEIGHT; - BLOCKING_INVOKE_METHOD(const_cast(this), "getHeight", Q_RETURN_ARG(float, result)); + BLOCKING_INVOKE_METHOD(const_cast(this), "getEyeHeight", Q_RETURN_ARG(float, result)); return result; }