这一篇来讲解自定义控件的移动轨迹

原理:我们采用QPainterPath先画一个弧线,然后加载一个物体让物体移动,设置100个关键帧,每个关键帧物体的坐标位置就是弧线的坐标位置,这样就能达到按照指定轨迹移动

首先,我们重写QLabel,加载一个小黑球到QLabel上

class Ball(QLabel):
def __init__(self, parent):
super(Ball, self).__init__(parent) self.pix = QPixmap("../ball.png") # 加载一个ball的图片
self.h = self.pix.height() # ball的高度
self.w = self.pix.width() # ball的宽度 self.setPixmap(self.pix) # 把ball加载到label上 def _set_pos(self, pos):
self.move(pos.x() - self.w / 2, pos.y() - self.h / 2) pos = pyqtProperty(QPointF, fset=_set_pos)

然后我们用QPainterPath来画弧线,先设置弧线:

    def initView(self):
self.path = QPainterPath()
self.path.moveTo(30, 30)
self.path.cubicTo(30, 30, 200, 350, 350, 30) # 设置弧线的样子

再通过paintEvent绘制弧线:

    def paintEvent(self, e):
qp = QPainter()
qp.begin(self)
qp.setRenderHint(QPainter.Antialiasing)
qp.drawPath(self.path) # 画弧线
qp.end()

最后组合起来就行了,剩下的不难,下面是完整代码:

#!/usr/bin/python3
# -*- coding: utf-8 -*- """
PyQt5 Animation tutorial This program will show along curve with QPropertyAnimation. Author: Semishigure 401219180@qq.com
Last edited: 2018.03.02
""" from PyQt5.QtWidgets import *
from PyQt5.QtGui import *
from PyQt5.QtCore import *
import sys class Ball(QLabel):
def __init__(self, parent):
super(Ball, self).__init__(parent) self.pix = QPixmap("../ball.png") # 加载一个ball的图片
self.h = self.pix.height() # ball的高度
self.w = self.pix.width() # ball的宽度 self.setPixmap(self.pix) # 把ball加载到label上 def _set_pos(self, pos):
self.move(pos.x() - self.w / 2, pos.y() - self.h / 2) pos = pyqtProperty(QPointF, fset=_set_pos) class Example(QWidget):
def __init__(self):
super(Example, self).__init__()
self.initView()
self.initAnimation() def initView(self):
self.path = QPainterPath()
self.path.moveTo(30, 30)
self.path.cubicTo(30, 30, 200, 350, 350, 30) # 设置弧线的样子 self.ball = Ball(self)
self.ball.pos = QPointF(30, 30) # 设置ball起点位置,这里就是弧线的起点位置 self.setWindowTitle("Animation along curve")
self.setGeometry(300, 300, 400, 300)
self.show() def paintEvent(self, e):
qp = QPainter()
qp.begin(self)
qp.setRenderHint(QPainter.Antialiasing)
qp.drawPath(self.path) # 画弧线
qp.end() def initAnimation(self):
self.anim = QPropertyAnimation(self.ball, b'pos')
self.anim.setDuration(3000)
self.anim.setStartValue(QPointF(30, 30)) vals = [p / 100 for p in range(0, 101)] for i in vals:
self.anim.setKeyValueAt(i, self.path.pointAtPercent(i)) # 设置100个关键帧 self.anim.setEndValue(QPointF(350, 30))
self.anim.start() if __name__ == '__main__':
app = QApplication(sys.argv)
ex = Example()
sys.exit(app.exec_())

界面预览效果:

备注:

1、关键帧的范围值为0-1,我们在其中创建100个点,即[0.01, 0.02, 0.03, 0.04...0.98, 0.99, 1.00],这里直接使用for循环 vals = [p / 100 for p in range(0, 101)]

2、通过i传递百分比到self.path.pointAtPercent()就可以拿到弧线的对应坐标QPoinF,所以关键帧就可以设置成self.anim.setKeyValueAt(i, self.path.pointAtPercent(i))

pyqt5 动画学习(三) 指定控件的移动轨迹的更多相关文章

  1. asp.net学习之 数据绑定控件--List数据绑定控件

    原文:asp.net学习之 数据绑定控件--List数据绑定控件 List控件(如 CheckBoxList.DropDownList.ListBox 和 RadioButtonList 类)继承自L ...

  2. asp.net学习之数据绑定控件、数据源控件概述

    原文:asp.net学习之数据绑定控件.数据源控件概述 1.asp.net数据绑定控件分为三大类,每个类分别进行详细:      ● 列表式数据绑定控件: 列表式数据绑定控件常用来在一个表格内的一个字 ...

  3. Python:GUI之tkinter学习笔记1控件的介绍及使用

    相关内容: tkinter的使用 1.模块的导入 2.使用 3.控件介绍 Tk Button Label Frame Toplevel Menu Menubutton Canvas Entry Mes ...

  4. WPF 动画:同为控件不同命 - 简书

    原文:WPF 动画:同为控件不同命 - 简书 1. 及格与优秀 读大学的时候,有一门课的作业是用 PPT 展示. 但是我们很多同学都把 PPT 当做 Word 来用,就单纯地往里面堆文字. 大家都单纯 ...

  5. iOS学习之UIPickerView控件的关联选择

    接上篇iOS学习之UIPickerView控件的简单使用 接着上篇的代码 http://download.csdn.net/detail/totogo2010/4391870 ,我们要实现的效果如下: ...

  6. Swift学习之熟悉控件

    最近是比较清闲一些的,对于一个开发者来说,这也是一个很好的充电机会.以前做项目都是使用Objective-C去开发,但我们都知道,Swift语言从2014年的出现到现在,一步一步变的完善,渐渐变的受欢 ...

  7. WinForm 批量设置指定控件中的控件状态

    在开发中常遇到当点击某个按钮的时候,禁用文本框或按钮的的状态,以防止误操作,下面的代码是我已批量设置指定控件中的按钮状态的代码,同理可以延伸出很多操作. /// <summary> /// ...

  8. asp.net学习之Repeater控件

    asp.net学习之Repeater控件 文章摘自:http://www.cnblogs.com/shipfi/archive/2009/10/19/1585703.html Repeater控件和D ...

  9. asp.net学习之DataList控件

    asp.net学习之DataList控件   DataList控件与Repeater控件一样由模板驱动,与Repeater控件不同的是: DataList控件默认输出是一个HTML表格.DataLis ...

随机推荐

  1. 解决设置clickablespan后长按冲突的问题

    解决设置ClickableSpan后长按冲突的问题 问题描述 3月份修改别人代码的时候想要屏蔽TextView的长按事件,发现TextView有重写OnTouchEvent方法,然后在其中加了长按事件 ...

  2. 原生js封装添加class,删除class

    一.添加class function addClass(ele,cName) { var arr = ele.className.split(' ').concat(cName.split(" ...

  3. win10下NeuralStyle的tensorflow版实验

    ---恢复内容开始--- 首先配置win10下的tensorflow-gpu的运行环境,然后在github上将NeuralStyle拷贝下来,最后根据文档说明参数,运行文件,即可得到自己喜欢的styl ...

  4. 201621123040《Java程序设计》第九周学习总结

    1.本周学习总结 1.1 以你喜欢的方式(思维导图或其他)归纳总结集合与泛型相关内容 泛型部分思维导图 集合部分学习总结 java.util.Collection 是一个集合接口;java.util. ...

  5. 个人作业2:QQ音乐APP案例分析

    APP案例分析 QQ音乐 选择理由:毕竟作为QQ音乐九年的资深老用户以及音乐爱好者 第一部分 调研 1.第一次上手的体验    我算是很早期的QQ音乐的用户,用QQ音乐七八年,除了体验各方面还不错之外 ...

  6. 201621123025《Java程序设计》第1周学习总结

    201621123025<Jave程序设计>第一周学习总结 1.本章学习总结 对于java这门课程,如果不会编码那么会很难学会如何去使用它,而在大一的一二学期的专业课--C语言和数据结构我 ...

  7. 第二周c语言PTA作业留

    6-1 计算两数的和与差(10 分) 本题要求实现一个计算输入的两数的和与差的简单函数. 函数接口定义: void sum_diff( float op1, float op2, float psum ...

  8. jwt验证登录信息

    为什么要告别session?有这样一个场景,系统的数据量达到千万级,需要几台服务器部署,当一个用户在其中一台服务器登录后,用session保存其登录信息,其他服务器怎么知道该用户登录了?(单点登录), ...

  9. JAVA_SE基础——15.循环嵌套

    嵌套循环是指在一个循环语句的循环体中再定义一个循环语句结构,while,do-while,for循环语句都可以进行嵌套,并且可以互相嵌套,下面来看下for循环中嵌套for循环的例子. 如下: publ ...

  10. SpringMVC之数据传递一

    之前的博客中也说了,mvc中数据传递是最主要的一部分,从url到Controller.从view到Controller.Controller到view以及Controller之间的数据传递.今天主要学 ...