利用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脚本将Bing的每日图片作为桌面的教程
May 04 Python
python3实现ftp服务功能(服务端 For Linux)
Mar 24 Python
Python实现将16进制字符串转化为ascii字符的方法分析
Jul 21 Python
将字典转换为DataFrame并进行频次统计的方法
Apr 08 Python
详解django自定义中间件处理
Nov 21 Python
Python实现将HTML转成PDF的方法分析
May 04 Python
python写日志文件操作类与应用示例
Jul 01 Python
python实现爬取百度图片的方法示例
Jul 06 Python
Keras预训练的ImageNet模型实现分类操作
Jul 07 Python
Python2.6版本pip安装步骤解析
Aug 17 Python
详解pycharm配置python解释器的问题
Oct 15 Python
pandas将list数据拆分成行或列的实现
Dec 13 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
jQuery Mobile + PHP实现文件上传
2014/12/12 PHP
smarty模板引擎中内建函数if、elseif和else的使用方法
2015/01/22 PHP
浅谈php中的循环while、do...while、for、foreach四种循环
2016/11/05 PHP
php策略模式简单示例分析【区别于工厂模式】
2019/09/25 PHP
善用事件代理,警惕闭包的性能陷阱。
2011/01/20 Javascript
jquery+css3打造一款ajax分页插件(自写)
2014/06/18 Javascript
JavaScript 基本概念
2015/01/20 Javascript
JS+DIV+CSS实现仿表单下拉列表效果
2015/08/18 Javascript
JS+CSS实现简易实用的滑动门菜单效果
2015/09/18 Javascript
Clipboard.js 无需Flash的JavaScript复制粘贴库
2015/10/02 Javascript
JS中多步骤多分步的StepJump组件实例详解
2016/04/01 Javascript
jQuery实现的鼠标经过时变宽的效果(附demo源码)
2016/04/28 Javascript
完美解决axios跨域请求出错的问题
2018/02/05 Javascript
Node.js 使用jade模板引擎的示例
2018/05/11 Javascript
vue+iview 实现可编辑表格的示例代码
2018/10/31 Javascript
python zip文件 压缩
2008/12/24 Python
python中遍历文件的3个方法
2014/09/02 Python
Python工程师面试题 与Python基础语法相关
2016/01/14 Python
python爬虫爬取淘宝商品信息
2018/02/23 Python
python logging日志模块以及多进程日志详解
2018/04/18 Python
python3模块smtplib实现发送邮件功能
2018/05/22 Python
python判断自身是否正在运行的方法
2019/08/08 Python
Python 闭包,函数分隔作用域,nonlocal声明非局部变量操作示例
2019/10/14 Python
浅谈django 模型类使用save()方法的好处与注意事项
2020/03/28 Python
Python抖音快手代码舞(字符舞)的实现方法
2021/02/07 Python
CSS3中的transform属性进行2D和3D变换的基本用法
2016/05/12 HTML / CSS
苹果中国官方网站:Apple中国
2016/07/22 全球购物
百丽国际旗下购物网站:优购
2017/02/28 全球购物
药店主任岗位责任制
2014/02/10 职场文书
一年级小学生评语
2014/04/22 职场文书
化工实习心得体会
2014/09/09 职场文书
卫生主题班会
2015/08/14 职场文书
小学数学国培研修日志
2015/11/13 职场文书
golang 在windows中设置环境变量的操作
2021/04/29 Golang
详解vue中v-for的key唯一性
2021/05/15 Vue.js
Linux系统下安装PHP7.3版本
2021/06/26 PHP