利用matplotlib为图片上添加触发事件进行交互


Posted in Python onApril 23, 2020

这篇文章的目的出于实验的需要,我需要对图片上的部分区域做出涂抹标记,本来是选择用opencv做交互的,但在需要进行图像的输出以及鼠标时间添加时,opencv出现错误。

解决方案网上有很多,尝试以后依然bug,这里先做一个记录,有时间再来处理。

错误报告如下:

OpenCV Error: Unspecified error (The function is not implemented. Rebuild the library with Windows, GTK+ 2.x or Carbon support. If you are on Ubuntu or Debian, install libgtk2.0-dev and pkg-config, then re-run cmake or configure script) in cvShowImage, file -------src-dir-------/opencv-2.4.10/modules/highgui/src/window.cpp, line 501
Traceback (most recent call last):
File "test.py", line 20, in <module>
cv2.imshow('img',img)
cv2.error: -------src-dir-------/opencv-2.4.10/modules/highgui/src/window.cpp:501: error: (-2) The function is not implemented. Rebuild the library with Windows, GTK+ 2.x or Carbon support. If you are on Ubuntu or Debian, install libgtk2.0-dev and pkg-config, then re-run cmake or configure script in function cvShowImage

这里我们切换另一种解决方案,利用python的matplotlib库完成图像的输出以及鼠标事件的添加。

点击图片,在图像中鼠标对应位置画点:

# coding=utf-8
from matplotlib import pyplot as plt
import cv2

def on_press(event):
 if event.inaxes == None:
  print "none"
  return 
 #在鼠标的当前位置绘制一个点
 ax.scatter(event.xdata, event.ydata)
 #更新画板
 fig.canvas.draw()

if __name__ == "__main__":
 fileN = r'./0107_1.3.6.1.4.1.14519.5.2.1.6279.6001.263660956768649083933159084365.bmp'
 img = cv2.imread(fileN)
 cv2.imshow('img',img)
 fig = py.figure()
 fig.canvas.mpl_connect("button_press_event", on_press) 
 ax = fig.add_subplot(121)
 ax1 = fig.add_subplot(122)
 ax.imshow(img)
 ax1.imshow(img)
 plt.axis("off")
 plt.show()

先来简单解释一下代码的含义:

fig.canvas.mpl_connect("button_press_event", on_press)#在这个figure上加点击事件,点击后的情况在自己写的on_press()方法里 
def on_press(event): 
  event.inaxes.figure.canvas.draw()#用于图片刷新 
  event.x#事件的坐标用于其他按钮点击和figure点击发生冲突时判断返回 
  event.xdata,event.ydata#鼠标点击的位置,与上面那个坐标表示形式不同

最后的输出结果入下图。我们得到了非常奇怪的结果,如果你自己亲自动手试的话体会应该会更有体会,两边的图像本来应该一样大,但在第一次绘制点的时候,左侧图像出现了闪动,然后尺寸的比例突然发生了变化。

利用matplotlib为图片上添加触发事件进行交互

是的,图像尺寸没有发生变化,但尺寸的比例的确变了,这里我们要做的就是关闭自动变化的尺度比例。

if __name__ == "__main__":
 fileN = r'./0107_1.3.6.1.4.1.14519.5.2.1.6279.6001.263660956768649083933159084365.bmp'
 img = cv2.imread(fileN)
 cv2.imshow('img',img)
 fig = py.figure()
 fig.canvas.mpl_connect("button_press_event", on_press) 
 ax = fig.add_subplot(121)
 ax1 = fig.add_subplot(122)
 ax.imshow(img)
 ax1.imshow(img)
 #关闭自动尺度适配
 ax.set_autoscale_on(False) 
 plt.axis("off")
 plt.show()

当然,我们可以改变绘制标记的样式:

ax.scatter(x,y,c='k',s=25,alpha=1.0,marker='o')
#T:散点的颜色
#s:散点的大小
#alpha:是透明程度

现在我们能够在图像上进行标记了,但这样还不够,程序需要获取这些标记点。

实际上fig.canvas.mpl_connect("button_press_event", on_press)能够进行自定义的多参数传递,如果在每次绘制的时候将数据保存在外部传入的列表中,那么当画板被销毁时,我们就能获取到原来所有的绘制点。

这里介绍两种使用方法:

def on_key(event, arg1, arg2, arg3):
 pass
canvas.mpl_connect('key_press_event', lambda event: on_key(event, plt1, plt2, plt3))

def on_key(event, args_list):
 pass
fig.canvas.mpl_connect('key_press_event', lambda event: on_key(event, [plt1, plt2, plt3]))

这里需要注意的是scatter绘制的点,实际上并没有大小的概念,这个点实质是一个坐标。

如果需要绘制有实际面积的圆形的标记,可以使用matplotlib.patches.Circle

具体的使用如下:

from matplotlib.patches import Circle

fig = plt.figure()
ax = fig.add_subplot(111)
cir = Circle(xy = (event.xdata, event.ydata),facecolor = 'black', edgecolor='black',radius=10, alpha=1.0) 
ax.add_patch(cir)

以上这篇利用matplotlib为图片上添加触发事件进行交互就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
Python使用稀疏矩阵节省内存实例
Jun 27 Python
Python爬虫包BeautifulSoup异常处理(二)
Jun 17 Python
解决python中遇到字典里key值为None的情况,取不出来的问题
Oct 17 Python
Python文件常见操作实例分析【读写、遍历】
Dec 10 Python
python贪吃蛇游戏代码
Apr 18 Python
详解Python3网络爬虫(二):利用urllib.urlopen向有道翻译发送数据获得翻译结果
May 07 Python
python操作excel让工作自动化
Aug 09 Python
python matplotlib库绘制条形图练习题
Aug 10 Python
wxpython绘制圆角窗体
Nov 18 Python
Python实现疫情通定时自动填写功能(附代码)
May 27 Python
Python3爬虫RedisDump的安装步骤
Feb 20 Python
pytorch分类模型绘制混淆矩阵以及可视化详解
Apr 07 Python
python中matplotlib实现随鼠标滑动自动标注代码
Apr 23 #Python
使用matplotlib动态刷新指定曲线实例
Apr 23 #Python
Flask模板引擎Jinja2使用实例
Apr 23 #Python
利用pandas向一个csv文件追加写入数据的实现示例
Apr 23 #Python
在matplotlib中改变figure的布局和大小实例
Apr 23 #Python
Python将二维列表list的数据输出(TXT,Excel)
Apr 23 #Python
Python基于DB-API操作MySQL数据库过程解析
Apr 23 #Python
You might like
强烈声明: 不要使用(include/require)_once
2013/06/06 PHP
PHP中session变量的销毁
2014/02/27 PHP
ThinkPHP内置jsonRPC的缺陷分析
2014/12/18 PHP
smarty内置函数config_load用法实例
2015/01/22 PHP
详解PHP函数 strip_tags 处理字符串缺陷bug
2017/06/11 PHP
js+css在交互上的应用
2010/07/18 Javascript
一些老手都不一定知道的JavaScript技巧
2014/05/06 Javascript
JavaScript的jQuery库中ready方法的学习教程
2015/08/14 Javascript
jQuery基于ajax()使用serialize()提交form数据的方法
2015/12/08 Javascript
JavaScript观察者模式(经典)
2015/12/09 Javascript
jQuery头像裁剪工具jcrop用法实例(附演示与demo源码下载)
2016/01/22 Javascript
JS中from 表单序列化提交的代码
2017/01/20 Javascript
jQuery实现弹幕效果
2017/02/17 Javascript
vue-router:嵌套路由的使用方法
2017/02/21 Javascript
Vue.js添加组件操作示例
2018/06/13 Javascript
webpack多入口多出口的实现方法
2018/08/17 Javascript
详解Angular6 热加载配置方案
2018/08/18 Javascript
使用validate.js实现表单数据提交前的验证方法
2018/09/04 Javascript
原生JS使用Canvas实现拖拽式绘图功能
2019/06/05 Javascript
基于vue写一个全局Message组件的实现
2019/08/15 Javascript
node实现简单的增删改查接口实例代码
2019/08/22 Javascript
用vue 实现手机触屏滑动功能
2020/05/28 Javascript
element el-table表格的二次封装实现(附表格高度自适应)
2021/01/19 Javascript
python 正则式 概述及常用字符
2009/05/07 Python
Python中除法使用的注意事项
2014/08/21 Python
举例讲解Python的Tornado框架实现数据可视化的教程
2015/05/02 Python
利用Python获取赶集网招聘信息前篇
2016/04/18 Python
使用Python获取并处理IP的类型及格式方法
2018/11/01 Python
selenium判断元素是否存在的两种方法小结
2020/12/07 Python
牵手50台湾:专为黄金岁月的单身人士而设的交友网站
2021/02/18 全球购物
商务专员岗位职责范本
2014/06/29 职场文书
五四青年节的活动方案
2014/08/20 职场文书
没有孩子的离婚协议书怎么写
2014/09/17 职场文书
停电调休通知
2015/04/16 职场文书
导游词之西递宏村
2019/12/10 职场文书
springboot集成flyway自动创表的详细配置
2021/06/26 Java/Android