summaryrefslogtreecommitdiffstats
path: root/src/Authoring/Studio/Render/StudioRotationWidget.cpp
diff options
context:
space:
mode:
authorOswald Buddenhagen <oswald.buddenhagen@qt.io>2017-10-06 11:49:09 +0000
committerOswald Buddenhagen <oswald.buddenhagen@qt.io>2017-10-06 16:58:43 +0200
commit07840524085bd1785b8f9142b03d942f678c5c51 (patch)
tree499c1674fdd1b3e0c07688d8e4e56748dfea2ca3 /src/Authoring/Studio/Render/StudioRotationWidget.cpp
Initial import
Diffstat (limited to 'src/Authoring/Studio/Render/StudioRotationWidget.cpp')
-rw-r--r--src/Authoring/Studio/Render/StudioRotationWidget.cpp437
1 files changed, 437 insertions, 0 deletions
diff --git a/src/Authoring/Studio/Render/StudioRotationWidget.cpp b/src/Authoring/Studio/Render/StudioRotationWidget.cpp
new file mode 100644
index 00000000..813cf7ac
--- /dev/null
+++ b/src/Authoring/Studio/Render/StudioRotationWidget.cpp
@@ -0,0 +1,437 @@
+/****************************************************************************
+**
+** Copyright (C) 2006 NVIDIA Corporation.
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of Qt 3D Studio.
+**
+** $QT_BEGIN_LICENSE:GPL-EXCEPT$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+#include "stdafx.h"
+#include "StudioWidgetImpl.h"
+#include "foundation/Qt3DSAtomic.h"
+#include "render/Qt3DSRenderContext.h"
+#include "render/Qt3DSRenderVertexBuffer.h"
+#include "UICRenderNode.h"
+#include "foundation/Qt3DSContainers.h"
+#include "UICRenderShaderCodeGeneratorV2.h"
+#include "UICRenderCamera.h"
+#include "render/Qt3DSRenderShaderProgram.h"
+#include "StudioUtils.h"
+
+using namespace uic::widgets;
+
+namespace {
+
+struct SRotationWidget : public SStudioWidgetImpl<StudioWidgetTypes::Rotation>
+{
+ typedef SStudioWidgetImpl<StudioWidgetTypes::Rotation> TBase;
+ NVRenderInputAssembler *m_XAxis;
+ NVRenderInputAssembler *m_YAxis;
+ NVRenderInputAssembler *m_ZAxis;
+ NVRenderInputAssembler *m_CameraAxis;
+ // We use a rect to clear the Z buffer.
+ NVRenderInputAssembler *m_CameraRect;
+
+ NVRenderShaderProgram *m_ZClearShader;
+
+ volatile QT3DSI32 mRefCount;
+
+ SRotationWidget(NVAllocatorCallback &inAlloc)
+ : TBase(inAlloc)
+ , m_XAxis(nullptr)
+ , m_YAxis(nullptr)
+ , m_ZAxis(nullptr)
+ , m_CameraAxis(nullptr)
+ , m_CameraRect(nullptr)
+ , m_ZClearShader(nullptr)
+ , mRefCount(0)
+ {
+ }
+
+ QT3DS_IMPLEMENT_REF_COUNT_ADDREF_RELEASE(m_Allocator)
+
+ NVRenderInputAssembler *CreateRing(IRenderWidgetContext &inWidgetContext,
+ NVRenderContext &inRenderContext, QT3DSVec3 inDirection,
+ QT3DSF32 inInnerRadius, QT3DSF32 inOuterRadius, QT3DSF32 inRingColor,
+ const char *inRingName)
+ {
+ QT3DS_ASSERT(inInnerRadius <= inOuterRadius);
+ CRegisteredString theItemName = inRenderContext.GetStringTable().RegisterStr(inRingName);
+ NVRenderInputAssembler *retval = inWidgetContext.GetInputAssembler(theItemName);
+ if (retval) {
+ return retval;
+ }
+
+ TResultVecType theVertexData(m_Allocator, "SRotationWidget::theVertexData");
+
+ QT3DSI32 numSubDivisions = 50;
+ QT3DSF32 arcRad = 360.0f / (QT3DSF32)numSubDivisions;
+ TORAD(arcRad);
+ QT3DSVec3 tempCross = inDirection.cross(QT3DSVec3(0, 1, 0));
+ if (tempCross.magnitudeSquared() < .05f)
+ tempCross = inDirection.cross(QT3DSVec3(1, 0, 0));
+
+ QT3DSVec3 upDir = inDirection.cross(tempCross);
+ QT3DSVec3 leftDir = upDir.cross(inDirection);
+ upDir.normalize();
+ leftDir.normalize();
+
+ QT3DSF32 ringWidth = inOuterRadius - inInnerRadius;
+ QT3DSF32 ringHalfWidth = ringWidth / 2.0f;
+ QT3DSF32 middleRadius = inInnerRadius + ringHalfWidth;
+
+ for (QT3DSI32 idx = 0, numLooper = numSubDivisions; idx < numLooper; ++idx) {
+ QT3DSF32 startDeg = idx * 360.0f / numSubDivisions;
+ QT3DSF32 endDeg = (idx + 1) * 360.0f / numSubDivisions;
+ QT3DSF32 startRad(startDeg);
+ QT3DSF32 endRad(endDeg);
+ TORAD(startRad);
+ TORAD(endRad);
+ QT3DSF32 startSin = NVSin(startRad);
+ QT3DSF32 endSin = NVSin(endRad);
+ QT3DSF32 startCos = NVCos(startRad);
+ QT3DSF32 endCos = NVCos(endRad);
+
+ QT3DSVec3 startDir = startSin * upDir + startCos * leftDir;
+ QT3DSVec3 endDir = endSin * upDir + endCos * leftDir;
+
+ QT3DSVec3 discStart = startDir * inInnerRadius;
+ QT3DSVec3 discEnd = endDir * inInnerRadius;
+ QT3DSVec3 ringStart = startDir * inOuterRadius;
+ QT3DSVec3 ringEnd = endDir * inOuterRadius;
+
+ QT3DSVec3 middleStart = startDir * (middleRadius);
+ QT3DSVec3 middleEnd = endDir * (middleRadius);
+ QT3DSVec3 middleTopLeft = middleStart + inDirection * ringHalfWidth;
+ QT3DSVec3 middleTopRight = middleStart - inDirection * ringHalfWidth;
+ QT3DSVec3 middleBottomLeft = middleEnd + inDirection * ringHalfWidth;
+ QT3DSVec3 middleBottomRight = middleEnd - inDirection * ringHalfWidth;
+
+ // Now two tris for the ring
+ theVertexData.push_back(QT3DSVec4(discStart, inRingColor));
+ theVertexData.push_back(QT3DSVec4(ringStart, inRingColor));
+ theVertexData.push_back(QT3DSVec4(ringEnd, inRingColor));
+ theVertexData.push_back(QT3DSVec4(ringEnd, inRingColor));
+ theVertexData.push_back(QT3DSVec4(discEnd, inRingColor));
+ theVertexData.push_back(QT3DSVec4(discStart, inRingColor));
+ // Two tris for the ring that is perpendicular to the viewer
+ theVertexData.push_back(QT3DSVec4(middleTopLeft, inRingColor));
+ theVertexData.push_back(QT3DSVec4(middleTopRight, inRingColor));
+ theVertexData.push_back(QT3DSVec4(middleBottomRight, inRingColor));
+ theVertexData.push_back(QT3DSVec4(middleBottomRight, inRingColor));
+ theVertexData.push_back(QT3DSVec4(middleBottomLeft, inRingColor));
+ theVertexData.push_back(QT3DSVec4(middleTopLeft, inRingColor));
+ }
+
+ QT3DSU32 stride;
+ QT3DSU32 offset = 0;
+ NVRenderAttribLayout *theAttribLayout = &inWidgetContext.CreateAttributeLayout(
+ IStudioWidget::GetVertexBufferAttributesAndStride(stride));
+ NVRenderVertexBuffer *theVertexBuffer = &inWidgetContext.GetOrCreateVertexBuffer(
+ theItemName, stride, toU8DataRef(theVertexData.begin(), theVertexData.size()));
+ retval = &inWidgetContext.GetOrCreateInputAssembler(
+ theItemName, theAttribLayout, toConstDataRef(&theVertexBuffer, 1), nullptr,
+ toConstDataRef(&stride, 1), toConstDataRef(&offset, 1));
+
+ return retval;
+ }
+
+ NVRenderInputAssembler *CreateRect(IRenderWidgetContext &inWidgetContext,
+ NVRenderContext &inRenderContext, QT3DSVec3 inDirection,
+ QT3DSF32 inHalfWidth, const char *inItemName)
+ {
+ CRegisteredString theItemName = inRenderContext.GetStringTable().RegisterStr(inItemName);
+ NVRenderInputAssembler *retval = inWidgetContext.GetInputAssembler(theItemName);
+ if (retval) {
+ return retval;
+ }
+
+ QT3DSVec3 tempCross = inDirection.cross(QT3DSVec3(0, 1, 0));
+ if (tempCross.magnitudeSquared() < .05f)
+ tempCross = inDirection.cross(QT3DSVec3(1, 0, 0));
+
+ QT3DSVec3 upDir = inDirection.cross(tempCross);
+ QT3DSVec3 leftDir = upDir.cross(inDirection);
+
+ TResultVecType theVertexData(m_Allocator, "SRotationWidget::theVertexData");
+
+ theVertexData.push_back(QT3DSVec4(upDir * inHalfWidth, 0.0f));
+ theVertexData.push_back(QT3DSVec4(leftDir * inHalfWidth, 0.0f));
+ theVertexData.push_back(QT3DSVec4(upDir * -1.0f * inHalfWidth, 0.0f));
+
+ theVertexData.push_back(QT3DSVec4(upDir * -1.0f * inHalfWidth, 0.0f));
+ theVertexData.push_back(QT3DSVec4(leftDir * -1.0f * inHalfWidth, 0.0f));
+ theVertexData.push_back(QT3DSVec4(upDir * inHalfWidth, 0.0f));
+
+ QT3DSU32 stride;
+ QT3DSU32 offset = 0;
+ NVRenderAttribLayout *theAttribLayout = &inWidgetContext.CreateAttributeLayout(
+ IStudioWidget::GetVertexBufferAttributesAndStride(stride));
+ NVRenderVertexBuffer *theVertexBuffer = &inWidgetContext.GetOrCreateVertexBuffer(
+ theItemName, stride, toU8DataRef(theVertexData.begin(), theVertexData.size()));
+
+ retval = &inWidgetContext.GetOrCreateInputAssembler(
+ theItemName, theAttribLayout, toConstDataRef(&theVertexBuffer, 1), nullptr,
+ toConstDataRef(&stride, 1), toConstDataRef(&offset, 1));
+ return retval;
+ }
+
+ NVRenderShaderProgram *CreateZClearShader(IRenderWidgetContext &inWidgetContext,
+ NVRenderContext &inRenderContext,
+ const char *inItemName)
+ {
+ CRegisteredString theItemName = inRenderContext.GetStringTable().RegisterStr(inItemName);
+ NVRenderShaderProgram *retval = inWidgetContext.GetShader(theItemName);
+ if (retval) {
+ return retval;
+ }
+
+ uic::render::IShaderProgramGenerator &theGenerator(inWidgetContext.GetProgramGenerator());
+ theGenerator.BeginProgram();
+ uic::render::IShaderStageGenerator &theVertexGenerator(
+ *theGenerator.GetStage(uic::render::ShaderGeneratorStages::Vertex));
+ uic::render::IShaderStageGenerator &theFragmentGenerator(
+ *theGenerator.GetStage(uic::render::ShaderGeneratorStages::Fragment));
+ theVertexGenerator.AddIncoming("attr_pos", "vec3");
+ theVertexGenerator.AddUniform("model_view_projection", "mat4");
+ theVertexGenerator.Append("void main() {");
+ theVertexGenerator.Append("\tgl_Position = model_view_projection * vec4(attr_pos, 1.0);");
+ theVertexGenerator.Append("}");
+ theFragmentGenerator.Append("void main() {");
+ theFragmentGenerator.Append("\tgl_FragColor.rgb = vec3(0.0, 0.0, 0.0);");
+ theFragmentGenerator.Append("\tgl_FragColor.a = 1.0;");
+ theFragmentGenerator.Append("}");
+ return inWidgetContext.CompileAndStoreShader(theItemName);
+ }
+
+ static inline QT3DSVec3 ToFixedCameraPos(const QT3DSVec3 &inCameraPos, const SCamera &inCamera)
+ {
+ if (inCamera.m_Flags.IsOrthographic()) {
+ return QT3DSVec3(inCameraPos.x, inCameraPos.y, -600.f);
+ }
+ QT3DSF32 multiplier = -600.f / inCameraPos.z;
+ return inCameraPos * multiplier;
+ }
+
+ void Render(IRenderWidgetContext &inWidgetContext, NVRenderContext &inRenderContext) override
+ {
+ // Widgets have to clear the depth buffer; they shouldn't interact with other components
+ // but they should self-occlude.
+ inRenderContext.SetDepthWriteEnabled(true);
+ inRenderContext.Clear(qt3ds::render::NVRenderClearValues::Depth);
+ inRenderContext.SetBlendFunction(qt3ds::render::NVRenderBlendFunctionArgument(
+ qt3ds::render::NVRenderSrcBlendFunc::SrcAlpha,
+ qt3ds::render::NVRenderDstBlendFunc::OneMinusSrcAlpha,
+ qt3ds::render::NVRenderSrcBlendFunc::One,
+ qt3ds::render::NVRenderDstBlendFunc::OneMinusSrcAlpha));
+ inRenderContext.SetBlendEquation(qt3ds::render::NVRenderBlendEquationArgument(
+ NVRenderBlendEquation::Add, NVRenderBlendEquation::Add));
+
+ float pixelRatio = float(devicePixelRatio());
+ QT3DSF32 theRingRadius = 100.0f * pixelRatio;
+ QT3DSF32 theRingWidth = 2.0f * pixelRatio;
+ QT3DSF32 theRingInner = theRingRadius;
+ QT3DSF32 theRingOuter = theRingRadius + theRingWidth;
+ if (m_XAxis == nullptr) {
+ TBase::SetupRender(inWidgetContext, inRenderContext);
+ m_PickShader = IStudioWidget::CreateWidgetPickShader(inWidgetContext, inRenderContext);
+ ;
+ m_XAxis = CreateRing(inWidgetContext, inRenderContext, QT3DSVec3(-1, 0, 0), theRingInner,
+ theRingOuter, 0.0f, "RotationWidgetXAxis");
+ m_YAxis = CreateRing(inWidgetContext, inRenderContext, QT3DSVec3(0, -1, 0), theRingInner,
+ theRingOuter, 0.0f, "RotationWidgetYAxis");
+ m_ZAxis = CreateRing(inWidgetContext, inRenderContext, QT3DSVec3(0, 0, -1), theRingInner,
+ theRingOuter, 0.0f, "RotationWidgetZAxis");
+ m_CameraAxis =
+ CreateRing(inWidgetContext, inRenderContext, QT3DSVec3(0, 0, -1), theRingInner + 5,
+ theRingOuter + 5, 0.0f, "RotationWidgetCameraAxis");
+ m_CameraRect = CreateRect(inWidgetContext, inRenderContext, QT3DSVec3(0, 0, -1), 200.0f,
+ "RotationWidgetZClear");
+ m_ZClearShader =
+ CreateZClearShader(inWidgetContext, inRenderContext, "RotationWidgetZClear");
+ }
+ QT3DSVec3 theXColor(GetXAxisColor());
+ QT3DSVec3 theYColor(GetYAxisColor());
+ QT3DSVec3 theZColor(GetZAxisColor());
+ QT3DSVec3 theRingColor(QT3DSVec3(.8, .8, .8));
+
+ QT3DSMat44 theMVP = TBase::SetupMVP(inWidgetContext);
+ inRenderContext.SetCullingEnabled(false);
+ QT3DSMat44 theCameraMVP = m_WidgetInfo.m_LayerProjection * m_CameraTranslationScale;
+
+ inRenderContext.SetBlendingEnabled(false);
+ inRenderContext.SetColorWritesEnabled(false);
+ inRenderContext.SetDepthTestEnabled(false);
+ inRenderContext.SetDepthWriteEnabled(true);
+ inRenderContext.SetActiveShader(m_ZClearShader);
+ inRenderContext.SetInputAssembler(m_CameraRect);
+ m_ZClearShader->SetPropertyValue("model_view_projection", theCameraMVP);
+ inRenderContext.Draw(NVRenderDrawMode::Triangles, m_CameraRect->GetVertexCount(), 0);
+
+ inRenderContext.SetColorWritesEnabled(true);
+ inRenderContext.SetActiveShader(m_Shader);
+ m_Shader->SetPropertyValue("model_view_projection", theCameraMVP);
+ inRenderContext.SetDepthTestEnabled(false);
+ inRenderContext.SetDepthWriteEnabled(false);
+ RenderSingleToneGeometry(StudioWidgetComponentIds::CameraPlane, theRingColor,
+ inRenderContext, m_CameraAxis);
+
+ inRenderContext.SetDepthTestEnabled(true);
+ inRenderContext.SetActiveShader(m_Shader);
+ m_Shader->SetPropertyValue("model_view_projection", theMVP);
+ RenderSingleToneGeometry(StudioWidgetComponentIds::XAxis, theXColor, inRenderContext,
+ m_XAxis);
+ RenderSingleToneGeometry(StudioWidgetComponentIds::YAxis, theYColor, inRenderContext,
+ m_YAxis);
+ RenderSingleToneGeometry(StudioWidgetComponentIds::ZAxis, theZColor, inRenderContext,
+ m_ZAxis);
+
+ if (m_RotationWedge.hasValue()) {
+ BeginImmediateDrawing(inWidgetContext, inRenderContext);
+
+ QT3DSMat33 theMVPRotation(m_WidgetInfo.m_CameraGlobalInverse.column0.getXYZ(),
+ m_WidgetInfo.m_CameraGlobalInverse.column1.getXYZ(),
+ m_WidgetInfo.m_CameraGlobalInverse.column2.getXYZ());
+ theMVPRotation = theMVPRotation.getInverse().getTranspose();
+
+ QT3DSVec3 theRotationAxis = theMVPRotation.transform(m_RotationWedge->m_RotationAxis);
+ QT3DSVec3 theStartDirection = theMVPRotation.transform(m_RotationWedge->m_StartDirection);
+ theRotationAxis.normalize();
+ theStartDirection.normalize();
+ QT3DSQuat theRotation(m_RotationWedge->m_Angle, theRotationAxis);
+ QT3DSVec3 theEndDirection = theRotation.rotate(theStartDirection);
+ inRenderContext.SetDepthWriteEnabled(true);
+ inRenderContext.Clear(qt3ds::render::NVRenderClearValues::Depth);
+ inRenderContext.SetDepthWriteEnabled(false);
+ inRenderContext.SetDepthTestEnabled(false);
+ inRenderContext.SetBlendingEnabled(true);
+ QT3DSVec4 lineColor(1, 1, 1, .7);
+ QT3DSVec4 fillColor(1, 1, 1, .2);
+ switch (m_Highlight) {
+ default:
+ break;
+ case StudioWidgetComponentIds::XAxis:
+ lineColor = QT3DSVec4(theXColor, .7);
+ fillColor = QT3DSVec4(theXColor, .2);
+ break;
+ case StudioWidgetComponentIds::YAxis:
+ lineColor = QT3DSVec4(theYColor, .7);
+ fillColor = QT3DSVec4(theYColor, .2);
+ break;
+ case StudioWidgetComponentIds::ZAxis:
+ lineColor = QT3DSVec4(theZColor, .7);
+ fillColor = QT3DSVec4(theZColor, .2);
+ break;
+ }
+ QT3DSVec3 theStartPos(m_WidgetInfo.m_Position);
+ QT3DSF32 theStartLineLen = theRingOuter * m_WidgetInfo.m_Scale;
+ if (m_Highlight == StudioWidgetComponentIds::CameraPlane)
+ theStartLineLen = (theRingOuter + 5) * m_WidgetInfo.m_Scale;
+ // Get the end line length in camera space.
+ QT3DSVec3 theGlobalStart = m_Node->GetGlobalPivot();
+ QT3DSQuat theGlobalRot(m_RotationWedge->m_Angle, m_RotationWedge->m_RotationAxis);
+ QT3DSVec3 theGlobalDir = theGlobalRot.rotate(m_RotationWedge->m_StartDirection);
+ QT3DSVec3 theGlobalEnd = theGlobalStart + theGlobalDir * m_RotationWedge->m_EndLineLen;
+ // Transform both start, end into camera space and get the length of the resulting
+ // vector
+ QT3DSVec3 theCameraStart = m_WidgetInfo.m_CameraGlobalInverse.transform(theGlobalStart);
+ QT3DSVec3 theCameraEnd = m_WidgetInfo.m_CameraGlobalInverse.transform(theGlobalEnd);
+ QT3DSF32 theCameraEndLineLen = QT3DSVec3(theCameraEnd - theCameraStart).magnitude();
+ QT3DSF32 theEndLineLen = theCameraEndLineLen;
+ // Draw lines in world space
+ SCamera &theCamera(*m_WidgetInfo.m_Camera);
+ QT3DSVec3 lineStart(ToFixedCameraPos(theStartPos, theCamera));
+ QT3DSVec3 startLineEnd(
+ ToFixedCameraPos(theStartPos + theStartDirection * theStartLineLen, theCamera));
+ QT3DSVec3 endLineEnd(ToFixedCameraPos(theCameraEnd, theCamera));
+ DrawImmediateLine(lineStart, startLineEnd, 1.0f, lineColor);
+ DrawImmediateLine(lineStart, endLineEnd, 1.0f, lineColor);
+ DrawFilledArc(theStartPos, theStartDirection, theStartLineLen, theRotationAxis,
+ m_RotationWedge->m_Angle, fillColor);
+ // Now setup the model-view-projection.
+ QT3DSMat44 theProjection = m_WidgetInfo.m_LayerProjection;
+ EndImmediateDrawing(inWidgetContext, inRenderContext, theProjection);
+
+ // Now we attempt to render some text. First we format it.
+
+ char textBuffer[25] = { 0 };
+ QT3DSF32 angleDeg(m_RotationWedge->m_Angle);
+ TODEG(angleDeg);
+ sprintf(textBuffer, "%.1f", angleDeg);
+ STextRenderInfo theInfo;
+ theInfo.m_Text = inRenderContext.GetStringTable().RegisterStr(textBuffer);
+ theInfo.m_HorizontalAlignment = TextHorizontalAlignment::Center;
+ theInfo.m_VerticalAlignment = TextVerticalAlignment::Bottom;
+ theInfo.m_FontSize = 12.0f * pixelRatio;
+ theInfo.m_Font = inRenderContext.GetStringTable().RegisterStr("TitilliumWeb-Regular");
+ QT3DSMat44 theTransMatrix(QT3DSMat44::createIdentity());
+ theTransMatrix.column3.x = endLineEnd.x;
+ theTransMatrix.column3.y = endLineEnd.y;
+ theTransMatrix.column3.z = endLineEnd.z;
+ // We want to scale the text *down* so that it looks better.
+ theTransMatrix.column0[0] = m_WidgetInfo.m_Scale * .8f;
+ theTransMatrix.column1[1] = m_WidgetInfo.m_Scale * .8f;
+ theTransMatrix.column2[2] = m_WidgetInfo.m_Scale * .8f;
+ QT3DSMat44 theTextMVP = theProjection * theTransMatrix;
+ inWidgetContext.RenderText(theInfo, QT3DSVec3(1, 1, 1), QT3DSVec3(.2, .2, .2), theTextMVP);
+ }
+ m_Highlight = StudioWidgetComponentIds::NoId;
+ }
+
+ void RenderPick(const QT3DSMat44 &inProjPremult, NVRenderContext &inRenderContext,
+ uic::render::SWindowDimensions /*inWinDimensions*/) override
+ {
+ if (m_XAxis && m_PickShader) {
+ QT3DSMat44 theCameraMVP =
+ inProjPremult * m_WidgetInfo.m_PureProjection * m_CameraTranslationScale;
+ QT3DSMat44 theMVP = inProjPremult * m_WidgetInfo.m_PureProjection * m_TranslationScale;
+
+ inRenderContext.SetDepthWriteEnabled(true);
+ inRenderContext.Clear(qt3ds::render::NVRenderClearValues::Depth);
+ inRenderContext.SetDepthTestEnabled(true);
+ inRenderContext.SetDepthWriteEnabled(true);
+ inRenderContext.SetBlendingEnabled(true);
+ inRenderContext.SetCullingEnabled(false);
+ inRenderContext.SetActiveShader(m_ZClearShader);
+ m_ZClearShader->SetPropertyValue("model_view_projection", theCameraMVP);
+ inRenderContext.SetInputAssembler(m_CameraRect);
+ inRenderContext.Draw(NVRenderDrawMode::Triangles, m_CameraRect->GetVertexCount(), 0);
+
+ inRenderContext.SetActiveShader(m_PickShader);
+ m_PickShader->SetPropertyValue("model_view_projection", theCameraMVP);
+ RenderPickBuffer(StudioWidgetComponentIds::CameraPlane, m_CameraAxis, inRenderContext);
+
+ m_PickShader->SetPropertyValue("model_view_projection", theMVP);
+
+ RenderPickBuffer(StudioWidgetComponentIds::XAxis, m_XAxis, inRenderContext);
+ RenderPickBuffer(StudioWidgetComponentIds::YAxis, m_YAxis, inRenderContext);
+ RenderPickBuffer(StudioWidgetComponentIds::ZAxis, m_ZAxis, inRenderContext);
+ }
+ }
+};
+}
+
+IStudioWidget &IStudioWidget::CreateRotationWidget(NVAllocatorCallback &inAlloc)
+{
+ return *QT3DS_NEW(inAlloc, SRotationWidget)(inAlloc);
+}