[python][vpython]用vpython实现小球砸弹簧代码
代码:
from vpython import * # 加载vpython模块 s1 = canvas(width=1200, height=500, background=color.white, center=vector(0, 1, 0)) # 定义画布 L0 = 1.4 # 定义初始高度 natural_length = 0.9 # 设置弹簧原长 base_spring = box(pos=vector(0, 0, 0), size=vector(0.1, 0.02, 0.1), color=color.white) # 创建基座 ball1 = sphere(pos=vector(0, L0, 0), radius=0.05, color=color.blue) # 创建小球 spring = helix(pos=vector(0, 0, 0), axis=vector(0, 1, 0), radius=0.03, coils=13, length=natural_length, thickness=0.01, color=color.yellow) # 创建弹簧 s1.autoscale = 0 # 禁止画面自动缩放 g1 = graph(width=400, height=300, xtitle="时间/s", ytitle="能量/J", align="left") # 定义曲线显示窗口 EKcurve = gcurve(color=color.red, graph=g1, label="动能") # 定义动能曲线 EPEcurve = gcurve(color=color.blue, graph=g1, label="弹性势能") # 定义弹性势能曲线 EPHcurve = gcurve(color=color.green, graph=g1, label="重力势能") # 定义弹性势能曲线 EEcurve = gcurve(color=color.yellow, graph=g1, label="小球机械能") # 定义小球机械能曲线 Ecurve = gcurve(color=color.black, graph=g1, label="系统机械能") # 定义系统机械能曲线 g2 = graph(width=400, height=300, xtitle="时间/s", ytitle="速度/m/s", align="left") # 定义曲线显示窗口 Vcurve = gcurve(color=color.red, graph=g2, label="速度") # 定义动能曲线 g3 = graph(width=400, height=300, xtitle="时间/s", ytitle="加速度/m/s^2", align="left") # 定义曲线显示窗口 Acurve = gcurve(color=color.magenta, graph=g3, label="加速度") # 定义动能曲线 vector_f = arrow(color=color.black, shaftwidth=0.01) # 定义弹簧弹力矢量箭头 f_label = label(text="T", height=20, opacity=0, box=False) # 定义弹簧弹力标签 vector_g = arrow(color=color.red, shaftwidth=0.01) # 定义重力矢量箭头 g_label = label(text='G', height=20, opacity=0, box=False) # 定义重力标签 EK_label = label(text="动能", height=20, opacity=0, box=False) # 定义小球动能标签 EPE_label = label(text="弹性势能", height=20, opacity=0, box=False) # 定义弹性势能标签 EPH_label = label(text="重力势能", height=20, opacity=0, box=False) # 定义弹性势能标签 vector_scale = 0.1 # 设置箭头缩放系数 m = 0.2 # 设定小球质量 k = 10 # 设置弹簧劲度系数 g = -10 # 设置重力加速度 ball1.v = vector(0, 0, 0) # 设定小球初始速度矢量 ball1.a = vector(0, 0, 0) # 设定小球初始加速度矢量 t = 0 # 设定时间变量 dt = 0.0001 # 设置时间间隔 EPE = 0 # 设定重力势能 G = m * g # 设定重力 while t < 5: # 设置循环总时间 rate(1000) # 设置每秒循环次数 if (ball1.pos.y > natural_length): ball1.a.y = g # 自由落体加速度 ball1.v = ball1.v + ball1.a * dt # 计算小球速度矢量更新值 ball1.pos = ball1.pos + ball1.v * dt # 计算小球位置矢量更新值 else: spring.length = ball1.pos.y # 计算新的弹簧长度 delta_length = spring.length - natural_length # 计算弹簧变形长度 f = -k * delta_length # 计算弹簧弹力 ball1.a.y = (f + G) / m # 根据牛顿第二定律计算小球加速度 ball1.v = ball1.v + ball1.a * dt # 计算小球速度矢量更新值 ball1.pos = ball1.pos + ball1.v * dt # 计算小球位置矢量更新值 EPE = 0.5 * k * delta_length ** 2 # 计算弹簧弹性势能 vector_f.pos = ball1.pos # 更新弹力箭头位置 vector_f.axis = vector(0, f, 0) * vector_scale # 更新弹力箭头大小 if (f > -G): # 更新弹力箭头颜色 vector_f.color = color.orange else: vector_f.color = color.purple f_label.pos = vector_f.pos + vector_f.axis * 1.2 # 设置弹力标签位置 f_label.pos.x = f_label.pos.x - 0.1 f_label.text = "f=" + str(f)[:4] # 设置弹力标签显示内容 EK = 0.5 * m * (mag(ball1.v)) ** 2 # 计算小球动能 EPH = m * g * (L0 - ball1.pos.y) E = EK + EPE + EPH # 计算系统机械能 EE = EK + EPH # 计算小球机械能 vector_g.pos = ball1.pos # 更新弹力箭头位置 vector_g.axis = vector(0, G, 0) * vector_scale # 更新弹力箭头大小 g_label.pos = vector_g.pos + vector_g.axis * 1.2 # 设置弹力标签位置 g_label.pos.x = g_label.pos.x - 0.1 g_label.text = "G=" + str(G)[:4] # 设置弹力标签显示内容 EK_label.pos = vector(ball1.pos.x + 0.5, ball1.pos.y, ball1.pos.z) # 设置动能标签位置 EK_label.text = "动 能=" + str("%.2f" % EK) # 设置动能标签显示内容 EPE_label.pos = vector(EK_label.pos.x + 0.0, EK_label.pos.y - 0.2, EK_label.pos.z) # 设置弹性势能标签位置 EPE_label.text = "弹性势能=" + str("%.2f" % EPE) # 设置弹性势能标签显示内容 EPH_label.pos = vector(ball1.pos.x + 0.5, ball1.pos.y - 0.1, ball1.pos.z) # 设置弹性势能标签位置 EPH_label.text = "重力势能=" + str("%.2f" % EPH) # 设置弹性势能标签显示内容 EKcurve.plot(t, EK) # 绘制动能曲线 EPEcurve.plot(t, EPE) # 绘制弹性势能曲线 EPHcurve.plot(t, EPH) # 绘制重力势能曲线 Ecurve.plot(t, E) # 绘制系统机械能曲线 EEcurve.plot(t, EE) # 绘制机械能曲线 Vcurve.plot(t, ball1.v.y) # 绘制速度曲线 Acurve.plot(t, ball1.a.y) # 绘制加速度曲线 t = t + dt # 迭代时间
结果:
运行会弹出到浏览器显示