博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
tkinter内嵌Matplotlib系列(二)之函数曲线绘制
阅读量:6952 次
发布时间:2019-06-27

本文共 6973 字,大约阅读时间需要 23 分钟。

目录

目录

前言

前一章节,我们解读了tkinter内嵌Matplotlib的教程,了解其内嵌的原理,就是在tkinter创建matplotlib的画布控件,再利用其返回的画布对象进行绘图,其他附加功能,使用tkinter控件实现。

(一)对matplotlib画布的封装:

(1)说明:

我们希望对官方的实例代码进行封装成一个函数,并返回一个画布对象,外部再调用该函数,并获取画布对象,进行绘制操作。

(2)封装后的代码:

"""    画布文件,实现绘图区域的显示,并返回画布的对象。"""import tkinter as tk# 创建画布需要的库from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg# 创建工具栏需要的库from matplotlib.backends.backend_tkagg import NavigationToolbar2Tk# 快捷键需要的库from matplotlib.backend_bases import key_press_handler# 导入画图常用的库from matplotlib.figure import Figuredef plot_fun(root):    """        该函数实现的是内嵌画布,不负责画图,返回画布对象。    :param root:父亲控件对象, 一般是容器控件或者窗体    :return: 画布对象    """    # 画布的大小和分别率    fig = Figure(dpi=100)    axs = fig.add_subplot(111)    # 创建画布    canvas = FigureCanvasTkAgg(fig, master=root)  # A tk.DrawingArea.    canvas.draw()    # 显示画布    canvas.get_tk_widget().pack()    # 创建工具条    toolbar = NavigationToolbar2Tk(canvas, root)    toolbar.update()    # 显示工具条    canvas.get_tk_widget().pack()    # 调用快捷键    def on_key_press(event):        key_press_handler(event, canvas, toolbar)    canvas.mpl_connect("key_press_event", on_key_press)    # 返回画布的对象    return axs

(二)思路分析:

1.需求说明:

(1)背景:

作为学生的我们,你是否有那么一个场景,唉……,这个数学函数好难求哦,要是知道它的图像这么画就好了。

(2)需求:

给出数学表达式,绘制出该数学表达式的函数曲线,一来可以观察函数的变化趋势,二来可以根据两条曲线的交点,来求解出方程的大致结果。

2.框架的设置:

(1)说明:

分模块编程,向来是众人所提倡的,再python里更是很好的实现。

再动手敲代码之前,我们先来大致的设置一下,小项目的框架。

(2)框架图解:

01.png

3.文件说明:

(1)main.py

主程序文件,负责程序的启动与结束和窗体的大致设置。

(2)widget.py

控件文件,负责程序控件的创建与布局

(3)figure.py

画布文件,实现绘图区域的显示,并返回画布的对象。

(4)plot.py

绘图文件,负责函数曲线的绘制

(三)各文件的源代码

1.main.py

"""    主程序文件,负责程序的启动与结束和窗体的大致设置。"""import tkinter as tkimport widgetdef win_w_h(root):    """        控制窗口的大小和出现的位置    :param root:    :return: 窗口的大小和出现的位置    """    # 设置标题:    win.title("数学函数绘图")    # 绘图区标签    label_plot = tk.Label(root, text="绘     图       区",                          font=("微软雅黑", 10), fg="blue")    label_plot.place(relx=0.26, rely=0)    label_func = tk.Label(root, text="功     能       区",                          font=("微软雅黑", 10), fg="blue")    label_func.place(relx=0.75, rely=0)    # 获取屏幕的大小;    screen_height = root.winfo_screenheight()    screen_width = root.winfo_screenwidth()    # 窗体的大小    win_width = 0.8 * screen_width    win_height = 0.8 * screen_height    # 窗体出现的位置:控制的是左上角的坐标    show_width = (screen_width - win_width) / 2    show_height = (screen_height - win_height) / 2    # 返回窗体 坐标    return win_width, win_height, show_width, show_heightwin = tk.Tk()# 大小 位置win.geometry("%dx%d+%d+%d" % (win_w_h(win)))# 创建一个容器, 没有画布时的背景frame1 = tk.Frame(win, bg="#c0c0c0")frame1.place(relx=0.00, rely=0.05, relwidth=0.62, relheight=0.89)# 控件区frame2 = tk.Frame(win, bg="#808080")frame2.place(relx=0.62, rely=0.05, relwidth=0.38, relheight=0.89)# 调用控件模块widget.widget_main(win, frame2)win.mainloop()

2.widget.py

"""    控件文件,负责程序控件的创建与布局"""import tkinter as tk# 对话框所需的库import tkinter.messagebox as mb# 画布文件import figure# 绘图文件import plotdef widget_main(win, root):    """        负责程序控件的创建与布局    :param win: 主窗体的对象。    :param root: 绘图区的容器对象。    :return: 无    """    # 控件区的容器对象    frame1 = None# ===========功能区============================    # 绘图的功能函数    def plot_f():        string = entry.get()        # 判断输入框是否为空        if string == "":            mb.showerror("提示", "没有输入值,请重新输入:")        else:            # 判断是否已经创建画布            if frame1==None:                mb.showerror("提示", "没有创建画布,不能画图,请先创建画布")            else:                axs = figure.plot_fun(frame1)                plot.plot_main(string, axs)    # 清除的功能函数    def clear():        nonlocal frame1        entry.delete(0, "end")        if frame1==None:            mb.showerror("提示", "已经没有画布,无法清除画布")        else:            frame1.destroy()            frame1 = None    # 创建画布的功能函数    def create():        nonlocal frame1        if frame1 != None:            mb.showerror("提示", "画布已经存在,请不要重复创建画布")        else:            frame1 = tk.LabelFrame(win, bg="#80ff80", text="画-----布", labelanchor="n", fg="green")            frame1.place(relx=0.00, rely=0.05, relwidth=0.62, relheight=0.95)# =============控件区======================    #  标签控件    label = tk.Label(root,                     text="请输入含x的数学公式:",                     font=("微软雅黑", 18),                     fg="blue")    label.place(relx=0.2, rely=0.1)    # 输入框    entry = tk.Entry(root, font=("华文楷体", 15))    entry.place(relx=0.1, rely=0.2, relwidth=0.8)    # 创建画布区    btn_draw = tk.Button(root,                         text="创建",                         cursor="hand2",                         width=10,                         bg="orange",                         relief="raised",                         command=create                         )    btn_draw.place(relx=0.1, rely=0.3)    # 绘图按钮    btn_draw = tk.Button(root,                         text="绘图",                         cursor="hand2",                         width=10,                         bg="green",                         relief="raised",                         command=plot_f                         )    btn_draw.place(relx=0.4, rely=0.3)    # 清除按钮    btn_clear = tk.Button(root,                          text="清除",                          cursor="hand2",                          width=10,                          bg="yellow",                          relief="raised",                          command=clear                          )    btn_clear.place(relx=0.7, rely=0.3)

3.figure.py

"""    画布文件,实现绘图区域的显示,并返回画布的对象。"""import tkinter as tk# 创建画布需要的库from matplotlib.backends.backend_tkagg import FigureCanvasTkAgg# 创建工具栏需要的库from matplotlib.backends.backend_tkagg import NavigationToolbar2Tk# 快捷键需要的库from matplotlib.backend_bases import key_press_handler# 导入画图常用的库from matplotlib.figure import Figuredef plot_fun(root):    """        该函数实现的是内嵌画布,不负责画图,返回画布对象。    :param root:父亲控件对象, 一般是容器控件或者窗体    :return: 画布对象    """    # 画布的大小和分别率    fig = Figure(dpi=100)    axs = fig.add_subplot(111)    # 创建画布    canvas = FigureCanvasTkAgg(fig, master=root)  # A tk.DrawingArea.    canvas.draw()    # 显示画布    canvas.get_tk_widget().pack()    # 创建工具条    toolbar = NavigationToolbar2Tk(canvas, root)    toolbar.update()    # 显示工具条    canvas.get_tk_widget().pack()    # 调用快捷键    def on_key_press(event):        key_press_handler(event, canvas, toolbar)    canvas.mpl_connect("key_press_event", on_key_press)    # 返回画布的对象    return axs

4.plot.py

"""    绘图文件,负责函数曲线的绘制"""import numpy as npdef plot_main(string, plt):    """        负责函数曲线的绘制    :param string: 数学表达式    :param plt: 画布的对象    :return: 无    """    list_expr = []    list_expr = string.split(",")    string1 = []    for sub_expr in list_expr:        string1.append(sub_expr)    x = np.linspace(-10, 10, 100)    y = []    num = string.count('x')    for i in x:        t = (i, ) * num        string = string.replace("x", "(%f)")        i = eval(string % t)        y.append(i)    plt.plot(x, y)    plt.grid(True)    plt.legend(labels=string1)

(四)文件结构

四个文件均处于同一个文件夹下,用main.py来运行。

02.png

(五)项目下载:

链接:

提取码:codq

作者:Mark

日期:2019/02/15 周五

转载于:https://www.cnblogs.com/zyg123/p/10385517.html

你可能感兴趣的文章
X3-02 gprs 设置
查看>>
列出对像属性,for(var i in obj)[转]
查看>>
Js(DOM) 和Jq 对象的相互转换
查看>>
HDUOJ3980取模运算
查看>>
20165318 2017-2018-2 《Java程序设计》第九周学习总结
查看>>
mysql 数据库备份的多种方式
查看>>
2-范数、1-范数、···
查看>>
C#闭包函数
查看>>
浅谈vr基础视频教程 改变技术革命
查看>>
c++调用DOS命令,不显示黑屏
查看>>
python虚拟环境
查看>>
ls -l 各项含义
查看>>
Helios与Katana的区别
查看>>
python从数据库取数据后写入excel 使用pandas.ExcelWriter设置单元格格式
查看>>
Android JPush(极光推送)的使用教程
查看>>
奇异值分解(SVD)小结
查看>>
MYSQL数据库设计规范
查看>>
python之socket编程
查看>>
Delphi在Vasta/win 7下通过UAC控制
查看>>
[转]DPM2012系列之一:安装Data Protection Manager 2012
查看>>