我想在一个QGraphicsPixmapItem上应用一个透明梯度,但是我不知道如何去做,因为现在我只能在整个QGraphicsPixmapItem上应用透明性(不是梯度)。这个项目经历了一个镜像效应(就像墙上的一个反射在地面上的元素),然后我想设置这个透明梯度(从上到下;顶部相当不透明……)在透明的几个阶段,它最终在项目的底部是完全透明的),然后我添加模糊。这是透明梯度的一部分,我似乎做不到.我不明白它怎么能起作用。我试过的一切都不管用。你能帮我吗?提前谢谢。
下面是一个相当短的代码:
for item in self.scene.selectedItems() :
# Width
item_height = item.boundingRect().height()
# mirroir
item.setTransform(QTransform(1, 0, 0, 0, -1, 0, 0, 0, 1))
#
item.setOpacity(0.7)
# Blur
blur = QGraphicsBlurEffect()
blur.setBlurRadius(8)
item.setGraphicsEffect(blur)
item.setPos(100, 100 + 2 * (int(item_height)))
##############################################
"""
alphaGradient = QLinearGradient(item.boundingRect().topLeft(), item.boundingRect().bottomLeft())
alphaGradient.setColorAt(0.0, Qt.transparent)
alphaGradient.setColorAt(0.5, Qt.black)
alphaGradient.setColorAt(1.0, Qt.transparent)
effect = QGraphicsOpacityEffect()
effect.setOpacityMask(alphaGradient)
item.setGraphicsEffect(effect) ########
"""
##############################################
"""
opacity = QGraphicsOpacityEffect()
lg = QLinearGradient()
lg.setStart(0, 0)
lg.setFinalStop(0, 100)
lg.setColorAt(0, Qt.transparent)
lg.setColorAt(0.5, Qt.transparent)
lg.setColorAt(1.0, Qt.transparent)
opacity.setOpacityMask(lg)
#opacity.setOpacity(1)
item.setGraphicsEffect(opacity)
"""
##############################################发布于 2022-05-24 15:13:11
每个目标项(或小部件)只能应用一个QGraphicsEffect,因此您有两个选项:
在这两种情况下,我建议您将“镜像”项创建为实际QGraphicsPixmapItem的子项,这将确保它始终遵循父级发生的情况,包括可见性和几何更改、转换等。
使用透明梯度生成镜像
为此,我们使用了作文的QPainter特性,特别是允许使用梯度作为所绘制图像的alpha通道的源的CompositionMode_SourceIn。
程序如下:
class MirrorPixmapItem(QtWidgets.QGraphicsPixmapItem):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.mirror = QtWidgets.QGraphicsPixmapItem(self)
self.blurEffect = QtWidgets.QGraphicsBlurEffect(blurRadius=8)
self.mirror.setGraphicsEffect(self.blurEffect)
if not self.pixmap().isNull():
self.createMirror()
def setPixmap(self, pixmap):
old = self.pixmap()
super().setPixmap(pixmap)
if old == pixmap:
return
self.createMirror()
def setOffset(self, *args):
super().setOffset(*args)
if not self.mirror.pixmap().isNull():
self.mirror.setOffset(self.offset())
def createMirror(self):
source = self.pixmap()
if source.isNull():
self.mirror.setPixmap(source)
return
scale = .5
height = int(source.height() * scale)
output = QtGui.QPixmap(source.width(), height)
output.fill(QtCore.Qt.transparent)
qp = QtGui.QPainter(output)
grad = QtGui.QLinearGradient(0, 0, 0, height)
grad.setColorAt(0, QtCore.Qt.black)
grad.setColorAt(1, QtCore.Qt.transparent)
qp.fillRect(output.rect(), grad)
qp.setCompositionMode(qp.CompositionMode_SourceIn)
qp.drawPixmap(0, 0,
source.transformed(QtGui.QTransform().scale(1, -scale)))
qp.end()
self.mirror.setPixmap(output)
self.mirror.setY(self.boundingRect().bottom())
self.mirror.setOffset(self.offset())设置父项的不透明度。
在这种情况下,我们仍然对镜像项有模糊效果,但是我们在父项(原始映像)上应用了一个QGraphicsOpacityEffect,并使用了包含原始图像和镜像的opacityMask,它将处于完全不透明状态,直到原始图像的高度,然后开始淡出到镜像的完全透明。
class MirrorPixmapItem2(QtWidgets.QGraphicsPixmapItem):
def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
self.opacity = QtWidgets.QGraphicsOpacityEffect(opacity=1)
self.setGraphicsEffect(self.opacity)
self.mirror = QtWidgets.QGraphicsPixmapItem(self)
self.blurEffect = QtWidgets.QGraphicsBlurEffect(blurRadius=8)
self.mirror.setGraphicsEffect(self.blurEffect)
if not self.pixmap().isNull():
self.createMirror()
# ... override setPixmap() and setOffset() as above
def createMirror(self):
source = self.pixmap()
if source.isNull():
self.mirror.setPixmap(source)
return
scale = .5
self.mirror.setPixmap(
source.transformed(QtGui.QTransform().scale(1, -scale)))
self.mirror.setPos(self.boundingRect().bottomLeft())
self.mirror.setOffset(self.offset())
height = source.height()
gradHeight = height + height * scale
grad = QtGui.QLinearGradient(0, 0, 0, gradHeight)
grad.setColorAt(height / gradHeight, QtCore.Qt.black)
grad.setColorAt(1, QtCore.Qt.transparent)
self.opacity.setOpacityMask(grad)这就是结果,正如您可以看到的,使用哪种方法是一个选择的问题,但是从性能的角度来看,第一个方法可能会稍微好一些,因为在绘制项目时不需要额外的效果,如果要有许多图像项和/或高分辨率,这可能很重要。

https://stackoverflow.com/questions/72363586
复制相似问题