Python基础之利用Matplotlib和Tkinter在应用程序中内嵌图表

简介: Python基础之利用Matplotlib和Tkinter在应用程序中内嵌图表

在日常应用程序开发中,图表(折线图,柱状图等)以其直观显示,清晰明了的优势,使得应用范围越来越广泛,本文以一个简单的小例子,简述如何将Tkinter和Matplotlib相互关联起来,在应用程序中嵌入图表,仅供学习分享使用,如有不足之处,还请指正。

涉及知识点

  1. Tkinter 是Python内置的桌面程序开发组件库,包含日常使用的基础组件(如:Label,Button,Entry等),利用Tkinter可以方便的开发可视化程序。
  2. Matplotlib 是一个开源的数据可视化类库,利用matplotlib可以绘制各种类型的图表(如:折线图,柱状图,散点图等)。
  3. Numpy 是一个开源的数学相关的类库,广泛应用于数学计算等领域。本例主要使用Numpy提供的数学函数和随机数生成数据源。

操作步骤

如果要将matplotlib生成图表和Tkinter生成的GUI程序关联起来,需要以下3个步骤:

  1. 创建Matplotlib的figure(画布)对象,并在figure上进行绘图。
  2. 创建FigureCanvasTkAgg(画布容器)对象,参数为第1步生成的figure对象和容器存放的父对象,并调用创建对象的draw函数。
  3. 调用FigureCanvasTkAgg对应组件的Pack方法,将对象显示在页面上。

示例效果图

将Matplotlib生成的曲线图,嵌入到普通的windows程序中,如下图所示:

核心代码

创建图表代码

def create_matplotlib(self):
        """创建绘图对象"""
        # 设置中文显示字体
        mpl.rcParams['font.sans-serif'] = ['SimHei']  # 中文显示
        mpl.rcParams['axes.unicode_minus'] = False  # 负号显示
        # 创建绘图对象f figsize的单位是英寸 像素 = 英寸*分辨率
        self.figure = plt.figure(num=2, figsize=(7, 4), dpi=80, facecolor="gold", edgecolor='green', frameon=True)
        # 创建一副子图
        fig1 = plt.subplot(1, 1, 1)  # 三个参数,依次是:行,列,当前索引
        # 创建数据源:x轴是等间距的一组数
        x = np.arange(-2 * np.pi, 2 * np.pi, 0.1)
        y1 = np.sin(x)
        y2 = np.cos(x)
        line1 = fig1.plot(x, y1, color='red', linewidth=2, label='y=sin(x)', linestyle='--')  # 画第一条线
        line2 = fig1.plot(x, y2, color='green', label='y=cos(x)')
        plt.setp(line2, linewidth=1, linestyle='-', alpha=0.7)  # 华第二条线 color='',
        fig1.set_title("数学曲线图", loc='center', pad=20, fontsize='xx-large', color='red')  # 设置标题
        # line1.set_label("正弦曲线")  # 确定图例
        # 定义legend 重新定义了一次label
        fig1.legend(['正弦', '余弦'], loc='lower right', facecolor='orange', frameon=True, shadow=True, framealpha=0.7)
        # ,fontsize='xx-large'
        fig1.set_xlabel('(x)横坐标')  # 确定坐标轴标题
        fig1.set_ylabel("(y)纵坐标")
        fig1.set_yticks([-1, -1 / 2, 0, 1 / 2, 1])  # 设置坐标轴刻度
        fig1.grid(which='major', axis='x', color='gray', linestyle='-', linewidth=0.5, alpha=0.2)  # 设置网格

创建图表容器,并显示代码

def createWidget(self, figure):
        """创建组件"""
        self.label = Label(self, text='这是一个Tkinter和Matplotlib相结合的小例子')
        self.label.pack()
        # 创建画布
        self.canvas = FigureCanvasTkAgg(figure, self)
        self.canvas.draw()
        self.canvas.get_tk_widget().pack(side=TOP, fill=BOTH, expand=1)
        # 把matplotlib绘制图形的导航工具栏显示到tkinter窗口上
        # toolbar = NavigationToolbar2Tk(self.canvas, self)
        # toolbar.update()
        # self.canvas._tkcanvas.pack(side=TOP, fill=BOTH, expand=1)
        # self.button = Button(master=self, text="退出", command=quit)
        # # 按钮放在下边
        # self.button.pack(side=BOTTOM)

整体代码及调用逻辑,如下所示:

from tkinter import *
import numpy as np
import matplotlib
import matplotlib.pyplot as plt
from matplotlib.pylab import mpl
from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg, NavigationToolbar2Tk
class Application(Frame):
    """一个经典的GUI写法"""
    def __init__(self, master=None):
        '''初始化方法'''
        super().__init__(master)  # 调用父类的初始化方法
        self.master = master
        self.pack(side=TOP, fill=BOTH, expand=1)  # 此处填充父窗体
        self.create_matplotlib()
        self.createWidget(self.figure)
    def createWidget(self, figure):
        """创建组件"""
        self.label = Label(self, text='这是一个Tkinter和Matplotlib相结合的小例子')
        self.label.pack()
        # 创建画布
        self.canvas = FigureCanvasTkAgg(figure, self)
        self.canvas.draw()
        self.canvas.get_tk_widget().pack(side=TOP, fill=BOTH, expand=1)
        # 把matplotlib绘制图形的导航工具栏显示到tkinter窗口上
        # toolbar = NavigationToolbar2Tk(self.canvas, self)
        # toolbar.update()
        # self.canvas._tkcanvas.pack(side=TOP, fill=BOTH, expand=1)
        # self.button = Button(master=self, text="退出", command=quit)
        # # 按钮放在下边
        # self.button.pack(side=BOTTOM)
    def create_matplotlib(self):
        """创建绘图对象"""
        # 设置中文显示字体
        mpl.rcParams['font.sans-serif'] = ['SimHei']  # 中文显示
        mpl.rcParams['axes.unicode_minus'] = False  # 负号显示
        # 创建绘图对象f figsize的单位是英寸 像素 = 英寸*分辨率
        self.figure = plt.figure(num=2, figsize=(7, 4), dpi=80, facecolor="gold", edgecolor='green', frameon=True)
        # 创建一副子图
        fig1 = plt.subplot(1, 1, 1)  # 三个参数,依次是:行,列,当前索引
        # 创建数据源:x轴是等间距的一组数
        x = np.arange(-2 * np.pi, 2 * np.pi, 0.1)
        y1 = np.sin(x)
        y2 = np.cos(x)
        line1 = fig1.plot(x, y1, color='red', linewidth=2, label='y=sin(x)', linestyle='--')  # 画第一条线
        line2 = fig1.plot(x, y2, color='green', label='y=cos(x)')
        plt.setp(line2, linewidth=1, linestyle='-', alpha=0.7)  # 华第二条线 color='',
        fig1.set_title("数学曲线图", loc='center', pad=20, fontsize='xx-large', color='red')  # 设置标题
        # line1.set_label("正弦曲线")  # 确定图例
        # 定义legend 重新定义了一次label
        fig1.legend(['正弦', '余弦'], loc='lower right', facecolor='orange', frameon=True, shadow=True, framealpha=0.7)
        # ,fontsize='xx-large'
        fig1.set_xlabel('(x)横坐标')  # 确定坐标轴标题
        fig1.set_ylabel("(y)纵坐标")
        fig1.set_yticks([-1, -1 / 2, 0, 1 / 2, 1])  # 设置坐标轴刻度
        fig1.grid(which='major', axis='x', color='gray', linestyle='-', linewidth=0.5, alpha=0.2)  # 设置网格
    def destroy(self):
        """重写destroy方法"""
        super().destroy()
        quit()
    def quit():
        """点击退出按钮时调用这个函数"""
        root.quit()  # 结束主循环
        root.destroy()  # 销毁窗口
if __name__ == '__main__':
    root = Tk()
    root.title('数学曲线窗口')
    root.geometry('560x400+200+200')
    app = Application(master=root)
    root.mainloop()

多图示例

如何利用Matplotlib在一张图里面,包含多张子图,如下所示:

多图核心代码

其他代码和上例保持一致,只是在创建图表时略有差异。主要是利用plt.subplot(2, 2, 1)方法对图片进行切分。如下所示:

def create_matplotlib(self):
        """创建绘图对象"""
        # 设置中文显示字体
        mpl.rcParams['font.sans-serif'] = ['SimHei']  # 中文显示
        mpl.rcParams['axes.unicode_minus'] = False  # 负号显示
        # 创建绘图对象f figsize的单位是英寸 像素 = 英寸*分辨率
        self.figure = plt.figure(num=2, figsize=(7, 4), dpi=80, facecolor="gold", edgecolor='green', frameon=True)
        self.figure.text(0.45, 0.94, '这是四幅图') # 设置显示的文本
        # 一张图上显示4张小图
        x = np.linspace(-6, 6, 100)
        y = np.sin(x)  # 正弦曲线
        y2 = np.cos(x)  # 余弦曲线
        y3 = np.tan(x)  # tan函数
        y4 = np.square(x)  # 平方函数
        fig1 = plt.subplot(2, 2, 1)  # 先进行分块,最后一个参数是序号
        self.setplot(fig1, x, y, 'y=sin(x)', 'red')
        fig2 = plt.subplot(2, 2, 2)
        self.setplot(fig2, x, y2, 'y=cos(x)', 'green')
        fig3 = plt.subplot(2, 2, 3)
        self.setplot(fig3, x, y3, 'y=tan(x)', 'black')
        fig4 = plt.subplot(2, 2, 4)
        self.setplot(fig4, x, y4, 'y=square(x)', 'gold')
    def setplot(self, fig, x, y, text, color='r'):
        """绘制子图"""
        line = fig.plot(x, y, color=color, label=text)
        fig.set_xlabel('(x)横坐标')  # 确定坐标轴标题
        fig.set_ylabel("(y)纵坐标")
        fig.grid(which='major', axis='x', color='gray', linestyle='-', linewidth=0.5, alpha=0.2)  # 设置网格
        fig.legend(loc='lower right', facecolor='orange', frameon=True, shadow=True, framealpha=0.7)

柱状图示例

如何利用Matplotlib绘制柱状图,如下所示:

柱状图核心代码

其他代码和上例保持一致,只是在创建图表时略有差异。主要是通过bar 函数创建柱状图,如下所示:

def create_matplotlib(self):
        """创建绘图对象"""
        # 设置中文显示字体
        mpl.rcParams['font.sans-serif'] = ['SimHei']  # 中文显示
        mpl.rcParams['axes.unicode_minus'] = False  # 负号显示
        # 创建绘图对象f figsize的单位是英寸 像素 = 英寸*分辨率
        self.figure = plt.figure(num=2, figsize=(7, 4), dpi=80, facecolor="gold", edgecolor='green', frameon=True)
        self.figure.text(0.45, 0.94, '这是柱状图图') # 设置显示的文本
        x = np.arange(12)
        y = np.random.uniform(0.5, 1.0, 12) * (1 - x / float(12))
        loc = zip(x, y)  # 将x, y 两两配对
        plt.ylim(0, 1.2)  # 设置y轴的范围
        plt.bar(x, y, facecolor='green', edgecolor='black')  # 绘制柱状图(填充颜色绿色,边框黑色)
        for x, y in loc:
            plt.text(x + 0.1, y + 0.01, '%.2f' % y, ha='center', va='bottom')  # 保留小数点2位

备注

Matplotlib的图表形式还有很多,本例只是抛砖引玉,简述两种图表的生成方式,其他的图表则不做赘述。

如需源码链接,可点击链接下载。一首小词,舒缓一下心情。

浣溪沙·堤上游人逐画船

宋代:欧阳修

堤上游人逐画船,拍堤春水四垂天。绿杨楼外出秋千。

白发戴花君莫笑,六幺催拍盏频传。人生何处似樽前!

相关文章
|
1月前
|
机器学习/深度学习 存储 数据挖掘
Python图像处理实用指南:PIL库的多样化应用
本文介绍Python中PIL库在图像处理中的多样化应用,涵盖裁剪、调整大小、旋转、模糊、锐化、亮度和对比度调整、翻转、压缩及添加滤镜等操作。通过具体代码示例,展示如何轻松实现这些功能,帮助读者掌握高效图像处理技术,适用于图片美化、数据分析及机器学习等领域。
79 20
|
10天前
|
算法 Serverless 数据处理
从集思录可转债数据探秘:Python与C++实现的移动平均算法应用
本文探讨了如何利用移动平均算法分析集思录提供的可转债数据,帮助投资者把握价格趋势。通过Python和C++两种编程语言实现简单移动平均(SMA),展示了数据处理的具体方法。Python代码借助`pandas`库轻松计算5日SMA,而C++代码则通过高效的数据处理展示了SMA的计算过程。集思录平台提供了详尽且及时的可转债数据,助力投资者结合算法与社区讨论,做出更明智的投资决策。掌握这些工具和技术,有助于在复杂多变的金融市场中挖掘更多价值。
39 12
|
9天前
|
存储 人工智能 程序员
通义灵码AI程序员实战:从零构建Python记账本应用的开发全解析
本文通过开发Python记账本应用的真实案例,展示通义灵码AI程序员2.0的代码生成能力。从需求分析到功能实现、界面升级及测试覆盖,AI程序员展现了需求转化、技术选型、测试驱动和代码可维护性等核心价值。文中详细解析了如何使用Python标准库和tkinter库实现命令行及图形化界面,并生成单元测试用例,确保应用的稳定性和可维护性。尽管AI工具显著提升开发效率,但用户仍需具备编程基础以进行调试和优化。
148 9
|
9天前
|
算法 安全 网络安全
基于 Python 的布隆过滤器算法在内网行为管理中的应用探究
在复杂多变的网络环境中,内网行为管理至关重要。本文介绍布隆过滤器(Bloom Filter),一种高效的空间节省型概率数据结构,用于判断元素是否存在于集合中。通过多个哈希函数映射到位数组,实现快速访问控制。Python代码示例展示了如何构建和使用布隆过滤器,有效提升企业内网安全性和资源管理效率。
44 9
|
1月前
|
人工智能 开发者 Python
Chainlit:一个开源的异步Python框架,快速构建生产级对话式 AI 应用
Chainlit 是一个开源的异步 Python 框架,帮助开发者在几分钟内构建可扩展的对话式 AI 或代理应用,支持多种工具和服务集成。
187 9
|
1月前
|
存储 NoSQL 数据库连接
在Python程序中实现LevelDB的海量key的分批次扫描
通过本文的步骤,您可以在Python程序中实现对LevelDB海量key的分批次扫描。这样不仅能够有效地管理大规模数据,还可以避免一次性加载过多数据到内存中,提高程序的性能和稳定性。希望这篇指南能为您的开发工作提供实用的帮助。
78 28
|
1月前
|
存储 SQL 大数据
Python 在企业级应用中的两大硬伤
关系数据库和SQL在企业级应用中面临诸多挑战,如复杂SQL难以移植、数据库负担重、应用间强耦合等。Python虽是替代选择,但在大数据运算和版本管理方面存在不足。SPL(esProc Structured Programming Language)作为开源语言,专门针对结构化数据计算,解决了Python的这些硬伤。它提供高效的大数据运算能力、并行处理、高性能文件存储格式(如btx、ctx),以及一致的版本管理,确保企业级应用的稳定性和高性能。此外,SPL与Java无缝集成,适合现代J2EE体系应用,简化开发并提升性能。
|
3月前
|
设计模式 开发者 Python
Python编程中的设计模式应用与实践感悟####
本文作为一篇技术性文章,旨在深入探讨Python编程中设计模式的应用价值与实践心得。在快速迭代的软件开发领域,设计模式如同导航灯塔,指引开发者构建高效、可维护的软件架构。本文将通过具体案例,展现设计模式如何在实际项目中解决复杂问题,提升代码质量,并分享个人在实践过程中的体会与感悟。 ####
|
8月前
|
数据采集 数据可视化 大数据
Python在大数据处理中的应用实践
Python在大数据处理中扮演重要角色,借助`requests`和`BeautifulSoup`抓取数据,`pandas`进行清洗预处理,面对大规模数据时,`Dask`提供分布式处理能力,而`matplotlib`和`seaborn`则助力数据可视化。通过这些工具,数据工程师和科学家能高效地管理、分析和展示海量数据。
421 4
|
3月前
|
机器学习/深度学习 数据采集 数据可视化
Python在数据科学中的应用:从入门到实践
本文旨在为读者提供一个Python在数据科学领域应用的全面概览。我们将从Python的基础语法开始,逐步深入到数据处理、分析和可视化的高级技术。文章不仅涵盖了Python中常用的数据科学库,如NumPy、Pandas和Matplotlib,还探讨了机器学习库Scikit-learn的使用。通过实际案例分析,本文将展示如何利用Python进行数据清洗、特征工程、模型训练和结果评估。此外,我们还将探讨Python在大数据处理中的应用,以及如何通过集成学习和深度学习技术来提升数据分析的准确性和效率。