前言
[youbanshan]
原创文章,转载引用请务必注明链接,水平有限,如有疏漏,欢迎交流指正。
文章如有更新请访问 DFRobot社区。
我们约定:主板 指 MCU 部分,上位机 指运行 Klippy 的 MPU Linux 部分。
看过前文 Klipper 温控风扇以及电源管理(部分) 的朋友,一定了解到了安全关闭上位机系统的重要性,当然如果你是平日自家电脑关机靠直接拔电的壮士,下面的文章可以不用看了。
由于 Gemini 二合一主板的 MCU 和 MPU 是不是独立供电的,此外越来越多朋友的 3D 打印机为了好看,选择把上位机和主板一起封在电气箱内,通过总电源开关一起控制,所以就有了如何打完自动 安全 关机的必要性。注意,这里的安全是先关闭上位机电脑的 Linux 操作系统,再关闭总电源。
1、手动安全关机方法的优化 —— 调用 API
前文介绍过,手动关闭上位机系统有四种方式:物理关机按钮,网页关机按钮、KlipperScreen 彩色触摸屏按钮和 12864 等 LCD 屏幕菜单。
其中 使用 Klipper 监听按钮状态
和 mini12864 屏幕菜单
两种方法都需要 shell_cmd 组件,而此组件的缺点也很明显:
那么有没有什么法子不安装额外的东西,即可以实现关闭系统吗?我们上面了解到 Moonraker (下文称 mrk) API 的 machine.shutdown
方法,而且 Fluidd 网页
/KlipperScreen 按钮
关机的方法就是创建用户组 mnrkrsudo、klipperscreensudo
,执行一些系统命令不需要密码,如下所示:
复制代码 隐藏代码
fly@flygemini:~$ sudo ls /etc/sudoers.d/
020-sudo-for-moonraker 021-sudo-for-klipperscreen README
fly@flygemini:~$ sudo cat /etc/sudoers.d/020-sudo-for-moonraker#####Defaults!/usr/bin/apt-get env_keep +="DEBIAN_FRONTEND"
Cmnd_Alias REBOOT = /sbin/shutdown -r now, /bin/systemctl "reboot"
Cmnd_Alias SHUTDOWN = /sbin/shutdown now, /sbin/shutdown -h now, /bin/systemctl "poweroff"
Cmnd_Alias APT = /usr/bin/apt-get
Cmnd_Alias SYSTEMCTL = /bin/systemctl%mnrkrsudo ALL=(ALL) NOPASSWD: REBOOT, SHUTDOWN, APT, SYSTEMCTL
1.1 Klipper 全家桶 API 介绍
我们常见的有 Klipper API Server、Moonraker Client API ,具体可以查看链接内文档,而其中的 machine.shutdown 就是属于 mrk api 。由此 mrk client 可以调用 klippy 提供的 API,同时可以被用户调用其 api。那么 klippy 可以调用 mrk api 来实现执行关机命令吗?也是可以的,还记得之前我们从 Klipper 内关闭打印机电源的示例吗,其有一个命令:action_call_remote_method
,查看 Klipper 文档,是这么说的:
action_call_remote_method(method_name)
: Calls a method registered by a remote client. If the method takes parameters they should be provided via keyword arguments, ie: action_call_remote_method("print_stuff", my_arg="hello_world")

意思就是除了上面两种 API 之外,Moonraker 还可以在 Klippy 那注册一个方法,告诉它(Klippy):我(Mrk)这里有此方法,可以被调用。

我们以已知方法(method)set_device_power
为关键词搜索 mrk 源码,可知关键词为 register_remote_method
,再以此搜索即获得支持的方法如下:
moonraker_test
shutdown_machine
reboot_machine
process_gcode_response
process_status_update
pause_job_queue
start_job_queue
set_wled_state
set_wled
publish_mqtt_topic
paneldue_beep
set_device_power
至此我们找到了想要的两个可以被 Klipper 调用的方法。
【更新:2022年3月13日】
笔者测试时还没有相关文档,2022-02-26 官方更新了 此部分文档 ,并补充了注意事项,建议阅读。虽然如此,我们查找答案的方法还是有记录借鉴意义的。
1.2 调用 Method
实现关机
物理关机按钮:
复制代码 隐藏代码
[gcode_macro SHUTDOWN]gcode: {action_call_remote_method("shutdown_machine")}[gcode_button poweroff_button]pin: host:gpiorelease_gcode: SHUTDOWN
测试通过,控制台输入 SHUTDOWN
或者被调用即可以实现关闭系统指令。
12864 屏幕菜单关机:
复制代码 隐藏代码
[menu __main __poweroff]type: listenable: {not printer.idle_timeout.state == "Printing"}name: PowerOff[menu __main __poweroff __no]type: commandname: NOenable: {not printer.idle_timeout.state == "Printing"}gcode: {menu.back()}
[menu __main __poweroff __yes]type: commandname: YESenable: {not printer.idle_timeout.state == "Printing"}gcode: SHUTDOWN
2、 传统打完关机方案
我们先说说传统的打完关机功能,适用于 【上位机独立供电的情况】,多数朋友借助原来 Marlin 上用的 打完关机模块
,或者使用 智能插座
,我们说说各自的优缺点:

2.1 打完关机模块
优点:
缺点:
接线麻烦
价格较高 (79 + 9元)
为了安全关闭上位机系统,需要上位机独立供电:
示例如下:
复制代码 隐藏代码
[output_pin mks_pwc]pin: PS_ONpwm: Falsevalue: 1shutdown_value: 0[gcode_macro M81]description: PowerOffgcode: M84 SET_PIN PIN=mks_pwc VALUE=0[gcode_macro M81]gcode: {action_call_remote_method("set_device_power",
device="printer",
state="off")}[power printer]type: gpiopin: gpio26off_when_shutdown: Trueinitial_state: off[delayed_gcode delayed_printer_off]initial_duration: 0.gcode: {% if printer.idle_timeout.state == "Idle" %}
M81 {% endif %}
[idle_timeout]gcode: M84 TURN_OFF_HEATERS UPDATE_DELAYED_GCODE ID=delayed_printer_off DURATION=60timeout: 360
2.2 智能插座
优点:
缺点:
使用方法有以下几种,各有其不足:
预估打印完成时间定时关机 —— 不准确
使用具有电量检测功能的插座,当打印机处于低耗电时,认为打印完成,实现关机 —— 相比准确,成本提高
使用 Home Assistant 等智能家居系统,Klipper 打印完成后,调用 Moonraker 向 HA 发送关闭智能插座命令 —— 准确,但是需要 HA
其他用法欢迎补充。前两种方法自己从 APP 里设置即可,第三种方法我们下面一起介绍。
还没有评论,来说两句吧...