MaxPlus Python API Reference
Python3/PySide2/docking_widgets.py
1 '''
2  Demonstrates how to create a QWidget with PySide2 and attach it to the 3dsmax main window.
3  Creates two types of dockable widgets, a QDockWidget and a QToolbar
4 '''
5 
6 import os
7 import ctypes
8 
9 from PySide2 import QtCore
10 from PySide2 import QtGui
11 from PySide2.QtWidgets import QMainWindow, QDockWidget, QToolButton, QToolBar, QAction
12 
13 from pymxs import runtime as rt
14 from qtmax import GetQMaxMainWindow
15 
16 def get_pos_to_dock_toolbar(dock_widget):
17  """
18  Get the docking widget position based on its size
19  """
20  space_between_widgets = 20 # Arbritrary hard coded value
21  dock_widget_rect = dock_widget.geometry()
22  x_pos = dock_widget_rect.x()
23  y_pos = dock_widget_rect.bottom() + space_between_widgets
24  return QtCore.QPoint(x_pos, y_pos)
25 
26 def make_toolbar_floating(toolbar, pos):
27  """
28  Set the toolbar widget properties to act as a tool floating window
29  """
30  toolbar.setWindowFlags(
31  QtCore.Qt.Tool | QtCore.Qt.FramelessWindowHint | QtCore.Qt.X11BypassWindowManagerHint)
32  toolbar.move(pos)
33  toolbar.adjustSize()
34  toolbar.show()
35  QtCore.QMetaObject.invokeMethod(toolbar, \
36  "topLevelChanged", \
37  QtCore.Qt.DirectConnection, \
38  QtCore.QGenericArgument("bool", ctypes.c_void_p(True)))
39 
40 def create_cylinder():
41  """
42  Create a cylinder node with predetermined radius and height values.
43  """
44  rt.Cylinder(radius=10, height=30)
45  rt.redrawViews()
46 
47 def demo_docking_widgets():
48  """
49  Demonstrates how to create a QWidget with PySide2 and attach it to the 3dsmax main window.
50  Creates two types of dockable widgets, a QDockWidget and a QToolbar
51  """
52  # Retrieve 3ds Max Main Window QWdiget
53  main_window = GetQMaxMainWindow()
54 
55  # QAction reused by both dockable widgets.
56  cylinder_icon_path = os.path.dirname(os.path.realpath(__file__)) + "\\cylinder_icon_48.png"
57  cylinder_icon = QtGui.QIcon(cylinder_icon_path)
58  create_cyl_action = QAction(cylinder_icon, u"Create Cylinder", main_window)
59  create_cyl_action.triggered.connect(create_cylinder)
60 
61  # QDockWidget construction and placement over the main window
62  dock_widget = QDockWidget(main_window)
63 
64  # Set for position persistence
65  dock_widget.setObjectName("Creators")
66  # Set to see dock widget name in toolbar customize popup
67  dock_widget.setWindowTitle("Creators")
68  dock_tool_button = QToolButton()
69  dock_tool_button.setAutoRaise(True)
70  dock_tool_button.setDefaultAction(create_cyl_action)
71  dock_tool_button.setToolButtonStyle(QtCore.Qt.ToolButtonTextOnly)
72  dock_widget.setWidget(dock_tool_button)
73 
74  main_window.addDockWidget(QtCore.Qt.LeftDockWidgetArea, dock_widget)
75  dock_widget.setFloating(True)
76  dock_widget.show()
77 
78  # QToolBar construction and attachement to main window
79  toolbar_widget = QToolBar(main_window)
80 
81  # Set for position persistence
82  toolbar_widget.setObjectName("Creators TB")
83  # Set to see dock widget name in toolbar customize popup
84  toolbar_widget.setWindowTitle("Creators TB")
85  toolbar_widget.setFloatable(True)
86  toolbar_widget.addAction(create_cyl_action)
87 
88  main_window.addToolBar(QtCore.Qt.BottomToolBarArea, toolbar_widget)
89  toolbar_widget.show()
90 
91  toolbar_position = get_pos_to_dock_toolbar(dock_widget)
92  make_toolbar_floating(toolbar_widget, toolbar_position)
93 
94 demo_docking_widgets()
QtWidgets