Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@

/*.cfg
/*.conf
/*.log
/.VERSION
/scripts/K-ShakeTune
/klipper


# -------------------------------------------------------------------
Expand Down
5 changes: 5 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@

### 🐛 Bug Fixes

- Fix aux fan tach monitoring disabled before end-print run-down
- Fix aux fan M106/M107 bridge to not break config load when no [fan] section is defined (moved bridge to fan_bridge.cfg, included only from configs that define [fan])
- Add `aux_fan_vent_temp > 0` guard to vent condition so room temperature no longer triggers a 2-minute delay
- Start aux fan tach monitoring before the chamber vent in START_PRINT
- Stop aux fan at end of `_MODULE_HEATSOAK_BED` to prevent run-away fan when chamber_soak is omitted
- Relax chamber heatsoak temperature check
- Use contact home action for Beacon
- Correct BTT EBB GEN2 fan aliases
Expand Down
13 changes: 13 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,15 @@ Klippain is regularly updated with new features and merged PRs from users. You c
Fun fact: "pain" \pɛ̃\ is the French word for bread, so there's no pain in this pain—only joy! Thanks to the French channel "honhonhonbaguette-FR" on the Voron Discord for the joke and name suggestion!


## What makes this fork different

This repository is a fork of [Frix-x/klippain](https://github.com/Frix-x/klippain) that tracks upstream and adds the following on top of it:

- **Auxiliary part cooling fan** (`AUX_FAN`): an independent secondary part cooling fan, natively controllable through `START_AUX_FAN`/`STOP_AUX_FAN` macros and compatible with OrcaSlicer's "Auxiliary Part Cooling Fan" via an `M106 P2`/`M107 P2` bridge. Optional `AUX_FAN_TACHO` tachometer monitoring provides the same safety checks as the base fans. It is integrated in the start/end/cancel print sequence for chamber venting (when too hot), heatsoak heat spreading, and a post-print run-down to cool the bed faster. Enabling it requires uncommenting `[include config/hardware/fans/aux_fan.cfg]` (or the `aux_fan_tachometer.cfg` variant) in `user_templates/printer.cfg`, wiring the `AUX_FAN`/`AUX_FAN_TACHO` pins in `mcu.cfg`, and tuning the `variable_aux_fan_*` settings in `user_templates/variables.cfg`.

- **Automated config validation**: a CI pipeline (`tests/lint_jinja.py` and `tests/config_check.py`, run by `.github/workflows/validate.yml`) syntax-checks every templated macro block with Klipper's own Jinja2 environment, then assembles a full reference configuration and loads it with a real Klippy (standard and aux-fan-tachometer variants) to catch errors before they reach your printer. Run it locally with `python3 tests/lint_jinja.py` and `python3 tests/config_check.py standard <path-to-klipper>`.


## Features

Klippain is designed for versatility. By selecting and enabling the desired hardware and software options, it can be used on a wide range of machines.
Expand All @@ -24,6 +33,10 @@ To install Klippain, first ensure you have already Klipper, Moonraker, and a Web

Then, run the installation script using the following command over SSH. This script will backup your old configuration, download this GitHub repository to your RaspberryPi home directory, and set up Klippain in `~/printer_data/config`. You will also be prompted to select and install MCU board_pins templates. This is recommended for faster `mcu.cfg` setup, but you can do it manually later if you prefer.

> **Note for users of this fork**:
>
> The command below installs **upstream** Klippain (the `Frix-x/klippain` repository). If you want to use the fork-specific additions described in [What makes this fork different](#what-makes-this-fork-different), install from this fork instead, e.g. via the `Code` button on GitHub or by cloning `git@github.com:ndotzbgt/klippain.git` into `~/printer_data/config`.

```bash
wget -O - https://raw.githubusercontent.com/Frix-x/klippain/main/install.sh | bash
```
Expand Down
13 changes: 13 additions & 0 deletions config/hardware/fans/aux_fan.cfg
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
# Secondary part cooling fan, independently controlled (e.g. OrcaSlicer "Auxiliary Part Cooling Fan")
[gcode_macro _USER_VARIABLES]
variable_aux_fan_enabled: True
variable_aux_fan_name: "aux_fan"
gcode:

# Also include directly the auxiliary fan control macros from here
[include ../../../macros/hardware_functions/aux_fan.cfg]

[fan_generic aux_fan]
pin: AUX_FAN
# Wired to the main MCU: define "AUX_FAN=<pin>" in your main mcu.cfg,
# or replace this pin with the raw main-board pin (e.g. PB6).
17 changes: 17 additions & 0 deletions config/hardware/fans/aux_fan_tachometer.cfg
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
# Secondary part cooling fan with tachometer monitoring (requires an AUX_FAN_TACHO pin, e.g. Fysetc H36/SB Combo)
# Use this file instead of aux_fan.cfg
[gcode_macro _USER_VARIABLES]
variable_aux_fan_enabled: True
variable_aux_fan_name: "aux_fan"
variable_aux_fan_tach_enabled: True
variable_aux_fan_tach_poll_interval: 3 # seconds between tachometer safety checks
gcode:

# Also include directly the auxiliary fan control macros from here
[include ../../../macros/hardware_functions/aux_fan.cfg]

[fan_generic aux_fan]
pin: AUX_FAN
tachometer_pin: AUX_FAN_TACHO
# Wired to the main MCU: define "AUX_FAN=<pin>" and "AUX_FAN_TACHO=<pin>" in your
# main mcu.cfg, or replace the pins with the raw main-board pins.
1 change: 1 addition & 0 deletions config/hardware/fans/hotend_fan_tachometer.cfg
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
[gcode_macro _USER_VARIABLES]
variable_hotend_fan_tach_enabled: True
variable_hotend_tach_poll_interval: 3 # seconds between tachometer safety checks
gcode:

[heater_fan hotend_fan]
Expand Down
4 changes: 4 additions & 0 deletions config/hardware/fans/part_fan.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -2,3 +2,7 @@
pin: PART_FAN
kick_start_time: 0.100
cycle_time: 0.010

# OrcaSlicer M106 P2 / M107 P2 bridge for the auxiliary fan (only effective when an aux fan is configured).
# Uses rename_existing, so it must be included alongside a [fan] section (like this file).
[include ../../../macros/hardware_functions/fan_bridge.cfg]
4 changes: 4 additions & 0 deletions config/hardware/fans/part_fan_tachometer.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -8,5 +8,9 @@ kick_start_time: 0.100
cycle_time: 0.010
tachometer_pin: PART_FAN_TACHO

# OrcaSlicer M106 P2 / M107 P2 bridge for the auxiliary fan (only effective when an aux fan is configured).
# Uses rename_existing, so it must be included alongside a [fan] section (like this file).
[include ../../../macros/hardware_functions/fan_bridge.cfg]

# And we also include the tachometer check macros from here
[include ../../../macros/helpers/tachometer_check.cfg]
2 changes: 2 additions & 0 deletions docs/pinout.md
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,8 @@ Here is a list of the common/public "Frix-x names" available to use in your own
- `E_FAN_TACHO`: tachometer of the hotend fan, optional and used to validate that the fan is spinning as a safety feature
- `PART_FAN`: part fan used during the print. This pin should be a PWM capable pin to allow modulation of the fan speed
- `PART_FAN_TACHO`: tachometer of the part fan, optional and used to validate that the fan is spinning as a safety feature
- `AUX_FAN`: secondary part cooling fan, independently controlled (e.g. OrcaSlicer "Auxiliary Part Cooling Fan"). This pin should be a PWM capable pin to allow modulation of the fan speed
- `AUX_FAN_TACHO`: tachometer of the auxiliary fan, optional and used to validate that the fan is spinning as a safety feature
- `EXHAUST_FAN`: for an exhaust filter (such as the Voron basic exhaust). This pin should be a PWM capable pin to allow modulation of the fan speed
- `FILTER_FAN`: for a filter (such as a Nevermore filter). This pin should be a PWM capable pin to allow modulation of the fan speed
- `CONTROLLER_FAN`: to cool down your MCUs or electronic bay
Expand Down
22 changes: 22 additions & 0 deletions macros/base/cancel_print.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,10 @@ gcode:
{% set filament_sensor_enabled = printer["gcode_macro _USER_VARIABLES"].filament_sensor_enabled|default(False) %}
{% set filter_default_time = printer["gcode_macro _USER_VARIABLES"].filter_default_time_on_end_print|default(600)|int %}
{% set hotend_fan_tach_enabled = printer["gcode_macro _USER_VARIABLES"].hotend_fan_tach_enabled|default(False) %}
{% set aux_fan_enabled = printer["gcode_macro _USER_VARIABLES"].aux_fan_enabled|default(False) %}
{% set aux_fan_tach_enabled = printer["gcode_macro _USER_VARIABLES"].aux_fan_tach_enabled|default(False) %}
{% set aux_fan_speed_on_end_print = printer["gcode_macro _USER_VARIABLES"].aux_fan_speed_on_end_print|default(100)|int %}
{% set aux_fan_time_on_end_print = printer["gcode_macro _USER_VARIABLES"].aux_fan_time_on_end_print|default(300)|int %}
{% set retract_length = printer["gcode_macro _USER_VARIABLES"].retract_length|default(20)|float %}

{% if printer.toolhead.homed_axes == "xyz" %}
Expand Down Expand Up @@ -41,6 +45,10 @@ gcode:
UPDATE_DELAYED_GCODE ID=_BACKGROUND_HOTEND_TACHO_CHECK DURATION=0
{% endif %}

{% if aux_fan_tach_enabled %}
UPDATE_DELAYED_GCODE ID=_BACKGROUND_AUX_TACHO_CHECK DURATION=0
{% endif %}

M107
M400

Expand All @@ -62,6 +70,20 @@ gcode:
{% endif %}
{% endif %}

# If an auxiliary fan is connected and enabled, keep it running after the cancel to
# cool the bed faster and help recirculating filters/exhaust fans work faster.
# Re-enable tach monitoring BEFORE starting the fan so it is monitored from the
# moment it spins up (previously tach was disabled earlier in this macro and only
# re-enabled after the fan was already running).
{% if aux_fan_enabled %}
{% set aux_fan_time = params.AUX_FAN_TIME|default(aux_fan_time_on_end_print)|int %}
{% if aux_fan_tach_enabled %}
UPDATE_DELAYED_GCODE ID=_BACKGROUND_AUX_TACHO_CHECK DURATION=1
{% endif %}
START_AUX_FAN SPEED={aux_fan_speed_on_end_print / 100}
UPDATE_DELAYED_GCODE ID=_STOP_AUX_FAN_DELAYED DURATION={aux_fan_time}
{% endif %}

{% if light_enabled %}
LIGHT_ON S={light_intensity_end_print}
{% endif %}
Expand Down
5 changes: 5 additions & 0 deletions macros/base/control.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,14 @@ gcode:
{% set light_enabled = printer["gcode_macro _USER_VARIABLES"].light_enabled %}
{% set status_leds_control_enabled = printer["gcode_macro _USER_VARIABLES"].status_leds_control_enabled|default(False) %}
{% set display_leds_enabled = printer["gcode_macro _USER_VARIABLES"].status_leds_minidisplay_enabled %}
{% set aux_fan_enabled = printer["gcode_macro _USER_VARIABLES"].aux_fan_enabled|default(False) %}
M84 ; turn steppers off
TURN_OFF_HEATERS ; turn bed / hotend off
M107 ; turn print cooling fan off
{% if aux_fan_enabled %}
UPDATE_DELAYED_GCODE ID=_STOP_AUX_FAN_DELAYED DURATION=0 ; deactivate any pending aux fan run-down
STOP_AUX_FAN ; turn auxiliary fan off
{% endif %}
{% if light_enabled %}
LIGHT_OFF ; turn off light
{% endif %}
Expand Down
23 changes: 23 additions & 0 deletions macros/base/end_print.cfg
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,10 @@ gcode:
{% set filter_default_time = printer["gcode_macro _USER_VARIABLES"].filter_default_time_on_end_print|default(600)|int %}
{% set filament_sensor_enabled = printer["gcode_macro _USER_VARIABLES"].filament_sensor_enabled|default(False) %}
{% set hotend_fan_tach_enabled = printer["gcode_macro _USER_VARIABLES"].hotend_fan_tach_enabled|default(False) %}
{% set aux_fan_enabled = printer["gcode_macro _USER_VARIABLES"].aux_fan_enabled|default(False) %}
{% set aux_fan_tach_enabled = printer["gcode_macro _USER_VARIABLES"].aux_fan_tach_enabled|default(False) %}
{% set aux_fan_speed_on_end_print = printer["gcode_macro _USER_VARIABLES"].aux_fan_speed_on_end_print|default(100)|int %}
{% set aux_fan_time_on_end_print = printer["gcode_macro _USER_VARIABLES"].aux_fan_time_on_end_print|default(300)|int %}

PARK

Expand Down Expand Up @@ -66,6 +70,20 @@ gcode:
{% endif %}
{% endif %}

# If an auxiliary fan is connected and enabled, keep it running after the print to
# cool the bed faster and help recirculating filters/exhaust fans work faster.
# Re-enable tach monitoring BEFORE starting the fan so it is monitored from the
# moment it spins up (previously tach was disabled in _MODULE_TURN_OFF_FANS and
# only re-enabled after the fan was already running).
{% if aux_fan_enabled %}
{% set aux_fan_time = params.AUX_FAN_TIME|default(aux_fan_time_on_end_print)|int %}
{% if aux_fan_tach_enabled %}
UPDATE_DELAYED_GCODE ID=_BACKGROUND_AUX_TACHO_CHECK DURATION=1
{% endif %}
START_AUX_FAN SPEED={aux_fan_speed_on_end_print / 100}
UPDATE_DELAYED_GCODE ID=_STOP_AUX_FAN_DELAYED DURATION={aux_fan_time}
{% endif %}

{% if light_enabled %}
LIGHT_ON S={light_intensity_end_print}
{% endif %}
Expand Down Expand Up @@ -127,11 +145,16 @@ gcode:
# ----- TURN OFF FANS -------------------------------------
# Turn off fans and fan monitoring at the end of a print job
{% set hotend_fan_tach_enabled = printer["gcode_macro _USER_VARIABLES"].hotend_fan_tach_enabled|default(False) %}
{% set aux_fan_tach_enabled = printer["gcode_macro _USER_VARIABLES"].aux_fan_tach_enabled|default(False) %}

{% if hotend_fan_tach_enabled %}
UPDATE_DELAYED_GCODE ID=_BACKGROUND_HOTEND_TACHO_CHECK DURATION=0
{% endif %}

{% if aux_fan_tach_enabled %}
UPDATE_DELAYED_GCODE ID=_BACKGROUND_AUX_TACHO_CHECK DURATION=0
{% endif %}

M107


Expand Down
Loading