Overview
An encoder is attached to the spindle, in my case a 1 pulse per revolution encoder. The position of the encoder is scaled using a HAL scale component from pulses per second to pulses per minute thereby giving RPMs. In my case since I had a single pulse per revolution I scaled by 60 to give spindle RPM. This spindle RPM is connected to the feedback pin of a HAL pid component. The commanded spindle RPM is connected to the command pin of the PID. The PID is tuned to use Pgain=0, Igain=1, Dgain=1. The output of the PID is added to the commanded spindle RPM and then fed into the pwmgen as the value of the pwm.
Hal file snippet
# -------------------------------------------------- # Closed Loop Spindle Control # -------------------------------------------------- # Initialize the encoder (spindle) loadrt encoder num_chan=1 addf encoder.update-counters base-thread addf encoder.capture-position servo-thread setp encoder.0.position-scale 1 setp encoder.0.counter-mode 1 # Initialize the PID loadrt pid num_chan=1 addf pid.0.do-pid-calcs servo-thread setp pid.0.Pgain 0 setp pid.0.Igain 1 setp pid.0.Dgain 1 setp pid.0.maxoutput 4000 # Initialize the pwmgen loadrt pwmgen output_type=0 addf pwmgen.update servo-thread addf pwmgen.make-pulses base-thread setp pwmgen.0.pwm-freq 1000.0 setp pwmgen.0.scale 4000 setp pwmgen.0.dither-pwm true # Initialize the scale # (This is used to scale the encoder pulse to RPM) # (In my case, i have 1 ppr so it is scaled by 60) loadrt scale count=1 addf scale.0 servo-thread setp scale.0.gain 60 # Initialize the sum2 loadrt sum2 count=1 addf sum2.0 servo-thread # Attach the motion.spindle-on to enable the pwmgen and the pid net spindle_enable motion.spindle-on => pwmgen.0.enable => pid.0.enable # Attach the encoder to the parallel port pin net parport_15_in parport.0.pin-15-in => encoder.0.phase-A => encoder.0.phase-Z # Attach the encoder to the motion and the scale net spindle_rev_count encoder.0.position => motion.spindle-revs net spindle_index_enable encoder.0.index-enable <=> motion.spindle-index-enable net encoder_raw_velocity encoder.0.velocity => scale.0.in # Attach the pid to the scale, motion, and sum net pid_feedback pid.0.feedback <= motion.spindle-speed-in <= scale.0.out net pid_command pid.0.command <= motion.spindle-speed-out => sum2.0.in0 net pid_output pid.0.output => sum2.0.in1 # Attach the pwmgen to the sum and the parallel port net pwmgen_value pwmgen.0.value <= sum2.0.out net pwmgen_out pwmgen.0.pwm => parport.0.pin-16-out