python【matplotlib】鼠标拖动滚动缩放坐标范围和拖动图例共存

背景

根据前面的博文: python【matplotlib】画图鼠标缩放拖动动态改变坐标轴范围
和Python【Matplotlib】图例可拖动改变位置
两个博文,博主考虑了一下,如何将两者的功能结合起来,让二者共存。
只需根据Python【Matplotlib】鼠标单击事件判断点击的是否为图例
博文所说的,判断鼠标的单击坐标是否在图例所在的区域内,然后进行区分即可

效果

在这里插入图片描述

单独鼠标缩放拖动动态改变坐标轴范围-效果

在这里插入图片描述

单独拖动图例效果

在这里插入图片描述

直接把二者结合起来,会因为Axis占用鼠标事件,而导致拖动图例失效,
进行一些坐标判断,判断鼠标的单击坐标是否在图例所在的区域内,然后进行区分即可完美实现。

if axtemp.get_legend():legend_bbox = axtemp.get_legend().get_window_extent()left_bottom = legend_bbox.get_points()[0]right_top = legend_bbox.get_points()[1]if left_bottom[0] <= mouse_x <= right_top[0] and left_bottom[1] <= mouse_y <= right_top[1]:# print("在图例上按下鼠标")# 在图例上按下鼠标mPress = False

直接上代码:

import matplotlib.pyplot as plt
from matplotlib.ticker import AutoLocator, MultipleLocator, MaxNLocatorplt.rcParams["font.family"] = "Microsoft YaHei"# 创建一个示例图形
fig, ax = plt.subplots()
ax.plot([1, 2, 3, ], [2, 4, 6, ], label=f'位移', ls='-')# 使用AutoLocator自动选择刻度位置
# ax.xaxis.set_major_locator(AutoLocator())
ax.yaxis.set_major_locator(AutoLocator())
# 使用MultipleLocator设置x轴刻度间隔为100
# ax.xaxis.set_major_locator(MultipleLocator(200))
# ax.yaxis.set_major_locator(MultipleLocator(100))
# 使用MaxNLocator设置x轴刻度最多显示5个
ax.xaxis.set_major_locator(MaxNLocator(10))ax.set_xlabel('时间(s)', color='black')
ax.set_ylabel('位移(m)', color='black')ax.legend(loc='lower right',    #  设置图例位置labelspacing=0,   #   设置图例间距handlelength=2,   #    设置图例中线的长度ncol=4,   #    设置图例的列数fontsize=8,   #     设置图例字体大小shadow=True,  #     设置图例阴影draggable=True    #  设置图例可拖动)startx = 0
starty = 0
mPress = False# 鼠标拖动 处理事件
def call_move(event):# print(event.name)global mPressglobal startxglobal startymouse_x = event.xmouse_y = event.yaxtemp = event.inaxesif event.name == 'button_press_event':if axtemp and event.button == 1:if axtemp.get_legend():legend_bbox = axtemp.get_legend().get_window_extent()left_bottom = legend_bbox.get_points()[0]right_top = legend_bbox.get_points()[1]if left_bottom[0] <= mouse_x <= right_top[0] and left_bottom[1] <= mouse_y <= right_top[1]:# print("在图例上按下鼠标")# 在图例上按下鼠标mPress = Falsereturn# 没有图例的情况# print("在 Axes 上按下鼠标")# 在 Axes 上按下鼠标mPress = Truestartx = event.xdatastarty = event.ydatareturnelif event.name == 'button_release_event':if axtemp and event.button == 1:mPress = Falseelif event.name == 'motion_notify_event':if axtemp and event.button == 1 and mPress:if axtemp.get_legend():legend_bbox = axtemp.get_legend().get_window_extent()left_bottom = legend_bbox.get_points()[0]right_top = legend_bbox.get_points()[1]if left_bottom[0] <= mouse_x <= right_top[0] and left_bottom[1] <= mouse_y <= right_top[1]:print("在图例上移动鼠标")# 在图例上按下鼠标mPress = Falsereturn# 没有图例的情况# print("在Axes上移动鼠标")x_min, x_max = axtemp.get_xlim()y_min, y_max = axtemp.get_ylim()w = x_max - x_minh = y_max - y_min# print(event)# 移动mx = event.xdata - startxmy = event.ydata - starty# 注意这里, -mx,  因为下一次 motion事件的坐标,已经是在本次做了移动之后的坐标系了,所以要体现出来# startx=event.xdata-mx  startx=event.xdata-(event.xdata-startx)=startx, 没必要再赋值了# starty=event.ydata-my# print(mx,my,x_min,y_min,w,h)axtemp.set(xlim=(x_min - mx, x_min - mx + w))axtemp.set(ylim=(y_min - my, y_min - my + h))fig.canvas.draw_idle()  # 绘图动作实时反映在图像上return# 滚轮滚动 处理事件
def call_scroll(event):# print(event.name)axtemp = event.inaxes# print('event:', event)# print(event.xdata, event.ydata)# 计算放大缩小后, xlim 和ylimif axtemp:x_min, x_max = axtemp.get_xlim()y_min, y_max = axtemp.get_ylim()w = x_max - x_minh = y_max - y_mincurx = event.xdatacury = event.ydatacurXposition = (curx - x_min) / wcurYposition = (cury - y_min) / hif event.button == 'down':# print('befor:', w, h)w = w * 1.1h = h * 1.1# print('down', w, h)elif event.button == 'up':# print('befor:', w, h)w = w / 1.1h = h / 1.1# print('up', w, h)# print(curXposition, curYposition)newx = curx - w * curXpositionnewy = cury - h * curYpositionaxtemp.set(xlim=(newx, newx + w))axtemp.set(ylim=(newy, newy + h))fig.canvas.draw_idle()  # 绘图动作实时反映在图像上fig.canvas.mpl_connect('scroll_event', call_scroll)
fig.canvas.mpl_connect('button_press_event', call_move)
fig.canvas.mpl_connect('button_release_event', call_move)
# fig.canvas.mpl_connect('draw_event', call_move)
fig.canvas.mpl_connect('motion_notify_event', call_move)plt.show()

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/226196.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

域名、DNS 和 IP是什么?网站搭建的必备知识,一文搞定

在正式进行WordPress站点搭建前&#xff0c;有一些最基础的知识是必备的&#xff0c;这篇文章会详细介绍给大家。 一、域名、DNS和IP的关系 域名、DNS和IP是互联网上的三个重要的概念&#xff0c;它们之间有着密切的联系&#xff0c;也影响着我们访问网站的方式和效果。接下来…

JNA实现JAVA调用C/C++动态库

1.JNA JNA全称Java Native Access&#xff0c;是一个建立在经典的JNI技术之上的Java开源框架&#xff08;https://github.com/twall/jna&#xff09;。JNA提供一组Java工具类用于在运行期动态访问系统本地库&#xff08;native library&#xff1a;如Window的dll&#xff09;而…

5.1 C++11强类型枚举

一、C枚举的缺陷 1.类型冲突 枚举值和类型都是全局可见的&#xff0c; 与正常C的namespace、类等都是格格不入的&#xff0c;并且还容易导致冲突。 enum Type { General, Light, Medium, Heavy }; enum Category { General, Pistol, MachineGun, Cannon }; 如果在相同作用域…

【CSS】用 CSS 写一个渐变色边框的输入框

Using_CSS_gradients MDN 多渐变色输入框&#xff0c;群友问了下&#xff0c;就试着写了下&#xff0c;看了看 css 渐变色 MDN 文档&#xff0c;其实很简单&#xff0c;代码记录下&#xff1a; <!DOCTYPE html> <html lang"en"><head><meta ch…

uniapp实现检查版本检测,更新

1.首先需要获取当前app的版本 const systemInfo uni.getSystemInfoSync();// 应用程序版本号// #ifdef APPme.version systemInfo.appWgtVersion;// #endif// #ifdef H5me.version systemInfo.appVersion;// #endif2.在获取到服务器保存的app版本 3.点击按钮验证版本号 //…

JS的箭头函数this:

箭头函数不会创建自己的this&#xff0c;它只会从自己的作用域链的上一层沿用this。 具体看实例&#xff1a; //以前&#xff1a;谁调用的这个函数 this就指向谁// console.log(this);//window// function fn(){// console.log(this);//window 因为这个函数也是window调用…

lwIP 细节之五:accept 回调函数是何时调用的

使用 lwIP 协议栈进行 TCP 裸机编程&#xff0c;其本质就是编写协议栈指定的各种回调函数。将你的应用逻辑封装成函数&#xff0c;注册到协议栈&#xff0c;在适当的时候&#xff0c;由协议栈自动调用&#xff0c;所以称为回调。 注&#xff1a;除非特别说明&#xff0c;以下内…

k8s-deployment initcontainers提前监测svc可用

背景&#xff1a;项目deploy需要依赖svc启动&#xff0c;但是k8s启动deploy是无序的&#xff0c;就需要人为控制 Init Container 应用场景 讲解了 Init Container 的使用&#xff0c;接下来介绍 Init Container 有哪些应用场景。 在很多的应用场景中&#xff0c;应用在启动之…

车载以太网-DoIP

文章目录 车载以太网DoIP协议(Diagnostics over Internet Protocol)DoIP协议的报文格式DoIP报文类型DoIP协议的完整流程车载以太网DoIP协议(Diagnostics over Internet Protocol) 车载以太网DoIP协议(Diagnostics over Internet Protocol)是一种用于车辆诊断的网络协议,…

Python中类与对象

一、前言 面向对象是一种设计哲学和方法论。它并非必需&#xff0c;不使用面向对象也可以编程。但有了面向对象&#xff0c;可以把程序组织得更有条理&#xff0c;让设计过程更加愉悦和轻松。面向对象&#xff1a;再解决问题的时候关注的是解决问题所需要的对象。 Python是一种…

2024GoCN线下活动全面启动,赠送深圳MeetUp门票

2024年GoCN社区将全面启动一系列令人期待的线下活动---不仅将在北京、上海、深圳、武汉、成都、杭州、广州、西安等地举办 meetup&#xff0c;还将在北京和上海举办 GopherChina 大会。 2024议题征集通道已开启&#xff0c;欢迎各位有实战经验、独特观点的Gopher前来分享~ 2024…

@RestController

1、RestController说明 RestController是 Spring Framework 4.0 引入的一个注解&#xff0c;用于将一个类标记为 Rest 控制器。它是Controller和ResponseBody注解的组合&#xff0c;使得使用该注解的类在处理 HTTP 请求时更加方便和简洁。 RestController注解由以下几个部分组…

Anaconda中使用Jupyter出现’No module named ‘pymysql‘问题解决

问题截图&#xff1a; 解决办法&#xff1a; 一.找到Anaconda所在文件夹&#xff0c;文件夹处输入 cmd 进入命令控制 二. 在打开的cmd中输入‘conda install pymysql’ 三、输入y 安装完成~ 测试&#xff1a; import pandas as pd from sqlalchemy import create_engine …

EAM系统在地铁设备管理中的应用

在现代城市的交通系统中&#xff0c;地铁作为一种高效、快速、可靠的公共交通工具&#xff0c;扮演着至关重要的角色。为了确保地铁系统的正常运行和可靠性&#xff0c;地铁管理部门需要有效地管理大量的设备和设施。在这个过程中&#xff0c;企业资产管理&#xff08;EAM&…

Python个人代码随笔(观看无益,请跳过)

异常抛错&#xff1a;一般来说&#xff0c;在程序中&#xff0c;遇到异常时&#xff0c;会从这一层逐层往外抛错&#xff0c;一直抛到最外层&#xff0c;由最外层把错误显示在用户终端。 try:raise ValueError("A value error...") except ValueError:print("V…

MVC框架和Spring MVC的基本流程

MVC&#xff08;Model-View-Controller&#xff09;是一种设计模式&#xff0c;用于将应用程序的逻辑分离为三个不同的组件&#xff1a;模型&#xff08;Model&#xff09;、视图&#xff08;View&#xff09;和控制器&#xff08;Controller&#xff09;。MVC框架的原理是基于…

linux源码包管理

8.2 源码包管理 source code需要经过GC,C编译环境编译才能运行 ​ 可以设定个人设置&#xff0c;但配置复杂 ​ 软件包示例: nginx-1.8.1.tar.gz -----------------------------------------------------------------------------------------------------------------------…

企业与员工

相信大家最近都关注到了董宇辉这件事,在看“热闹”的同时,我们也要关注到事情的本质。最后回到根本,归根到底就是企业与员工。 在此之前,我们先一起回顾一下历史,当然,以下内容都是我根据老一辈的分享以及历史资料做出来的总结: 我们新中国成立,经历了很多事情,特别是…

Event Driven设计模式

EDA&#xff08;Event-Driven Architecture&#xff09;是一种实现组件之间松耦合、易扩展的架构方式。一个最简单的EDA设计需要包含如下几个组件&#xff1a; Events&#xff1a;需要被处理的数据。一个Event至少包含两个属性&#xff0c;类型和数据&#xff0c;类型决定了Eve…

知识付费小程序开发:构建个性化学习平台的技术实践

随着在线学习和知识付费的兴起&#xff0c;开发一款知识付费小程序成为了创新的热点之一。本文将通过使用Node.js、Express和MongoDB为例&#xff0c;演示如何构建一个基础的知识付费小程序后端&#xff0c;并实现用户认证和知识内容管理。 1. 初始化项目 首先&#xff0c;确…