############### Config options ##################

[gcode_macro _BEDFANVARS]
variable_threshold: 100		# If bed temp target is above this threshold, fans will be enabled. If temp is set to below this threshold, fans will be disabled.
variable_fast: 0.6		# Fan speed once bed temp is reached  
variable_slow: 0.2		# Fan speed while bed is heating
gcode:

########## Bed Fans #########

[fan_generic BedFans]
pin: PB11
#cycle_time: 0.05
kick_start_time: 0.5

########## Aliases #########

[gcode_macro BEDFANSSLOW]
gcode:
	# Vars
	{% set SLOW = printer["gcode_macro _BEDFANVARS"].slow|float %}
	
	SET_FAN_SPEED FAN=BedFans SPEED={SLOW}

[gcode_macro BEDFANSFAST]
gcode:
	# Vars
	{% set FAST = printer["gcode_macro _BEDFANVARS"].fast|float %}
	
	SET_FAN_SPEED FAN=BedFans SPEED={FAST}

[gcode_macro BEDFANSOFF]
gcode:
	SET_FAN_SPEED FAN=BedFans SPEED=0

############ Command overrides ############

# Override, set fan speeds to low and start monitoring loop.
[gcode_macro SET_HEATER_TEMPERATURE]
rename_existing: _SET_HEATER_TEMPERATURE
gcode:
	# Parameters
	{% set HEATER = params.HEATER|default("None") %}
	{% set TARGET = params.TARGET|default(0)|int %}
	# Vars
	{% set THRESHOLD = printer["gcode_macro _BEDFANVARS"].threshold|int %}
	
	{% if HEATER|lower == "extruder" %}
		M104 S{TARGET}
	{% elif HEATER|lower == "heater_bed" %}
		M99140 S{TARGET}
	{% else %}
		{action_respond_info("Heater %s not supported" % HEATER)}
	{% endif %}

	# Set fans to low if heater_bed temp is requested above threshold temp, and kick off monitoring loop.
	{% if HEATER|lower == "heater_bed" %}
		{% if TARGET >= THRESHOLD %}
			BEDFANSSLOW
			UPDATE_DELAYED_GCODE ID=bedfanloop DURATION=1
		{% else %}
			BEDFANSOFF
			UPDATE_DELAYED_GCODE ID=bedfanloop DURATION=0 #	Cancel bed fan loop if it's running
		{% endif %}
	{% endif %}
	
# Override M190 (Wait for Bed Temperature)
# As a bonus, use TEMPERATURE_WAIT so we don't have to wait for PID to level off.
[gcode_macro M190]
rename_existing: M99190
gcode:
	# Parameters
	{% set S = params.S|int %}
	# Vars
	{% set THRESHOLD = printer["gcode_macro _BEDFANVARS"].threshold|int %}
	
	{% if S >= THRESHOLD %}
		BEDFANSSLOW																# >= Threshold temp: Low speed fans while heating 
	{% else %}
		BEDFANSOFF																# < Threshold temp: Turn bed fans off
	{% endif %}                                        

	M140 {% for p in params
	  %}{'%s%s' % (p, params[p])}{%
	  endfor %}																	# Set bed temp
	  
	{% if S != 0 %}
		TEMPERATURE_WAIT SENSOR=heater_bed MINIMUM={S|int} MAXIMUM={S|int + 5}	# Wait for bed temp within 5 degrees
	{% endif %}

	# Post-heating fan speeds
	{% if S >= THRESHOLD %}								    
		BEDFANSFAST																# >= Threshold temp: Higher speed fans after heating finished
	{% endif %}
	
# Replace M140 (Set Bed Temperature) to just be an alias of SET_HEATER_TEMPERATURE (which has associated bed fan logic if enabled)
[gcode_macro M140]
rename_existing: M99140
gcode:
	# Parameters
	{% set S = params.S|float %}
	
	SET_HEATER_TEMPERATURE HEATER=heater_bed TARGET={S}
	
# Replace TURN_OFF_HEATERS
[gcode_macro TURN_OFF_HEATERS]
rename_existing: _TURN_OFF_HEATERS
gcode:
	BEDFANSOFF
	_TURN_OFF_HEATERS
	
################ Monitoring loop #####################

# Turns bed fans to "fast" speed once target bed temp is reached.
[delayed_gcode bedfanloop]
gcode:
	# Vars
	{% set THRESHOLD = printer["gcode_macro _BEDFANVARS"].threshold|int %}
	
	{% if printer.heater_bed.target >= THRESHOLD %}								# Continue only if target temp greater than threshold.
		{% if printer.heater_bed.temperature|int >= (printer.heater_bed.target|int - 1) %}
			BEDFANSFAST															# If within 1 degree of target temp: Higher speed fans
		{% else %}
			UPDATE_DELAYED_GCODE ID=bedfanloop DURATION=5						# If temp not reached yet: loop again
		{% endif %}
	{% endif %}