from maya import OpenMayaUI as omui from maya import cmds from ngSkinTools2.api.log import getLogger from ngSkinTools2.api.pyside import QtCore, QtGui, QtWidgets, QWidget, wrap_instance from ngSkinTools2.api.session import session from ngSkinTools2.ui.options import config from .. import cleanup, signal, version from ..observableValue import ObservableValue from . import ( aboutwindow, dialogs, hotkeys_setup, qt, tabLayerEffects, tabMirror, tabPaint, tabSetWeights, tabTools, targetui, updatewindow, ) from .layout import scale_multiplier log = getLogger("main window") def get_image_path(file_name): import os for i in os.getenv("XBMLANGPATH", "").split(os.path.pathsep): result = os.path.join(i, file_name) if os.path.isfile(result): return result return file_name def build_menu(parent, actions): menu = QtWidgets.QMenuBar(parent=parent) def top_level_menu(label): sub_item = menu.addMenu(label) sub_item.setSeparatorsCollapsible(False) sub_item.setTearOffEnabled(True) return sub_item sub = top_level_menu("File") sub.addSeparator().setText("Import/Export") sub.addAction(actions.importFile) sub.addAction(actions.exportFile) sub = top_level_menu("Layers") sub.addSeparator().setText("Layer actions") sub.addAction(actions.initialize) sub.addAction(actions.import_v1) actions.addLayersActions(sub) sub.addSeparator().setText("Copy") sub.addAction(actions.transfer) sub = top_level_menu("Tools") sub.addAction(actions.add_influences) sub.addAction(actions.toolsAssignFromClosestJoint) sub.addSeparator() sub.addAction(actions.transfer) sub.addSeparator() sub.addAction(actions.toolsDeleteCustomNodesOnSelection) sub.addAction(actions.toolsDeleteCustomNodes) sub = top_level_menu("View") sub.addAction(actions.show_used_influences_only) sub = top_level_menu("Help") sub.addAction(actions.documentation.user_guide) sub.addAction(actions.documentation.api_root) sub.addAction(actions.documentation.changelog) sub.addAction(actions.documentation.contact) sub.addSeparator() sub.addAction(actions.check_for_updates) sub.addAction("About...").triggered.connect(lambda: aboutwindow.show(parent)) return menu def build_rmb_menu_layers(view, actions): view.setContextMenuPolicy(QtCore.Qt.ActionsContextMenu) actions.addLayersActions(view) class MainWindowOptions: current_tab = ObservableValue(0) def build_ui(parent): """ :type parent: QWidget """ options = MainWindowOptions() window = QtWidgets.QWidget(parent) session.addQtWidgetReference(window) from ngSkinTools2.ui.actions import Actions actions = Actions(parent=window, session=session) tabs = QtWidgets.QTabWidget(window) tabs.addTab(tabPaint.build_ui(tabs, actions), "Paint") tabs.addTab(tabSetWeights.build_ui(tabs), "Set Weights") tabs.addTab(tabMirror.build_ui(tabs), "Mirror") tabs.addTab(tabLayerEffects.build_ui(), "Effects") tabs.addTab(tabTools.build_ui(actions, session), "Tools") @signal.on(options.current_tab.changed) def set_current_tab(): tabs.setCurrentIndex(options.current_tab()) layers_toolbar = QtWidgets.QToolBar() layers_toolbar.addAction(actions.addLayer) layers_toolbar.setOrientation(QtCore.Qt.Vertical) spacing_h = 5 spacing_v = 5 layers_row = targetui.build_target_ui(window, actions, session) split = QtWidgets.QSplitter(orientation=QtCore.Qt.Vertical, parent=window) split.addWidget(layers_row) split.addWidget(tabs) split.setStretchFactor(0, 2) split.setStretchFactor(1, 3) split.setContentsMargins(spacing_h, spacing_v, spacing_h, spacing_v) def build_icon_label(): w = QWidget() w.setStyleSheet("background-color: #dcce87;color: #373737;") l = QtWidgets.QHBoxLayout() icon = QtWidgets.QLabel() icon.setPixmap(QtGui.QIcon(":/error.png").pixmap(16 * scale_multiplier, 16 * scale_multiplier)) icon.setFixedSize(16 * scale_multiplier, 16 * scale_multiplier) text = QtWidgets.QLabel("") text.setWordWrap(True) text.setTextInteractionFlags(QtCore.Qt.TextSelectableByMouse) l.addWidget(icon) l.addWidget(text) w.setContentsMargins(0, 0, 0, 0) w.setLayout(l) return w, text.setText layout = QtWidgets.QVBoxLayout(window) layout.setContentsMargins(0, 0, 0, 0) layout.addWidget(build_menu(window, actions)) layout.addWidget(split) window.setLayout(layout) hotkeys_setup.install_hotkeys() dialogs.promptsParent = window if config.checkForUpdatesAtStartup(): updatewindow.silent_check_and_show_if_available(qt.mainWindow) return window, options DOCK_NAME = 'ngSkinTools2_mainWindow' def workspace_control_permanent_script(): from ngSkinTools2 import workspace_control_main_window return "import {f.__module__}; {f.__module__}.{f.__name__}()".format(f=workspace_control_main_window) # noinspection PyShadowingBuiltins def open(): """ opens main window """ if not cmds.workspaceControl(DOCK_NAME, q=True, exists=True): # build UI script in type-safe manner cmds.workspaceControl( DOCK_NAME, retain=False, floating=True, # ttc=["AttributeEditor",-1], uiScript=workspace_control_permanent_script(), ) # bring tab to front cmds.evalDeferred(lambda *args: cmds.workspaceControl(DOCK_NAME, e=True, r=True)) def close(): from maya import cmds # noinspection PyBroadException try: cmds.deleteUI(DOCK_NAME) except: pass pass cleanup.registerCleanupHandler(close) def resume_in_workspace_control(): """ this method is responsible for resuming workspace control when Maya is building/restoring UI as part of it's workspace management cycle (open UI for the first time, restart maya, change workspace, etc) """ cmds.workspaceControl(DOCK_NAME, e=True, label="ngSkinTools " + version.pluginVersion()) widget = wrap_instance(omui.MQtUtil.findControl(DOCK_NAME), QtWidgets.QWidget) ui, _ = build_ui(widget) widget.layout().addWidget(ui)