用python实现CNC插补

1.项目平台

本项目基于python平台设计,适用于python3.6及以上的版本。该项目主要调用了python内置的GUI模块Tkinter,并在其中内嵌了python的海龟绘图(TurtleGraphics)。其主要借鉴的是海龟绘图中的turtle.RawTurtle模块,其特点是轻量化且能嵌入Tkinter中。

2.项目主要功能

该项目主要针对数控机床CNC中的插补算法进行模拟,并对课本中仅在第一象限的插补进行扩展。目前,能够实现圆弧以及直线的插补。此外,该插补项目设计了用户交互界面,操作简单。

2.1直线插补功能

针对直线插补,用户以标准形式输入任意多个点,并点击“开始绘图”即可开始动态直线绘图以及插补。如输入[(0,0),(4,3)]并点击“开始绘图”即可实现(0,0)点到(4,3)点的直线插补。此外,该直线插补能够实现任意象限的跨越以及任意点对点之间的组合。

2.2圆弧插补功能

针对圆弧插补,用户输入圆形坐标,平行于X轴的半径坐标以及平行于Y轴的半径坐标并点击“开始绘图”即可开始动态的圆弧绘制以及插补。如输入[(0,0),(5,0),(0,5)]并点击“开始绘图”即可生成以(0,0)点为圆心,5为半径,起始坐标为(5,0),终点坐标为(0,5)的1/4圆弧插补。该项目的圆弧均以90°为单位进行插补,圆心可任意自取。

3.应用功能举例

3.1直线插补举例

多点直线插补的数控模拟界面如图1所示。其中,蓝色线段为理想直线,红色线段为插补直线。我们输入的多段直线坐标为[(3,5),(-12,10),(-20,-13),(-6,-8),(6,-8),(19,-19),(7,15),(7,20),(-12,20),(-20,15)]。这里一共包含了10个坐标点,9段直线,既有象限与象限之间的跨越,又有水平直线与数值直线的插补,基本能够满足直线插补的所有要求。
图片

图1 多点直线插补演示界面

3.2圆弧插补举例

圆弧插补的演示界面如图2所示。图2中的蓝色圆弧为绘制的理想圆弧,红色线段为插补线段。在该例中,输入的坐标为[(-4,-3),(11,-3),(-4,12),(-19,-3),(-4,-18),(11,-3)],即是以(-4,-3)点为圆心,四段圆弧组成的一个整圆。该例子实现了圆弧的跨象限插补,圆心坐标不在原点的插补,以及多个圆弧的拼接。相比课本中例子,该插补体现了本项目更加出色的功能。
图片

图2 圆弧插补演示界面

4.项目源代码

4.1画布设计

改项目的画布设计采用了tkinter包,其原因有两点。一是该代码包的画布比较简单,可以添加按钮。同时可以调用RawTurtle,也就是海龟绘图,海龟绘图是插补演示的核心,在下面会重点强调。

import turtle
import tkinter as tk
import math

root = tk.Tk() #创建一个画布
root.title('数控插补演示界面') #取名
# 设计画布的大小以及线宽,这里要注意一下,如果画布太大了,可能按钮界面就被遮住了。 
canvas = tk.Canvas(master=root, bd=5, width =650, height =650) 
canvas.pack()
# 导入海龟绘图,这是画布自带的海龟绘图
turtle = turtle.RawTurtle(canvas)
turtle.hideturtle()  #把海龟藏起来
## 这部分就是在画布里加入输出框,和判断框,就是在调用这个程序时用户输入的内容。
# 加入带有提示的文本框
l1 = tk.Label(root, text="输入坐标 格式[(x0,y0),(x1,y1)...(xn,yn)]")  # 标签
l1.pack(side=tk.LEFT)  # 指定包管理器放置组件
user_text = tk.StringVar()
user_text = tk.Entry(root, textvariable=user_text,width=25)  # 创建文本框
user_text.pack(side=tk.LEFT) #文本框放置在左侧
# 设置选择按钮 v1表示直线插补,v2表示圆插补
v1 = tk.IntVar()            # 用来表示按钮是否选中
v2 = tk.IntVar()
# 放置按钮的位置
c1 = tk.Checkbutton(root, text='直线', variable=v1).pack(side=tk.LEFT)
c2 = tk.Checkbutton(root, text='圆', variable=v2).pack(side=tk.LEFT)

4.2 背景网格线绘制函数

在布置完成背景后,我们得到了输入坐标的文本框以及选择直线插补或是圆插补的信息选择框,接下来我们需要在空白的背景上加上我们的网格线,使得插补的过程和书中内容更加接近。

def draw_coordinate():   # 绘制坐标线
    turtle.pencolor("#000000") 
# 这里是画虚线
    for i in range(40):
        canvas.create_line(-500, int(20 * i), 500, int(20 * i), dash=1, width=1, )
        canvas.create_line(-500, -int(20 * i), 500, -int(20 * i), dash=1, width=1, )
        canvas.create_line(int(20 * i), -500, int(20 * i), 500, dash=1, width=1,)
        canvas.create_line(-int(20 * i), -500, -int(20 * i), 500, dash=1, width=1, )
# 绘制坐标轴
    canvas.create_line(-500, 0, 500, 0, fill='black', width=3)
    canvas.create_line(0, 500, 0, -500, fill='black', width=3)

4.3 画布信息获取函数

在上文中提到的文本框以及信息选择框的内容,我们通过函数将其提取。确定插补的起点终点以及插补的类型为直线插补还是圆弧插补。

# 提取文本框的内容
def getuser():  # 该函数用来获得文本框内容
    user = user_text.get()  # 获取文本框内容
    return user

# 提取选择框的内容
def get_style():
    v_1 = v1.get()
    v_2 = v2.get()
    return v_1, v_2

4.4 绘制插补图形函数

输入信息被提取后,我们就可以绘制相应的插补图像了。插补图像里调用了很多的函数,我们后面就以比较复杂的圆来解释好啦。

def draw_whole():
    line, circle = get_style()  #提取信息判断是圆插补还是直线插补
    if line == 1 and circle == 0:
        turtle.clear() #清理画布
        line_path = eval(getuser()) #将文本框内容进行输出
        for i in range(0, len(line_path)-1):
        	# 这里是一个放大,因为海龟绘图的一步太小了,所以以20步代替一步,在画布里比较明显。
            xo = line_path[i][0]*my_step
            yo = line_path[i][1]*my_step
            xe = line_path[i+1][0]*my_step
            ye = line_path[i+1][1]*my_step
            # 绘制理想的直线
            draw_orignalline(xo, yo, xe, ye)
            # 判断象限
            quadrant = judge_quadrant(xo, yo, xe, ye)
            # 计算插补的数组
            interpolation(quadrant, xo, yo, xe, ye)
            # 将插补得到的数组绘制出来
            draw_line()
    # 这是选中了圆的情况
    elif line == 0 and circle == 1:
        turtle.clear() #清理画布
        line_path = eval(getuser()) # 得到文本框内容
        # 这里也是放大
        for i in range(0, len(line_path) - 2):
            xo = line_path[0][0] * my_step
            yo = line_path[0][1] * my_step
            print(xo, yo)
            x1 = line_path[i + 1][0] * my_step
            y1 = line_path[i + 1][1] * my_step

            x2 = line_path[i + 2][0] * my_step
            y2 = line_path[i + 2][1] * my_step
            print(x1, y1, "  ", x2, y2)
            # 绘制理想的圆的曲线
            draw_ideal_circle(xo, yo, x1, y1, x2, y2)
            # 判断圆弧的象限
            quadrant = judge_quadrant_circle(xo, yo, x1, y1, x2, y2)
            print(quadrant)
            # 圆需要计算总步数
            total_steps = (abs(x2 - x1) + abs(y2 - y1)) / my_step
            # 确定的逆元还是顺圆
            sn = get_sn(line_path)
            # 得到圆弧的插补数组
            arc_interpolation(quadrant, sn, xo, yo, x1, y1, total_steps)
            # 绘制圆弧
            draw_line_circle()

4.4.1 绘制理想的圆

绘制理想圆就是输入圆心坐标,圆弧起点终点坐标绘制的圆弧,同样是利用了python的海龟绘图。主要是需要判断一下象限位置。

def draw_ideal_circle(xo, yo, x1, y1, x2, y2):
    turtle.penup() #提笔
    turtle.goto(0, 0) #去0,0点
    turtle.pendown()  #落笔
    turtle.setheading(0) #初始一下海龟头的方向,转弯用
    turtle.speed(10)  #设置速度
    turtle.pencolor("#6495ED")
    turtle.width(
  • 5
    点赞
  • 13
    收藏
    觉得还不错? 一键收藏
  • 7
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 7
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值