Step 3 — Proportional Control Correction
The error map from Step 2 is fed into a proportional controller that adjusts the G-code feedrates for the next layer to compensate for measured surface-height deviations. This closes the control loop.
Control Law
Section titled “Control Law”F_corrected = F_nominal * (1 + K_p * z_err_mm)Where:
F_nominal— the feedrate in the original (uncorrected) G-code for the next layer.K_p— proportional gain (default: 1.0). Tuned experimentally.z_err_mm— the surface height error at the nearest measured point from the previous layer’s error map.
Intuition
Section titled “Intuition”- Positive error (surface too high) → increase feedrate → robot moves faster → deposits less material → surface drops.
- Negative error (surface too low) → decrease feedrate → robot moves slower → deposits more material → surface rises.
Spatial Matching
Section titled “Spatial Matching”For each extruding G-code point (E > 0) in the next layer’s toolpath,
the controller finds the nearest point in the error map CSV (by 3D
Euclidean distance) and applies that point’s err_mm value to the
feedrate formula. Only extruding moves are modified; travel moves are
passed through unchanged.
Command
Section titled “Command”uv run python simple_proportional.py \ <next_layer.gcode> \ <L<N>_error_map.csv> \ -k <K_p> \ -o <next_layer_corrected.gcode>Working directory: ros2_ws/lib/control/simple_proportional/
Arguments
Section titled “Arguments”| Flag | Default | Purpose |
|---|---|---|
| Positional 1 | — | Next layer’s nominal G-code file |
| Positional 2 | — | Previous layer’s error_map.csv |
-k, --proportional_constant | 1.0 | Proportional gain K_p |
-o | — | Output path for corrected G-code |
--lower_bounds_corrected_feed | 3.2 | Minimum allowed corrected feedrate |
--preview | — | Generate an HTML 3D plot of the feedrate corrections (path auto-derived if flag given without value) |
Inputs
Section titled “Inputs”1. Next Layer G-Code (nominal)
Section titled “1. Next Layer G-Code (nominal)”Standard slicer output. Only G1 moves with non-zero E values have
their F parameter adjusted.
G1 X-7.119 Y-17.261 E24.0 F3.4 ;N4G1 X-5.676 Y-16.964 E24.0 F3.4 ;N52. Previous Layer Error Map (CSV)
Section titled “2. Previous Layer Error Map (CSV)”X,Y,Z,err_mm12.2021,47.3637,43.2479,4.064410.7972,47.6810,43.2649,4.0644Output
Section titled “Output”A corrected G-code file identical to the input except that feedrate (F)
values on extruding moves have been scaled according to the control law.
This file becomes the input to Step 1 for the next iteration.
Future Work
Section titled “Future Work”The current controller is purely proportional (P-only). Planned extensions include:
- Integral (I) term — accumulate historical error across multiple layers to eliminate steady-state offset.
- Derivative (D) term — respond to the rate of error change between consecutive layers.
- Full PID tuning with per-region gain scheduling.