Пример #1
0
class PlotControlWidget(QWidget):
    # noinspection PyTypeChecker
    def __init__(self, parent=None):
        super().__init__(parent)

        # setup settings for the class
        self.settings = QSettings()
        self.settings.beginGroup("plot_control")

        self.base_vector_data = vpype.VectorData()
        self.vector_data: vpype.VectorData = None

        # settings
        self.page_format: str = self.settings.value("page_format", "A4")
        self.landscape: bool = self.settings.value("landscape", False)
        self.rotated: bool = self.settings.value("rotate", False)
        self.rotated: bool = self.settings.value("rotated", False)
        self.center: bool = self.settings.value("center", True)
        self.fit_page: bool = self.settings.value("fit_page", False)
        self.margin_value: float = self.settings.value("margin_value", 2.0)
        self.margin_unit: str = self.settings.value("margin_unit", "cm")

        # setup plot area
        self.plot = VectorDataPlotWidget()
        self.plot.setSizePolicy(
            QSizePolicy(QSizePolicy.Expanding, QSizePolicy.Expanding))

        # page layout controls
        page_box = QGroupBox("Page layout")
        page_layout = QFormLayout()
        page_format_combo = QComboBox()
        for k in PAGE_FORMATS:
            page_format_combo.addItem(k)
        page_format_combo.setCurrentText(self.page_format)
        page_format_combo.currentTextChanged.connect(
            lambda text: self.set_page_format(text))
        landscape_check = QCheckBox("Landscape")
        landscape_check.setChecked(self.landscape)
        landscape_check.stateChanged.connect(
            lambda: self.set_landscape(landscape_check.isChecked()))
        rotated_check = QCheckBox("Rotated")
        rotated_check.setChecked(self.landscape)
        rotated_check.stateChanged.connect(
            lambda: self.set_rotated(rotated_check.isChecked()))
        center_check = QCheckBox("Center on page")
        center_check.setChecked(self.center)
        center_check.stateChanged.connect(
            lambda: self.set_center(center_check.isChecked()))
        fit_page_check = QCheckBox("Fit to page")
        fit_page_check.setChecked(self.fit_page)
        fit_page_check.stateChanged.connect(
            lambda: self.set_fit_page(fit_page_check.isChecked()))
        margin_layout = QHBoxLayout()
        margin_spin = QDoubleSpinBox()
        margin_spin.setValue(self.margin_value)
        margin_spin.valueChanged.connect(lambda: self.set_margin(
            margin_spin.value(), margin_unit.currentText()))
        margin_unit = UnitComboBox()
        margin_unit.setCurrentText(self.margin_unit)
        margin_unit.currentTextChanged.connect(lambda: self.set_margin(
            margin_spin.value(), margin_unit.currentText()))
        margin_layout.addWidget(margin_spin)
        margin_layout.addWidget(margin_unit)
        page_layout.addRow("Page format:", page_format_combo)
        page_layout.addRow("", landscape_check)
        page_layout.addRow("", rotated_check)
        page_layout.addRow("", center_check)
        page_layout.addRow("", fit_page_check)
        page_layout.addRow("Margin:", margin_layout)
        page_box.setLayout(page_layout)

        # Action buttons
        pen_up_btn = QPushButton("UP")
        pen_down_btn = QPushButton("DOWN")
        pen_up_btn.clicked.connect(lambda: axy.pen_up())
        pen_down_btn.clicked.connect(lambda: axy.pen_down())
        pen_up_spin = AxySettingsSpinBox(self.settings, "pen_pos_up", 60.0)
        pen_down_spin = AxySettingsSpinBox(self.settings, "pen_pos_down", 40.0)
        pen_up_layout = QHBoxLayout()
        pen_up_layout.addWidget(pen_up_spin)
        pen_up_layout.addWidget(pen_up_btn)
        pen_down_layout = QHBoxLayout()
        pen_down_layout.addWidget(pen_down_spin)
        pen_down_layout.addWidget(pen_down_btn)
        shutdown_btn = QPushButton("OFF")
        shutdown_btn.clicked.connect(lambda: axy.shutdown())
        plot_btn = QPushButton("PLOT")
        plot_btn.clicked.connect(lambda: self.plot_svg())
        action_box = QGroupBox("Actions")
        action_layout = QFormLayout()
        action_layout.addRow("Pen up: ", pen_up_layout)
        action_layout.addRow("Pen down: ", pen_down_layout)
        action_layout.addRow("Motor off:", shutdown_btn)
        action_layout.addRow("Plot:", plot_btn)
        action_box.setLayout(action_layout)

        self.list = QListView()
        self.list.setFixedHeight(120)
        self.list.setSizePolicy(
            QSizePolicy(QSizePolicy.Preferred, QSizePolicy.Preferred))

        # controls layout
        controls_layout = QVBoxLayout()
        controls_layout.addWidget(self.list)
        controls_layout.addWidget(page_box)
        controls_layout.addWidget(action_box)
        controls_layout.addItem(
            QSpacerItem(20, 40, QSizePolicy.Minimum, QSizePolicy.Expanding))

        # setup layout
        root_layout = QHBoxLayout()
        root_layout.addWidget(self.plot)
        root_layout.addLayout(controls_layout)
        self.setLayout(root_layout)

        self.update_view()

        # FIXME: stub vector data
        # vd = vpype.VectorData()
        # vd.add(vpype.LineCollection([(0, 100), (200, 1001 + 201j)]), 1)
        # vd.add(vpype.LineCollection([(0, 100 + 100j), (300j, 400j + 100)]), 2)
        self.load_svg(
            "/Users/hhip/Drive/axidraw/wheel_cards/wheel_card_triple_5_40.svg")
        # self.load_svg("/Users/hhip/Downloads/spirograph-grids/spirograph-grid.svg")

    def add_actions(self, toolbar: QToolBar):
        colorful_act = toolbar.addAction(QIcon("images/icons_colorful.png"),
                                         "Colorful")
        colorful_act.setCheckable(True)
        colorful_act.setChecked(self.plot.colorful)
        colorful_act.triggered.connect(
            lambda checked: setattr(self.plot, "colorful", checked))

        show_points_act = toolbar.addAction(
            QIcon("images/icons_show_points.png"), "Points")
        show_points_act.setCheckable(True)
        show_points_act.setChecked(self.plot.show_points)
        show_points_act.triggered.connect(
            lambda checked: setattr(self.plot, "show_points", checked))

        show_pen_up_act = toolbar.addAction(
            QIcon("images/icons_show_pen_up.png"), "Pen-Up")
        show_pen_up_act.setCheckable(True)
        show_pen_up_act.setChecked(self.plot.show_pen_up)
        show_pen_up_act.triggered.connect(
            lambda checked: setattr(self.plot, "show_pen_up", checked))

        show_axes_act = toolbar.addAction(QIcon("images/icons_show_axes.png"),
                                          "Axes")
        show_axes_act.setCheckable(True)
        show_axes_act.setChecked(self.plot.show_axes)
        show_axes_act.triggered.connect(
            lambda checked: setattr(self.plot, "show_axes", checked))

        scale = UnitComboBox()
        scale.setCurrentText(self.plot.unit)
        scale.currentTextChanged.connect(
            lambda text: setattr(self.plot, "unit", text))
        toolbar.addWidget(scale)

    def load_svg(self, path: str):
        # TODO: make quantization a parameters
        vd = vpype.read_multilayer_svg(path, 0.05)
        self.set_vector_data(vd)

    def plot_svg(self):
        vd = vpype.VectorData()
        for lid in self.vector_data.layers:
            if self.plot.layer_visible(lid):
                vd.add(self.vector_data.layers[lid], 1)
        svg = io.StringIO()
        vpype.write_svg(svg, vd, page_format=self.plot.page_format)
        axy.plot_svg(svg.getvalue())

    def set_vector_data(self, vector_data: vpype.VectorData):
        self.base_vector_data = vector_data

        self.update_view()
        model = QStandardItemModel()
        for lid in vector_data.layers:
            item = QStandardItem()
            item.setCheckable(True)
            item.setCheckState(
                Qt.Checked if self.plot.layer_visible(lid) else Qt.Unchecked)
            pixmap = QPixmap(16, 12)
            pixmap.fill(QColor(*[c * 255 for c in self.plot.layer_color(lid)]))
            item.setIcon(QIcon(pixmap))
            item.setText(f"Layer {lid}")
            item.setSelectable(False)
            item.setEditable(False)
            item.setData(lid, Qt.UserRole + 1)
            model.appendRow(item)

        model.itemChanged.connect(lambda it: self.plot.set_layer_visible(
            it.data(Qt.UserRole + 1),
            it.checkState() == Qt.Checked))
        self.list.setModel(model)

    def set_page_format(self, page_format: str):
        self.page_format = page_format
        self.settings.setValue("page_format", page_format)
        self.update_view()

    def set_landscape(self, landscape: bool):
        self.landscape = landscape
        self.settings.setValue("landscape", landscape)
        self.update_view()

    def set_rotated(self, rotated: bool):
        self.rotated = rotated
        self.settings.setValue("rotated", rotated)
        self.update_view()

    def set_center(self, center: bool):
        self.center = center
        self.settings.setValue("center", center)
        self.update_view()

    def set_fit_page(self, fit_page: bool):
        self.fit_page = fit_page
        self.settings.setValue("fit_page", fit_page)
        self.update_view()

    def set_margin(self, value: float, unit: str):
        self.margin_value = value
        self.margin_unit = unit
        self.settings.setValue("margin_value", value)
        self.settings.setValue("margin_unit", unit)
        if self.fit_page:
            self.update_view()

    def update_view(self):
        self.vector_data = copy.deepcopy(self.base_vector_data)

        # scale/center according to settings
        width, height = PAGE_FORMATS[str(self.page_format)]
        if self.landscape:
            width, height = height, width
        if self.rotated:
            self.vector_data.rotate(-math.pi / 2)
            self.vector_data.translate(0, height)

        bounds = self.vector_data.bounds()
        if bounds is not None:
            min_x, min_y, max_x, max_y = bounds
            margin = self.margin_value * vpype.convert(self.margin_unit)
            if self.fit_page:
                factor_x = (width - 2 * margin) / (max_x - min_x)
                factor_y = (height - 2 * margin) / (max_y - min_y)
                scale = min(factor_x, factor_y)

                self.vector_data.translate(-min_x, -min_y)
                self.vector_data.scale(scale)
                if factor_x < factor_y:
                    self.vector_data.translate(
                        margin, margin + (height - 2 * margin -
                                          (max_y - min_y) * scale) / 2)
                else:
                    self.vector_data.translate(
                        margin + (width - 2 * margin -
                                  (max_x - min_x) * scale) / 2, margin)
            elif self.center:
                self.vector_data.translate(
                    (width - (max_x - min_x)) / 2 - min_x,
                    (height - (max_y - min_y)) / 2 - min_y,
                )

        # configure plot widget
        self.plot.vector_data = self.vector_data
        self.plot.page_format = (width, height)
Пример #2
0
class FormMidContextWidget(QtWidgets.QWidget):
    #定义成员变量

    #定义信号

    def __init__(self):
        super().__init__()

        self.__initForm()
        self.__loadMusicLibraryListWidgetData()
        self.__loadSongsNameListWidgetData()
        self.__loadCollectionMusicListWidgetData()

    def __initForm(self):
        self.mainLayout = QHBoxLayout()
        self.mainLayout.setContentsMargins(1, 1, 1, 1)
        self.contextFrame = QtWidgets.QFrame()
        self.contextFrame.setObjectName("contextFrame")
        self.midContextLayout = QHBoxLayout()
        self.midContextLayout.setSpacing(1)
        self.midContextLayout.setContentsMargins(0, 1, 0, 1)
        self.midLeftFrame = QtWidgets.QFrame()
        self.midLeftFrame.setObjectName("midLeftFrame")
        self.midLeftLayout = QVBoxLayout()
        self.midLeftFrame.setLayout(self.midLeftLayout)
        self.midLeftLayout.setSpacing(0)
        self.midLeftLayout.setContentsMargins(2, 2, 2, 2)

        self.musicLibraryTitleLabel = QLabel("音乐库")
        self.textFont = QFont("微软雅黑", 11)
        self.textFont.setBold(True)
        self.musicLibraryTitleLabel.setFont(self.textFont)
        self.musicLibraryListView = QListView()
        self.musicLibraryListView.setFixedHeight(140)
        self.musicLibraryListView.setObjectName('musicLibraryListView')
        self.musicLibraryListView.setFixedWidth(190)

        self.localCollectionTitleLabel = QLabel("本地收藏")
        self.localCollectionTitleLabel.setFont(self.textFont)
        self.localCollectionListView = QListView()
        self.localCollectionListView.setObjectName('localCollectionListView')
        self.localCollectionListView.setFixedWidth(190)

        self.songsNameListTitleLabel = QLabel("歌单列表")
        self.songsNameListTitleLabel.setFont(self.textFont)
        self.songsNameListView = QListView()
        self.songsNameListView.setObjectName('songsNameListView')
        self.songsNameListView.setFixedWidth(190)
        self.songsNameListView.setFixedHeight(300)

        self.midLeftLayout.addWidget(self.musicLibraryTitleLabel)
        self.midLeftLayout.addWidget(self.musicLibraryListView)
        self.midLeftLayout.addWidget(self.songsNameListTitleLabel)
        self.midLeftLayout.addWidget(self.songsNameListView)
        self.midLeftLayout.addWidget(self.localCollectionTitleLabel)
        self.midLeftLayout.addWidget(self.localCollectionListView)
        self.rightContextStackWidget = QStackedWidget()
        self.testLabel = QLabel()
        self.testLabel.setScaledContents(True)
        self.testLabel.setPixmap(
            QPixmap(":/icon/Resources/icon/icon-meinv.jpg").scaled(
                self.testLabel.width(), self.testLabel.height(),
                Qt.KeepAspectRatio, Qt.SmoothTransformation))
        self.rightContextStackWidget.addWidget(self.testLabel)
        self.midContextLayout.addWidget(self.midLeftFrame)
        self.midContextLayout.addWidget(self.rightContextStackWidget)
        self.midContextLayout.setStretch(0, 0)
        self.midContextLayout.setStretch(1, 1)
        self.contextFrame.setLayout(self.midContextLayout)
        self.mainLayout.addWidget(self.contextFrame)
        self.setLayout(self.mainLayout)

    def __loadMusicLibraryListWidgetData(self):
        self.textFont = QFont("微软雅黑", 11)

        self.localMusicItemData = QStandardItem("本地音乐")
        self.localMusicItemData.setFont(self.textFont)
        self.localMusicItemData.setEditable(False)
        self.localMusicItemData.setData(
            QIcon(":/icon/Resources/icon/icon-localmusic.svg"),
            Qt.DecorationRole)

        self.wangyiYunItemData = QStandardItem("网易云音乐")
        self.wangyiYunItemData.setFont(self.textFont)
        self.wangyiYunItemData.setEditable(False)
        self.wangyiYunItemData.setData(
            QIcon(":/icon/Resources/icon/icon-wangyiyunmusic.svg"),
            Qt.DecorationRole)

        self.qqMusicItemData = QStandardItem("QQ音乐")
        self.qqMusicItemData.setFont(self.textFont)
        self.qqMusicItemData.setEditable(False)
        self.qqMusicItemData.setData(
            QIcon(":/icon/Resources/icon/icon-qqmusic.svg"), Qt.DecorationRole)

        self.xiaMiItemData = QStandardItem("虾米音乐")
        self.xiaMiItemData.setFont(self.textFont)
        self.xiaMiItemData.setEditable(False)
        self.xiaMiItemData.setData(
            QIcon(":/icon/Resources/icon/icon-xiamimusic.svg"),
            Qt.DecorationRole)

        self.musicLibraryModel = QStandardItemModel()
        self.musicLibraryModel.appendRow(self.localMusicItemData)
        self.musicLibraryModel.appendRow(self.wangyiYunItemData)
        self.musicLibraryModel.appendRow(self.qqMusicItemData)
        self.musicLibraryModel.appendRow(self.xiaMiItemData)

        self.musicLibraryListView.setSpacing(2)
        self.musicLibraryListView.setModel(self.musicLibraryModel)

    def __loadSongsNameListWidgetData(self):
        self.wubaiItemData = QStandardItem("伍佰&China blue")
        self.textFont = QFont("微软雅黑", 11)
        self.wubaiItemData.setFont(self.textFont)
        self.wubaiItemData.setEditable(False)
        self.wubaiItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.zongguanxianItemData = QStandardItem("纵贯线")
        self.zongguanxianItemData.setFont(self.textFont)
        self.zongguanxianItemData.setEditable(False)
        self.zongguanxianItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.zhaoleiItemData = QStandardItem("赵雷专辑")
        self.zhaoleiItemData.setFont(self.textFont)
        self.zhaoleiItemData.setEditable(False)
        self.zhaoleiItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.xuweiItemData = QStandardItem("许巍专辑")
        self.xuweiItemData.setFont(self.textFont)
        self.xuweiItemData.setEditable(False)
        self.xuweiItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.zhouhuajianItemData = QStandardItem("周华健专辑")
        self.zhouhuajianItemData.setFont(self.textFont)
        self.zhouhuajianItemData.setEditable(False)
        self.zhouhuajianItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.banderuiItemData = QStandardItem("班得瑞专辑")
        self.banderuiItemData.setFont(self.textFont)
        self.banderuiItemData.setEditable(False)
        self.banderuiItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.yaogunItemData = QStandardItem("摇滚专辑")
        self.yaogunItemData.setFont(self.textFont)
        self.yaogunItemData.setEditable(False)
        self.yaogunItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.yinshiyuanshenItemData = QStandardItem("影视原声")
        self.yinshiyuanshenItemData.setFont(self.textFont)
        self.yinshiyuanshenItemData.setEditable(False)
        self.yinshiyuanshenItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.minyaoItemData = QStandardItem("民谣专辑")
        self.minyaoItemData.setFont(self.textFont)
        self.minyaoItemData.setEditable(False)
        self.minyaoItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.tianlaizhiyinItemData = QStandardItem("天籁之音")
        self.tianlaizhiyinItemData.setFont(self.textFont)
        self.tianlaizhiyinItemData.setEditable(False)
        self.tianlaizhiyinItemData.setData(
            QIcon(":/icon/Resources/icon/icon-gedanlist.svg"),
            Qt.DecorationRole)

        self.songsNameListModel = QStandardItemModel()
        self.songsNameListModel.appendRow(self.wubaiItemData)
        self.songsNameListModel.appendRow(self.zongguanxianItemData)
        self.songsNameListModel.appendRow(self.zhaoleiItemData)
        self.songsNameListModel.appendRow(self.xuweiItemData)
        self.songsNameListModel.appendRow(self.zhouhuajianItemData)
        self.songsNameListModel.appendRow(self.banderuiItemData)
        self.songsNameListModel.appendRow(self.yaogunItemData)
        self.songsNameListModel.appendRow(self.yinshiyuanshenItemData)
        self.songsNameListModel.appendRow(self.minyaoItemData)
        self.songsNameListModel.appendRow(self.tianlaizhiyinItemData)

        self.songsNameListView.setSpacing(2)
        self.songsNameListView.setModel(self.songsNameListModel)

    def __loadCollectionMusicListWidgetData(self):
        self.jingdianItemData = QStandardItem("经典老歌")
        self.textFont = QFont("微软雅黑", 11)
        self.jingdianItemData.setFont(self.textFont)
        self.jingdianItemData.setEditable(False)
        self.jingdianItemData.setData(
            QIcon(":/icon/Resources/icon/icon-collectionmusic.svg"),
            Qt.DecorationRole)

        self.qinyinyueItemData = QStandardItem("轻音乐系")
        self.qinyinyueItemData.setFont(self.textFont)
        self.qinyinyueItemData.setEditable(False)
        self.qinyinyueItemData.setData(
            QIcon(":/icon/Resources/icon/icon-collectionmusic.svg"),
            Qt.DecorationRole)

        self.jitaxilieItemData = QStandardItem("吉他系列")
        self.jitaxilieItemData.setFont(self.textFont)
        self.jitaxilieItemData.setEditable(False)
        self.jitaxilieItemData.setData(
            QIcon(":/icon/Resources/icon/icon-collectionmusic.svg"),
            Qt.DecorationRole)

        self.remengequItemData = QStandardItem("热门歌曲")
        self.remengequItemData.setFont(self.textFont)
        self.remengequItemData.setEditable(False)
        self.remengequItemData.setData(
            QIcon(":/icon/Resources/icon/icon-collectionmusic.svg"),
            Qt.DecorationRole)

        self.songsNameModel = QStandardItemModel()
        self.songsNameModel.appendRow(self.jingdianItemData)
        self.songsNameModel.appendRow(self.qinyinyueItemData)
        self.songsNameModel.appendRow(self.jitaxilieItemData)
        self.songsNameModel.appendRow(self.remengequItemData)
        self.localCollectionListView.setSpacing(2)
        self.localCollectionListView.setModel(self.songsNameModel)