python基于opencv 实现图像时钟


Posted in Python onJanuary 04, 2021

解决方案详解

python基于opencv 实现图像时钟

绘制表盘

表盘上只有60条分/秒刻线和12条小时刻线,当然还有表盘的外部轮廓圆,也就是重点在如何画72根线。先把简单的圆画出来:

import cv2 as cv
import math
import datetime
import numpy as np

margin = 5 # 上下左右边距
radius = 220 # 圆的半径
center = (center_x, center_y) = (225, 225) # 圆心

# 1. 新建一个画板并填充成白色
img = np.zeros((450, 450, 3), np.uint8)
img[:] = (255, 255, 255)

# 2. 画出圆盘
cv.circle(img, center, radius, (0, 0, 0), thickness=5)

我们使用OpenCV画直线的时候,需知道直线的起点和终点坐标,那么画72根线就变成了获取72组坐标。
平面坐标系下,已知半径和角度的话,A点的坐标可以表示为:
x=r×cosα
y=r×sinα

python基于opencv 实现图像时钟

先只考虑将坐标系原点移动到左上角,角度依然是平面坐标系中的逆时针计算,那么新坐标是:
x=r+r×cosα
y=r+r×sinα
对于60条分/秒刻线,刻线间的夹角是360°/60=6°,对于小时刻线,角度是360°/12=30°,这样就得到了72组起点坐标,那怎么得到终点坐标呢?其实同样的原理,用一个同心的小圆来计算得到B点:

python基于opencv 实现图像时钟

通过A/B两点就可以画出直线:

pt1 = []

# 3. 画出60条秒和分钟的刻线
for i in range(60):
  # 最外部圆,计算A点
  x1 = center_x+(radius-margin)*math.cos(i*6*np.pi/180.0)
  y1 = center_y+(radius-margin)*math.sin(i*6*np.pi/180.0)
  pt1.append((int(x1), int(y1)))

  # 同心小圆,计算B点
  x2 = center_x+(radius-15)*math.cos(i*6*np.pi/180.0)
  y2 = center_y+(radius-15)*math.sin(i*6*np.pi/180.0)

  cv.line(img, pt1[i], (int(x2), int(y2)), (0, 0, 0), thickness=2)

# 4. 画出12条小时的刻线
for i in range(12):
  # 12条小时刻线应该更长一点
  x = center_x+(radius-25)*math.cos(i*30*np.pi/180.0)
  y = center_y+(radius-25)*math.sin(i*30*np.pi/180.0)
  # 这里用到了前面的pt1
  cv.line(img, pt1[i*5], (int(x), int(y)), (0, 0, 0), thickness=5)


# 到这里基本的表盘图就已经画出来了

python基于opencv 实现图像时钟

角度换算

接下来算是一个小难点,首先时钟的起始坐标在正常二维坐标系的90°方向,其次时钟跟图像一样,都是顺时针计算角度的,所以三者需要统一下:

python基于opencv 实现图像时钟

因为角度是完全对称的,顺逆时针没有影响,所以平面坐标系完全不用理会,放在这里只是便于大家理解。对于时钟坐标和图像坐标,时钟0的0°对应图像的270°,时钟15的90°对应图像的360°,时钟30的180°对应图像的450°(360°+90°)…
所以两者之间的关系便是:
计算角度 = 时钟角度+270°
计算角度 = 计算角度 if 计算角度<=360° else 计算角度-360°

同步时间

Python中如何获取当前时间和添加日期文字都比较简单,看代码就行,我就不解释了。

while(1):
  # 不断拷贝表盘图,才能更新绘制,不然会重叠在一起
  temp = np.copy(img)

  # 5. 获取系统时间,画出动态的时-分-秒三条刻线
  now_time = datetime.datetime.now()
  hour, minute, second = now_time.hour, now_time.minute, now_time.second

  # 画秒刻线
  # 参见博客,OpenCV中的角度是顺时针计算的,所以需要转换下
  sec_angle = second*6+270 if second <= 15 else (second-15)*6
  sec_x = center_x+(radius-margin)*math.cos(sec_angle*np.pi/180.0)
  sec_y = center_y+(radius-margin)*math.sin(sec_angle*np.pi/180.0)
  cv.line(temp, center, (int(sec_x), int(sec_y)), (255, 0, 0), 2)

  # 画分刻线
  min_angle = minute*6+270 if minute <= 15 else (minute-15)*6
  min_x = center_x+(radius-35)*math.cos(min_angle*np.pi/180.0)
  min_y = center_y+(radius-35)*math.sin(min_angle*np.pi/180.0)
  cv.line(temp, center, (int(min_x), int(min_y)), (0, 255, 0), 8)

  # 画时刻线
  hour_angle = hour*30+270 if hour <= 3 else (hour-3)*30
  hour_x = center_x+(radius-75)*math.cos(hour_angle*np.pi/180.0)
  hour_y = center_y+(radius-75)*math.sin(hour_angle*np.pi/180.0)
  cv.line(temp, center, (int(hour_x), int(hour_y)), (0, 0, 255), 20)

  # 6. 添加当前日期文字
  font = cv.FONT_HERSHEY_SIMPLEX
  time_str = now_time.strftime("%d/%m/%Y")
  cv.putText(img, time_str, (135, 275), font, 1, (0, 0, 0), 2)

  cv.imshow('clocking', temp)
  if cv.waitKey(1) == 27: # 按下ESC键退出
    break

python基于opencv 实现图像时钟

以上就是python基于opencv 实现图像时钟的详细内容,更多关于python opencv 实现图像时钟的资料请关注三水点靠木其它相关文章!

Python 相关文章推荐
在python中的socket模块使用代理实例
May 29 Python
python装饰器实例大详解
Oct 25 Python
Python WEB应用部署的实现方法
Jan 02 Python
Python设计模式之适配器模式原理与用法详解
Jan 15 Python
python创造虚拟环境方法总结
Mar 04 Python
详解利用Python scipy.signal.filtfilt() 实现信号滤波
Jun 05 Python
Python Numpy 控制台完全输出ndarray的实现
Feb 19 Python
python 批量下载bilibili视频的gui程序
Nov 20 Python
详解Python函数print用法
Jun 18 Python
一文搞懂Python Sklearn库使用
Aug 23 Python
Python使用mitmproxy工具监控手机 下载手机小视频
Apr 18 Python
利用Python实现模拟登录知乎
May 25 Python
python基于opencv实现人脸识别
Jan 04 #Python
利用python绘制正态分布曲线
Jan 04 #Python
Python 打印自己设计的字体的实例讲解
Jan 04 #Python
Python关于拓扑排序知识点讲解
Jan 04 #Python
Python经典五人分鱼实例讲解
Jan 04 #Python
Python约瑟夫生者死者小游戏实例讲解
Jan 04 #Python
python邮件中附加文字、html、图片、附件实现方法
Jan 04 #Python
You might like
非洲第一个咖啡超凡杯大赛承办国—卢旺达的咖啡怎么样
2021/03/03 咖啡文化
新浪新闻小偷
2006/10/09 PHP
dedecms 制作模板中使用的全局标记图文教程
2007/03/11 PHP
PHPEXCEL 使用小记
2013/01/06 PHP
ThinkPHP提交表单时默认自动转义的解决方法
2014/11/25 PHP
php通过Chianz.com获取IP地址与地区的方法
2015/01/14 PHP
IE中createElement需要注意的一个问题
2010/07/13 Javascript
浅谈Javascript鼠标和滚轮事件
2012/06/27 Javascript
Js 代码中,ajax请求地址后加随机数防止浏览器缓存的原因
2013/05/07 Javascript
jquery事件与函数的使用介绍
2013/09/29 Javascript
写JQuery插件的基本知识
2013/11/25 Javascript
textarea 控制输入字符字节数(示例代码)
2013/12/27 Javascript
JavaScript获取当前页面上的指定对象示例代码
2014/02/28 Javascript
JS模拟键盘打字效果的方法
2015/08/05 Javascript
每天一篇javascript学习小结(RegExp对象)
2015/11/17 Javascript
javaScript事件学习小结(四)event的公共成员(属性和方法)
2016/06/09 Javascript
jQuery实现select模糊查询(反射机制)
2017/01/14 Javascript
jQuery中animate()的使用方法及解决$(”body“).animate({“scrollTop”:top})不被Firefox支持的问题
2017/04/04 jQuery
深入理解Angular.JS中的Scope继承
2017/06/04 Javascript
微信小程序url与token设置详解
2017/09/26 Javascript
Vue.js分页组件实现:diVuePagination的使用详解
2018/01/10 Javascript
angular2中Http请求原理与用法详解
2018/01/11 Javascript
layer.open的自适应及居中及子页面标题的修改方法
2019/09/05 Javascript
JavaScript自定义超时API代码实例
2020/04/30 Javascript
vue 自定指令生成uuid滚动监听达到tab表格吸顶效果的代码
2020/09/16 Javascript
[01:19:23]2018DOTA2亚洲邀请赛 4.5 淘汰赛 Mineski vs VG 第二场
2018/04/06 DOTA
简单谈谈Python中函数的可变参数
2016/09/02 Python
python opencv设置摄像头分辨率以及各个参数的方法
2018/04/02 Python
使用NumPy和pandas对CSV文件进行写操作的实例
2018/06/14 Python
Python发送邮件测试报告操作实例详解
2018/12/08 Python
在Python中os.fork()产生子进程的例子
2019/08/08 Python
工程师必须了解的LRU缓存淘汰算法以及python实现过程
2020/10/15 Python
瑞典灯具和照明网上商店:Lamp24.se
2018/03/17 全球购物
Omio葡萄牙:全欧洲低价大巴、火车和航班搜索和比价
2019/02/09 全球购物
2014年学校国庆主题活动方案
2014/09/16 职场文书
python对文档中元素删除,替换操作
2022/04/02 Python