Meshroom/meshroom/ui/qml/Viewer3D/Viewer3D.qml
Yann Lanthony 2f307c16fb [ui] Viewer3D: synchronize media list and graph hover/selection
* ease bidirectional navigation between 3D media list and graph
* use same mechanism to indicate selected/hovered elements
* remove 'frame' button (space gain + action available on double click)
2018-12-07 16:07:42 +01:00

245 lines
7.7 KiB
QML

import QtQuick 2.7
import QtQuick.Controls 2.3
import QtQuick.Controls 1.4 as Controls1
import QtQuick.Layouts 1.3
import QtQml.Models 2.2
import QtQuick.Scene3D 2.0
import Qt3D.Core 2.1
import Qt3D.Render 2.1
import Qt3D.Extras 2.1
import Qt3D.Input 2.1 as Qt3DInput // to avoid clash with Controls2 Action
import MaterialIcons 2.2
import Controls 1.0
FocusScope {
id: root
property int renderMode: 2
property alias library: mediaLibrary
property alias inspector: inspector3d
// functions
function resetCameraCenter() {
mainCamera.viewCenter = Qt.vector3d(0.0, 0.0, 0.0);
mainCamera.upVector = Qt.vector3d(0.0, 1.0, 0.0);
}
function resetCameraPosition() {
mainCamera.position = Qt.vector3d(28.0, 21.0, 28.0);
mainCamera.upVector = Qt.vector3d(0.0, 1.0, 0.0);
mainCamera.viewCenter = Qt.vector3d(0.0, 0.0, 0.0);
}
function load(filepath) {
mediaLibrary.load(filepath);
}
function view(attribute) {
mediaLibrary.view(attribute)
}
function clear() {
mediaLibrary.clear()
}
SystemPalette { id: activePalette }
Scene3D {
id: scene3D
anchors.fill: parent
cameraAspectRatioMode: Scene3D.AutomaticAspectRatio // vs. UserAspectRatio
hoverEnabled: true // if true, will trigger positionChanged events in attached MouseHandler
aspects: ["logic", "input"]
focus: true
Keys.onPressed: {
if (event.key == Qt.Key_F) {
resetCameraCenter();
resetCameraPosition();
}
else if(Qt.Key_1 <= event.key && event.key <= Qt.Key_3)
{
Viewer3DSettings.renderMode = event.key - Qt.Key_1;
}
else {
event.accepted = false
}
}
Entity {
id: rootEntity
Camera {
id: mainCamera
projectionType: CameraLens.PerspectiveProjection
fieldOfView: 45
nearPlane : 0.01
farPlane : 10000.0
position: Qt.vector3d(28.0, 21.0, 28.0)
upVector: Qt.vector3d(0.0, 1.0, 0.0)
viewCenter: Qt.vector3d(0.0, 0.0, 0.0)
aspectRatio: width/height
Behavior on viewCenter {
Vector3dAnimation { duration: 250 }
}
// Scene light, attached to the camera
Entity {
components: [
PointLight {
color: "white"
}
]
}
}
Entity {
components: [
SphereMesh {
},
Transform {
id: viewCenterTransform
translation: mainCamera.viewCenter
scale: 0.005 * mainCamera.viewCenter.minus(mainCamera.position).length()
},
PhongMaterial {
ambient: "#FFF"
shininess: 0.2
diffuse: activePalette.highlight
specular: activePalette.highlight
}
]
}
DefaultCameraController {
id: cameraController
camera: mainCamera
focus: scene3D.activeFocus
onMousePressed: {
scene3D.forceActiveFocus()
if(mouse.button == Qt.LeftButton)
{
if(!doubleClickTimer.running)
doubleClickTimer.restart()
}
else
doubleClickTimer.stop()
}
onMouseReleased: {
if(moving)
return
if(mouse.button == Qt.RightButton)
{
contextMenu.popup()
}
}
// Manually handle double click to activate object picking
// for camera re-centering only during a short amount of time
Timer {
id: doubleClickTimer
running: false
interval: 300
}
}
components: [
RenderSettings {
pickingSettings.pickMethod: PickingSettings.PrimitivePicking // enables point/edge/triangle picking
pickingSettings.pickResultMode: PickingSettings.NearestPick
renderPolicy: RenderSettings.OnDemand
activeFrameGraph: RenderSurfaceSelector {
// Use the whole viewport
Viewport {
normalizedRect: Qt.rect(0.0, 0.0, 1.0, 1.0)
CameraSelector {
id: cameraSelector
camera: mainCamera
FrustumCulling {
ClearBuffers {
clearColor: "transparent"
buffers : ClearBuffers.ColorDepthBuffer
RenderStateSet {
renderStates: [
PointSize {
sizeMode: Viewer3DSettings.fixedPointSize ? PointSize.Fixed : PointSize.Programmable
value: Viewer3DSettings.pointSize
},
DepthTest { depthFunction: DepthTest.Less }
]
}
}
}
}
}
}
},
Qt3DInput.InputSettings { }
]
MediaLibrary {
id: mediaLibrary
renderMode: Viewer3DSettings.renderMode
// Picking to set focus point (camera view center)
// Only activate it when a double click may happen or when the 'Control' key is pressed
pickingEnabled: cameraController.pickingActive || doubleClickTimer.running
components: [
Transform {
id: transform
}
]
onPressed: {
if(pick.button == Qt.LeftButton)
{
mainCamera.viewCenter = pick.worldIntersection;
}
doubleClickTimer.stop();
}
Locator3D { enabled: Viewer3DSettings.displayLocator }
}
Grid3D { enabled: Viewer3DSettings.displayGrid }
}
}
// UI Overlay
Controls1.SplitView {
id: overlaySplitView
anchors.fill: parent
Item { Layout.fillWidth: true; Layout.minimumWidth: parent.width * 0.5 }
Inspector3D {
id: inspector3d
width: 220
Layout.minimumWidth: 5
camera: mainCamera
targetTransform: transform
mediaLibrary: mediaLibrary
}
}
// Menu
Menu {
id: contextMenu
MenuItem {
text: "Fit All"
onTriggered: mainCamera.viewAll()
}
MenuItem {
text: "Reset View"
onTriggered: resetCameraPosition()
}
}
}