delta_calibrate: Perform coordinate descent in a background process

Run the coordinate descent in a background process so that the main
thread does not block.

Signed-off-by: Kevin O'Connor <kevin@koconnor.net>
This commit is contained in:
Kevin O'Connor 2018-10-15 18:52:28 -04:00
parent 46355f903e
commit 368703fd78
2 changed files with 30 additions and 8 deletions

View File

@ -216,12 +216,7 @@ class DeltaCalibrate:
adj_params += ('arm_a', 'arm_b', 'arm_c')
z_weight = len(distances) / (MEASURE_WEIGHT * len(probe_positions))
# Perform coordinate descent
call_count = [0]
def delta_errorfunc(params):
call_count[0] += 1
if not call_count[0] % 1000:
self.gcode.respond_info("Working on calibration...")
self.printer.get_reactor().pause(0.)
# Build new delta_params for params under test
delta_params = build_delta_params(params)
# Calculate z height errors
@ -237,8 +232,8 @@ class DeltaCalibrate:
d = math.sqrt((x1-x2)**2 + (y1-y2)**2 + (z1-z2)**2)
total_error += (d - dist)**2
return total_error
new_params = mathutil.coordinate_descent(
adj_params, params, delta_errorfunc)
new_params = mathutil.background_coordinate_descent(
self.printer, adj_params, params, delta_errorfunc)
# Log and report results
logging.info("Calculated delta_calibrate parameters: %s", new_params)
new_delta_params = build_delta_params(new_params)

View File

@ -3,7 +3,7 @@
# Copyright (C) 2018 Kevin O'Connor <kevin@koconnor.net>
#
# This file may be distributed under the terms of the GNU GPLv3 license.
import math, logging
import math, logging, multiprocessing
######################################################################
@ -45,6 +45,33 @@ def coordinate_descent(adj_params, params, error_func):
logging.info("Coordinate descent best_err: %s rounds: %d", best_err, rounds)
return params
# Helper to run the coordinate descent function in a background
# process so that it does not block the main thread.
def background_coordinate_descent(printer, adj_params, params, error_func):
parent_conn, child_conn = multiprocessing.Pipe()
def wrapper():
res = coordinate_descent(adj_params, params, error_func)
child_conn.send(res)
child_conn.close()
# Start a process to perform the calculation
calc_proc = multiprocessing.Process(target=wrapper)
calc_proc.daemon = True
calc_proc.start()
# Wait for the process to finish
reactor = printer.get_reactor()
gcode = printer.lookup_object("gcode")
eventtime = last_report_time = reactor.monotonic()
while calc_proc.is_alive():
if eventtime > last_report_time + 5.:
last_report_time = eventtime
gcode.respond_info("Working on calibration...")
eventtime = reactor.pause(eventtime + .1)
# Return results
res = parent_conn.recv()
calc_proc.join()
parent_conn.close()
return res
######################################################################
# Trilateration