利用PyQt5模擬實(shí)現(xiàn)網(wǎng)頁(yè)鼠標(biāo)移動(dòng)特效
核心代碼:
from random import random
from time import time
from PyQt5.QtCore import QPropertyAnimation, QObject, pyqtProperty, QEasingCurve,\
Qt, QRectF, pyqtSignal
from PyQt5.QtGui import QColor, QPainterPath, QPainter
from PyQt5.QtWidgets import QWidget
__Author__ = """By: Irony
QQ: 892768447
Email: 892768447@qq.com"""
__Copyright__ = 'Copyright (c) 2018 Irony'
__Version__ = 1.0
try:
import pointtool # @UnusedImport @UnresolvedImport
getDistance = pointtool.getDistance
findClose = pointtool.findClose
except:
import math
def getDistance(p1, p2):
return math.pow(p1.x - p2.x, 2) + math.pow(p1.y - p2.y, 2)
def findClose(points):
plen = len(points)
for i in range(plen):
closest = [None, None, None, None, None]
p1 = points[i]
for j in range(plen):
p2 = points[j]
dte1 = getDistance(p1, p2)
if p1 != p2:
placed = False
for k in range(5):
if not placed:
if not closest[k]:
closest[k] = p2
placed = True
for k in range(5):
if not placed:
if dte1 < getDistance(p1, closest[k]):
closest[k] = p2
placed = True
p1.closest = closest
class Target:
def __init__(self, x, y):
self.x = x
self.y = y
class Point(QObject):
valueChanged = pyqtSignal()
def __init__(self, x, ox, y, oy, *args, **kwargs):
super(Point, self).__init__(*args, **kwargs)
self.__x = x
self._x = x
self.originX = ox
self._y = y
self.__y = y
self.originY = oy
# 5個(gè)閉合點(diǎn)
self.closest = [0, 0, 0, 0, 0]
# 圓半徑
self.radius = 2 + random() * 2
# 連線顏色
self.lineColor = QColor(156, 217, 249)
# 圓顏色
self.circleColor = QColor(156, 217, 249)
def initAnimation(self):
# 屬性動(dòng)畫
if not hasattr(self, 'xanimation'):
self.xanimation = QPropertyAnimation(
self, b'x', self, valueChanged=self.valueChanged.emit,
easingCurve=QEasingCurve.InOutSine)
self.yanimation = QPropertyAnimation(
self, b'y', self, valueChanged=self.valueChanged.emit,
easingCurve=QEasingCurve.InOutSine,
finished=self.updateAnimation)
self.updateAnimation()
def updateAnimation(self):
self.xanimation.stop()
self.yanimation.stop()
duration = (1 + random()) * 1000
self.xanimation.setDuration(duration)
self.yanimation.setDuration(duration)
self.xanimation.setStartValue(self.__x)
self.xanimation.setEndValue(self.originX - 50 + random() * 100)
self.yanimation.setStartValue(self.__y)
self.yanimation.setEndValue(self.originY - 50 + random() * 100)
self.xanimation.start()
self.yanimation.start()
@pyqtProperty(float)
def x(self):
return self._x
@x.setter
def x(self, x):
self._x = x
@pyqtProperty(float)
def y(self):
return self._y
@y.setter
def y(self, y):
self._y = y
class Window(QWidget):
def __init__(self, *args, **kwargs):
super(Window, self).__init__(*args, **kwargs)
self.setMouseTracking(True)
self.resize(800, 600)
self.points = []
self.target = Target(self.width() / 2, self.height() / 2)
self.initPoints()
def paintEvent(self, event):
super(Window, self).paintEvent(event)
painter = QPainter()
painter.begin(self)
painter.setRenderHint(QPainter.Antialiasing)
painter.fillRect(self.rect(), Qt.black)
self.animate(painter)
painter.end()
def mouseMoveEvent(self, event):
super(Window, self).mouseMoveEvent(event)
# 鼠標(biāo)移動(dòng)時(shí)更新xy坐標(biāo)
self.target.x = event.x()
self.target.y = event.y()
self.update()
def initPoints(self):
t = time()
self.points.clear()
# 創(chuàng)建點(diǎn)
stepX = self.width() / 20
stepY = self.height() / 20
for x in range(0, self.width(), int(stepX)):
for y in range(0, self.height(), int(stepY)):
ox = x + random() * stepX
oy = y + random() * stepY
point = Point(ox, ox, oy, oy)
point.valueChanged.connect(self.update)
self.points.append(point)
print(time() - t)
t = time()
# 每個(gè)點(diǎn)尋找5個(gè)閉合點(diǎn)
findClose(self.points)
print(time() - t)
def animate(self, painter):
for p in self.points:
# 檢測(cè)點(diǎn)的范圍
value = abs(getDistance(self.target, p))
if value < 4000:
# 其實(shí)就是修改顏色透明度
p.lineColor.setAlphaF(0.3)
p.circleColor.setAlphaF(0.6)
elif value < 20000:
p.lineColor.setAlphaF(0.1)
p.circleColor.setAlphaF(0.3)
elif value < 40000:
p.lineColor.setAlphaF(0.02)
p.circleColor.setAlphaF(0.1)
else:
p.lineColor.setAlphaF(0)
p.circleColor.setAlphaF(0)
# 畫線條
if p.lineColor.alpha():
for pc in p.closest:
if not pc:
continue
path = QPainterPath()
path.moveTo(p.x, p.y)
path.lineTo(pc.x, pc.y)
painter.save()
painter.setPen(p.lineColor)
painter.drawPath(path)
painter.restore()
# 畫圓
painter.save()
painter.setPen(Qt.NoPen)
painter.setBrush(p.circleColor)
painter.drawRoundedRect(QRectF(
p.x - p.radius, p.y - p.radius, 2 * p.radius, 2 * p.radius), p.radius, p.radius)
painter.restore()
# 開(kāi)啟動(dòng)畫
p.initAnimation()
if __name__ == '__main__':
import sys
import cgitb
sys.excepthook = cgitb.enable(1, None, 5, '')
from PyQt5.QtWidgets import QApplication
app = QApplication(sys.argv)
w = Window()
w.show()
sys.exit(app.exec_())運(yùn)行結(jié)果如下:

以上就是利用PyQt5模擬實(shí)現(xiàn)網(wǎng)頁(yè)鼠標(biāo)移動(dòng)特效的詳細(xì)內(nèi)容,更多關(guān)于PyQt5鼠標(biāo)特效的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
使用python將時(shí)間轉(zhuǎn)換為指定的格式方法
今天小編就為大家分享一篇使用python將時(shí)間轉(zhuǎn)換為指定的格式方法,具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2018-11-11
Django模板中變量的運(yùn)算實(shí)現(xiàn)
這篇文章主要介紹了Django模板中變量的運(yùn)算,文中通過(guò)示例代碼介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價(jià)值,需要的朋友們下面隨著小編來(lái)一起學(xué)習(xí)學(xué)習(xí)吧2021-04-04
Python常見(jiàn)數(shù)據(jù)類型轉(zhuǎn)換操作示例
這篇文章主要介紹了Python常見(jiàn)數(shù)據(jù)類型轉(zhuǎn)換操作,結(jié)合實(shí)例形式分析了Python針對(duì)列表、集合、元組、字典等數(shù)據(jù)類型轉(zhuǎn)換的相關(guān)操作技巧,需要的朋友可以參考下2019-05-05
Python實(shí)現(xiàn)爬取騰訊招聘網(wǎng)崗位信息
這篇文章主要介紹了如何用python爬取騰訊招聘網(wǎng)崗位信息保存到表格,并做成簡(jiǎn)單可視化。文中的示例代碼對(duì)學(xué)習(xí)Python有一定的幫助,感興趣的可以了解一下2022-01-01
如何使用pandas讀取txt文件中指定的列(有無(wú)標(biāo)題)
這篇文章主要介紹了如何使用pandas讀取txt文件中指定的列(有無(wú)標(biāo)題),具有很好的參考價(jià)值,希望對(duì)大家有所幫助。一起跟隨小編過(guò)來(lái)看看吧2020-03-03
Django中更改默認(rèn)數(shù)據(jù)庫(kù)為mysql的方法示例
這篇文章主要介紹了Django中更改默認(rèn)數(shù)據(jù)庫(kù)為mysql的方法示例,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2018-12-12
OpenAI的Whisper模型進(jìn)行語(yǔ)音識(shí)別使用詳解
這篇文章主要介紹了OpenAI的Whisper模型進(jìn)行語(yǔ)音識(shí)別使用詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進(jìn)步,早日升職加薪2023-02-02

