Blame | Last modification | View Log | RSS feed
#!/usr/bin/python3# This file is for preprocessing gcode and the new G29 Autobedleveling from Marlin# It will analyse the first 2 Layer and return the maximum size for this part# After this it will replace with g29_keyword = ';MarlinG29Script' with the new G29 LRFB# the new file will be created in the same folder.# your gcode-file/folderfolder = './'my_file = 'test.gcode'# this is the minimum of G1 instructions which should be between 2 different heightsmin_g1 = 3# maximum number of lines to parse, I don't want to parse the complete file# only the first plane is we are interested inmax_g1 = 100000000# g29 keywordg29_keyword = 'g29'g29_keyword = g29_keyword.upper()# output filenameoutput_file = folder + 'g29_' + my_file# input filenameinput_file = folder + my_file# minimum scan sizemin_size = 40probing_points = 3 # points x points# other stuffmin_x = 500min_y = min_xmax_x = -500max_y = max_xlast_z = 0.001layer = 0lines_of_g1 = 0gcode = []# return only g1-linesdef has_g1(line):return line[:2].upper() == "G1"# find position in g1 (x,y,z)def find_axis(line, axis):found = Falsenumber = ""for char in line:if found:if char == ".":number += charelif char == "-":number += charelse:try:int(char)number += charexcept ValueError:breakelse:found = char.upper() == axis.upper()try:return float(number)except ValueError:return None# save the min or max-values for each axisdef set_mima(line):global min_x, max_x, min_y, max_y, last_zcurrent_x = find_axis(line, 'x')current_y = find_axis(line, 'y')if current_x is not None:min_x = min(current_x, min_x)max_x = max(current_x, max_x)if current_y is not None:min_y = min(current_y, min_y)max_y = max(current_y, max_y)return min_x, max_x, min_y, max_y# find z in the code and return itdef find_z(gcode, start_at_line=0):for i in range(start_at_line, len(gcode)):my_z = find_axis(gcode[i], 'Z')if my_z is not None:return my_z, idef z_parse(gcode, start_at_line=0, end_at_line=0):i = start_at_lineall_z = []line_between_z = []z_at_line = []# last_z = 0last_i = -1while len(gcode) > i:try:z, i = find_z(gcode, i + 1)except TypeError:breakall_z.append(z)z_at_line.append(i)temp_line = i - last_i -1line_between_z.append(i - last_i - 1)# last_z = zlast_i = iif 0 < end_at_line <= i or temp_line >= min_g1:# print('break at line {} at heigth {}'.format(i, z))breakline_between_z = line_between_z[1:]return all_z, line_between_z, z_at_line# get the lines which should be the first layerdef get_lines(gcode, minimum):i = 0all_z, line_between_z, z_at_line = z_parse(gcode, end_at_line=max_g1)for count in line_between_z:i += 1if count > minimum:# print('layer: {}:{}'.format(z_at_line[i-1], z_at_line[i]))return z_at_line[i - 1], z_at_line[i]with open(input_file, 'r') as file:lines = 0for line in file:lines += 1if lines > 1000:breakif has_g1(line):gcode.append(line)file.close()start, end = get_lines(gcode, min_g1)for i in range(start, end):set_mima(gcode[i])print('x_min:{} x_max:{}\ny_min:{} y_max:{}'.format(min_x, max_x, min_y, max_y))# resize min/max - values for minimum scanif max_x - min_x < min_size:offset_x = int((min_size - (max_x - min_x)) / 2 + 0.5) # int round up# print('min_x! with {}'.format(int(max_x - min_x)))min_x = int(min_x) - offset_xmax_x = int(max_x) + offset_xif max_y - min_y < min_size:offset_y = int((min_size - (max_y - min_y)) / 2 + 0.5) # int round up# print('min_y! with {}'.format(int(max_y - min_y)))min_y = int(min_y) - offset_ymax_y = int(max_y) + offset_ynew_command = 'G29 L{0} R{1} F{2} B{3} P{4}\n'.format(min_x,max_x,min_y,max_y,probing_points)out_file = open(output_file, 'w')in_file = open(input_file, 'r')for line in in_file:if line[:len(g29_keyword)].upper() == g29_keyword:out_file.write(new_command)print('write G29')else:out_file.write(line)file.close()out_file.close()print('auto G29 finished')