【发布时间】:2020-12-29 08:07:00
【问题描述】:
这张照片很好地代表了我想要模仿的东西。
目标是创建项目或小部件,类似于上面的示例,用户可以通过 MouseDoubleClicked 事件在 QSlider 上创建它们,并且它们将保持在最初创建的 Tick 位置(它将保持不动)。 我已经尝试过使用 QLabels 和 Pixmaps 或 QGraphicsItems 和 QGraphicsView 的组合,但都是徒劳的。
不过,我觉得我很可能把事情复杂化了,可能有一种更简单的方法可以实现这一点。
制作这些“标记”的方法是什么?
编辑:我已尽力编辑我以前的尝试之一,以使其成为最小可重现示例。虽然可能仍然太长,但它就是这样。
import random
from PySide2 import QtCore, QtGui, QtWidgets
class Marker(QtWidgets.QLabel):
def __init__(self, parent=None):
super(Marker, self).__init__(parent)
self._slider = None
self.setAcceptDrops(True)
pix = QtGui.QPixmap(30, 30)
pix.fill(QtGui.QColor("transparent"))
paint = QtGui.QPainter(pix)
slider_color = QtGui.QColor(random.randint(130, 180), random.randint(130, 180), random.randint(130, 180))
handle_pen = QtGui.QPen(QtGui.QColor(slider_color.darker(200)))
handle_pen.setWidth(3)
paint.setPen(handle_pen)
paint.setBrush(QtGui.QBrush(slider_color, QtCore.Qt.SolidPattern))
points = QtGui.QPolygon([
QtCore.QPoint(5, 5),
QtCore.QPoint(5, 19),
QtCore.QPoint(13, 27),
QtCore.QPoint(21, 19),
QtCore.QPoint(21, 5),
])
paint.drawPolygon(points)
del paint
self.setPixmap(pix)
class myTimeline(QtWidgets.QWidget):
def __init__(self, parent=None):
super(myTimeline, self).__init__(parent)
layout = QtWidgets.QGridLayout(self)
self.slider = QtWidgets.QSlider(QtCore.Qt.Horizontal)
self.slider.setMinimum(0)
self.slider.setMaximum(50)
self.slider.setTickPosition(QtWidgets.QSlider.TicksAbove)
self.slider.setTickInterval(1)
self.slider.setSingleStep(1)
self.slider.setAcceptDrops(True)
self.resize(self.width(), 50)
layout.addWidget(self.slider)
def create_marker(self):
bookmark = Marker(self)
opt = QtWidgets.QStyleOptionSlider()
self.slider.initStyleOption(opt)
rect = self.slider.style().subControlRect(
QtWidgets.QStyle.CC_Slider,
opt,
QtWidgets.QStyle.SC_SliderHandle,
self.slider
)
bookmark.move(rect.center().x(), 0)
bookmark.show()
def mouseDoubleClickEvent(self, event):
self.create_marker()
【问题讨论】:
-
您能否提供一个minimal, reproducible example 来说明您目前所获得的信息?可能使用更接近您想要实现的东西的代码(即使它没有按预期工作)。
-
感谢您的评论,但这实际上是我的问题的重点:我不能。虽然我当然可以把我以前的尝试之一放在这里,但它绝对不会是“最小的”,因此这个问题。最重要的是,即使我这样做了,它也可能违反 Stack Overflow 的规则,我想在这里避免与版主发生问题。
-
我理解您的担忧,但是 QSlider 不容易映射,而且如果没有最小的 MRE,很难根据“猜测”提供答案。我们可以尝试给出答案,但它可能非常通用,并且可能不是正确的解决方案(和答案)。不要担心版主可能出现的“问题”,尽量先举个例子,如果有问题,他们会收到你的通知。
-
再次感谢您的评论。我最终冒险了,我只是编辑了我的问题,以添加我认为最接近最小可重现示例的内容。
-
别担心,你的代码很好,不会太长。据我所见,您几乎可以使用它,除了 QLabel 几何形状的一个小问题以及如果手柄靠近标记它会使滑块几乎无法使用的事实。除此之外(以及某些样式的标记位置略微偏离),我看不到任何其他问题:您的实现有什么问题?