Make sidebar view working for active stage

This commit is contained in:
ChrisTerBeke 2017-12-06 12:23:41 +01:00
parent 0e1c9146cf
commit a57a5aab6b
14 changed files with 605 additions and 812 deletions

View file

@ -721,6 +721,7 @@ class CuraApplication(QtApplication):
run_headless = self.getCommandLineOption("headless", False) run_headless = self.getCommandLineOption("headless", False)
if not run_headless: if not run_headless:
self.initializeEngine() self.initializeEngine()
controller.setActiveStage("PrepareStage")
if run_headless or self._engine.rootObjects: if run_headless or self._engine.rootObjects:
self.closeSplash() self.closeSplash()

View file

@ -1,66 +0,0 @@
# Copyright (c) 2017 Ultimaker B.V.
from UM.Logger import Logger
from UM.Preferences import Preferences
from UM.Signal import Signal
from UM.PluginRegistry import PluginRegistry
# The sidebar controller manages available sidebar components and decides which one to display.
# The cura.qml file uses this controller to repeat over the sidebars and show the active index.
class SidebarController:
def __init__(self, application):
self._application = application
self._sidebar_views = {"default": {}} # default is needed for the default settings sidebar
self._active_sidebar_view = None
# Register the sidebar_view plugin type so plugins can expose custom sidebar views.
PluginRegistry.addType("sidebar_view", self.addSidebarView)
## Emitted when the list of views changes.
sidebarViewsChanged = Signal()
## Emitted when the active view changes.
activeSidebarViewChanged = Signal()
## Get the active application instance.
def getApplication(self):
return self._application
## Get all sidebar views registered in this controller.
def getAllSidebarViews(self):
return self._sidebar_views
## Add a sidebar view to the registry.
# It get's a unique name based on the plugin ID.
def addSidebarView(self, sidebar_view):
sidebar_view_id = sidebar_view.getPluginId()
if sidebar_view_id not in self._sidebar_views:
self._sidebar_views[sidebar_view_id] = sidebar_view
self.sidebarViewsChanged.emit()
## Get a registered sidebar view by name.
# The name is the ID of the plugin that registered the view.
def getSidebarView(self, name: str):
try:
return self._sidebar_views[name]
except KeyError:
Logger.log("e", "Unable to find %s in sidebar view list", name)
return None
## Get the active sidebar view.
def getActiveSidebarView(self):
return self._active_sidebar_view
## Get the ID of the active sidebar view.
def getActiveSidebarViewId(self):
if self._active_sidebar_view:
if hasattr(self._active_sidebar_view, "getPluginId"):
return self._active_sidebar_view.getPluginId()
return "default"
## Change the active sidebar view to one of the registered views.
def setActiveSidebarView(self, sidebar_view_id: str):
if sidebar_view_id in self._sidebar_views:
self._active_sidebar_view = self._sidebar_views[sidebar_view_id]
Preferences.getInstance().setValue("cura/active_sidebar_view", sidebar_view_id)
self.activeSidebarViewChanged.emit()

View file

@ -1,41 +0,0 @@
# Copyright (c) 2017 Ultimaker B.V.
from PyQt5.QtCore import QObject, pyqtSlot, QUrl, pyqtProperty, pyqtSignal
from UM.Application import Application
## The sidebar controller proxy acts a proxy between the sidebar controller and the QMl context of the controller.
from UM.Logger import Logger
class SidebarControllerProxy(QObject):
def __init__(self, parent = None):
super().__init__(parent)
self._controller = Application.getInstance().getSidebarController()
self._controller.activeSidebarViewChanged.connect(self._onActiveSidebarViewChanged)
activeSidebarViewChanged = pyqtSignal()
@classmethod
def createSidebarControllerProxy(self, engine, script_engine):
return SidebarControllerProxy()
@pyqtProperty(str, notify = activeSidebarViewChanged)
def activeSidebarId(self):
return self._controller.getActiveSidebarViewId()
@pyqtSlot(str)
def setActiveSidebarView(self, sidebar_view_id):
Logger.log("d", "Setting active sidebar view to %s", sidebar_view_id)
self._controller.setActiveSidebarView(sidebar_view_id)
@pyqtSlot(str, result = QObject)
def getSidebarComponent(self, sidebar_id):
return self._controller.getSidebarView(sidebar_id).getComponent()
@pyqtSlot(str, result = QUrl)
def getSidebarComponentPath(self, sidebar_id):
return self._controller.getSidebarView(sidebar_id).getComponentPath()
def _onActiveSidebarViewChanged(self):
self.activeSidebarViewChanged.emit()

View file

@ -1,35 +0,0 @@
# Copyright (c) 2017 Ultimaker B.V.
import os.path
from UM.Application import Application
from UM.Logger import Logger
from UM.PluginObject import PluginObject
from UM.PluginRegistry import PluginRegistry
# Abstract class for sidebar view objects.
# By default the sidebar is Cura's settings, slicing and printing overview.
# The last plugin to claim the sidebar QML target will be displayed.
class SidebarView(PluginObject):
def __init__(self):
super().__init__()
self._view = None
def getComponent(self):
if not self._view:
self.createView()
return self._view
def createView(self):
component_path = self.getComponentPath()
self._view = Application.getInstance().createQmlComponent(component_path, {"manager": self})
## Get the path to the component QML file as QUrl
def getComponentPath(self):
try:
plugin_path = PluginRegistry.getInstance().getPluginPath(self.getPluginId())
sidebar_component_file_path = PluginRegistry.getInstance().getMetaData(self.getPluginId())["sidebar_view"]["sidebar_component"]
return os.path.join(plugin_path, sidebar_component_file_path)
except KeyError:
Logger.log("w", "Could not find sidebar component QML file for %s", self.getPluginId())
return ""

View file

@ -1,66 +0,0 @@
# Copyright (c) 2017 Ultimaker B.V.
from PyQt5.QtCore import Qt
from UM.Qt.ListModel import ListModel
from UM.Application import Application
from UM.PluginRegistry import PluginRegistry
## The SidebarViewModel is the default sidebar view in Cura with all the print settings and print button.
class SidebarViewModel(ListModel):
IdRole = Qt.UserRole + 1
NameRole = Qt.UserRole + 2
ActiveRole = Qt.UserRole + 3
def __init__(self, parent = None):
super().__init__(parent)
# connect views changed signals
self._controller = Application.getInstance().getSidebarController()
self._controller.sidebarViewsChanged.connect(self._onSidebarViewsChanged)
self._controller.activeSidebarViewChanged.connect(self._onSidebarViewsChanged)
# register Qt list roles
self.addRoleName(self.IdRole, "id")
self.addRoleName(self.NameRole, "name")
self.addRoleName(self.ActiveRole, "active")
## Update the model when new views are added or another view is made the active view.
def _onSidebarViewsChanged(self):
items = []
current_view_id = "default"
sidebar_views = self._controller.getAllSidebarViews()
current_view = self._controller.getActiveSidebarView()
if current_view and hasattr(current_view, "getPluginId"):
current_view_id = current_view.getPluginId()
for sidebar_view_id, sidebar_view in sidebar_views.items():
# Override fields for default settings sidebar
if sidebar_view_id == "default":
items.append({
"id": "default",
"name": "Print settings sidebar",
"active": sidebar_view_id == current_view_id,
"weight": 0
})
continue
sidebar_view_metadata = PluginRegistry.getInstance().getMetaData(sidebar_view_id).get("sidebar_view", {})
# Skip view modes that are marked as not visible
if "visible" in sidebar_view_metadata and not sidebar_view_metadata["visible"]:
continue
name = sidebar_view_metadata.get("name", sidebar_view_id)
weight = sidebar_view_metadata.get("weight", 1)
items.append({
"id": sidebar_view_id,
"name": name,
"active": sidebar_view_id == current_view_id,
"weight": weight
})
# Sort the views by weight
items.sort(key=lambda t: t["weight"])
self.setItems(items)

View file

@ -1,5 +1,6 @@
# Copyright (c) 2017 Ultimaker B.V. # Copyright (c) 2017 Ultimaker B.V.
# Cura is released under the terms of the LGPLv3 or higher. # Cura is released under the terms of the LGPLv3 or higher.
from PyQt5.QtCore import pyqtProperty, QObject
from UM.Stage import Stage from UM.Stage import Stage
@ -8,8 +9,10 @@ class CuraStage(Stage):
def __init__(self): def __init__(self):
super().__init__() super().__init__()
def getMainView(self): @pyqtProperty(QObject, constant = True)
return self.getView("main") def mainComponent(self):
return self.getDisplayComponent("main")
def getSidebarView(self): @pyqtProperty(QObject, constant = True)
return self.getView("sidebar") def sidebarComponent(self):
return self.getDisplayComponent("sidebar")

View file

@ -1,6 +1,6 @@
# Copyright (c) 2017 Ultimaker B.V. # Copyright (c) 2017 Ultimaker B.V.
# Cura is released under the terms of the LGPLv3 or higher. # Cura is released under the terms of the LGPLv3 or higher.
from UM.Application import Application
from cura.Stages.CuraStage import CuraStage from cura.Stages.CuraStage import CuraStage
@ -9,3 +9,7 @@ class MonitorStage(CuraStage):
def __init__(self): def __init__(self):
super().__init__() super().__init__()
Application.getInstance().engineCreatedSignal.connect(self._engineCreated)
def _engineCreated(self):
self.setIconSource(Application.getInstance().getTheme().getIcon("tab_status_connected"))

View file

@ -10,10 +10,11 @@ def getMetaData():
return { return {
"stage": { "stage": {
"name": i18n_catalog.i18nc("@item:inmenu", "Monitor"), "name": i18n_catalog.i18nc("@item:inmenu", "Monitor"),
"weight": 1, "weight": 1
"icon": ""
} }
} }
def register(app): def register(app):
return { "stage": MonitorStage.MonitorStage() } return {
"stage": MonitorStage.MonitorStage()
}

View file

@ -1,6 +1,8 @@
# Copyright (c) 2017 Ultimaker B.V. # Copyright (c) 2017 Ultimaker B.V.
# Cura is released under the terms of the LGPLv3 or higher. # Cura is released under the terms of the LGPLv3 or higher.
import os.path
from UM.Application import Application
from UM.Resources import Resources
from cura.Stages.CuraStage import CuraStage from cura.Stages.CuraStage import CuraStage
@ -9,3 +11,9 @@ class PrepareStage(CuraStage):
def __init__(self): def __init__(self):
super().__init__() super().__init__()
Application.getInstance().engineCreatedSignal.connect(self._engineCreated)
def _engineCreated(self):
sidebar_component_path = os.path.join(Resources.getPath(Application.getInstance().ResourceTypes.QmlFiles), "Sidebar.qml")
sidebar_component = Application.getInstance().createQmlComponent(sidebar_component_path)
self.addDisplayComponent("sidebar", sidebar_component)

View file

@ -15,4 +15,6 @@ def getMetaData():
} }
def register(app): def register(app):
return { "stage": PrepareStage.PrepareStage() } return {
"stage": PrepareStage.PrepareStage()
}

View file

@ -366,8 +366,7 @@ UM.MainWindow
onStopMonitoringPrint: base.showPrintMonitor = false onStopMonitoringPrint: base.showPrintMonitor = false
} }
Sidebar Loader {
{
id: sidebar id: sidebar
anchors anchors
@ -379,7 +378,8 @@ UM.MainWindow
width: UM.Theme.getSize("sidebar").width width: UM.Theme.getSize("sidebar").width
z: 1 z: 1
monitoringPrint: base.showPrintMonitor
sourceComponent: UM.Controller.activeStage.sidebarComponent
} }
Rectangle Rectangle

File diff suppressed because it is too large Load diff

View file

@ -6,7 +6,7 @@ import QtQuick.Controls 1.1
import QtQuick.Controls.Styles 1.1 import QtQuick.Controls.Styles 1.1
import QtQuick.Layouts 1.1 import QtQuick.Layouts 1.1
import UM 1.2 as UM import UM 1.4 as UM
import Cura 1.0 as Cura import Cura 1.0 as Cura
import "Menus" import "Menus"
@ -83,34 +83,13 @@ Rectangle
style: UM.Theme.styles.topbar_header_tab style: UM.Theme.styles.topbar_header_tab
height: UM.Theme.getSize("sidebar_header").height height: UM.Theme.getSize("sidebar_header").height
onClicked: UM.Controller.setActiveStage(model.id) onClicked: UM.Controller.setActiveStage(model.id)
iconSource: model.stage.iconSource
property color overlayColor: "transparent"
property string overlayIconSource: ""
} }
} }
// Button
// {
// id: showSettings
// height: UM.Theme.getSize("sidebar_header").height
// text: catalog.i18nc("@title:tab", "Prepare")
// checkable: true
// checked: isChecked()
// exclusiveGroup: sidebarHeaderBarGroup
// style: UM.Theme.styles.topbar_header_tab
//
// // We use a Qt.binding to re-bind the checkbox state after manually setting it
// // https://stackoverflow.com/questions/38798450/qt-5-7-qml-why-are-my-checkbox-property-bindings-disappearing
// onClicked: {
// base.stopMonitoringPrint()
// checked = Qt.binding(isChecked)
// }
//
// function isChecked () {
// return !base.monitoringPrint
// }
//
// property color overlayColor: "transparent"
// property string overlayIconSource: ""
// }
// Button // Button
// { // {
// id: showMonitor // id: showMonitor