Update 6.0.0

This commit is contained in:
Cyril 2024-05-01 16:10:07 +02:00
parent bb0b7539a0
commit c8db437b79
63 changed files with 3667 additions and 737 deletions

View file

@ -8,7 +8,6 @@ timeout: 2
verbose: False
[gcode_macro BEEP]
gcode:
RUN_SHELL_COMMAND CMD=beep
RUN_SHELL_COMMAND CMD=beep
description: Play a sound
gcode:
RUN_SHELL_COMMAND CMD=beep

View file

@ -0,0 +1,43 @@
########################################
# Camera Settings Control
########################################
[gcode_shell_command v4l2-ctl]
command: v4l2-ctl
timeout: 5.0
verbose: True
[gcode_macro CAM_SETTINGS]
description: Show current camera settings
gcode:
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 -l"
[gcode_macro CAM_BRIGHTNESS]
description: min=50 / max=160
gcode:
{% set brightness = params.BRIGHTNESS|default(100) %}
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 --set-ctrl brightness="{brightness}
[gcode_macro CAM_CONTRAST]
description: min=50 / max=160
gcode:
{% set contrast = params.CONTRAST|default(50) %}
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 --set-ctrl contrast="{contrast}
[gcode_macro CAM_SATURATION]
description: min=50 / max=160
gcode:
{% set saturation = params.SATURATION|default(56) %}
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 --set-ctrl saturation="{saturation}
[gcode_macro CAM_HUE]
description: min=50 / max=160
gcode:
{% set hue = params.HUE|default(50) %}
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 --set-ctrl hue="{hue}
[gcode_macro CAM_WHITE_BALANCE_TEMPERATURE_AUTO]
description: disable=0 / enable=1
gcode:
{% set white_balance_temperature_auto = params.WHITE_BALANCE_TEMPERATURE_AUTO|default(1) %}
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 --set-ctrl white_balance_temperature_auto="{white_balance_temperature_auto}

View file

@ -25,6 +25,7 @@ timeout: 5.0
verbose: True
[gcode_macro CAM_SETTINGS]
description: Show current camera settings
gcode:
RUN_SHELL_COMMAND CMD=v4l2-ctl PARAMS="-d /dev/video4 -l"

553
files/fixes/gcode_3v3.py Normal file
View file

@ -0,0 +1,553 @@
# Parse gcode commands
#
# Copyright (C) 2016-2021 Kevin O'Connor <kevin@koconnor.net>
#
# This file may be distributed under the terms of the GNU GPLv3 license.
import os, re, logging, collections, shlex
from extras.tool import reportInformation
class CommandError(Exception):
pass
Coord = collections.namedtuple('Coord', ('x', 'y', 'z', 'e'))
class GCodeCommand:
error = CommandError
def __init__(self, gcode, command, commandline, params, need_ack):
self._command = command
self._commandline = commandline
self._params = params
self._need_ack = need_ack
# Method wrappers
self.respond_info = gcode.respond_info
self.respond_raw = gcode.respond_raw
def get_command(self):
return self._command
def get_commandline(self):
return self._commandline
def get_command_parameters(self):
return self._params
def get_raw_command_parameters(self):
command = self._command
if command.startswith("M117 ") or command.startswith("M118 "):
command = command[:4]
rawparams = self._commandline
urawparams = rawparams.upper()
if not urawparams.startswith(command):
rawparams = rawparams[urawparams.find(command):]
end = rawparams.rfind('*')
if end >= 0:
rawparams = rawparams[:end]
rawparams = rawparams[len(command):]
if rawparams.startswith(' '):
rawparams = rawparams[1:]
return rawparams
def ack(self, msg=None):
if not self._need_ack:
return False
ok_msg = "ok"
if msg:
ok_msg = "ok %s" % (msg,)
self.respond_raw(ok_msg)
self._need_ack = False
return True
# Parameter parsing helpers
class sentinel: pass
def get(self, name, default=sentinel, parser=str, minval=None, maxval=None,
above=None, below=None):
value = self._params.get(name)
if value is None:
if default is self.sentinel:
raise self.error("""{"code":"key251", "msg":"Error on '%s': missing %s", "values":["%s",%s"]}"""
% (self._commandline, name, self._commandline, name))
return default
try:
value = parser(value)
except:
raise self.error(
"""{"code":"key171", "msg": "Unable to parse '%s' as a %s", "values": ["%s", "%s"]}""" % (self._commandline, value,
self._commandline, value)
)
if minval is not None and value < minval:
raise self.error("""{"code":"key252","msg":"Error on '%s': %s must have minimum of %s","values":["%s","%s","%s"]}"""
% (self._commandline, name, minval, self._commandline, name, minval))
if maxval is not None and value > maxval:
raise self.error("""{"code":"key253", "msg":"Error on '%s': %s must have maximumof %s", "values":["%s","%s","%s"]}"""
% (self._commandline, name, maxval, self._commandline, name, maxval))
if above is not None and value <= above:
raise self.error("""{"code":"key254", "msg":"Error on '%s': %s must be above %s", "values":["%s","%s","%s"]}"""
% (self._commandline, name, above, self._commandline, name, above))
if below is not None and value >= below:
raise self.error("""{"code":"key255", "msg":"Error on '%s': %s must be below %s", "values":["%s","%s","%s"]}"""
% (self._commandline, name, below, self._commandline, name, below))
return value
def get_int(self, name, default=sentinel, minval=None, maxval=None):
return self.get(name, default, parser=int, minval=minval, maxval=maxval)
def get_float(self, name, default=sentinel, minval=None, maxval=None,
above=None, below=None):
return self.get(name, default, parser=float, minval=minval,
maxval=maxval, above=above, below=below)
# Parse and dispatch G-Code commands
class GCodeDispatch:
error = CommandError
Coord = Coord
def __init__(self, printer):
self.printer = printer
self.is_fileinput = not not printer.get_start_args().get("debuginput")
printer.register_event_handler("klippy:ready", self._handle_ready)
printer.register_event_handler("klippy:shutdown", self._handle_shutdown)
printer.register_event_handler("klippy:disconnect",
self._handle_disconnect)
# Command handling
self.is_printer_ready = False
self.mutex = printer.get_reactor().mutex()
self.output_callbacks = []
self.base_gcode_handlers = self.gcode_handlers = {}
self.ready_gcode_handlers = {}
self.mux_commands = {}
self.gcode_help = {}
# Register commands needed before config file is loaded
handlers = ['M110', 'M112', 'M115',
'RESTART', 'FIRMWARE_RESTART', 'ECHO', 'STATUS', 'HELP']
for cmd in handlers:
func = getattr(self, 'cmd_' + cmd)
desc = getattr(self, 'cmd_' + cmd + '_help', None)
self.register_command(cmd, func, True, desc)
self.last_temperature_info = "/usr/data/creality/userdata/config/temperature_info.json"
self.exclude_object_info = "/usr/data/creality/userdata/config/exclude_object_info.json"
def is_traditional_gcode(self, cmd):
# A "traditional" g-code command is a letter and followed by a number
try:
cmd = cmd.upper().split()[0]
val = float(cmd[1:])
return cmd[0].isupper() and cmd[1].isdigit()
except:
return False
def register_command(self, cmd, func, when_not_ready=False, desc=None):
if func is None:
old_cmd = self.ready_gcode_handlers.get(cmd)
if cmd in self.ready_gcode_handlers:
del self.ready_gcode_handlers[cmd]
if cmd in self.base_gcode_handlers:
del self.base_gcode_handlers[cmd]
return old_cmd
if cmd in self.ready_gcode_handlers:
raise self.printer.config_error(
"""{"code":"key57", "msg":"gcode command %s already registered", "values": ["%s"]}""" % (cmd, cmd))
if not self.is_traditional_gcode(cmd):
origfunc = func
func = lambda params: origfunc(self._get_extended_params(params))
self.ready_gcode_handlers[cmd] = func
if when_not_ready:
self.base_gcode_handlers[cmd] = func
if desc is not None:
self.gcode_help[cmd] = desc
def register_mux_command(self, cmd, key, value, func, desc=None):
prev = self.mux_commands.get(cmd)
if prev is None:
handler = lambda gcmd: self._cmd_mux(cmd, gcmd)
self.register_command(cmd, handler, desc=desc)
self.mux_commands[cmd] = prev = (key, {})
prev_key, prev_values = prev
if prev_key != key:
raise self.printer.config_error(
"""{"code":"key58", "msg":"mux command %s %s %s may have only one key (%s)", "values": ["%s", "%s", "%s", "%s"]}""" % (
cmd, key, value, prev_key, cmd, key, value, prev_key))
if value in prev_values:
raise self.printer.config_error(
"""{"code":"key59", "msg":"mux command %s %s %s already registered (%s)", "values": ["%s", "%s", "%s", "%s"]}""" % (
cmd, key, value, prev_values, cmd, key, value, prev_values))
prev_values[value] = func
def get_command_help(self):
return dict(self.gcode_help)
def register_output_handler(self, cb):
self.output_callbacks.append(cb)
def _handle_shutdown(self):
if not self.is_printer_ready:
return
self.is_printer_ready = False
self.gcode_handlers = self.base_gcode_handlers
self._respond_state("Shutdown")
def _handle_disconnect(self):
self._respond_state("Disconnect")
def _handle_ready(self):
self.is_printer_ready = True
self.gcode_handlers = self.ready_gcode_handlers
self._respond_state("Ready")
# Parse input into commands
args_r = re.compile('([A-Z_]+|[A-Z*/])')
def _process_commands(self, commands, need_ack=True):
for line in commands:
# Ignore comments and leading/trailing spaces
line = origline = line.strip()
cpos = line.find(';')
if cpos >= 0:
line = line[:cpos]
# Break line into parts and determine command
parts = self.args_r.split(line.upper())
numparts = len(parts)
cmd = ""
if numparts >= 3 and parts[1] != 'N':
cmd = parts[1] + parts[2].strip()
elif numparts >= 5 and parts[1] == 'N':
# Skip line number at start of command
cmd = parts[3] + parts[4].strip()
# Build gcode "params" dictionary
params = { parts[i]: parts[i+1].strip()
for i in range(1, numparts, 2) }
gcmd = GCodeCommand(self, cmd, origline, params, need_ack)
# Invoke handler for command
handler = self.gcode_handlers.get(cmd, self.cmd_default)
try:
handler(gcmd)
except self.error as e:
self._respond_error(str(e))
self.printer.send_event("gcode:command_error")
if not need_ack:
raise
except:
msg = """{"code":"key60", "msg":"Internal error on command:%s", "values": ["%s"]}""" % (cmd, cmd)
logging.exception(msg)
self.printer.invoke_shutdown(msg)
self._respond_error(msg)
if not need_ack:
raise
gcmd.ack()
if line.startswith("G1") or line.startswith("G0"):
pass
elif line.startswith("M104"):
self.set_temperature("extruder", line)
elif line.startswith("M140"):
self.set_temperature("bed", line)
elif line.startswith("M109"):
self.set_temperature("extruder", line)
elif line.startswith("M190"):
self.set_temperature("bed", line)
elif line.startswith("EXCLUDE_OBJECT_DEFINE") or line.startswith("EXCLUDE_OBJECT NAME"):
self.record_exclude_object_info(line)
def set_temperature(self, key, value):
import json
try:
# configfile = self.printer.lookup_object('configfile')
# print_stats = self.printer.load_object(configfile, 'print_stats')
temp_value = float(value.strip("\n").split("S")[-1])
# if key == "extruder" and print_stats and print_stats.state == "printing":
# if temp_value >= 240:
# self.run_script_from_command("M107 P1")
# logging.info("Fan Off SET M107 P1")
# elif temp_value >= 170:
# self.run_script_from_command("M106 P1 S255")
# logging.info("Fan On SET M106 P1 S255")
if key == "extruder" and temp_value < 170:
return
if not os.path.exists(self.last_temperature_info):
from subprocess import call
call("touch %s" % self.last_temperature_info, shell=True)
with open(self.last_temperature_info, "r") as f:
ret = f.read()
if len(ret) > 0:
ret = json.loads(ret)
else:
ret = {}
ret[key] = temp_value
with open(self.last_temperature_info, "w") as f:
f.write(json.dumps(ret))
f.flush()
except Exception as err:
logging.error("set_temperature error: %s" % err)
def record_exclude_object_info(self, line):
import json
try:
if not os.path.exists(self.exclude_object_info):
with open(self.exclude_object_info, "w") as f:
data = {}
data["EXCLUDE_OBJECT_DEFINE"] = []
data["EXCLUDE_OBJECT"] = []
f.write(json.dumps(data))
f.flush()
with open(self.exclude_object_info, "r") as f:
ret = f.read()
if len(ret) > 0:
ret = eval(ret)
else:
ret = {}
if line.startswith("EXCLUDE_OBJECT_DEFINE"):
if line not in ret["EXCLUDE_OBJECT_DEFINE"]:
ret["EXCLUDE_OBJECT_DEFINE"].append(line)
elif line.startswith("EXCLUDE_OBJECT NAME"):
if line not in ret["EXCLUDE_OBJECT"]:
ret["EXCLUDE_OBJECT"].append(line)
with open(self.exclude_object_info, "w") as f:
f.write(json.dumps(ret))
f.flush()
except Exception as err:
logging.error("record_exclude_object_info error: %s" % err)
def run_script_from_command(self, script):
self._process_commands(script.split('\n'), need_ack=False)
def run_script(self, script):
with self.mutex:
self._process_commands(script.split('\n'), need_ack=False)
def get_mutex(self):
return self.mutex
def create_gcode_command(self, command, commandline, params):
return GCodeCommand(self, command, commandline, params, False)
# Response handling
def respond_raw(self, msg):
for cb in self.output_callbacks:
cb(msg)
def respond_info(self, msg, log=True):
if log:
logging.info(msg)
lines = [l.strip() for l in msg.strip().split('\n')]
self.respond_raw("// " + "\n// ".join(lines))
def _respond_error(self, msg):
import time
from extras.tool import reportInformation
try:
v_sd = self.printer.lookup_object('virtual_sdcard')
if v_sd.print_id and "key" in msg and re.findall('key(\d+)', msg) and v_sd.cur_print_data:
v_sd.update_print_history_info(only_update_status=True, state="error", error_msg=eval(msg))
if os.path.exists("/tmp/camera_main"):
reportInformation("key608", data={"print_id": v_sd.print_id})
time.sleep(0.2)
v_sd.print_id = ""
reportInformation("key701", data=v_sd.cur_print_data)
v_sd.cur_print_data = {}
except Exception as err:
logging.error(err)
try:
if "key" in msg and re.findall('key(\d+)', msg):
reportInformation(msg)
except Exception as err:
logging.error(err)
logging.warning(msg)
lines = msg.strip().split('\n')
if len(lines) > 1:
self.respond_info("\n".join(lines), log=False)
self.respond_raw('!! %s' % (lines[0].strip(),))
if self.is_fileinput:
self.printer.request_exit('error_exit')
def _respond_state(self, state):
self.respond_info("Klipper state: %s" % (state,), log=False)
# Parameter parsing helpers
extended_r = re.compile(
r'^\s*(?:N[0-9]+\s*)?'
r'(?P<cmd>[a-zA-Z_][a-zA-Z0-9_]+)(?:\s+|$)'
r'(?P<args>[^#*;]*?)'
r'\s*(?:[#*;].*)?$')
def _get_extended_params(self, gcmd):
m = self.extended_r.match(gcmd.get_commandline())
if m is None:
raise self.error("""{"code":"key513", "msg": "Malformed command '%s'", "values": ["%s"]}""" % (gcmd.get_commandline(), gcmd.get_commandline()))
eargs = m.group('args')
try:
eparams = [earg.split('=', 1) for earg in shlex.split(eargs)]
eparams = { k.upper(): v for k, v in eparams }
gcmd._params.clear()
gcmd._params.update(eparams)
return gcmd
except ValueError as e:
raise self.error("""{"code":"key514", "msg": "Malformed command args '%s'", "values": ["%s"]}""" % (gcmd.get_commandline(), str(e)))
# G-Code special command handlers
def cmd_default(self, gcmd):
cmd = gcmd.get_command()
if cmd == 'M105':
# Don't warn about temperature requests when not ready
gcmd.ack("T:0")
return
if cmd == 'M21':
# Don't warn about sd card init when not ready
return
if not self.is_printer_ready:
raise gcmd.error(self.printer.get_state_message()[0])
return
if not cmd:
cmdline = gcmd.get_commandline()
if cmdline:
logging.debug(cmdline)
return
if cmd.startswith("M117 ") or cmd.startswith("M118 "):
# Handle M117/M118 gcode with numeric and special characters
handler = self.gcode_handlers.get(cmd[:4], None)
if handler is not None:
handler(gcmd)
return
elif cmd in ['M140', 'M104'] and not gcmd.get_float('S', 0.):
# Don't warn about requests to turn off heaters when not present
return
elif cmd == 'M107' or (cmd == 'M106' and (
not gcmd.get_float('S', 1.) or self.is_fileinput)):
# Don't warn about requests to turn off fan when fan not present
return
gcmd.respond_info("""{"code":"key61, "msg":"Unknown command:%s", "values": ["%s"]}""" % (cmd, cmd))
def get_muxcmd(self, cmdkey):
if cmdkey in self.mux_commands:
key, values = self.mux_commands[cmdkey]
return values
return None
def _cmd_mux(self, command, gcmd):
key, values = self.mux_commands[command]
if None in values:
key_param = gcmd.get(key, None)
else:
key_param = gcmd.get(key)
if key_param not in values:
raise gcmd.error("""{"code":"key69", "msg": "The value '%s' is not valid for %s", "values": ["%s", "%s"]}"""
% (key_param, key, key_param, key))
values[key_param](gcmd)
# Low-level G-Code commands that are needed before the config file is loaded
def cmd_M110(self, gcmd):
# Set Current Line Number
pass
def cmd_M112(self, gcmd):
# Emergency Stop
self.printer.invoke_shutdown("""{"code":"key70", "msg": "Shutdown due to M112 command", "values": []}""")
def cmd_M115(self, gcmd):
# Get Firmware Version and Capabilities
software_version = self.printer.get_start_args().get('software_version')
kw = {"FIRMWARE_NAME": "Klipper", "FIRMWARE_VERSION": software_version}
msg = " ".join(["%s:%s" % (k, v) for k, v in kw.items()])
did_ack = gcmd.ack(msg)
if not did_ack:
gcmd.respond_info(msg)
def request_restart(self, result):
if self.is_printer_ready:
toolhead = self.printer.lookup_object('toolhead')
print_time = toolhead.get_last_move_time()
if result == 'exit':
logging.info("Exiting (print time %.3fs)" % (print_time,))
self.printer.send_event("gcode:request_restart", print_time)
toolhead.dwell(0.500)
toolhead.wait_moves()
self.printer.request_exit(result)
cmd_RESTART_help = "Reload config file and restart host software"
def cmd_RESTART(self, gcmd):
self.request_restart('restart')
cmd_FIRMWARE_RESTART_help = "Restart firmware, host, and reload config"
def cmd_FIRMWARE_RESTART(self, gcmd):
self.request_restart('firmware_restart')
def cmd_ECHO(self, gcmd):
gcmd.respond_info(gcmd.get_commandline(), log=False)
cmd_STATUS_help = "Report the printer status"
def cmd_STATUS(self, gcmd):
if self.is_printer_ready:
self._respond_state("Ready")
return
msg = self.printer.get_state_message()[0]
msg = msg.rstrip() + "\nKlipper state: Not ready"
raise gcmd.error(msg)
cmd_HELP_help = "Report the list of available extended G-Code commands"
def cmd_HELP(self, gcmd):
cmdhelp = []
if not self.is_printer_ready:
cmdhelp.append("""{"code":"key72", "msg": "Printer is not ready - not all commands available.\n""")
cmdhelp.append("Available extended commands:")
for cmd in sorted(self.gcode_handlers):
if cmd in self.gcode_help:
cmdhelp.append("%-10s: %s" % (cmd, self.gcode_help[cmd]))
gcmd.respond_info("\n".join(cmdhelp), log=False)
# Support reading gcode from a pseudo-tty interface
class GCodeIO:
def __init__(self, printer):
self.printer = printer
printer.register_event_handler("klippy:ready", self._handle_ready)
printer.register_event_handler("klippy:shutdown", self._handle_shutdown)
self.gcode = printer.lookup_object('gcode')
self.gcode_mutex = self.gcode.get_mutex()
self.fd = printer.get_start_args().get("gcode_fd")
self.reactor = printer.get_reactor()
self.is_printer_ready = False
self.is_processing_data = False
self.is_fileinput = not not printer.get_start_args().get("debuginput")
self.pipe_is_active = True
self.fd_handle = None
if not self.is_fileinput:
self.gcode.register_output_handler(self._respond_raw)
self.fd_handle = self.reactor.register_fd(self.fd,
self._process_data)
self.partial_input = ""
self.pending_commands = []
self.bytes_read = 0
self.input_log = collections.deque([], 50)
def _handle_ready(self):
self.is_printer_ready = True
if self.is_fileinput and self.fd_handle is None:
self.fd_handle = self.reactor.register_fd(self.fd,
self._process_data)
def _dump_debug(self):
out = []
out.append("Dumping gcode input %d blocks" % (len(self.input_log),))
for eventtime, data in self.input_log:
out.append("Read %f: %s" % (eventtime, repr(data)))
logging.info("\n".join(out))
def _handle_shutdown(self):
if not self.is_printer_ready:
return
self.is_printer_ready = False
self._dump_debug()
if self.is_fileinput:
self.printer.request_exit('error_exit')
m112_r = re.compile('^(?:[nN][0-9]+)?\s*[mM]112(?:\s|$)')
def _process_data(self, eventtime):
# Read input, separate by newline, and add to pending_commands
try:
data = str(os.read(self.fd, 4096).decode())
except (os.error, UnicodeDecodeError):
logging.exception("Read g-code")
return
self.input_log.append((eventtime, data))
self.bytes_read += len(data)
lines = data.split('\n')
lines[0] = self.partial_input + lines[0]
self.partial_input = lines.pop()
pending_commands = self.pending_commands
pending_commands.extend(lines)
self.pipe_is_active = True
# Special handling for debug file input EOF
if not data and self.is_fileinput:
if not self.is_processing_data:
self.reactor.unregister_fd(self.fd_handle)
self.fd_handle = None
self.gcode.request_restart('exit')
pending_commands.append("")
# Handle case where multiple commands pending
if self.is_processing_data or len(pending_commands) > 1:
if len(pending_commands) < 20:
# Check for M112 out-of-order
for line in lines:
if self.m112_r.match(line) is not None:
self.gcode.cmd_M112(None)
if self.is_processing_data:
if len(pending_commands) >= 20:
# Stop reading input
self.reactor.unregister_fd(self.fd_handle)
self.fd_handle = None
return
# Process commands
self.is_processing_data = True
while pending_commands:
self.pending_commands = []
with self.gcode_mutex:
self.gcode._process_commands(pending_commands)
pending_commands = self.pending_commands
self.is_processing_data = False
if self.fd_handle is None:
self.fd_handle = self.reactor.register_fd(self.fd,
self._process_data)
def _respond_raw(self, msg):
if self.pipe_is_active:
try:
os.write(self.fd, (msg+"\n").encode())
# if 'key506' not in msg and 'key507' not in msg and 'key3"' not in msg and "key" in msg:
# reportInformation(msg)
except os.error:
logging.exception("Write g-code response")
self.pipe_is_active = False
def stats(self, eventtime):
return False, "gcodein=%d" % (self.bytes_read,)
def add_early_printer_objects(printer):
printer.add_object('gcode', GCodeDispatch(printer))
printer.add_object('gcode_io', GCodeIO(printer))

View file

@ -1,26 +1,29 @@
#!/bin/sh
start_git_backup() {
echo "Info: Starting Git Backup..."
/usr/data/helper-script/files/git-backup/git-backup.sh -b "$BRANCH" -t "$IFS" -g origin > /dev/null 2>&1 &
}
case "$1" in
start)
echo "Starting Git Backup..."
/usr/data/helper-script/files/git-backup/git-backup.sh -b "$BRANCH" -t "$IFS" -g origin & > /dev/null
start_git_backup
;;
stop)
echo "Stopping Git Backup..."
pkill Git-Backup
pkill inotifywait
pkill git-backup.sh
echo "Info: Stopping Git Backup..."
killall -q git-backup.sh
killall -q inotifywait
;;
restart)
echo "Restarting Git Backup..."
pkill Git-Backup
pkill inotifywait
echo "Info: Restarting Git Backup..."
$0 stop
sleep 1
/usr/data/helper-script/files/git-backup/git-backup.sh -b "$BRANCH" -t "$IFS" -g origin & > /dev/null
start_git_backup
;;
*)
echo "Usage: $0 {start|stop|restart}"
exit 1
;;
esac
exit 0
exit 0

View file

@ -20,16 +20,52 @@ timeout: 600.0
verbose: true
[gcode_macro GIT_BACKUP_STOP]
[gcode_macro _GIT_STOP]
description: Stop pushing to GitHub until manually resumed
gcode:
RUN_SHELL_COMMAND CMD=Backup_Stop
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _GIT_PAUSE]
description: Stop pushing to GitHub until next reboot or until manually resumed
gcode:
RUN_SHELL_COMMAND CMD=Backup_Pause
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _GIT_RESUME]
description: Resume pushing to GitHub
gcode:
RUN_SHELL_COMMAND CMD=Backup_Resume
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro GIT_BACKUP_STOP]
description: Stop pushing to GitHub until manually resumed
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Git Backup"
RESPOND TYPE=command MSG="action:prompt_text Do you want to stop pushing to GitHub until manually resumed?"
RESPOND TYPE=command MSG="action:prompt_footer_button NO|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button YES|_GIT_STOP|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro GIT_BACKUP_PAUSE]
description: Stop pushing to GitHub until next reboot or until manually resumed
gcode:
RUN_SHELL_COMMAND CMD=Backup_Pause
RESPOND TYPE=command MSG="action:prompt_begin Git Backup"
RESPOND TYPE=command MSG="action:prompt_text Do you want to stop pushing to GitHub until next reboot or until manually resumed?"
RESPOND TYPE=command MSG="action:prompt_footer_button NO|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button YES|_GIT_PAUSE|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro GIT_BACKUP_RESUME]
description: Resume pushing to GitHub
gcode:
RUN_SHELL_COMMAND CMD=Backup_Resume
RESPOND TYPE=command MSG="action:prompt_begin Git Backup"
RESPOND TYPE=command MSG="action:prompt_text Do you want to resume pushing to GitHub?"
RESPOND TYPE=command MSG="action:prompt_footer_button NO|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button YES|_GIT_RESUME|primary"
RESPOND TYPE=command MSG="action:prompt_show"

View file

@ -7,37 +7,12 @@
# - Dominik D. Geyer
# - Phil Thompson
# - Dave Musicant
#
# Edited to work on busybox ash shell, specifically the Creality K1 & K1Max
#############################################################################
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/>.
#############################################################################
#
# Idea and original code taken from http://stackoverflow.com/a/965274
# original work by Lester Buck
# (but heavily modified by now)
#
# Requires the command 'inotifywait' to be available, which is part of
# the inotify-tools (See https://github.com/rvoicilas/inotify-tools ),
# and (obviously) git.
# Will check the availability of both commands using the `which` command
# and will abort if either command (or `which`) is not found.
#
# - Guislain Cyril
white=`echo -en "\033[m"`
yellow=`echo -en "\033[1;33m"`
green=`echo -en "\033[01;32m"`
darkred=`echo -en "\033[31m"`
INSTALL=0
PAUSE=0
@ -49,7 +24,7 @@ TARGET=""
EVENTS="${EVENTS:-close_write,move,move_self,delete,create,modify}"
SLEEP_TIME=5
DATE_FMT="+%d-%m-%Y (%H:%M:%S)"
COMMITMSG="Auto-commit on %d by Git Backup"
COMMITMSG="Auto-commit by Git Backup"
SKIP_IF_MERGING=0
# Function to print script help
@ -110,61 +85,161 @@ if [ "$PAUSE" = 1 ]; then
exit 0
elif [ "$STOP" = 1 ]; then
echo "Info: Stopping automatic backups until manually restarted..."
mv /etc/init.d/S52Git-Backup /etc/init.d/disabled.S52Git-Backup
if [ -f mv /etc/init.d/S52Git-Backup ];then
mv /etc/init.d/S52Git-Backup /etc/init.d/disabled.S52Git-Backup
fi
/etc/init.d/S52Git-Backup stop
exit 0
elif [ "$RESUME" = 1 ]; then
echo "Info: Resuming automatic backups..."
mv /etc/init.d/disabled.S52Git-Backup /etc/init.d/S52Git-Backup
if [ -f /etc/init.d/disabled.S52Git-Backup ];then
mv /etc/init.d/disabled.S52Git-Backup /etc/init.d/S52Git-Backup
fi
/etc/init.d/S52Git-Backup start
exit 0
elif [ "$INSTALL" = 1 ]; then
# Install required packages using opkg
if [ -f /opt/bin/opkg ]; then
/opt/bin/opkg update
/opt/bin/opkg install inotifywait procps-ng-pkill
/opt/bin/opkg install inotifywait
else
echo "Error: opkg package manager not found. Please install Entware."
echo
echo "${white}${darkred} ✗ opkg package manager not found. Please install Entware.${white}"
echo
exit 1
fi
# Prompt user for configuration
echo "${white}"
read -p " Please enter your ${green}GitHub username${white} and press Enter: ${yellow}" USER_NAME
while [ -z "$USER_NAME" ]; do
echo "${white}"
echo "${darkred} ✗ Invalid GitHub username!${white}"
echo
read -p " Please enter your ${green}GitHub username${white} and press Enter: ${yellow}" USER_NAME
done
valid_email=false
while [ "$valid_email" != true ]; do
echo "${white}"
read -p " Please enter your ${green}GitHub email address${white} and press Enter: ${yellow}" USER_MAIL
echo "$USER_MAIL" | grep -E -q "^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$"
if [ $? -ne 0 ]; then
echo "${white}"
echo "${darkred} ✗ Invalid email address!${white}"
else
valid_email=true
fi
done
echo "${white}"
read -p " Please enter your ${green}GitHub repository name${white} and press Enter: ${yellow}" REPO_NAME
while [ -z "$REPO_NAME" ]; do
echo "${white}"
echo "${darkred} ✗ Invalid GitHub repository name!${white}"
echo
read -p " Please enter your ${green}GitHub repository name${white} and press Enter: ${yellow}" REPO_NAME
done
echo "${white}"
read -p " Please enter your ${green}GitHub branch name${white} and press Enter: ${yellow}" REPO_BRANCH
while [ -z "$REPO_BRANCH" ]; do
echo "${white}"
echo "${darkred} ✗ Invalid GitHub branch name!${white}"
echo
read -p " Please enter your ${green}GitHub branch name${white} and press Enter: ${yellow}" REPO_BRANCH
done
echo "${white}"
read -p " Please enter your ${green}GitHub personal access token${white} and press Enter: ${yellow}" GITHUB_TOKEN
while [ -z "$GITHUB_TOKEN" ]; do
echo "${white}"
echo "${darkred} ✗ Invalid GitHub personal access token!${white}"
echo
read -p " Please enter your ${green}GitHub personal access token${white} and press Enter: ${yellow}" GITHUB_TOKEN
done
echo "${white}"
# Prompt user to select folders to be watched
# Folder to be watched
IFS=/usr/data/printer_data/config
# Connect config directory to github
cd "$IFS" || exit
git config --global user.name "$USER_NAME"
git config --global user.email "$USER_MAIL"
git init
git remote add origin "https://$USER_NAME:$GITHUB_TOKEN@github.com/$USER_NAME/$REPO_NAME.git"
git checkout -b "$REPO_BRANCH"
git add .
git commit -m "Initial Backup"
git push -u origin "$REPO_BRANCH"
push_repo=$(git push -u origin "$REPO_BRANCH" 2>&1)
if echo "$push_repo" | grep -q "fatal: remote origin already exists"; then
echo
rm -rf /usr/data/printer_data/config/.git
killall -q inotifywait >/dev/null 2>&1
/opt/bin/opkg --autoremove remove inotifywait >/dev/null 2>&1
echo "${white}${darkred} ✗ A branch named $REPO_BRANCH already exists!"
echo " Use another branch name or clean your repo and restart Git Backup installation.${white}"
echo
exit 0
elif echo "$push_repo" | grep -q "error: failed to push some refs to"; then
echo
rm -rf /usr/data/printer_data/config/.git
killall -q inotifywait >/dev/null 2>&1
/opt/bin/opkg --autoremove remove inotifywait >/dev/null 2>&1
echo "${white}${darkred} ✗ Your repository already contains commits and files cannot be merged!"
echo " Please clean your repo and restart Git Backup installation.${white}"
echo
exit 0
elif echo "$push_repo" | grep -q "remote: Repository not found"; then
echo
rm -rf /usr/data/printer_data/config/.git
killall -q inotifywait >/dev/null 2>&1
/opt/bin/opkg --autoremove remove inotifywait >/dev/null 2>&1
echo "${white}${darkred} ✗ Your repository was not found!"
echo " Check your provided information and restart Git Backup installation.${white}"
echo
exit 0
elif echo "$push_repo" | grep -q "fatal: Authentication failed"; then
echo
rm -rf /usr/data/printer_data/config/.git
killall -q inotifywait >/dev/null 2>&1
/opt/bin/opkg --autoremove remove inotifywait >/dev/null 2>&1
echo "${white}${darkred} ✗ Authentication failed!"
echo " Check your GitHub personal access token and restart Git Backup installation.${white}"
echo
exit 0
else
git push -u origin "$REPO_BRANCH"
fi
# Write configuration to .env file
echo "IFS=$IFS" > "$IFS/.env"
echo "GITHUB_TOKEN=$GITHUB_TOKEN" >> "$IFS/.env"
echo "REMOTE=$REPO_NAME" >> "$IFS/.env"
echo "BRANCH=$REPO_BRANCH" >> "$IFS/.env"
echo "USER=$USER_NAME" >> "$IFS/.env"
# Create .gitignore file to protect .env variables
echo ".env" > "$IFS/.gitignore"
if [ ! -d /usr/data/helper-script-backup/git-backup ]; then
mkdir -p /usr/data/helper-script-backup/git-backup
fi
ENV=/usr/data/helper-script-backup/git-backup/.env
echo "IFS=$IFS" > "$ENV"
echo "GITHUB_TOKEN=$GITHUB_TOKEN" >> "$ENV"
echo "REMOTE=$REPO_NAME" >> "$ENV"
echo "BRANCH=$REPO_BRANCH" >> "$ENV"
echo "USER=$USER_NAME" >> "$ENV"
# Insert .env to S52gitwatch.sh and move to init.d
# Insert .env to init.d
echo "Info: Copying file..."
cp -f /usr/data/helper-script/files/git-backup/S52Git-Backup /etc/init.d/S52Git-Backup
sed -i "2i source $IFS/.env" /etc/init.d/S52Git-Backup
sed -i "2i source $ENV" /etc/init.d/S52Git-Backup
echo "Info: Linking file..."
ln -sf /usr/data/helper-script/files/git-backup/git-backup.cfg /usr/data/printer_data/config/Helper-Script/git-backup.cfg
if grep -q "include Helper-Script/git-backup" /usr/data/printer_data/config/printer.cfg ; then
echo "Info: Git Backup configurations are already enabled in printer.cfg file..."
else
echo "Info: Adding Git Backup configurations in printer.cfg file..."
sed -i '/\[include printer_params\.cfg\]/a \[include Helper-Script/git-backup\.cfg\]' /usr/data/printer_data/config/printer.cfg
fi
echo "Info: Starting Git Backup service..."
chmod +x /etc/init.d/S52Git-Backup
/etc/init.d/S52Git-Backup start
/etc/init.d/S52Git-Backup start >/dev/null 2>&1
echo "Info: Restarting Klipper service..."
/etc/init.d/S55klipper_service start
echo
echo "${white}${green} ✓ Git Backup has been installed and configured successfully!${white}"
echo
exit 0
fi
@ -225,16 +300,13 @@ else
fi
if [ -d "$TARGET" ]; then # if the target is a directory
TARGETDIR=$(echo "$IN" | sed -e "s/\/*$//") # dir to CD into before using git commands: trim trailing slash, if any
# construct inotifywait-commandline
if [ "$(uname)" != "Darwin" ]; then
INW_ARGS="-qmr -e $EVENTS $TARGETDIR"
fi
GIT_ADD="git add -A ." # add "." (CWD) recursively to index
GIT_COMMIT_ARGS="-a" # add -a switch to "commit" call just to be sure
else
stderr "Error: The target is neither a regular file nor a directory."
exit 3
@ -283,7 +355,7 @@ while true; do
if [ -n "$line" ]; then
# Process changes
if [ -n "$DATE_FMT" ]; then
COMMITMSG=$(echo "$COMMITMSG" | awk -v date="$(date "$DATE_FMT")" '{gsub(/%d/, date)}1') # splice the formatted date-time into the commit message
COMMITMSG=$(echo "$COMMITMSG") # splice the formatted date-time into the commit message
fi
cd "$TARGETDIR" || {
@ -299,11 +371,10 @@ while true; do
$GIT_ADD # add file(s) to index
$GIT commit $GIT_COMMIT_ARGS -m "$COMMITMSG" # construct commit message and commit
if [ -n "$PUSH_CMD" ]; then
echo "Push command is $PUSH_CMD"
eval "$PUSH_CMD"
pkill 'inotifywait'
killall -q inotifywait
timeout
fi
fi

View file

@ -0,0 +1,33 @@
########################################
# Guppy Screen Update
########################################
[gcode_shell_command guppy_update]
command: sh /usr/data/helper-script/files/guppy-screen/guppy-update.sh
timeout: 600.0
verbose: True
[gcode_macro GUPPY_UPDATE]
description: Check for Guppy Screen Updates
gcode:
{% if printer.idle_timeout.state == "Printing" %}
RESPOND TYPE=error MSG="It's not possible to update Guppy Screen while printing!"
{% else %}
RUN_SHELL_COMMAND CMD=guppy_update
{% endif %}
[gcode_macro INPUT_SHAPER_CALIBRATION]
description: Measure X and Y Axis Resonances and Save values
gcode:
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
G28
{% endif %}
RESPOND TYPE=command MSG="Measuring X and Y Resonances..."
SHAPER_CALIBRATE
M400
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=45
CXSAVE_CONFIG

View file

@ -21,8 +21,8 @@ gcode:
[gcode_macro INPUT_SHAPER_CALIBRATION]
description: Measure X and Y Axis Resonances and Save values
gcode:
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=30
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% endif %}
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
@ -31,7 +31,7 @@ gcode:
RESPOND TYPE=command MSG="Measuring X and Y Resonances..."
SHAPER_CALIBRATE
M400
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=50
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=50
{% endif %}
CXSAVE_CONFIG

View file

@ -0,0 +1,51 @@
{
"config_path": "/usr/data/guppyscreen/guppyconfig.json",
"default_printer": "Ender-3 V3",
"display_rotate": 3,
"display_sleep_sec": -1,
"guppy_init_script": "/etc/init.d/S99guppyscreen",
"invert_z_icon": true,
"log_path": "/usr/data/printer_data/logs/guppyscreen.log",
"printers": {
"Ender-3 V3": {
"default_macros": {
"cooldown": "SET_HEATER_TEMPERATURE HEATER=extruder TARGET=0\nSET_HEATER_TEMPERATURE HEATER=heater_bed TARGET=0",
"load_filament": "LOAD_MATERIAL",
"unload_filament": "QUIT_MATERIAL"
},
"fans": [
{
"display_name": "Model Cooling",
"id": "output_pin fan0"
},
{
"display_name": "Auxiliary Cooling",
"id": "output_pin fan2"
}
],
"leds": null,
"log_level": "debug",
"monitored_sensors": [
{
"color": "red",
"controllable": true,
"display_name": "Extruder",
"id": "extruder"
},
{
"color": "purple",
"controllable": true,
"display_name": "Bed",
"id": "heater_bed"
}
],
"moonraker_api_key": false,
"moonraker_host": "127.0.0.1",
"moonraker_port": 7125
}
},
"prompt_emergency_stop": true,
"thumbnail_path": "/usr/data/printer_data/thumbnails",
"touch_calibrated": false,
"wpa_supplicant": "/var/run/wpa_supplicant"
}

View file

@ -0,0 +1,125 @@
########################################
# Improved Shapers Configurations
########################################
[respond]
[calibrate_shaper_config]
[gcode_shell_command resonance_graph]
command: /usr/data/printer_data/config/Helper-Script/improved-shapers/scripts/calibrate_shaper.py
timeout: 600.0
verbose: False
[gcode_shell_command belts_graph]
command: /usr/data/printer_data/config/Helper-Script/improved-shapers/scripts/graph_belts.py
timeout: 600.0
verbose: False
[gcode_shell_command delete_graph]
command: sh /usr/data/helper-script/files/improved-shapers/delete_graph.sh
timeout: 600.0
verbose: False
[gcode_shell_command delete_csv]
command: sh /usr/data/helper-script/files/improved-shapers/delete_csv.sh
timeout: 600.0
verbose: False
[gcode_macro INPUT_SHAPER_CALIBRATION]
description: Measure X and Y Axis Resonances and Save values
gcode:
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
G28
{% endif %}
RESPOND TYPE=command MSG="Measuring X and Y Resonances..."
SHAPER_CALIBRATE
M400
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=45
RUN_SHELL_COMMAND CMD=delete_csv
RESPOND TYPE=command MSG="Input Shaper Calibration complete!"
SAVE_CONFIG
[gcode_macro TEST_RESONANCES_GRAPHS]
description: Test X and Y Axis Resonances and Generate Graphs
gcode:
RUN_SHELL_COMMAND CMD=delete_graph
{% set x_png = params.X_PNG|default("/usr/data/printer_data/config/Helper-Script/improved-shapers/resonances_x.png") %}
{% set y_png = params.Y_PNG|default("/usr/data/printer_data/config/Helper-Script/improved-shapers/resonances_y.png") %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
G28
{% endif %}
RESPOND TYPE=command MSG="Testing X Resonances..."
TEST_RESONANCES AXIS=X NAME=x
M400
RESPOND TYPE=command MSG="Generating X Graph... This may take some time."
RUN_SHELL_COMMAND CMD=resonance_graph PARAMS="/tmp/resonances_x_x.csv -o {x_png}"
RESPOND TYPE=command MSG="X Graph (resonances_x.png) is now available in /Helper-Script/improved-shapers folder."
RESPOND TYPE=command MSG="Testing Y Resonances..."
TEST_RESONANCES AXIS=Y NAME=y
M400
RESPOND TYPE=command MSG="Generating Y Graph... This may take some time."
RUN_SHELL_COMMAND CMD=resonance_graph PARAMS="/tmp/resonances_y_y.csv -o {y_png}"
RESPOND TYPE=command MSG="Y Graph (resonances_y.png) is now available in /Helper-Script/improved-shapers folder."
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=45
RUN_SHELL_COMMAND CMD=delete_csv
RESPOND TYPE=command MSG="Resonances Test complete!"
[gcode_macro BELTS_SHAPER_CALIBRATION]
description: Perform a custom half-axis test to analyze and compare the frequency profiles of individual belts on CoreXY printers
gcode:
RUN_SHELL_COMMAND CMD=delete_graph
{% set min_freq = params.FREQ_START|default(5)|float %}
{% set max_freq = params.FREQ_END|default(133.33)|float %}
{% set hz_per_sec = params.HZ_PER_SEC|default(1)|float %}
{% set png_width = params.PNG_WIDTH|default(8)|float %}
{% set png_height = params.PNG_HEIGHT|default(4.8)|float %}
{% set png_out_path = params.PNG_OUT_PATH|default("/usr/data/printer_data/config/Helper-Script/improved-shapers/belts_calibration.png") %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
G28
{% endif %}
TEST_RESONANCES AXIS=1,1 OUTPUT=raw_data NAME=b FREQ_START={min_freq} FREQ_END={max_freq} HZ_PER_SEC={hz_per_sec}
M400
TEST_RESONANCES AXIS=1,-1 OUTPUT=raw_data NAME=a FREQ_START={min_freq} FREQ_END={max_freq} HZ_PER_SEC={hz_per_sec}
M400
RESPOND TYPE=command MSG="Generating Belts Frequency Profiles Graph... This may take some time."
RUN_SHELL_COMMAND CMD=belts_graph PARAMS="-w {png_width} -l {png_height} -n -o {png_out_path} -k /usr/share/klipper /tmp/raw_data_axis=1.000,-1.000_a.csv /tmp/raw_data_axis=1.000,1.000_b.csv"
RESPOND TYPE=command MSG="Graph (belts_calibration.png) is now available in /Helper-Script/improved-shapers folder."
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=45
RUN_SHELL_COMMAND CMD=delete_csv
RESPOND TYPE=command MSG="Belts Shaper Calibration complete!"
[gcode_macro EXCITATE_AXIS_AT_FREQ]
description: Maintain a specified excitation frequency for a period of time to diagnose and locate a vibration source
gcode:
{% set frequency = params.FREQUENCY|default(25)|int %}
{% set time = params.TIME|default(10)|int %}
{% set axis = params.AXIS|default("x")|string|lower %}
{% if axis not in ["x", "y", "a", "b"] %}
{ action_raise_error("AXIS selection is invalid. Should be either x, y, a or b!") }
{% endif %}
{% if axis == "a" %}
{% set axis = "1,-1" %}
{% elif axis == "b" %}
{% set axis = "1,1" %}
{% endif %}
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
G28
{% endif %}
TEST_RESONANCES OUTPUT=raw_data AXIS={axis} FREQ_START={frequency-1} FREQ_END={frequency+1} HZ_PER_SEC={1/(time/3)}
M400

View file

@ -34,8 +34,8 @@ verbose: False
[gcode_macro INPUT_SHAPER_CALIBRATION]
description: Measure X and Y Axis Resonances and Save values
gcode:
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=30
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% endif %}
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
@ -44,8 +44,8 @@ gcode:
RESPOND TYPE=command MSG="Measuring X and Y Resonances..."
SHAPER_CALIBRATE
M400
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=50
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=50
{% endif %}
RUN_SHELL_COMMAND CMD=delete_csv
RESPOND TYPE=command MSG="Input Shaper Calibration complete!"
@ -58,8 +58,8 @@ gcode:
RUN_SHELL_COMMAND CMD=delete_graph
{% set x_png = params.X_PNG|default("/usr/data/printer_data/config/Helper-Script/improved-shapers/resonances_x.png") %}
{% set y_png = params.Y_PNG|default("/usr/data/printer_data/config/Helper-Script/improved-shapers/resonances_y.png") %}
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=30
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% endif %}
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
@ -77,8 +77,8 @@ gcode:
RESPOND TYPE=command MSG="Generating Y Graph... This may take some time."
RUN_SHELL_COMMAND CMD=resonance_graph PARAMS="/tmp/resonances_y_y.csv -o {y_png}"
RESPOND TYPE=command MSG="Y Graph (resonances_y.png) is now available in /Helper-Script/improved-shapers folder."
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=50
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=50
{% endif %}
RUN_SHELL_COMMAND CMD=delete_csv
RESPOND TYPE=command MSG="Resonances Test complete!"
@ -94,8 +94,8 @@ gcode:
{% set png_width = params.PNG_WIDTH|default(8)|float %}
{% set png_height = params.PNG_HEIGHT|default(4.8)|float %}
{% set png_out_path = params.PNG_OUT_PATH|default("/usr/data/printer_data/config/Helper-Script/improved-shapers/belts_calibration.png") %}
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=30
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=30
{% endif %}
{% if printer.toolhead.homed_axes != "xyz" %}
RESPOND TYPE=command MSG="Homing..."
@ -108,8 +108,8 @@ gcode:
RESPOND TYPE=command MSG="Generating Belts Frequency Profiles Graph... This may take some time."
RUN_SHELL_COMMAND CMD=belts_graph PARAMS="-w {png_width} -l {png_height} -n -o {png_out_path} -k /usr/share/klipper /tmp/raw_data_axis=1.000,-1.000_a.csv /tmp/raw_data_axis=1.000,1.000_b.csv"
RESPOND TYPE=command MSG="Graph (belts_calibration.png) is now available in /Helper-Script/improved-shapers folder."
{% if printer["configfile"].config["temperature_fan mcu_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=mcu_fan TARGET=50
{% if printer["configfile"].config["temperature_fan soc_fan"] %}
SET_TEMPERATURE_FAN_TARGET TEMPERATURE_FAN=soc_fan TARGET=50
{% endif %}
RUN_SHELL_COMMAND CMD=delete_csv
RESPOND TYPE=command MSG="Belts Shaper Calibration complete!"

View file

@ -1,5 +1,5 @@
###########################################
# Adaptive Meshing for Creality K1 Series
# Adaptive Bed Meshing Macros
###########################################
[gcode_macro BED_MESH_CALIBRATE]
@ -50,44 +50,26 @@ gcode:
{% set points_y = [points_y , probe_count[1]]|min %}
{% if verbose_enable == True %}
{% if printer.exclude_object.objects != [] %}
RESPOND TYPE=command MSG="Algorithm: {algorithm}"
RESPOND TYPE=command MSG="Default probe count: {probe_count[0]},{probe_count[1]}"
RESPOND TYPE=command MSG="Adapted probe count: {points_x},{points_y}"
RESPOND TYPE=command MSG="Default mesh bounds: {bed_mesh_min[0]},{bed_mesh_min[1]}, {bed_mesh_max[0]},{bed_mesh_max[1]}"
{% if mesh_margin > 0 %}
RESPOND TYPE=command MSG="Mesh margin is {mesh_margin}, mesh bounds extended by {mesh_margin}mm."
{% else %}
RESPOND TYPE=command MSG="Mesh margin is 0, margin not increased."
{% endif %}
{% if fuzz_amount > 0 %}
RESPOND TYPE=command MSG="Mesh point fuzzing enabled, points fuzzed up to {fuzz_amount}mm"
{% else %}
RESPOND TYPE=command MSG="Fuzz amount is 0, mesh points not fuzzed."
{% endif %}
RESPOND TYPE=command MSG="Adapted mesh bounds: {adapted_x_min},{adapted_y_min}, {adapted_x_max},{adapted_y_max}"
RESPOND TYPE=command MSG="KAMP adjustments successful. Happy KAMPing!"
{% else %}
RESPOND TYPE=command MSG="No object detected! Make sure you have enabled Exclude Objets setting in your slicer. Using Full Bed Mesh."
G4 P5000
{% endif %}
{% endif %}
_BED_MESH_CALIBRATE mesh_min={adapted_x_min},{adapted_y_min} mesh_max={adapted_x_max},{adapted_y_max} ALGORITHM={algorithm} PROBE_COUNT={points_x},{points_y}

View file

@ -1,5 +1,5 @@
###########################################
# KAMP Settings for Creality K1 Series
# KAMP Settings
###########################################
# Below you can enable or disable specific configuration files depending on what you want KAMP to do:
@ -37,4 +37,4 @@ variable_flow_rate: 12 # Flow rate of purge in mm3/s. Defau
variable_smart_park_height: 10 # Z position for Smart Park. Default is 10.
gcode:
RESPOND TYPE=command MSG="Running the KAMP_Settings macro does nothing, it's only used for storing KAMP settings."
RESPOND TYPE=command MSG="Running the _KAMP_Settings macro does nothing, it's only used for storing KAMP settings."

View file

@ -1,5 +1,5 @@
###########################################
# Line Purge for Creality K1 Series
# Purge Line Macros
###########################################
[gcode_macro _LINE_PURGE]
@ -44,70 +44,28 @@ gcode:
{% set purge_move_speed = (flow_rate / 5.0) * 60 | float %}
{% if cross_section < 5 %}
RESPOND TYPE=command MSG="[Extruder] max_extrude_cross_section is insufficient for line purge, please set it to 5 or greater. Purge skipped."
{% else %}
{% if verbose_enable == True %}
RESPOND TYPE=command MSG="Moving filament tip {tip_distance}mm"
{% endif %}
{% if detect_object == 0 %}
RESPOND TYPE=command MSG="No object detected! Using classic purge line."
{% elif purge_y_origin_low > 0 %}
RESPOND TYPE=command MSG="KAMP line purge starting at {purge_x_center}, {purge_y_origin_low} and purging {purge_amount}mm of filament, requested flow rate is {flow_rate}mm3/s."
{% elif purge_x_origin_low > 0 %}
RESPOND TYPE=command MSG="KAMP line purge starting at {purge_x_origin_low}, {purge_y_center} and purging {purge_amount}mm of filament, requested flow rate is {flow_rate}mm3/s."
{% elif purge_y_origin_high < bed_y_max %}
RESPOND TYPE=command MSG="KAMP line purge starting at {purge_x_center}, {purge_y_origin_high} and purging {purge_amount}mm of filament, requested flow rate is {flow_rate}mm3/s."
{% elif purge_x_origin_high < bed_x_max %}
RESPOND TYPE=command MSG="KAMP line purge starting at {purge_x_origin_high}, {purge_y_center} and purging {purge_amount}mm of filament, requested flow rate is {flow_rate}mm3/s."
{% else %}
RESPOND TYPE=command MSG="No space for purge line! Using classic purge line."
{% endif %}
SAVE_GCODE_STATE NAME=Prepurge_State
{% if detect_object == 0 %}
G92 E0
G1 Z0.1 F600
M83
{RETRACT}
SET_VELOCITY_LIMIT SQUARE_CORNER_VELOCITY=5
M204 S12000
SET_VELOCITY_LIMIT ACCEL_TO_DECEL=6000
M220 S100
M221 S100
G1 Z2.0 F1200
G1 X0.1 Y20 Z0.3 F6000.0
G1 X0.1 Y180.0 Z0.3 F3000.0 E10.0
G1 X0.4 Y180.0 Z0.3 F3000.0
G1 X0.4 Y20.0 Z0.3 F3000.0 E10.0
G1 Y10.0 F3000.0
G1 Z2.0 F3000.0
G92 E0
M82
G1 F12000
G21
CX_PRINT_DRAW_ONE_LINE
{% elif purge_y_origin_low > 0 %}
G92 E0
G0 F{travel_speed}
G90
@ -121,9 +79,7 @@ gcode:
G92 E0
M82
G0 Z{purge_height * 2} F{travel_speed}
{% elif purge_x_origin_low > 0 %}
G92 E0
G0 F{travel_speed}
G90
@ -137,9 +93,7 @@ gcode:
G92 E0
M82
G0 Z{purge_height * 2} F{travel_speed}
{% elif purge_y_origin_high < bed_y_max %}
G92 E0
G0 F{travel_speed}
G90
@ -153,9 +107,7 @@ gcode:
G92 E0
M82
G0 Z{purge_height * 2} F{travel_speed}
{% elif purge_x_origin_high < bed_x_max %}
G92 E0
G0 F{travel_speed}
G90
@ -169,32 +121,8 @@ gcode:
G92 E0
M82
G0 Z{purge_height * 2} F{travel_speed}
{% else %}
G92 E0
G1 Z0.1 F600
M83
{RETRACT}
SET_VELOCITY_LIMIT SQUARE_CORNER_VELOCITY=5
M204 S12000
SET_VELOCITY_LIMIT ACCEL_TO_DECEL=6000
M220 S100
M221 S100
G1 Z2.0 F1200
G1 X0.1 Y20 Z0.3 F6000.0
G1 X0.1 Y180.0 Z0.3 F3000.0 E10.0
G1 X0.4 Y180.0 Z0.3 F3000.0
G1 X0.4 Y20.0 Z0.3 F3000.0 E10.0
G1 Y10.0 F3000.0
G1 Z2.0 F3000.0
G92 E0
M82
G1 F12000
G21
CX_PRINT_DRAW_ONE_LINE
{% endif %}
RESTORE_GCODE_STATE NAME=Prepurge_State
{% endif %}

View file

@ -1,32 +1,38 @@
###########################################
# PrusaSlicer Macros for Creality K1 Series
# PrusaSlicer Macros
###########################################
[gcode_macro DEFINE_OBJECT]
description: Needed macro for Exclude Objects
gcode:
EXCLUDE_OBJECT_DEFINE {rawparams}
[gcode_macro START_CURRENT_OBJECT]
description: Needed macro for Exclude Objects
gcode:
EXCLUDE_OBJECT_START NAME={params.NAME}
[gcode_macro END_CURRENT_OBJECT]
description: Needed macro for Exclude Objects
gcode:
EXCLUDE_OBJECT_END {% if params.NAME %}NAME={params.NAME}{% endif %}
[gcode_macro LIST_OBJECTS]
description: Needed macro for Exclude Objects
gcode:
EXCLUDE_OBJECT_DEFINE
[gcode_macro LIST_EXCLUDED_OBJECTS]
description: Needed macro for Exclude Objects
gcode:
EXCLUDE_OBJECT
[gcode_macro REMOVE_ALL_EXCLUDED]
description: Needed macro for Exclude Objects
gcode:
EXCLUDE_OBJECT RESET=1

View file

@ -1,5 +1,5 @@
###########################################
# Smart Park for Creality K1 Series
# Smart Park Macros
###########################################
[gcode_macro _SMART_PARK]
@ -59,21 +59,13 @@ gcode:
{% endif %}
{% if verbose_enable == True %}
RESPOND TYPE=command MSG="Smart Park location: {x_min},{y_min}"
{% endif %}
SAVE_GCODE_STATE NAME=Presmartpark_State
G90
{% if printer.toolhead.position.z < z_height %}
G0 Z{z_height}
{% endif %}
G0 X{x_min} Y{y_min} F{travel_speed}
G0 Z{z_height}
RESTORE_GCODE_STATE NAME=Presmartpark_State

View file

@ -0,0 +1,131 @@
###########################################
# Additional Macros for Creality Ender-3 V3
###########################################
[respond]
[virtual_pins]
[output_pin ADAPTIVE_BED_MESH]
pin: virtual_pin:ADAPTIVE_BED_MESH_pin
value: 1
[output_pin FULL_BED_MESH]
pin: virtual_pin:FULL_BED_MESH_pin
value: 0
[output_pin ADAPTIVE_PURGE_LINE]
pin: virtual_pin:ADAPTIVE_PURGE_LINE_pin
value: 1
[gcode_macro _ADAPTIVE_BED_MESH_ON]
description: Enable Adaptive Bed Mesh and Disable Full Bed Mesh
gcode:
SET_PIN PIN=ADAPTIVE_BED_MESH VALUE=1
SET_PIN PIN=FULL_BED_MESH VALUE=0
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _FULL_BED_MESH_ON]
description: Disable Adaptive Bed Mesh and Enable Full Bed Mesh
gcode:
SET_PIN PIN=ADAPTIVE_BED_MESH VALUE=0
SET_PIN PIN=FULL_BED_MESH VALUE=1
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _BED_MESH_OFF]
description: Disable Adaptive Bed Mesh and Enable Full Bed Mesh
gcode:
SET_PIN PIN=ADAPTIVE_BED_MESH VALUE=0
SET_PIN PIN=FULL_BED_MESH VALUE=0
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _ADAPTIVE_PURGE_LINE_ON]
description: Enable Adaptive Purge Line
gcode:
SET_PIN PIN=ADAPTIVE_PURGE_LINE VALUE=1
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _ADAPTIVE_PURGE_LINE_OFF]
description: Disable Adaptive Purge Line
gcode:
SET_PIN PIN=ADAPTIVE_PURGE_LINE VALUE=0
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro KAMP_BED_MESH_SETTINGS]
description: Configure Bed Mesh type
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Bed Mesh Settings"
RESPOND TYPE=command MSG="action:prompt_text What type of bed mesh do you want to use when you start printing?"
RESPOND TYPE=command MSG="action:prompt_button ADAPTIVE BED MESH|_ADAPTIVE_BED_MESH_ON|primary"
RESPOND TYPE=command MSG="action:prompt_button FULL BED MESH|_FULL_BED_MESH_ON|primary"
RESPOND TYPE=command MSG="action:prompt_button NONE|_BED_MESH_OFF|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro KAMP_PURGE_LINE_SETTINGS]
description: Configure Purge Line type
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Purge Line Settings"
RESPOND TYPE=command MSG="action:prompt_text What type of purge line do you want to use when you start printing?"
RESPOND TYPE=command MSG="action:prompt_button ADAPTIVE PURGE LINE|_ADAPTIVE_PURGE_LINE_ON|primary"
RESPOND TYPE=command MSG="action:prompt_button CLASSIC PURGE LINE|_ADAPTIVE_PURGE_LINE_OFF|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro START_PRINT]
variable_prepare: 0
variable_z_sensorless: 0
gcode:
SET_GCODE_VARIABLE MACRO=M106 VARIABLE=user_flag VALUE=0
WAIT_TEMP_END
CLEAR_PAUSE
SET_TEMPERATURE_FAN_TARGET temperature_fan=soc_fan target=5
{% set g28_extruder_temp = printer.custom_macro.g28_ext_temp %}
{% set bed_temp = printer.custom_macro.default_bed_temp %}
{% set extruder_temp = printer.custom_macro.default_extruder_temp %}
{% if 'BED_TEMP' in params|upper and (params.BED_TEMP|float) %}
{% set bed_temp = params.BED_TEMP %}
{% endif %}
{% if 'EXTRUDER_TEMP' in params|upper and (params.EXTRUDER_TEMP|float) %}
{% set extruder_temp = params.EXTRUDER_TEMP %}
{% endif %}
{% if printer['gcode_macro START_PRINT'].prepare|int == 0 %}
{action_respond_info("not prepare.\n")}
PRINT_PREPARE_CLEAR
CX_ROUGH_G28 EXTRUDER_TEMP={extruder_temp} BED_TEMP={bed_temp}
CX_NOZZLE_CLEAR
Z_SENSORLESS_SET
ACCURATE_G28
{% if printer['output_pin ADAPTIVE_BED_MESH'].value == 1 %}
RESPOND TYPE=command MSG="Starting Adaptative Bed Mesh..."
BED_MESH_CLEAR
BED_MESH_CALIBRATE
BED_MESH_PROFILE SAVE=adaptive
BED_MESH_PROFILE LOAD=adaptive
{% else %}
{% if printer['output_pin FULL_BED_MESH'].value == 1 %}
RESPOND TYPE=command MSG="Starting Full Bed Mesh..."
CX_PRINT_LEVELING_CALIBRATION
{% endif %}
BED_MESH_PROFILE LOAD=default
{% endif %}
{% else %}
PRINT_PREPARE_CLEAR
{% endif %}
{% if printer['output_pin ADAPTIVE_PURGE_LINE'].value == 1 %}
_SMART_PARK
M109 S{extruder_temp}
M190 S{bed_temp}
RESPOND TYPE=command MSG="Starting Adaptive Purge Line..."
_LINE_PURGE
{% else %}
RESPOND TYPE=command MSG="Starting Classic Purge Line..."
CX_PRINT_DRAW_ONE_LINE
{% endif %}
SET_VELOCITY_LIMIT ACCEL={printer.configfile.settings.printer.max_accel}

View file

@ -1,20 +1,83 @@
###########################################
# Start Print Macro for Creality K1 Series
# Additional Macros for Creality K1 Series
###########################################
[respond]
[virtual_pins]
[output_pin KAMP]
pin: virtual_pin:KAMP_pin
[output_pin ADAPTIVE_BED_MESH]
pin: virtual_pin:ADAPTIVE_BED_MESH_pin
value: 1
[output_pin BED_LEVELING]
pin: virtual_pin:BED_LEVELING_pin
[output_pin FULL_BED_MESH]
pin: virtual_pin:FULL_BED_MESH_pin
value: 0
[output_pin ADAPTIVE_PURGE_LINE]
pin: virtual_pin:ADAPTIVE_PURGE_LINE_pin
value: 1
[gcode_macro _ADAPTIVE_BED_MESH_ON]
description: Enable Adaptive Bed Mesh and Disable Full Bed Mesh
gcode:
SET_PIN PIN=ADAPTIVE_BED_MESH VALUE=1
SET_PIN PIN=FULL_BED_MESH VALUE=0
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _FULL_BED_MESH_ON]
description: Disable Adaptive Bed Mesh and Enable Full Bed Mesh
gcode:
SET_PIN PIN=ADAPTIVE_BED_MESH VALUE=0
SET_PIN PIN=FULL_BED_MESH VALUE=1
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _BED_MESH_OFF]
description: Disable Adaptive Bed Mesh and Enable Full Bed Mesh
gcode:
SET_PIN PIN=ADAPTIVE_BED_MESH VALUE=0
SET_PIN PIN=FULL_BED_MESH VALUE=0
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _ADAPTIVE_PURGE_LINE_ON]
description: Enable Adaptive Purge Line
gcode:
SET_PIN PIN=ADAPTIVE_PURGE_LINE VALUE=1
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _ADAPTIVE_PURGE_LINE_OFF]
description: Disable Adaptive Purge Line
gcode:
SET_PIN PIN=ADAPTIVE_PURGE_LINE VALUE=0
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro KAMP_BED_MESH_SETTINGS]
description: Configure Bed Mesh type
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Bed Mesh Settings"
RESPOND TYPE=command MSG="action:prompt_text What type of bed mesh do you want to use when you start printing?"
RESPOND TYPE=command MSG="action:prompt_button ADAPTIVE BED MESH|_ADAPTIVE_BED_MESH_ON|primary"
RESPOND TYPE=command MSG="action:prompt_button FULL BED MESH|_FULL_BED_MESH_ON|primary"
RESPOND TYPE=command MSG="action:prompt_button NONE|_BED_MESH_OFF|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro KAMP_PURGE_LINE_SETTINGS]
description: Configure Purge Line type
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Purge Line Settings"
RESPOND TYPE=command MSG="action:prompt_text What type of purge line do you want to use when you start printing?"
RESPOND TYPE=command MSG="action:prompt_button ADAPTIVE PURGE LINE|_ADAPTIVE_PURGE_LINE_ON|primary"
RESPOND TYPE=command MSG="action:prompt_button CLASSIC PURGE LINE|_ADAPTIVE_PURGE_LINE_OFF|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro START_PRINT]
variable_prepare: 0
gcode:
@ -34,14 +97,14 @@ gcode:
CX_ROUGH_G28 EXTRUDER_TEMP={extruder_temp} BED_TEMP={bed_temp}
CX_NOZZLE_CLEAR
ACCURATE_G28
{% if printer['output_pin KAMP'].value == 1 %}
RESPOND TYPE=command MSG="Starting KAMP Bed Mesh..."
{% if printer['output_pin ADAPTIVE_BED_MESH'].value == 1 %}
RESPOND TYPE=command MSG="Starting Adaptive Bed Mesh..."
BED_MESH_CLEAR
BED_MESH_CALIBRATE
BED_MESH_PROFILE SAVE=kamp
BED_MESH_PROFILE LOAD=kamp
BED_MESH_PROFILE SAVE=adaptive
BED_MESH_PROFILE LOAD=adaptive
{% else %}
{% if printer['output_pin BED_LEVELING'].value == 1 %}
{% if printer['output_pin FULL_BED_MESH'].value == 1 %}
RESPOND TYPE=command MSG="Starting Full Bed Mesh..."
CX_PRINT_LEVELING_CALIBRATION
{% endif %}
@ -50,14 +113,14 @@ gcode:
{% else %}
PRINT_PREPARE_CLEAR
{% endif %}
{% if printer['output_pin KAMP'].value == 1 %}
{% if printer['output_pin ADAPTIVE_PURGE_LINE'].value == 1 %}
_SMART_PARK
M109 S{extruder_temp}
M190 S{bed_temp}
RESPOND TYPE=command MSG="Starting KAMP line purge..."
RESPOND TYPE=command MSG="Starting Adaptive Purge Line..."
_LINE_PURGE
{% else %}
RESPOND TYPE=command MSG="Starting classic line purge..."
RESPOND TYPE=command MSG="Starting Classic Purge Line..."
CX_PRINT_DRAW_ONE_LINE
{% endif %}
SET_VELOCITY_LIMIT ACCEL={printer.configfile.settings.printer.max_accel}

View file

@ -0,0 +1,176 @@
########################################
# M600 Support
########################################
[respond]
[idle_timeout]
gcode:
RESPOND TYPE=command MSG="Stopping hotend heating..."
M104 S0
timeout: 99999999
[filament_switch_sensor filament_sensor]
pause_on_runout: false
switch_pin: !PC15
runout_gcode:
M600
[gcode_macro _UNLOAD_FILAMENT]
gcode:
RESTORE_E_CURRENT
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
RESPOND TYPE=command MSG="Unloading filament..."
M83
G1 E10 F300
G1 E-15 F3000
G1 E-22.4700 F2400
G1 E-6.4200 F1200
G1 E-3.2100 F720
G1 E5.0000 F356
G1 E-5.0000 F384
G1 E5.0000 F412
G1 E-5.0000 F440
G1 E5.0000 F467
G1 E-5.0000 F495
G1 E5.0000 F523
G1 E-5.0000 F3000
G1 E-15 F3000
SET_E_MIN_CURRENT
[gcode_macro _LOAD_FILAMENT]
gcode:
RESTORE_E_CURRENT
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
RESPOND TYPE=command MSG="Loading filament..."
G91
G1 E100 F180
G90
M400
SET_E_MIN_CURRENT
[gcode_macro _PURGE_MORE]
gcode:
RESTORE_E_CURRENT
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
RESPOND TYPE=command MSG="Purging filament..."
G91
G1 E10 F180
G90
M400
SET_E_MIN_CURRENT
[gcode_macro M600]
description: Filament Change
variable_m600_state: 0
variable_fan0_speed: 0
gcode:
{% set E = printer["gcode_macro PAUSE"].extrude|float %}
{% set y_park = printer.toolhead.axis_minimum.y|float + 5.0 %}
{% set x_park = printer.toolhead.axis_maximum.x|float - 10.0 %}
{% set max_z = printer["gcode_macro PRINTER_PARAM"].max_z_position|float %}
{% set act_z = printer.toolhead.position.z|float %}
{% set z_safe = 0.0 %}
{% if act_z < 48.0 %}
{% set z_safe = 50.0 - act_z %}
{% elif act_z < (max_z - 2.0) %}
{% set z_safe = 2.0 %}
{% elif act_z < max_z %}
{% set z_safe = max_z - act_z %}
{% endif %}
{action_respond_info("z_safe = %s"% (z_safe))}
SET_GCODE_VARIABLE MACRO=M600 VARIABLE=m600_state VALUE=1
SET_GCODE_VARIABLE MACRO=PRINTER_PARAM VARIABLE=hotend_temp VALUE={printer.extruder.target}
SET_GCODE_VARIABLE MACRO=PRINTER_PARAM VARIABLE=z_safe_pause VALUE={z_safe|float}
RESPOND TYPE=command MSG="Print paused for filament change!"
PAUSE_BASE
G91
{% if "xyz" in printer.toolhead.homed_axes %}
{% if printer.extruder.can_extrude|lower == 'true' %}
G1 E-1.0 F180
G1 E-{E} F4000
{% else %}
RESPOND TYPE=command MSG="Extruder not hot enough!"
{% endif %}
G1 Z{z_safe} F600
M400
G90
G1 X{x_park} Y{y_park} F12000
{% endif %}
_UNLOAD_FILAMENT
SET_GCODE_VARIABLE MACRO=PRINTER_PARAM VARIABLE=fan2_speed VALUE={printer['output_pin fan2'].value}
SET_GCODE_VARIABLE MACRO=M600 VARIABLE=fan0_speed VALUE={printer['output_pin fan0'].value}
M106 P0 S0
M106 P2 S0
SET_IDLE_TIMEOUT TIMEOUT=900
SET_E_MIN_CURRENT
RESPOND TYPE=command MSG="action:prompt_begin Filament change detected!"
RESPOND TYPE=command MSG="action:prompt_text A necessary filament change has been detected. Please replace filament, LOAD it and click RESUME button."
RESPOND TYPE=command MSG="action:prompt_button UNLOAD FILAMENT|_UNLOAD_FILAMENT|secondary"
RESPOND TYPE=command MSG="action:prompt_button LOAD FILAMENT|_LOAD_FILAMENT|secondary"
RESPOND TYPE=command MSG="action:prompt_button PURGE MORE FILAMENT|_PURGE_MORE|secondary"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL PRINT|CANCEL_PRINT|error"
RESPOND TYPE=command MSG="action:prompt_footer_button IGNORE|RESPOND TYPE=command MSG=action:prompt_end|warning"
RESPOND TYPE=command MSG="action:prompt_footer_button RESUME|RESUME|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro RESUME]
description: Resume the current print
rename_existing: RESUME_BASE
gcode:
RESTORE_E_CURRENT
{% if printer['gcode_macro PRINTER_PARAM'].hotend_temp|int != 0 %}
{% if printer['gcode_macro PRINTER_PARAM'].hotend_temp|int > printer.extruder.temperature %}
RESPOND TYPE=command MSG="Starting hotend heating..."
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
{% else %}
RESPOND TYPE=command MSG="Starting hotend heating..."
M104 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
{% endif %}
SET_GCODE_VARIABLE MACRO=PRINTER_PARAM VARIABLE=hotend_temp VALUE=0
{% endif %}
{% if printer['gcode_macro PRINTER_PARAM'].fan2_speed > 0 %}
{% set s_value = (printer['gcode_macro PRINTER_PARAM'].fan2_speed * 255 - printer['gcode_macro PRINTER_PARAM'].fan2_min) * 255 / (255 - printer['gcode_macro PRINTER_PARAM'].fan2_min)|float %}
M106 P2 S{s_value} G1
{% endif %}
{% if printer['gcode_macro M600'].m600_state != 1 %}
{% set z_resume_move = printer['gcode_macro PRINTER_PARAM'].z_safe_pause|int %}
{% if z_resume_move > 2 %}
{% set z_resume_move = z_resume_move - 2 %}
G91
G1 Z-{z_resume_move} F600
M400
{% endif %}
{% endif %}
{% set E = printer["gcode_macro PAUSE"].extrude|float + 1.0 %}
{% if 'VELOCITY' in params|upper %}
{% set get_params = ('VELOCITY=' + params.VELOCITY) %}
{%else %}
{% set get_params = "" %}
{% endif %}
{% if printer["gcode_macro M600"].m600_state == 1 %}
{% if printer['gcode_macro M600'].fan0_speed > 0 %}
{% set s_value = (printer['gcode_macro M600'].fan0_speed * 255 - printer['gcode_macro PRINTER_PARAM'].fan0_min) * 255 / (255 - printer['gcode_macro PRINTER_PARAM'].fan0_min)|float %}
M106 P0 S{s_value} G1
{% endif %}
SET_GCODE_VARIABLE MACRO=M600 VARIABLE=m600_state VALUE=0
SET_IDLE_TIMEOUT TIMEOUT=99999999
{% else %}
{% if printer.extruder.can_extrude|lower == 'true' %}
G91
G1 E{E} F2100
G90
M400
{% else %}
RESPOND TYPE=command MSG="Extruder not hot enough!"
{% endif %}
{% endif %}
RESPOND TYPE=command MSG="action:prompt_end"
RESPOND TYPE=command MSG="Restarting print..."
RESUME_BASE {get_params}

View file

@ -18,6 +18,53 @@ runout_gcode:
M600
[gcode_macro _UNLOAD_FILAMENT]
gcode:
RESTORE_E_CURRENT
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
RESPOND TYPE=command MSG="Unloading filament..."
M83
G1 E10 F300
G1 E-15 F3000
G1 E-22.4700 F2400
G1 E-6.4200 F1200
G1 E-3.2100 F720
G1 E5.0000 F356
G1 E-5.0000 F384
G1 E5.0000 F412
G1 E-5.0000 F440
G1 E5.0000 F467
G1 E-5.0000 F495
G1 E5.0000 F523
G1 E-5.0000 F3000
G1 E-15 F3000
SET_E_MIN_CURRENT
[gcode_macro _LOAD_FILAMENT]
gcode:
RESTORE_E_CURRENT
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
RESPOND TYPE=command MSG="Loading filament..."
G91
G1 E100 F180
G90
M400
SET_E_MIN_CURRENT
[gcode_macro _PURGE_MORE]
gcode:
RESTORE_E_CURRENT
M109 S{printer['gcode_macro PRINTER_PARAM'].hotend_temp|int}
RESPOND TYPE=command MSG="Purging filament..."
G91
G1 E10 F180
G90
M400
SET_E_MIN_CURRENT
[gcode_macro M600]
description: Filament Change
variable_m600_state: 0
@ -55,22 +102,22 @@ gcode:
G90
G1 X{x_park} Y{y_park} F30000
{% endif %}
G91
{% if printer.extruder.can_extrude|lower == 'true' %}
RESPOND TYPE=command MSG="Extracting filament..."
G1 E20 F180
G1 E-30 F180
G1 E-50 F2000
{% else %}
RESPOND TYPE=command MSG="Extruder not hot enough!"
{% endif %}
_UNLOAD_FILAMENT
SET_GCODE_VARIABLE MACRO=PRINTER_PARAM VARIABLE=fan2_speed VALUE={printer['output_pin fan2'].value}
SET_GCODE_VARIABLE MACRO=M600 VARIABLE=fan0_speed VALUE={printer['output_pin fan0'].value}
M106 P0 S0
M106 P2 S0
SET_IDLE_TIMEOUT TIMEOUT=900
SET_E_MIN_CURRENT
RESPOND TYPE=command MSG="Replace filament at the extruder inlet and click on Resume button!"
RESPOND TYPE=command MSG="action:prompt_begin Filament change detected!"
RESPOND TYPE=command MSG="action:prompt_text A necessary filament change has been detected. Please replace filament, LOAD it and click RESUME button."
RESPOND TYPE=command MSG="action:prompt_button UNLOAD FILAMENT|_UNLOAD_FILAMENT|secondary"
RESPOND TYPE=command MSG="action:prompt_button LOAD FILAMENT|_LOAD_FILAMENT|secondary"
RESPOND TYPE=command MSG="action:prompt_button PURGE MORE FILAMENT|_PURGE_MORE|secondary"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL PRINT|CANCEL_PRINT|error"
RESPOND TYPE=command MSG="action:prompt_footer_button IGNORE|RESPOND TYPE=command MSG=action:prompt_end|warning"
RESPOND TYPE=command MSG="action:prompt_footer_button RESUME|RESUME|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro RESUME]
@ -108,15 +155,6 @@ gcode:
{% set get_params = "" %}
{% endif %}
{% if printer["gcode_macro M600"].m600_state == 1 %}
{% if printer.extruder.can_extrude|lower == 'true' %}
RESPOND TYPE=command MSG="Loading and purging filament..."
G91
G1 E100 F180
G90
M400
{% else %}
RESPOND TYPE=command MSG="Extruder not hot enough!"
{% endif %}
{% if printer['gcode_macro M600'].fan0_speed > 0 %}
{% set s_value = (printer['gcode_macro M600'].fan0_speed * 255 - printer['gcode_macro PRINTER_PARAM'].fan0_min) * 255 / (255 - printer['gcode_macro PRINTER_PARAM'].fan0_min)|float %}
M106 P0 S{s_value}
@ -133,5 +171,6 @@ gcode:
RESPOND TYPE=command MSG="Extruder not hot enough!"
{% endif %}
{% endif %}
RESPOND TYPE=command MSG="action:prompt_end"
RESPOND TYPE=command MSG="Restarting print..."
RESUME_BASE {get_params}

View file

@ -5,7 +5,7 @@
[respond]
[duplicate_pin_override]
pins: PC0, PC5, PB2, ADC_TEMPERATURE
pins: PC0, PC5, PB2, PC6, ADC_TEMPERATURE
[temperature_fan chamber_fan]
@ -25,7 +25,7 @@ max_speed: 1.0
min_speed: 0.0
[temperature_fan mcu_fan]
[temperature_fan soc_fan]
pin: PB2
cycle_time: 0.0100
hardware_pwm: false
@ -39,9 +39,10 @@ max_delta: 2
target_temp: 50.0
max_speed: 1.0
min_speed: 0.0
tachometer_pin:PC6
[output_pin mcu_fan]
[output_pin soc_fan]
pin: PB2
pwm: True
cycle_time: 0.0100

View file

@ -0,0 +1,232 @@
########################################
# Useful Macros
########################################
[gcode_shell_command Klipper_Backup]
command: sh /usr/data/helper-script/files/scripts/useful_macros.sh -backup_klipper
timeout: 600.0
verbose: true
[gcode_shell_command Klipper_Restore]
command: sh /usr/data/helper-script/files/scripts/useful_macros.sh -restore_klipper
timeout: 600.0
verbose: true
[gcode_shell_command Moonraker_Backup]
command: sh /usr/data/helper-script/files/scripts/useful_macros.sh -backup_moonraker
timeout: 600.0
verbose: true
[gcode_shell_command Moonraker_Restore]
command: sh /usr/data/helper-script/files/scripts/useful_macros.sh -restore_moonraker
timeout: 600.0
verbose: true
[gcode_shell_command Reload_Camera]
command: sh /usr/data/helper-script/files/scripts/useful_macros.sh -reload_camera
timeout: 600.0
verbose: true
[gcode_macro _KLIPPER_BACKUP]
gcode:
RUN_SHELL_COMMAND CMD=Klipper_Backup
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _KLIPPER_RESTORE]
gcode:
RUN_SHELL_COMMAND CMD=Klipper_Restore
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _MOONRAKER_BACKUP]
gcode:
RUN_SHELL_COMMAND CMD=Moonraker_Backup
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _MOONRAKER_RESTORE]
gcode:
RUN_SHELL_COMMAND CMD=Moonraker_Restore
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro KLIPPER_BACKUP_CONFIG]
description: Backup Klipper configuration files
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Backup Klipper configuration files"
RESPOND TYPE=command MSG="action:prompt_text Do you want to backup Klipper configuration files?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button BACKUP|_KLIPPER_BACKUP|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro KLIPPER_RESTORE_CONFIG]
description: Restore Klipper configuration files
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Restore Klipper configuration files"
RESPOND TYPE=command MSG="action:prompt_text Do you want to restore Klipper configuration files?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button RESTORE|_KLIPPER_RESTORE|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro MOONRAKER_BACKUP_DATABASE]
description: Backup Moonraker database
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Backup Moonraker database"
RESPOND TYPE=command MSG="action:prompt_text Do you want to backup Moonraker database?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button BACKUP|_MOONRAKER_BACKUP|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro MOONRAKER_RESTORE_DATABASE]
description: Restore Moonraker database
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Restore Moonraker database"
RESPOND TYPE=command MSG="action:prompt_text Do you want to restore Moonraker database?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button RESTORE|_MOONRAKER_RESTORE|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro RELOAD_CAMERA]
description: Reload camera service
gcode:
RUN_SHELL_COMMAND CMD=Reload_Camera
[gcode_macro BED_LEVELING]
description: Start Bed Leveling
gcode:
{% if 'PROBE_COUNT' in params|upper %}
{% set get_count = ('PROBE_COUNT=' + params.PROBE_COUNT) %}
{%else %}
{% set get_count = "" %}
{% endif %}
{% set bed_temp = printer.custom_macro.default_bed_temp %}
{% set extruder_temp = printer.custom_macro.g28_ext_temp %}
{% set nozzle_clear_temp = printer.custom_macro.default_extruder_temp %}
{% if 'BED_TEMP' in params|upper %}
{% set bed_temp = params.BED_TEMP %}
{% endif %}
{% if 'EXTRUDER_TEMP' in params|upper %}
{% set nozzle_clear_temp = params.EXTRUDER_TEMP %}
{% endif %}
SET_FILAMENT_SENSOR SENSOR=filament_sensor ENABLE=0
SET_TEMPERATURE_FAN_TARGET temperature_fan=soc_fan target=5
M109 S140
{% if printer.toolhead.homed_axes != "xyz" %}
G28
{% endif %}
BED_MESH_CLEAR
NOZZLE_CLEAR HOT_MIN_TEMP={hotend_temp} HOT_MAX_TEMP={nozzle_clear_temp} BED_MAX_TEMP={bed_temp}
M204 S5000
SET_VELOCITY_LIMIT ACCEL_TO_DECEL=5000
BED_MESH_CALIBRATE {get_count}
BED_MESH_OUTPUT
{% set y_park = printer.toolhead.axis_maximum.y/2 %}
{% set x_park = printer.toolhead.axis_maximum.x|float - 10.0 %}
G1 X{x_park} Y{y_park} F3600
TURN_OFF_HEATERS
SET_TEMPERATURE_FAN_TARGET temperature_fan=soc_fan target=45
SET_FILAMENT_SENSOR SENSOR=filament_sensor ENABLE=1
[gcode_macro PID_BED]
description: Start Bed PID
gcode:
G90
{% if printer.toolhead.homed_axes != "xyz" %}
G28
{% endif %}
G1 Z10 F600
M106
PID_CALIBRATE HEATER=heater_bed TARGET={params.BED_TEMP|default(70)}
M107
{% set y_park = printer.toolhead.axis_maximum.y/2 %}
{% set x_park = printer.toolhead.axis_maximum.x|float - 10.0 %}
G1 X{x_park} Y{y_park} F6000
[gcode_macro PID_HOTEND]
description: Start Hotend PID
gcode:
G90
{% if printer.toolhead.homed_axes != "xyz" %}
G28
{% endif %}
G1 Z10 F600
M106
PID_CALIBRATE HEATER=extruder TARGET={params.HOTEND_TEMP|default(250)}
M107
{% set y_park = printer.toolhead.axis_maximum.y/2 %}
{% set x_park = printer.toolhead.axis_maximum.x|float - 10.0 %}
G1 X{x_park} Y{y_park} F6000
WAIT_TEMP_START
[gcode_macro WARMUP]
description: Stress Test
variable_maxd: 14142.14 ; = SQRT(2*maxy)
gcode:
{% set min_loops = 2 %}
{% set max_loops = params.LOOPS|default(3)|int %}
{% if 'LOOPS' in params|upper %}
{% if max_loops < min_loops %}
{% set max_loops = min_loops %}
{% endif %}
{% endif %}
{% set loop_cnt = max_loops %}
{% set maxx = params.X_ACCEL_MAX|default(10000)|int %}
{% set maxy = params.Y_ACCEL_MAX|default(10000)|int %}
{% set max_x = (printer.toolhead.axis_maximum.x|int-5) %}
{% set max_y = (printer.toolhead.axis_maximum.y|int-5) %}
{% set loop_step_y = max_y//(loop_cnt-1) %}
{% set loop_step_x = max_x//(loop_cnt-1) %}
{% set y_park = printer.toolhead.axis_maximum.y/2 %}
{% set x_park = printer.toolhead.axis_maximum.x|float - 10.0 %}
{% if printer.toolhead.homed_axes != "xyz" %}
G28
{% endif %}
SET_VELOCITY_LIMIT ACCEL={maxx} ACCEL_TO_DECEL={maxx/2}
{% for number in range(10,max_y+11,loop_step_y) %}
{% if number >= max_y %}
{% set number = max_y %}
{% endif %}
G1 F{maxy} X10 Y{number}
G1 F{maxx} X{max_x} Y{number}
{% endfor %}
SET_VELOCITY_LIMIT ACCEL={maxy} ACCEL_TO_DECEL={maxy/2}
{% for number in range(10,max_x+11,loop_step_y) %}
{% if number >= max_x %}
{% set number = max_x %}
{% endif %}
G1 F{maxy} X{number} Y{max_y}
G1 F{maxy} X{number} Y10
{% endfor %}
SET_VELOCITY_LIMIT ACCEL={maxd} ACCEL_TO_DECEL={maxd/2}
{% for times in range(loop_cnt) %}
G1 F{maxx} X10 Y10
G1 F{maxd} X{max_x} Y{max_y}
G1 F{maxx} X10 Y{max_y}
G1 F{maxd} X{max_x} Y10
G1 F{maxy} X{max_x} Y{max_y}
G1 F{maxd} X10 Y10
G1 F{maxy} X10 Y{max_y}
G1 F{maxd} X{max_x} Y10
{% endfor %}
SET_VELOCITY_LIMIT ACCEL={maxx} ACCEL_TO_DECEL={maxx/2}
{% for times in range(loop_cnt) %}
G1 F{maxy} X10 Y10
G1 F{maxy} X10 Y{max_y}
G1 F{maxx} X{max_x} Y{max_y}
G1 F{maxy} X{max_x} Y10
G1 F{maxx} X10 Y10
G1 F{maxx} X{max_x} Y10
G1 F{maxy} X{max_x} Y{max_y}
G1 F{maxx} X10 Y{max_y}
{% endfor %}
G1 X{x_park} Y{y_park} F15000

View file

@ -28,26 +28,72 @@ timeout: 600.0
verbose: true
[gcode_macro KLIPPER_BACKUP_CONFIG]
[gcode_macro _KLIPPER_BACKUP]
gcode:
RUN_SHELL_COMMAND CMD=Klipper_Backup
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _KLIPPER_RESTORE]
gcode:
RUN_SHELL_COMMAND CMD=Klipper_Restore
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _MOONRAKER_BACKUP]
gcode:
RUN_SHELL_COMMAND CMD=Moonraker_Backup
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro _MOONRAKER_RESTORE]
gcode:
RUN_SHELL_COMMAND CMD=Moonraker_Restore
RESPOND TYPE=command MSG="action:prompt_end"
[gcode_macro KLIPPER_BACKUP_CONFIG]
description: Backup Klipper configuration files
gcode:
RESPOND TYPE=command MSG="action:prompt_begin Backup Klipper configuration files"
RESPOND TYPE=command MSG="action:prompt_text Do you want to backup Klipper configuration files?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button BACKUP|_KLIPPER_BACKUP|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro KLIPPER_RESTORE_CONFIG]
description: Restore Klipper configuration files
gcode:
RUN_SHELL_COMMAND CMD=Klipper_Restore
RESPOND TYPE=command MSG="action:prompt_begin Restore Klipper configuration files"
RESPOND TYPE=command MSG="action:prompt_text Do you want to restore Klipper configuration files?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button RESTORE|_KLIPPER_RESTORE|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro MOONRAKER_BACKUP_DATABASE]
description: Backup Moonraker database
gcode:
RUN_SHELL_COMMAND CMD=Moonraker_Backup
RESPOND TYPE=command MSG="action:prompt_begin Backup Moonraker database"
RESPOND TYPE=command MSG="action:prompt_text Do you want to backup Moonraker database?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button BACKUP|_MOONRAKER_BACKUP|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro MOONRAKER_RESTORE_DATABASE]
description: Restore Moonraker database
gcode:
RUN_SHELL_COMMAND CMD=Moonraker_Restore
RESPOND TYPE=command MSG="action:prompt_begin Restore Moonraker database"
RESPOND TYPE=command MSG="action:prompt_text Do you want to restore Moonraker database?"
RESPOND TYPE=command MSG="action:prompt_footer_button CANCEL|RESPOND TYPE=command MSG="action:prompt_end"|error"
RESPOND TYPE=command MSG="action:prompt_footer_button RESTORE|_MOONRAKER_RESTORE|primary"
RESPOND TYPE=command MSG="action:prompt_show"
[gcode_macro RELOAD_CAMERA]
description: Reload camera service
gcode:
RUN_SHELL_COMMAND CMD=Reload_Camera
@ -56,9 +102,9 @@ gcode:
description: Start Bed Leveling
gcode:
{% if 'PROBE_COUNT' in params|upper %}
{% set get_count = ('PROBE_COUNT=' + params.PROBE_COUNT) %}
{% set get_count = ('PROBE_COUNT=' + params.PROBE_COUNT) %}
{%else %}
{% set get_count = "" %}
{% set get_count = "" %}
{% endif %}
{% set bed_temp = params.BED_TEMP|default(50)|float %}
{% set hotend_temp = params.HOTEND_TEMP|default(140)|float %}
@ -114,38 +160,6 @@ gcode:
WAIT_TEMP_START
[gcode_macro LUBRICATE_RODS]
description: Distribute lubricant on Rods
gcode:
{% set min_speed = 3000 %} # Minimum speed in mm/min
{% set max_speed = 18000 %} # Maximum speed in mm/min
{% if printer.toolhead.homed_axes != "xyz" %}
G28
{% endif %}
G1 Z50 F300
{% set x_max = printer.toolhead.axis_maximum.x|int %}
{% set y_max = printer.toolhead.axis_maximum.y|int %}
{% set edge_offset_x = x_max * 0.05 %}
{% set edge_offset_y = y_max * 0.05 %}
{% set x_range = x_max - edge_offset_x %}
{% set y_range = y_max - edge_offset_y %}
{% set num_steps_x = (x_range / 10)|int %}
{% set num_steps_y = (y_range / 10)|int %}
{% set speed_increment_x = (max_speed - min_speed) / num_steps_x %}
{% set speed_increment_y = (max_speed - min_speed) / num_steps_y %}
{% set current_speed_x = min_speed %}
{% set current_speed_y = min_speed %}
{% for i in range(num_steps_x) %}
G1 X{edge_offset_x + i * 10} Y{edge_offset_y} F{current_speed_x}
G1 X{edge_offset_x + i * 10} Y{y_range} F{current_speed_x}
{% set current_speed_x = current_speed_x + speed_increment_x %}
{% endfor %}
{% for j in range(num_steps_y) %}
G1 Y{edge_offset_y + j * 10} X{edge_offset_x} F{current_speed_y}
G1 Y{edge_offset_y + j * 10} X{x_range} F{current_speed_y}
{% set current_speed_y = current_speed_y + speed_increment_y %}
{% endfor %}
[gcode_macro WARMUP]
description: Stress Test
variable_maxd: 14142.14 ; = SQRT(2*maxy)
@ -158,12 +172,8 @@ gcode:
{% endif %}
{% endif %}
{% set loop_cnt = max_loops %}
{% if 'X_ACCEL_MAX' in params|upper %}
{% set maxx = params.X_ACCEL_MAX|default(10000)|int %}
{% endif %}
{% if 'Y_ACCEL_MAX' in params|upper %}
{% set maxy = params.Y_ACCEL_MAX|default(10000)|int %}
{% endif %}
{% set maxx = params.X_ACCEL_MAX|default(10000)|int %}
{% set maxy = params.Y_ACCEL_MAX|default(10000)|int %}
{% set max_x = (printer.toolhead.axis_maximum.x|int-5) %}
{% set max_y = (printer.toolhead.axis_maximum.y|int-5) %}
{% set loop_step_y = max_y//(loop_cnt-1) %}

Binary file not shown.

201
files/moonraker/nginx.conf Normal file
View file

@ -0,0 +1,201 @@
worker_processes 1;
events {
worker_connections 1024;
}
http {
include mime.types;
default_type application/octet-stream;
sendfile on;
keepalive_timeout 65;
proxy_connect_timeout 1600;
proxy_send_timeout 1600;
proxy_read_timeout 1600;
send_timeout 1600;
server {
listen 4408 default_server;
access_log off;
error_log off;
gzip on;
gzip_vary on;
gzip_proxied any;
gzip_proxied expired no-cache no-store private auth;
gzip_comp_level 4;
gzip_buffers 16 8k;
gzip_http_version 1.1;
gzip_types text/plain text/css text/xml text/javascript application/x-javascript application/json application/xml;
root /usr/share/fluidd;
index index.html;
server_name _;
client_max_body_size 0;
proxy_request_buffering off;
location / {
try_files $uri $uri/ /index.html;
}
location = /index.html {
add_header Cache-Control "no-store, no-cache, must-revalidate";
}
location /websocket {
proxy_pass http://apiserver/websocket;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_read_timeout 86400;
}
location ~ ^/(printer|api|access|machine|server)/ {
proxy_pass http://apiserver$request_uri;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Scheme $scheme;
}
location /webcam/ {
proxy_pass http://mjpgstreamer1/;
}
location /webcam2/ {
proxy_pass http://mjpgstreamer2/;
}
location /webcam3/ {
proxy_pass http://mjpgstreamer3/;
}
location /webcam4/ {
proxy_pass http://mjpgstreamer4/;
}
}
server {
listen 4409 default_server;
access_log off;
error_log off;
gzip on;
gzip_vary on;
gzip_proxied any;
gzip_proxied expired no-cache no-store private auth;
gzip_comp_level 4;
gzip_buffers 16 8k;
gzip_http_version 1.1;
gzip_types text/plain text/css text/xml text/javascript application/javascript application/x-javascript application/json application/xml;
root /usr/data/mainsail;
index index.html;
server_name _;
client_max_body_size 0;
proxy_request_buffering off;
location / {
try_files $uri $uri/ /index.html;
}
location = /index.html {
add_header Cache-Control "no-store, no-cache, must-revalidate";
}
location /websocket {
proxy_pass http://apiserver/websocket;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection $connection_upgrade;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_read_timeout 86400;
}
location ~ ^/(printer|api|access|machine|server)/ {
proxy_pass http://apiserver$request_uri;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Scheme $scheme;
}
location /webcam/ {
postpone_output 0;
proxy_buffering off;
proxy_ignore_headers X-Accel-Buffering;
access_log off;
error_log off;
proxy_pass http://mjpgstreamer1/;
}
location /webcam2/ {
postpone_output 0;
proxy_buffering off;
proxy_ignore_headers X-Accel-Buffering;
access_log off;
error_log off;
proxy_pass http://mjpgstreamer2/;
}
location /webcam3/ {
postpone_output 0;
proxy_buffering off;
proxy_ignore_headers X-Accel-Buffering;
access_log off;
error_log off;
proxy_pass http://mjpgstreamer3/;
}
location /webcam4/ {
postpone_output 0;
proxy_buffering off;
proxy_ignore_headers X-Accel-Buffering;
access_log off;
error_log off;
proxy_pass http://mjpgstreamer4/;
}
}
map $http_upgrade $connection_upgrade {
default upgrade;
'' close;
}
upstream apiserver {
ip_hash;
server 127.0.0.1:7125;
}
upstream mjpgstreamer1 {
ip_hash;
server 127.0.0.1:8080;
}
upstream mjpgstreamer2 {
ip_hash;
server 127.0.0.1:8081;
}
upstream mjpgstreamer3 {
ip_hash;
server 127.0.0.1:8082;
}
upstream mjpgstreamer4 {
ip_hash;
server 127.0.0.1:8083;
}
}

Binary file not shown.

View file

@ -77,4 +77,4 @@ elif [ "$1" == "-reload_camera" ]; then
else
echo -e "Invalid argument. Usage: $0 [-backup_klipper | -restore_klipper | -backup_moonraker | -restore_moonraker | -reload_camera]"
exit 1
fi
fi

View file

@ -9,13 +9,16 @@ NGINX_ARGS="-c /usr/data/nginx/nginx/nginx.conf"
case "$1" in
start)
echo "Starting nginx..."
mkdir -p /var/log/nginx /var/tmp/nginx
start-stop-daemon -S -p "$PIDFILE" --exec "$NGINX" -- $NGINX_ARGS
;;
stop)
echo "Stopping nginx..."
start-stop-daemon -K -x "$NGINX" -p "$PIDFILE" -o
;;
reload|force-reload)
echo "Reloading nginx..."
"$NGINX" -s reload
;;
restart)

View file

@ -0,0 +1,31 @@
#!/bin/sh
# USB Camera Service
# Credit: destinal & Guilouz
case "$1" in
start)
echo "Starting USB Camera..."
V4L_DEVS=$(v4l2-ctl --list-devices | grep -A1 usb | sed 's/^[[:space:]]*//g' | grep '^/dev')
CREALITY_CAMS=$(v4l2-ctl --list-devices | grep -E 'CREALITY' | wc -l)
if [ "x$V4L_DEVS" = "x" -o $CREALITY_CAMS -gt 0 ]; then
/opt/bin/mjpg_streamer -b -i "/opt/lib/mjpg-streamer/input_uvc.so -d /dev/video4 -r 1280x720 -f 15" -o "/opt/lib/mjpg-streamer/output_http.so -p 8080"
/opt/bin/mjpg_streamer -b -i "/opt/lib/mjpg-streamer/input_uvc.so -d /dev/video6 -r 1280x720 -f 15" -o "/opt/lib/mjpg-streamer/output_http.so -p 8081"
else
/opt/bin/mjpg_streamer -b -i "/opt/lib/mjpg-streamer/input_uvc.so -d /dev/video4 -r 1280x720 -f 15" -o "/opt/lib/mjpg-streamer/output_http.so -p 8080"
fi
;;
stop)
echo "Stopping USB Camera..."
killall -q mjpg_streamer
;;
restart|reload)
"$0" stop
sleep 1
"$0" start
;;
*)
echo "Usage: /etc/init.d/S50usb_camera {start|stop|restart}"
exit 1
esac
exit $?

View file

@ -0,0 +1,34 @@
#!/bin/sh
# USB Camera Service
# Credit: destinal & Guilouz
case "$1" in
start)
echo "Starting USB Camera..."
V4L_DEVS=$(v4l2-ctl --list-devices | grep -A1 usb | sed 's/^[[:space:]]*//g' | grep '^/dev')
CREALITY_CAMS=$(v4l2-ctl --list-devices | grep -E 'CREALITY|CCX2F3298' | wc -l)
if [ "x$V4L_DEVS" = "x" -o $CREALITY_CAMS -gt 0 ]; then
echo "Error: No third party camera found or you use a Creality camera!"
exit 1
fi
PORT=8080
for V4L_DEV in $V4L_DEVS; do
/opt/bin/mjpg_streamer -b -i "/opt/lib/mjpg-streamer/input_uvc.so -d $V4L_DEV -r 1280x720 -f 15" -o "/opt/lib/mjpg-streamer/output_http.so -p $PORT"
PORT=`expr $PORT + 1`
done
;;
stop)
echo "Stopping USB Camera..."
killall -q mjpg_streamer
;;
restart|reload)
"$0" stop
sleep 1
"$0" start
;;
*)
echo "Usage: /etc/init.d/S50usb_camera {start|stop|restart}"
exit 1
esac
exit $?

View file

@ -12,36 +12,36 @@ PRINTER_LOGS_DIR=$PRINTER_DATA_DIR/logs
PID_FILE=/var/run/moonraker.pid
start() {
[ -d $PRINTER_DATA_DIR ] || mkdir -p $PRINTER_DATA_DIR
[ -d $PRINTER_CONFIG_DIR ] || mkdir -p $PRINTER_CONFIG_DIR
[ -d $PRINTER_LOGS_DIR ] || mkdir -p $PRINTER_LOGS_DIR
rm -rf /usr/data/moonraker/tmp; mkdir -p /usr/data/moonraker/tmp
TMPDIR=/usr/data/moonraker/tmp HOME=/root start-stop-daemon -S -q -b -m -p $PID_FILE \
--exec $PROG -- $PY_SCRIPT -d $PRINTER_DATA_DIR
[ -d $PRINTER_DATA_DIR ] || mkdir -p $PRINTER_DATA_DIR
[ -d $PRINTER_CONFIG_DIR ] || mkdir -p $PRINTER_CONFIG_DIR
[ -d $PRINTER_LOGS_DIR ] || mkdir -p $PRINTER_LOGS_DIR
HOME=/root start-stop-daemon -S -q -b -m -p $PID_FILE \
--exec $PROG -- $PY_SCRIPT -d $PRINTER_DATA_DIR
}
stop() {
start-stop-daemon -K -q -p $PID_FILE
start-stop-daemon -K -q -p $PID_FILE
}
restart() {
stop
sleep 1
start
stop
sleep 1
start
}
case "$1" in
start)
start
;;
start
;;
stop)
stop
;;
stop
;;
restart|reload)
restart
;;
restart
;;
*)
echo "Usage: $0 {start|stop|restart}"
exit 1
echo "Usage: $0 {start|stop|restart}"
exit 1
esac
exit $?