From 3f17c9607d6f4e0930f1bdc615578ed8f53ff1b7 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Rostislav=20L=C3=A1n?= Date: Sun, 25 Dec 2022 17:49:54 +0100 Subject: [PATCH] Added method to convert processed image to lithophane. --- src/main.py | 83 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 83 insertions(+) diff --git a/src/main.py b/src/main.py index 209140d..a25a030 100644 --- a/src/main.py +++ b/src/main.py @@ -197,6 +197,89 @@ class apply_filters: def make_lithophane(self): pass + '''After processing image, make a lithophane from it. + ''' + + print("Making meshgrid", file=sys.stderr) + self.make_meshgrid() + print("Converting to stl format", file=sys.stderr) + self.make_mesh() + plt.show() + self.save_model() + + def make_meshgrid(self): + + # Modify image to make it more suitable depth + # values1 = (1 + (1 - self.img/255)/6) * 255/10 # this works + # values2 = (1 - (1 - self.img/255)/6) * 255/10 # TODO: i dont know how to make white surrounding be extruded + values1better = 28.05 - 0.01*self.img + #values2better = 22.95 - 0.01*self.img + # (np.around(values2[::300],3)) + + # Add zero padding to image to make sides of the plate + self.height = self.img.shape[0] + 2 + self.width = self.img.shape[1] + 2 + self.img = np.zeros([self.height, self.width]) + self.img[1:-1:1, 1:-1:1] = values1better + + # Create meshgrid for 3D model + verticesX = np.around(np.linspace(0, self.width / 10, self.width), 3) + verticesY = np.around(np.linspace(0, self.height / 10, self.height), 3) + self.meshgrid = np.meshgrid(verticesX, verticesY) + + def make_mesh(self): + # Convert meshgrid and image matrix to array of 3D points + vertice_arr = np.vstack(list(map(np.ravel, self.meshgrid))).T + z = (self.img / 10).reshape(-1, 1) + vertice_arr = np.concatenate((vertice_arr, z), axis=1) + + # Convert back to matrix of 3D points + vertice_arr = vertice_arr.reshape(self.height, self.width, 3) + + count = 0 + vertices = [] + faces = [] + + # Function to add faces to the list + def add_faces(c): + faces.append([c, c + 1, c + 2]) + faces.append([c + 1, c + 3, c + 2]) + c += 4 + return c + + # Iterate over all vertices, create faces + for j in range(self.width - 1): + for i in range(self.height - 1): + + vertices.append([vertice_arr[i][j]]) + vertices.append([vertice_arr[i][j+1]]) + vertices.append([vertice_arr[i+1][j]]) + vertices.append([vertice_arr[i+1][j+1]]) + + count = add_faces(count) + + # Add faces for the backside of the lithophane + # This makes it closed, so it can be printed + vertices.append([vertice_arr[0][0]]) + vertices.append([vertice_arr[0][self.width - 1]]) + vertices.append([vertice_arr[self.height - 1][0]]) + vertices.append([vertice_arr[self.height - 1][self.width - 1]]) + + count = add_faces(count) + + # Convert to numpy arrays + faces = np.array(faces) + vertices = np.array(vertices) + + # Create the mesh + self.model = mesh.Mesh(np.zeros(len(faces), dtype=mesh.Mesh.dtype)) + for i, face in enumerate(faces): + for j in range(3): + self.model.vectors[i][j] = vertices[face[j], :] + + def save_model(self): + print("Saving stl model", file=sys.stderr) + self.model.save('res/test.stl') image = apply_filters()