Refactored inefficient code present in stl generation.

master
Rostislav Lán 2 years ago
parent 9f624f84c2
commit e0e95f69b5

@ -135,17 +135,17 @@ class fingerprint_app:
# Get mode and model parameters # Get mode and model parameters
if self.mode == 'p': if self.mode == 'p':
self.height_line = float(self.args.stl[1]) if len( self.height_line = float(self.args.stl[1]) if len(
self.args.stl) > 1 else def_val.get("hl") self.args.stl) > 1 else def_val.get("hl")
self.height_base = float(self.args.stl[2]) if len( self.height_base = float(self.args.stl[2]) if len(
self.args.stl) > 2 else def_val.get("hb") self.args.stl) > 2 else def_val.get("hb")
if len(self.args.stl) < 3: if len(self.args.stl) < 3:
log.print_message( log.print_message(
"Warning: Too few arguments, using some default values") "Warning: Too few arguments, using some default values")
log.print_message("Base height:", self.height_base, log.print_message("Base height:", self.height_base,
"mm, lines depth/height:", self.height_line, "mm") "mm, lines depth/height:", self.height_line, "mm")
elif self.mode == 'c': elif self.mode == 'c':
@ -157,13 +157,13 @@ class fingerprint_app:
self.args.stl) > 3 else def_val.get("crx") self.args.stl) > 3 else def_val.get("crx")
self.curv_rate_y = float(self.args.stl[4]) if len( self.curv_rate_y = float(self.args.stl[4]) if len(
self.args.stl) > 4 else def_val.get("cry") self.args.stl) > 4 else def_val.get("cry")
if len(self.args.stl) < 5: if len(self.args.stl) < 5:
log.print_message( log.print_message(
"Warning: Too few arguments, using some default values") "Warning: Too few arguments, using some default values")
log.print_message("Line height:", self.height_line, "mm, base height:", self.height_base, log.print_message("Line height:", self.height_line, "mm, base height:", self.height_base,
"mm, x axis curvature:", self.curv_rate_x, ", y axis curvature:", self.curv_rate_y) "mm, x axis curvature:", self.curv_rate_x, ", y axis curvature:", self.curv_rate_y)
elif self.mode == 'm': elif self.mode == 'm':
self.height_line = float(self.args.stl[1]) if len( self.height_line = float(self.args.stl[1]) if len(
@ -178,12 +178,12 @@ class fingerprint_app:
self.args.stl) > 5 else def_val.get("fz") self.args.stl) > 5 else def_val.get("fz")
self.finger_name = str(self.args.stl[6]) if len( self.finger_name = str(self.args.stl[6]) if len(
self.args.stl) > 6 else def_val.get("f") self.args.stl) > 6 else def_val.get("f")
if len(self.args.stl) < 6: if len(self.args.stl) < 6:
log.print_message( log.print_message(
"Warning: Too few arguments, using some default values") "Warning: Too few arguments, using some default values")
log.print_message("Line height:", self.height_line, "mm, iterations:", self.iter, log.print_message("Line height:", self.height_line, "mm, iterations:", self.iter,
", finger position:", self.finger_x, self.finger_y, self.finger_z, "mm, finger model:", self.finger_name) ", finger position:", self.finger_x, self.finger_y, self.finger_z, "mm, finger model:", self.finger_name)
else: else:
log.error_exit("Unrecognized generation mode") log.error_exit("Unrecognized generation mode")
@ -319,7 +319,8 @@ class fingerprint_app:
if self.height_line <= 0: if self.height_line <= 0:
log.error_exit("Line height must be positive") log.error_exit("Line height must be positive")
if self.iter < 0: if self.iter < 0:
log.error_exit("Number of iterations must be positive orr zero") log.error_exit(
"Number of iterations must be positive orr zero")
self.height_base = 0 self.height_base = 0
# TODO: curved height base could be done here? # TODO: curved height base could be done here?
@ -359,8 +360,7 @@ class fingerprint_app:
# add parameters specific to the model creation process # add parameters specific to the model creation process
if self.args.config: if self.args.config:
param_list.append(self.config_file) param_list.extend([self.config_file, self.preset_name])
param_list.append(self.preset_name)
else: else:
# add filters with their params # add filters with their params
filter_list = [] filter_list = []
@ -379,28 +379,18 @@ class fingerprint_app:
param_list.append(filter_string) param_list.append(filter_string)
# these are the same for all types of models # these are the same for all types of models
param_list.append(str(self.height_line)) param_list.extend([str(self.height_line), str(self.height_base)])
param_list.append(str(self.height_base))
# add parameters specific to the model type # add parameters specific to the model type
if self.mode == "c": if self.mode == "c":
param_list.append(str(self.curv_rate_x)) param_list.extend([str(self.curv_rate_x), str(self.curv_rate_y)])
param_list.append(str(self.curv_rate_y))
if self.mode == "m":
param_list.append(str(self.height_line))
param_list.append(str(self.iter))
param_list.append(str(self.finger_x))
param_list.append(str(self.finger_y))
param_list.append(str(self.finger_z))
param_list.append(str(self.finger_name))
if self.mode == "p":
param_list.append("P")
elif self.mode == "c":
param_list.append("C")
elif self.mode == "m": elif self.mode == "m":
param_list.append("M") param_list.extend(
[str(self.height_line), str(self.iter), str(self.finger_x),
str(self.finger_y), str(self.finger_z), str(self.finger_name)])
param_list.append(self.mode)
if self.args.mirror: if self.args.mirror:
param_list.append("F") param_list.append("F")
@ -462,26 +452,21 @@ class fingerprint_app:
data = np.frombuffer(fig.canvas.tostring_rgb(), dtype=np.uint8) data = np.frombuffer(fig.canvas.tostring_rgb(), dtype=np.uint8)
data = data.reshape(fig.canvas.get_width_height()[::-1] + (3,)) data = data.reshape(fig.canvas.get_width_height()[::-1] + (3,))
plt.close() plt.close()
# scale inscription layer to suitable height # scale inscription layer to suitable height
data = (data/255)/10 data = (data/255)/10
# add the bottom array
OFFSET = 0.01
for i in range(self.height): for i in range(self.height):
if self.mode == "p": if self.mode == "p":
for j in range(self.width): for j in range(self.width):
bottom_vert_arr[i][j][2] = data[i][j][0] bottom_vert_arr[i][j][2] = data[i][j][0]
elif self.mode == "c": elif self.mode == "c":
# TODO: this is very badly written, fix it, why is teh offset needed at all?
# TODO: this sometimes generates invalid mesh, fix it
for j in range(self.width): for j in range(self.width):
bottom_vert_arr[i][j][2] += data[i][j][0] bottom_vert_arr[i][j][2] += data[i][j][0]
if (bottom_vert_arr[i][j][2] < (top_vert_arr[i][0][2])-OFFSET): if (bottom_vert_arr[i][j][2] < (top_vert_arr[i][0][2])):
bottom_vert_arr[i][j][2] = top_vert_arr[i][0][2]-OFFSET bottom_vert_arr[i][j][2] = top_vert_arr[i][0][2]
if (bottom_vert_arr[i][j][2] < (top_vert_arr[0][j][2])-OFFSET): if (bottom_vert_arr[i][j][2] < (top_vert_arr[0][j][2])):
bottom_vert_arr[i][j][2] = top_vert_arr[0][j][2]-OFFSET bottom_vert_arr[i][j][2] = top_vert_arr[0][j][2]
return bottom_vert_arr return bottom_vert_arr
@ -503,20 +488,20 @@ class fingerprint_app:
for i, face in enumerate(faces): for i, face in enumerate(faces):
for j in range(3): for j in range(3):
self.stl_model.vectors[i][j] = vertices[face[j], :] self.stl_model.vectors[i][j] = vertices[face[j], :]
# Prints out generation progress # Prints out generation progress
if i % 100 == 0: if i % 100 == 0:
percentage = round(i/len(faces) * 100, 2) percentage = round(i/len(faces) * 100, 2)
if percentage > c: if percentage > c:
log.print_message("Creating model " + str(c) + "%") log.print_message("Creating model " + str(c) + "%")
c += 10 c += 10
log.print_message("Model creation finished") log.print_message("Model creation finished")
def create_faces(self, top_vert_arr, bottom_vert_arr): def create_faces(self, top_vert_arr, bottom_vert_arr):
'''Create faces for the model. '''Create faces for the model.
Iterate over all vertices, append to vector and create faces from indices. Iterate over all vertices, append to vector and create faces from indices.
:param bottom_vert_arr: Bottom vertex array. :param bottom_vert_arr: Bottom vertex array.
:param top_vert_arr: Top vertex array :param top_vert_arr: Top vertex array
''' '''
@ -524,57 +509,46 @@ class fingerprint_app:
count = 0 count = 0
vertices = [] vertices = []
faces = [] faces = []
max_width = self.width - 1
max_height = self.height - 1
# Front side faces # Front side faces and vertices
for i in range(self.height - 1): for i in range(self.height - 1):
for j in range(self.width - 1): for j in range(self.width - 1):
vertices.append([top_vert_arr[i][j]]) vertices.extend([[top_vert_arr[i][j]], [top_vert_arr[i][j+1]],
vertices.append([top_vert_arr[i][j+1]]) [top_vert_arr[i+1][j]], [top_vert_arr[i+1][j+1]]])
vertices.append([top_vert_arr[i+1][j]])
vertices.append([top_vert_arr[i+1][j+1]])
count = self.append_faces(faces, count) count = self.append_faces(faces, count)
# Back side faces # Back side faces and vertices
for i in range(self.height - 1): for i in range(self.height - 1):
for j in range(self.width - 1): for j in range(self.width - 1):
vertices.append([bottom_vert_arr[i][j]]) vertices.extend([[bottom_vert_arr[i][j]], [bottom_vert_arr[i+1][j]],
vertices.append([bottom_vert_arr[i+1][j]]) [bottom_vert_arr[i][j+1]], [bottom_vert_arr[i+1][j+1]]])
vertices.append([bottom_vert_arr[i][j+1]])
vertices.append([bottom_vert_arr[i+1][j+1]])
count = self.append_faces(faces, count) count = self.append_faces(faces, count)
# Horizontal side faces
# Horizontal side faces and vertices
for i in range(self.height - 1): for i in range(self.height - 1):
vertices.append([top_vert_arr[i][0]]) vertices.extend([[top_vert_arr[i][0]], [top_vert_arr[i+1][0]],
vertices.append([top_vert_arr[i+1][0]]) [bottom_vert_arr[i][0]], [bottom_vert_arr[i+1][0]]])
vertices.append([bottom_vert_arr[i][0]])
vertices.append([bottom_vert_arr[i+1][0]])
count = self.append_faces(faces, count) count = self.append_faces(faces, count)
max = self.width - 1
vertices.extend([[top_vert_arr[i+1][max_width]], [top_vert_arr[i][max_width]],
vertices.append([top_vert_arr[i+1][max]]) [bottom_vert_arr[i+1][max_width]], [bottom_vert_arr[i][max_width]]])
vertices.append([top_vert_arr[i][max]])
vertices.append([bottom_vert_arr[i+1][max]])
vertices.append([bottom_vert_arr[i][max]])
count = self.append_faces(faces, count) count = self.append_faces(faces, count)
# Vertical side faces # Vertical side faces and vertices
for j in range(self.width - 1): for j in range(self.width - 1):
vertices.append([top_vert_arr[0][j+1]]) vertices.extend([[top_vert_arr[0][j+1]], [top_vert_arr[0][j]],
vertices.append([top_vert_arr[0][j]]) [bottom_vert_arr[0][j+1]], [bottom_vert_arr[0][j]]])
vertices.append([bottom_vert_arr[0][j+1]])
vertices.append([bottom_vert_arr[0][j]])
count = self.append_faces(faces, count) count = self.append_faces(faces, count)
max = self.height - 1
vertices.extend([[top_vert_arr[max_height][j]], [top_vert_arr[max_height][j+1]],
vertices.append([top_vert_arr[max][j]]) [bottom_vert_arr[max_height][j]], [bottom_vert_arr[max_height][j+1]]])
vertices.append([top_vert_arr[max][j+1]])
vertices.append([bottom_vert_arr[max][j]])
vertices.append([bottom_vert_arr[max][j+1]])
count = self.append_faces(faces, count) count = self.append_faces(faces, count)
return faces, vertices return faces, vertices
@ -615,7 +589,7 @@ class fingerprint_app:
z = np.sqrt(1 - x**2) * self.curv_rate_x**2 z = np.sqrt(1 - x**2) * self.curv_rate_x**2
z = np.tile(z, (self.height, 1)) z = np.tile(z, (self.height, 1))
z *= np.sqrt((1 - ((self.height - y) / self.height)**2) z *= np.sqrt((1 - ((self.height - y) / self.height)**2)
* self.curv_rate_y**2) * self.curv_rate_y**2)
z = z.reshape(-1, 1) z = z.reshape(-1, 1)
# Make a copy of z for the bottom side # Make a copy of z for the bottom side
@ -685,7 +659,7 @@ class fingerprint_app:
c = 0 c = 0
for k, vertice in enumerate(vertices): for k, vertice in enumerate(vertices):
# Skip vertices under plane xy # Skip vertices under plane xy
# also skip vertices under the fingerprint image, # also skip vertices under the fingerprint image,
# they are all unused # they are all unused
if vertice[2] < 0 or vertice[1] > self.height * px2mm: if vertice[2] < 0 or vertice[1] > self.height * px2mm:
continue continue
@ -698,7 +672,8 @@ class fingerprint_app:
# To the 2D image projection of vertice, add its value # To the 2D image projection of vertice, add its value
point = find_nearest(vertice[0], vertice[1], self.img) point = find_nearest(vertice[0], vertice[1], self.img)
except IndexError: except IndexError:
log.error_exit("Fingerprint image is outside of the finger model") log.error_exit(
"Fingerprint image is outside of the finger model")
vertices[k][2] += point vertices[k][2] += point

Loading…
Cancel
Save