summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorKaj Grönholm <kaj.gronholm@qt.io>2019-09-09 11:09:02 +0300
committerKaj Grönholm <kaj.gronholm@qt.io>2019-09-11 10:03:50 +0300
commit0d6360909793aab11c66f4b8f7001f71cbacfee7 (patch)
treec026da7505a6c0b1b93382f3a20e57c2020ac32b
parent025beb76e9abfba594870ee480448a1fa0a3ca09 (diff)
Stereoscopic improvements
Make left & right eye camera nodes pointers, fixing e.g. presentations with specular reflection. Use separate textures for fixing temporal AA. Don't allow eye separation become negative. Task-number: QT3DS-3899 Change-Id: Ide4d26d293c37b16048e2691ad51a32b8d4cc276 Reviewed-by: Janne Kangas <janne.kangas@qt.io> Reviewed-by: Tomi Korpipää <tomi.korpipaa@qt.io> Reviewed-by: Mahmoud Badri <mahmoud.badri@qt.io>
-rw-r--r--src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.cpp28
-rw-r--r--src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.h4
-rw-r--r--src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.cpp61
-rw-r--r--src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.h5
-rw-r--r--tools/viewer/qml/main.qml6
5 files changed, 77 insertions, 27 deletions
diff --git a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.cpp b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.cpp
index 7b7043f..b99773b 100644
--- a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.cpp
+++ b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.cpp
@@ -76,7 +76,8 @@ namespace render {
SLayerRenderData::SLayerRenderData(SLayer &inLayer, Qt3DSRendererImpl &inRenderer)
: SLayerRenderPreparationData(inLayer, inRenderer)
, m_LayerTexture(inRenderer.GetQt3DSContext().GetResourceManager())
- , m_TemporalAATexture(inRenderer.GetQt3DSContext().GetResourceManager())
+ , m_TemporalAATexture{inRenderer.GetQt3DSContext().GetResourceManager(),
+ inRenderer.GetQt3DSContext().GetResourceManager()}
, m_LayerDepthTexture(inRenderer.GetQt3DSContext().GetResourceManager())
, m_LayerPrepassDepthTexture(inRenderer.GetQt3DSContext().GetResourceManager())
, m_LayerWidgetTexture(inRenderer.GetQt3DSContext().GetResourceManager())
@@ -96,6 +97,7 @@ namespace render {
, mRefCount(0)
, m_DepthBufferFormat(NVRenderTextureFormats::Unknown)
{
+
}
SLayerRenderData::~SLayerRenderData()
@@ -163,7 +165,8 @@ namespace render {
m_LayerSsaoTexture.ReleaseTexture();
m_LayerWidgetTexture.ReleaseTexture();
m_LayerPrepassDepthTexture.ReleaseTexture();
- m_TemporalAATexture.ReleaseTexture();
+ m_TemporalAATexture[0].ReleaseTexture();
+ m_TemporalAATexture[1].ReleaseTexture();
m_LayerMultisampleTexture.ReleaseTexture();
m_LayerMultisamplePrepassDepthTexture.ReleaseTexture();
m_LayerMultisampleWidgetTexture.ReleaseTexture();
@@ -1373,6 +1376,11 @@ namespace render {
m_ProgressiveAAPassIndex && m_ProgressiveAAPassIndex < thePrepResult.m_MaxAAPassIndex;
bool isTemporalAABlendPass = m_Layer.m_TemporalAAEnabled && m_ProgressiveAAPassIndex == 0;
+ // Select correct temporal AA texture
+ StereoViews::Enum stereoView = m_Renderer.GetQt3DSContext().GetStereoView();
+ int temporalIndex = (stereoView == StereoViews::Right) ? 1 : 0;
+ CResourceTexture2D &temporalAATexture = m_TemporalAATexture[temporalIndex];
+
if (isProgressiveAABlendPass || isTemporalAABlendPass) {
theBlendShader = m_Renderer.GetLayerProgAABlendShader();
if (theBlendShader) {
@@ -1385,13 +1393,11 @@ namespace render {
aaFactorIndex = (m_ProgressiveAAPassIndex - 1);
theVertexOffsets = s_VertexOffsets[aaFactorIndex];
} else {
- if (m_TemporalAATexture.GetTexture())
- theLastLayerTexture.StealTexture(m_TemporalAATexture);
- else {
- if (hadLayerTexture) {
- theLastLayerTexture.StealTexture(m_LayerTexture);
- }
- }
+ if (temporalAATexture.GetTexture())
+ theLastLayerTexture.StealTexture(temporalAATexture);
+ else if (hadLayerTexture)
+ theLastLayerTexture.StealTexture(m_LayerTexture);
+
theVertexOffsets = s_TemporalVertexOffsets[m_TemporalAAPassIndex];
++m_TemporalAAPassIndex;
++m_NonDirtyTemporalAAPassIndex;
@@ -1454,7 +1460,7 @@ namespace render {
sampleCount);
if (!isTemporalAABlendPass)
- m_TemporalAATexture.ReleaseTexture();
+ temporalAATexture.ReleaseTexture();
// Allocating a frame buffer can cause it to be bound, so we need to save state before this
// happens.
@@ -1648,7 +1654,7 @@ namespace render {
theFB->Attach(NVRenderFrameBufferAttachments::Color0,
qt3ds::render::NVRenderTextureOrRenderBuffer());
if (isTemporalAABlendPass)
- m_TemporalAATexture.StealTexture(m_LayerTexture);
+ temporalAATexture.StealTexture(m_LayerTexture);
m_LayerTexture.StealTexture(targetTexture);
}
diff --git a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.h b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.h
index 4e237b0..8e5c694 100644
--- a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.h
+++ b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderData.h
@@ -53,7 +53,9 @@ struct AdvancedBlendModes
// or just because a flag forces it. If they are rendered offscreen we can then
// cache the result so we don't render the layer again if it isn't dirty.
CResourceTexture2D m_LayerTexture;
- CResourceTexture2D m_TemporalAATexture;
+ // Multiple temporal AA textures for stereoscopic needs.
+ // First used for mono/left view, second for right view.
+ CResourceTexture2D m_TemporalAATexture[2];
// Sometimes we need to render our depth buffer to a depth texture.
CResourceTexture2D m_LayerDepthTexture;
CResourceTexture2D m_LayerPrepassDepthTexture;
diff --git a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.cpp b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.cpp
index 9f0cc2d..79e2185 100644
--- a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.cpp
+++ b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.cpp
@@ -68,8 +68,10 @@ QT3DSVec2 ToRectRelativeCoords(const QT3DSVec2 &inCoords, const NVRenderRectF &i
}
SLayerRenderHelper::SLayerRenderHelper()
- : m_Layer(NULL)
- , m_Camera(NULL)
+ : m_Layer(nullptr)
+ , m_Camera(nullptr)
+ , m_CameraLeftEye(nullptr)
+ , m_CameraRightEye(nullptr)
, m_Offscreen(false)
{
}
@@ -87,6 +89,9 @@ SLayerRenderHelper::SLayerRenderHelper(const NVRenderRectF &inPresentationViewpo
, m_PresentationScissor(inPresentationScissor)
, m_PresentationDesignDimensions(inPresentationDesignDimensions)
, m_Layer(&inLayer)
+ , m_Camera(nullptr)
+ , m_CameraLeftEye(nullptr)
+ , m_CameraRightEye(nullptr)
, m_Offscreen(inOffscreen)
, m_ScaleMode(inScaleMode)
, m_StereoMode(inStereoMode)
@@ -260,9 +265,9 @@ QSize SLayerRenderHelper::GetTextureDimensions() const
SCamera *SLayerRenderHelper::GetCamera() {
if (m_StereoView == StereoViews::Left)
- return &m_CameraLeftEye;
+ return m_CameraLeftEye;
if (m_StereoView == StereoViews::Right)
- return &m_CameraRightEye;
+ return m_CameraRightEye;
return m_Camera;
}
@@ -312,7 +317,7 @@ Option<SRay> SLayerRenderHelper::GetPickRay(const QT3DSVec2 &inMouseCoords,
bool inForceIntersect,
bool sceneCameraView) const
{
- if (m_Camera == NULL)
+ if (!m_Camera)
return Empty();
Option<QT3DSVec2> theCoords(
GetLayerMouseCoords(inMouseCoords, inWindowDimensions, inForceIntersect));
@@ -336,11 +341,45 @@ bool SLayerRenderHelper::isStereoscopic() const
return m_StereoMode != StereoModes::Mono;
}
+void SLayerRenderHelper::copyCameraProperties(SCamera *sourceCamera,
+ SCamera *destinationCamera)
+{
+ if (!sourceCamera || !destinationCamera)
+ return;
+
+ destinationCamera->m_FOV = sourceCamera->m_FOV;
+ destinationCamera->m_ClipFar = sourceCamera->m_ClipFar;
+ destinationCamera->m_ClipNear = sourceCamera->m_ClipNear;
+ destinationCamera->m_ScaleMode = sourceCamera->m_ScaleMode;
+ destinationCamera->m_Projection = sourceCamera->m_Projection;
+ destinationCamera->m_ScaleAnchor = sourceCamera->m_ScaleAnchor;
+ destinationCamera->m_FrustumScale = sourceCamera->m_FrustumScale;
+ destinationCamera->m_FOVHorizontal = sourceCamera->m_FOVHorizontal;
+ destinationCamera->m_EnableFrustumCulling = sourceCamera->m_EnableFrustumCulling;
+ destinationCamera->m_Flags = sourceCamera->m_Flags;
+ destinationCamera->m_Pivot = sourceCamera->m_Pivot;
+ destinationCamera->m_Scale = sourceCamera->m_Scale;
+ destinationCamera->m_DFSIndex = sourceCamera->m_DFSIndex;
+ destinationCamera->m_Position = sourceCamera->m_Position;
+ destinationCamera->m_Rotation = sourceCamera->m_Rotation;
+ destinationCamera->m_UserData = sourceCamera->m_UserData;
+ destinationCamera->m_LocalOpacity = sourceCamera->m_LocalOpacity;
+ destinationCamera->m_GlobalOpacity = sourceCamera->m_GlobalOpacity;
+ destinationCamera->m_RotationOrder = sourceCamera->m_RotationOrder;
+ destinationCamera->m_LocalTransform = sourceCamera->m_LocalTransform;
+ destinationCamera->m_GlobalTransform = sourceCamera->m_GlobalTransform;
+}
+
void SLayerRenderHelper::adjustCameraStereoSeparation()
{
+ if (!m_CameraLeftEye)
+ m_CameraLeftEye = new SCamera();
+ if (!m_CameraRightEye)
+ m_CameraRightEye = new SCamera();
+
// Copy m_Camera properties into left & right cameras
- m_CameraLeftEye = SCamera(*m_Camera);
- m_CameraRightEye = SCamera(*m_Camera);
+ copyCameraProperties(m_Camera, m_CameraLeftEye);
+ copyCameraProperties(m_Camera, m_CameraRightEye);
// Adjust left & right camera positions by eye separation
QT3DSMat44 mat = QT3DSMat44::createIdentity();
@@ -349,12 +388,12 @@ void SLayerRenderHelper::adjustCameraStereoSeparation()
camPos.x = m_Camera->m_Position.x - m_StereoEyeSeparation;
mat.scale(QT3DSVec4(m_Camera->m_Scale, 1.0f));
mat.setPosition(camPos);
- m_CameraLeftEye.SetLocalTransformFromMatrix(mat);
+ m_CameraLeftEye->SetLocalTransformFromMatrix(mat);
camPos.x = m_Camera->m_Position.x + m_StereoEyeSeparation;
mat.scale(QT3DSVec4(m_Camera->m_Scale, 1.0f));
mat.setPosition(camPos);
- m_CameraRightEye.SetLocalTransformFromMatrix(mat);
+ m_CameraRightEye->SetLocalTransformFromMatrix(mat);
- m_CameraLeftEye.MarkDirty();
- m_CameraRightEye.MarkDirty();
+ m_CameraLeftEye->MarkDirty();
+ m_CameraRightEye->MarkDirty();
}
diff --git a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.h b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.h
index 3b29c7d..19fd3f5 100644
--- a/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.h
+++ b/src/runtimerender/rendererimpl/Qt3DSRendererImplLayerRenderHelper.h
@@ -60,8 +60,8 @@ namespace render {
QT3DSVec2 m_PresentationDesignDimensions;
SLayer *m_Layer;
SCamera *m_Camera;
- SCamera m_CameraLeftEye;
- SCamera m_CameraRightEye;
+ SCamera *m_CameraLeftEye;
+ SCamera *m_CameraRightEye;
bool m_Offscreen;
NVRenderRectF m_Viewport;
@@ -130,6 +130,7 @@ namespace render {
// different than the layer to presentation viewport.
NVRenderRectF GetLayerRenderViewport() const;
+ void copyCameraProperties(SCamera *sourceCamera, SCamera *destinationCamera);
void adjustCameraStereoSeparation();
};
}
diff --git a/tools/viewer/qml/main.qml b/tools/viewer/qml/main.qml
index 58afb69..1a59739 100644
--- a/tools/viewer/qml/main.qml
+++ b/tools/viewer/qml/main.qml
@@ -625,8 +625,10 @@ ApplicationWindow {
shortcut: "Ctrl+Shift+-"
enabled: _viewerHelper.contentView === ViewerHelper.StudioView
onTriggered: {
- if (enabled)
- window.stereoEyeSeparation -= 0.1;
+ if (enabled) {
+ window.stereoEyeSeparation
+ = Math.max(0, window.stereoEyeSeparation - 0.1);
+ }
}
}
}