PyQt6/PySide6 的 QPropertyAnimation 類適用場(chǎng)景分析
一、概述
QGraphicsView 和 QGraphicsScene 是 Qt 圖形視圖框架的核心類,用于構(gòu)建高性能、可交互的 2D 圖形界面。
核心分工:
- QGraphicsScene:管理場(chǎng)景中的圖形項(xiàng)(
QGraphicsItem),處理事件和坐標(biāo)系統(tǒng)。 - QGraphicsView:作為觀察場(chǎng)景的視口,提供縮放、平移、旋轉(zhuǎn)等視圖變換功能。
適用場(chǎng)景:
- 復(fù)雜繪圖(如 CAD 工具)
- 游戲開發(fā)(2D 場(chǎng)景)
- 數(shù)據(jù)可視化(圖表、流程圖)
- 交互式圖形界面(可拖拽、編輯的組件)
二、核心組件與關(guān)系
組件層級(jí)
QGraphicsView (視圖)
└── QGraphicsScene (場(chǎng)景)
└── QGraphicsItem (圖形項(xiàng):矩形、橢圓、文本、自定義項(xiàng)等)坐標(biāo)系差異
- 場(chǎng)景坐標(biāo):場(chǎng)景的全局坐標(biāo)系(原點(diǎn)在場(chǎng)景中心或自定義位置)。
- 視圖坐標(biāo):視圖窗口的坐標(biāo)系(原點(diǎn)在左上角)。
- 項(xiàng)坐標(biāo):每個(gè)圖形項(xiàng)自身的局部坐標(biāo)系。
三、基礎(chǔ)使用步驟
創(chuàng)建場(chǎng)景與視圖
from PyQt6.QtWidgets import QGraphicsView, QGraphicsScene, QApplication from PyQt6.QtCore import Qt scene = QGraphicsScene() # 創(chuàng)建場(chǎng)景 view = QGraphicsView(scene) # 創(chuàng)建視圖并綁定場(chǎng)景 view.setRenderHint(QPainter.RenderHint.Antialiasing) # 抗鋸齒 view.resize(800, 600) view.show()
添加圖形項(xiàng)到場(chǎng)景
# 添加矩形(位置、大小、顏色)
rect = scene.addRect(0, 0, 100, 50, Qt.GlobalColor.red, Qt.GlobalColor.blue)
# 添加文本
text = scene.addText("Hello Graphics", QFont("Arial", 12))
text.setPos(50, 50)
# 添加橢圓
ellipse = scene.addEllipse(200, 100, 80, 60, Qt.GlobalColor.green)四、核心功能與實(shí)戰(zhàn)案例
交互式圖形項(xiàng)(拖拽、旋轉(zhuǎn))
class MovableRect(QGraphicsRectItem):
def __init__(self, x, y, w, h):
super().__init__(x, y, w, h)
self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemIsMovable) # 允許拖拽
self.setFlag(QGraphicsItem.GraphicsItemFlag.ItemIsSelectable) # 允許選中
self.setBrush(Qt.GlobalColor.cyan)
# 添加可移動(dòng)矩形到場(chǎng)景
movable_rect = MovableRect(300, 200, 80, 40)
scene.addItem(movable_rect)視圖操作(縮放與平移)
# 鼠標(biāo)滾輪縮放
def wheelEvent(self, event):
factor = 1.2 if event.angleDelta().y() > 0 else 0.8
self.scale(factor, factor)
# 右鍵拖拽平移
view.setDragMode(QGraphicsView.DragMode.ScrollHandDrag) # 設(shè)置拖拽模式自定義圖形項(xiàng)(繪制箭頭)
class ArrowItem(QGraphicsItem):
def boundingRect(self):
return QRectF(-10, -5, 20, 10) # 定義項(xiàng)邊界
def paint(self, painter, option, widget):
painter.setPen(QPen(Qt.GlobalColor.black, 2))
painter.drawLine(0, 0, 10, 0) # 箭頭主體
painter.drawLine(10, 0, 5, -5) # 箭頭尖端
painter.drawLine(10, 0, 5, 5)
arrow = ArrowItem()
arrow.setPos(400, 300)
scene.addItem(arrow)動(dòng)畫與圖形項(xiàng)結(jié)合
# 使用 QPropertyAnimation 移動(dòng)圖形項(xiàng) from PyQt6.QtCore import QPropertyAnimation anim = QPropertyAnimation(arrow, b"pos") anim.setDuration(2000) anim.setStartValue(QPointF(400, 300)) anim.setEndValue(QPointF(500, 400)) anim.setEasingCurve(QEasingCurve.Type.InOutQuad) anim.start()
五、高級(jí)功能
碰撞檢測(cè)
# 檢測(cè)矩形與其他項(xiàng)的碰撞
colliding_items = rect.collidingItems()
for item in colliding_items:
item.setBrush(Qt.GlobalColor.yellow) # 高亮碰撞項(xiàng)組合項(xiàng)(QGraphicsItemGroup)
group = QGraphicsItemGroup() group.addToGroup(rect) group.addToGroup(text) group.setRotation(45) # 整體旋轉(zhuǎn) 45 度 scene.addItem(group)
場(chǎng)景事件處理
class CustomScene(QGraphicsScene):
def mousePressEvent(self, event):
if event.button() == Qt.MouseButton.LeftButton:
print(f"Scene 點(diǎn)擊位置:{event.scenePos()}")
super().mousePressEvent(event)六、注意事項(xiàng)
性能優(yōu)化
- 避免在場(chǎng)景中放置過多項(xiàng)(超過數(shù)千個(gè))。
- 使用
QGraphicsItem.ItemClipsToShape或setCacheMode優(yōu)化渲染。
坐標(biāo)轉(zhuǎn)換
使用 mapToScene() 和 mapFromScene() 在視圖、場(chǎng)景、項(xiàng)之間轉(zhuǎn)換坐標(biāo)。
# 將視圖坐標(biāo) (100, 200) 轉(zhuǎn)換為場(chǎng)景坐標(biāo) scene_pos = view.mapToScene(100, 200)
內(nèi)存管理
刪除圖形項(xiàng)時(shí)需調(diào)用 removeItem(),避免內(nèi)存泄漏。
scene.removeItem(rect) del rect # 顯式刪除對(duì)象
七、綜合案例:簡(jiǎn)易繪圖工具
class DrawingScene(QGraphicsScene):
def __init__(self):
super().__init__()
self.current_item = None
def mousePressEvent(self, event):
if event.button() == Qt.MouseButton.LeftButton:
self.current_item = QGraphicsEllipseItem()
self.current_item.setRect(event.scenePos().x(),
event.scenePos().y(),
0, 0)
self.addItem(self.current_item)
def mouseMoveEvent(self, event):
if self.current_item:
start_pos = event.buttonDownScenePos(Qt.MouseButton.LeftButton)
current_pos = event.scenePos()
self.current_item.setRect(
start_pos.x(), start_pos.y(),
current_pos.x() - start_pos.x(),
current_pos.y() - start_pos.y()
)
def mouseReleaseEvent(self, event):
self.current_item = None
# 使用示例
app = QApplication([])
scene = DrawingScene()
view = QGraphicsView(scene)
view.show()
app.exec()八、總結(jié)
QGraphicsView 和 QGraphicsScene 為復(fù)雜圖形應(yīng)用提供了強(qiáng)大支持,通過組合圖形項(xiàng)、處理事件和優(yōu)化渲染,可實(shí)現(xiàn)高度定制化的交互式界面。開發(fā)時(shí)需重點(diǎn)關(guān)注坐標(biāo)系統(tǒng)、性能管理和用戶交互邏輯。
到此這篇關(guān)于PyQt6/PySide6 的 QPropertyAnimation 類適用場(chǎng)景分析的文章就介紹到這了,更多相關(guān)PyQt6 QPropertyAnimation 類內(nèi)容請(qǐng)搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
使用Matplotlib 繪制精美的數(shù)學(xué)圖形例子
今天小編就為大家分享一篇使用Matplotlib 繪制精美的數(shù)學(xué)圖形例子,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過來看看吧2019-12-12
基于Python的網(wǎng)頁(yè)自動(dòng)化工具DrissionPage的使用詳解
DrissionPage 是一個(gè)基于 python 的網(wǎng)頁(yè)自動(dòng)化工具,它既能控制瀏覽器,也能收發(fā)數(shù)據(jù)包,還能把兩者合而為一,下面就跟隨小編一起來學(xué)習(xí)一下它的具體使用吧2024-01-01
使用Django和Ansible實(shí)現(xiàn)自動(dòng)化部署方式
這篇文章主要介紹了使用Django和Ansible實(shí)現(xiàn)自動(dòng)化部署方式,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2025-05-05
Python雙向循環(huán)鏈表實(shí)現(xiàn)方法分析
這篇文章主要介紹了Python雙向循環(huán)鏈表,結(jié)合實(shí)例形式分析了Python雙向鏈表的定義、遍歷、添加、刪除、搜索等相關(guān)操作技巧,需要的朋友可以參考下2018-07-07
Python實(shí)現(xiàn)的數(shù)據(jù)結(jié)構(gòu)與算法之快速排序詳解
這篇文章主要介紹了Python實(shí)現(xiàn)的數(shù)據(jù)結(jié)構(gòu)與算法之快速排序,詳細(xì)分析了快速排序的原理與Python實(shí)現(xiàn)技巧,需要的朋友可以參考下2015-04-04
Python 中創(chuàng)建 PostgreSQL 數(shù)據(jù)庫(kù)連接池
這篇文章主要介紹了Python 中創(chuàng)建 PostgreSQL 數(shù)據(jù)庫(kù)連接池,Python 連接 PostgreSQL 是主要有兩個(gè)包, py-postgresql 和 psycopg2 , 而本文的實(shí)例將使用后者,感興趣的小伙伴可以參考一下2021-10-10
Python實(shí)現(xiàn)將單張或多張圖片轉(zhuǎn)PDF
這篇文章主要為大家詳細(xì)介紹了如何使用Python實(shí)現(xiàn)將單張或多張圖片轉(zhuǎn)PDF,文中的示例代碼講解詳細(xì),感興趣的小伙伴可以跟隨小編一起學(xué)習(xí)一下2025-11-11

