mirror of
https://github.com/alicevision/Meshroom.git
synced 2025-05-31 09:56:32 +02:00
[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)
This commit is contained in:
parent
05854ed897
commit
2f307c16fb
3 changed files with 91 additions and 40 deletions
|
@ -19,6 +19,7 @@ FloatingPane {
|
|||
property Grid3D grid: null
|
||||
property MediaLibrary mediaLibrary
|
||||
property Camera camera
|
||||
property var uigraph: null
|
||||
|
||||
signal mediaFocusRequest(var index)
|
||||
signal mediaRemoveRequest(var index)
|
||||
|
@ -128,6 +129,13 @@ FloatingPane {
|
|||
}
|
||||
}
|
||||
|
||||
currentIndex: -1
|
||||
|
||||
Connections {
|
||||
target: uigraph
|
||||
onSelectedNodeChanged: mediaListView.currentIndex = -1
|
||||
}
|
||||
|
||||
Connections {
|
||||
target: mediaLibrary
|
||||
onLoadRequest: {
|
||||
|
@ -136,6 +144,7 @@ FloatingPane {
|
|||
}
|
||||
|
||||
delegate: RowLayout {
|
||||
id: mediaDelegate
|
||||
// add mediaLibrary.count in the binding to ensure 'entity'
|
||||
// is re-evaluated when mediaLibrary delegates are modified
|
||||
property bool loading: model.status === SceneLoader.Loading
|
||||
|
@ -145,11 +154,36 @@ FloatingPane {
|
|||
property string src: model.source
|
||||
onSrcChanged: focusAnim.restart()
|
||||
|
||||
RowLayout {
|
||||
Layout.alignment: Qt.AlignTop
|
||||
spacing: 0
|
||||
property bool hovered: model.attribute ? uigraph.hoveredNode === model.attribute.node : mouseArea.containsMouse
|
||||
property bool isSelectedNode: model.attribute ? uigraph.selectedNode === model.attribute.node : false
|
||||
|
||||
function updateCurrentIndex() {
|
||||
if(isSelectedNode) { mediaListView.currentIndex = index }
|
||||
}
|
||||
|
||||
onIsSelectedNodeChanged: updateCurrentIndex()
|
||||
|
||||
Connections {
|
||||
target: mediaListView
|
||||
onCountChanged: mediaDelegate.updateCurrentIndex()
|
||||
}
|
||||
|
||||
// Current/selected element indicator
|
||||
Rectangle {
|
||||
Layout.fillHeight: true
|
||||
width: 2
|
||||
color: {
|
||||
if(mediaListView.currentIndex == index || mediaDelegate.isSelectedNode)
|
||||
return label.palette.highlight;
|
||||
if(mediaDelegate.hovered)
|
||||
return Qt.darker(label.palette.highlight, 1.5);
|
||||
return "transparent";
|
||||
}
|
||||
}
|
||||
|
||||
// Media visibility/loading control
|
||||
MaterialToolButton {
|
||||
Layout.alignment: Qt.AlignTop
|
||||
text: model.visible ? MaterialIcons.visibility : MaterialIcons.visibility_off
|
||||
font.pointSize: 10
|
||||
ToolTip.text: model.visible ? "Hide" : "Show"
|
||||
|
@ -175,29 +209,28 @@ FloatingPane {
|
|||
}
|
||||
}
|
||||
}
|
||||
MaterialToolButton {
|
||||
text: MaterialIcons.filter_center_focus
|
||||
font.pointSize: 10
|
||||
ToolTip.text: "Frame"
|
||||
onClicked: camera.viewEntity(mediaLibrary.entityAt(index))
|
||||
flat: true
|
||||
}
|
||||
}
|
||||
|
||||
ColumnLayout {
|
||||
// Media label and info
|
||||
Item {
|
||||
implicitHeight: childrenRect.height
|
||||
Layout.fillWidth: true
|
||||
spacing: 1
|
||||
Layout.alignment: Qt.AlignTop
|
||||
ColumnLayout {
|
||||
id: centralLayout
|
||||
width: parent.width
|
||||
spacing: 1
|
||||
|
||||
Label {
|
||||
id: label
|
||||
Layout.fillWidth: true
|
||||
leftPadding: 0
|
||||
rightPadding: 0
|
||||
topPadding: 3
|
||||
bottomPadding: topPadding
|
||||
Layout.fillWidth: true
|
||||
text: model.label
|
||||
opacity: model.valid ? 1.0 : 0.6
|
||||
elide: Text.ElideMiddle
|
||||
font.weight: mediaListView.currentIndex == index ? Font.DemiBold : Font.Normal
|
||||
background: Rectangle {
|
||||
Connections {
|
||||
target: mediaLibrary
|
||||
|
@ -209,10 +242,6 @@ FloatingPane {
|
|||
to: "transparent"
|
||||
duration: 2000
|
||||
}
|
||||
MouseArea {
|
||||
anchors.fill: parent
|
||||
onDoubleClicked: camera.viewEntity(mediaLibrary.entityAt(index))
|
||||
}
|
||||
}
|
||||
}
|
||||
Item {
|
||||
|
@ -231,6 +260,25 @@ FloatingPane {
|
|||
}
|
||||
}
|
||||
}
|
||||
MouseArea {
|
||||
id: mouseArea
|
||||
anchors.fill: centralLayout
|
||||
hoverEnabled: true
|
||||
onEntered: { if(model.attribute) uigraph.hoveredNode = model.attribute.node }
|
||||
onExited: { if(model.attribute) uigraph.hoveredNode = null }
|
||||
onClicked: {
|
||||
if(model.attribute)
|
||||
uigraph.selectedNode = model.attribute.node;
|
||||
else
|
||||
uigraph.selectedNode = null;
|
||||
mediaListView.currentIndex = index;
|
||||
}
|
||||
onDoubleClicked: {
|
||||
model.visible = true;
|
||||
camera.viewEntity(mediaLibrary.entityAt(index));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// Media unavailability indicator
|
||||
MaterialToolButton {
|
||||
|
|
|
@ -19,6 +19,7 @@ FocusScope {
|
|||
|
||||
property int renderMode: 2
|
||||
property alias library: mediaLibrary
|
||||
property alias inspector: inspector3d
|
||||
|
||||
// functions
|
||||
function resetCameraCenter() {
|
||||
|
@ -218,7 +219,7 @@ FocusScope {
|
|||
Item { Layout.fillWidth: true; Layout.minimumWidth: parent.width * 0.5 }
|
||||
|
||||
Inspector3D {
|
||||
id: inspector
|
||||
id: inspector3d
|
||||
width: 220
|
||||
Layout.minimumWidth: 5
|
||||
|
||||
|
|
|
@ -124,6 +124,8 @@ Item {
|
|||
readonly property int outputMediaIndex: library.find(outputAttribute)
|
||||
|
||||
anchors.fill: parent
|
||||
inspector.uigraph: reconstruction
|
||||
|
||||
DropArea {
|
||||
anchors.fill: parent
|
||||
keys: ["text/uri-list"]
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue