def CheckPointConstraints(csg_file, pos_points, neg_points): # Save positive and negative points into temporary files. tmp_pos_file = os.path.join(csg_output_dir, '.pos.data') tmp_neg_file = os.path.join(csg_output_dir, '.neg.data') tmp_point_file = os.path.join(csg_output_dir, '.point.data') # Check positive points first. helper.SaveDataFile(tmp_point_file, pos_points) helper.Run('%s csg-flag -d %s -e %f -i %s -n %s -p %s' % \ (os.environ['CSG_CPP_EXE'], tmp_point_file, 0, csg_file, \ tmp_neg_file, tmp_pos_file)) unsatisfied_pos = helper.LoadDataFile(tmp_neg_file) # Check if some points are missing. satisfied_pos = helper.LoadDataFile(tmp_pos_file) if satisfied_pos.shape[0] + unsatisfied_pos.shape[0] != pos_points.shape[0]: helper.PrintWithRedColor('Error: some pos constraints are ignored.') # Then check negative points. helper.SaveDataFile(tmp_point_file, neg_points) helper.Run('%s csg-flag -d %s -e %f -i %s -n %s -p %s' % \ (os.environ['CSG_CPP_EXE'], tmp_point_file, 0, csg_file, \ tmp_neg_file, tmp_pos_file)) unsatisfied_neg = helper.LoadDataFile(tmp_pos_file) # Check if some points are missing. satisfied_neg = helper.LoadDataFile(tmp_neg_file) if satisfied_neg.shape[0] + unsatisfied_neg.shape[0] != neg_points.shape[0]: helper.PrintWithRedColor('Error: some neg constraints are ignored.') os.remove(tmp_pos_file) os.remove(tmp_neg_file) os.remove(tmp_point_file) return unsatisfied_pos, unsatisfied_neg
def InstallEigen(root_folder, init=True): if init: helper.Run('wget http://bitbucket.org/eigen/eigen/get/3.3.4.zip') cpp_lib_folder = os.path.join(root_folder, 'cpp', 'lib') helper.Run('unzip 3.3.4.zip -d %s' % os.path.join(cpp_lib_folder)) helper.Run('mv %s %s' % (os.path.join(cpp_lib_folder, \ 'eigen-eigen-5a0156e40feb'), os.path.join(cpp_lib_folder, 'eigen-3.3.4'))) helper.Run('rm 3.3.4.zip') helper.PrintWithGreenColor('Installed Eigen')
def InstallEigen(root_folder, init=True): if init: # helper.Run('wget http://bitbucket.org/eigen/eigen/get/3.3.4.zip') helper.Run( 'wget https://github.com/eigenteam/eigen-git-mirror/archive/3.3.4.zip' ) cpp_lib_folder = os.path.join(root_folder, 'cpp', 'lib') helper.Run('unzip 3.3.4.zip -d %s' % os.path.join(cpp_lib_folder)) helper.Run('mv %s %s' % (os.path.join(cpp_lib_folder, \ 'eigen-git-mirror-3.3.4'), os.path.join(cpp_lib_folder, 'eigen-3.3.4'))) helper.Run('rm 3.3.4.zip') helper.PrintWithGreenColor('Installed Eigen')
def InstallJava(): helper.Run('sudo apt-get install software-properties-common') helper.Run('sudo apt-get update') helper.Run('sudo apt install default-jdk') # Currently JAVA_HOME is hard coded. helper.RunWithStdout('ls /usr/lib/jvm/') if os.environ['TRAVIS_DIST_NAME'] == 'bionic': java_home = '/usr/lib/jvm/java-1.11.0-openjdk-amd64/' if os.environ['TRAVIS_DIST_NAME'] == 'xenial': java_home = '/usr/lib/jvm/java-1.8.0-openjdk-amd64/' if os.environ['TRAVIS_DIST_NAME'] == 'eoan': java_home = '/usr/lib/jvm/java-1.11.0-openjdk-amd64/' env_variables['JAVA_HOME'] = os.environ['JAVA_HOME'] = java_home path = os.path.join(java_home, 'bin') + ':' + os.environ['PATH'] env_variables['PATH'] = os.environ['PATH'] = path helper.Run('%s -version' % os.path.join(java_home, 'bin', 'java'))
def InstallMaven(): # maven_url = 'http://mirrors.koehn.com/apache/maven/maven-3/3.5.3/' \ # 'binaries/apache-maven-3.5.3-bin.zip' # maven_file = os.path.join(build_folder, 'maven.zip') # urllib.request.urlretrieve(maven_url, maven_file) # helper.Run('unzip -q %s -d %s' % (maven_file, build_folder)) # os.remove(maven_file) # Add it to the environment variable. # for folder_name in os.listdir(build_folder): # if 'maven' in folder_name: # maven_loc = os.path.join(build_folder, folder_name, 'bin') # env_variables['PATH'] = os.environ['PATH'] \ # = maven_loc + ':' + os.environ['PATH'] helper.Run('sudo apt-get install build-essential autoconf libtool flex bison mercurial maven') # Check maven. helper.Run('mvn -v')
def DetectPrimitivesInRoi(input_primitive_file, input_meta_point_file, \ output_primitive_file, roi): # Call primitive-local. helper.Run('%s primitive-local -p %s -o %s -i %s -s %f %f %f %f %f %f' % (\ os.environ['CSG_CPP_EXE'], input_primitive_file, output_primitive_file, \ input_meta_point_file, roi[0], roi[1], roi[2], roi[3], roi[4], roi[5])) return ReadPrimitiveFile(output_primitive_file)
def InstallJava(): # java not hosted anymore: http://www.webupd8.org/2014/03/how-to-install-oracle-java-8-in-debian.html # helper.Run('sudo add-apt-repository -y ppa:webupd8team/java') # helper.Run('sudo apt-get update') # helper.Run('sudo apt-get install oracle-java8-installer') helper.Run('sudo apt-get install openjdk-8-jre') # Currently JAVA_HOME is hard coded. # java_home = '/usr/lib/jvm/java-8-oracle/' # java_home = '/usr/lib/jvm/java-8-openjdk-amd64' java_path_cmd = "jrunscript -e \'java.lang.System.out.println(java.lang.System.getProperty(\"java.home\"));\'" java_home, _ = helper.Run(java_path_cmd, return_msg=True) env_variables['JAVA_HOME'] = os.environ['JAVA_HOME'] = java_home path = os.path.join(java_home, 'bin') + ':' + os.environ['PATH'] env_variables['PATH'] = os.environ['PATH'] = path # helper.Run('%s -version' % os.path.join(java_home, 'bin', 'javac')) helper.Run('%s -version' % os.path.join(java_home, 'bin', 'java'))
def InstallCGAL(build_folder, init=True): helper.Run('sudo apt-get install libcgal-dev') helper.PrintWithGreenColor('Installed libcgal-dev') if init: cgal_url = 'https://github.com/CGAL/cgal/releases/download/' \ 'releases%2FCGAL-4.12/CGAL-4.12.zip' cgal_file = os.path.join(build_folder, 'cgal.zip') urllib.request.urlretrieve(cgal_url, cgal_file) helper.Run('unzip -o -q %s -d %s' % (cgal_file, build_folder)) os.remove(cgal_file) # Now you have the source code. helper.PrintWithGreenColor('Downloaded and unzipped CGAL 4.12') cgal_dir = '' for folder_name in os.listdir(build_folder): if 'cgal' in folder_name or 'CGAL' in folder_name: cgal_dir = os.path.join(build_folder, folder_name) break # Add cgal_root to the environment variable list. env_variables['CGAL_DIR'] = os.environ['CGAL_DIR'] = cgal_dir
def DetectPrimitives(mesh_file, output_primitive_file, output_meta_point_file, \ options): # Given a mesh file, return a list of all primitives we detect and write them # into the output_primitive_file. The format of this file can be found in # cpp/src/common/file_helper.cpp:WritePrimFile. All primitives must be unique. # For comparison we can replace the code in this function with RANSAC, # GlobFit, etc. We always have to return an output_primitive_file and a meta # point file, but for debugging purposes, each method (RANSAC, GlobFit, etc.) # can pass options to ask for auxiliary files. # TODO: Since we are now using RANSAC, we assume it has the following optional # files: # ransac_config_file: will be removed in the future. # cluster_file: used to visualize the segmentation results. ransac_config_file = options['ransac_config_file'] cluster_file = options['cluster_file'] helper.Run('%s primitive -i %s -o %s -c %s -l %s -m %s -v' % ( \ os.environ['CSG_CPP_EXE'], mesh_file, output_primitive_file, \ ransac_config_file, cluster_file, output_meta_point_file)) return ReadPrimitiveFile(output_primitive_file)
def GetSketchCompile(sketch_harness_file): sketch_name = os.path.basename(sketch_harness_file) # Remove .sk extension. sketch_name = os.path.splitext(sketch_name)[0] sketch_exe = os.path.join(sketch_output_dir, sketch_name) sketch_cpp = os.path.join(sketch_output_dir, sketch_name + '.cpp') sketch_test_cpp = os.path.join(sketch_output_dir, sketch_name + '_test.cpp') # Compile. sketch_runtime_dir = os.path.join(os.environ['CSG_SKETCH_FRONTEND'], \ 'src/runtime/include') helper.Run('g++ -w -I %s -o %s %s %s' % \ (sketch_runtime_dir, sketch_exe, sketch_cpp, sketch_test_cpp)) # Execute and get the solution. solution = subprocess.check_output('%s -n 1' % sketch_exe, \ stderr=subprocess.STDOUT, shell=True).decode('utf-8') lines = solution.splitlines() solution = [] for l in lines: solution.append(l.strip()) if '// End.' in l: break return '\n'.join(solution)
sys.exit(-1) build_folder = os.path.realpath(sys.argv[1]) root_folder = os.path.dirname(os.path.realpath(sys.argv[0])) if not os.path.exists(build_folder): os.makedirs(build_folder) helper.PrintWithGreenColor('Build folder created.') # Add a new environment variable to save the location of the root folder. env_variables['CSG_ROOT'] = os.environ['CSG_ROOT'] = root_folder # show LIBC version helper.RunWithStdout('sudo dpkg -l libc6') # This may work on Xenial helper.Run('sudo apt-get update') helper.Run('sudo apt-get install build-essential ' \ 'software-properties-common -y') helper.RunWithStdout('sudo apt-get install gcc-snapshot -y') # Install python dependencies. helper.RunWithStdout( 'sudo python3 -m pip install numpy scipy matplotlib ipython ' 'jupyter pandas sympy nose') helper.RunWithStdout('sudo python3 -m pip install -U scikit-learn') helper.RunWithStdout('sudo apt-get install autoconf libtool flex bison ' 'mercurial zsh cmake -y') # BISON version should be gt 3 helper.RunWithStdout('bison --version')
def RunSketchPipeline(): mesh_info = Preprocessing() all_pos_points = helper.LoadDataFile(mesh_info['pos_file']) vol_pos_points = helper.LoadDataFile(mesh_info['vol_pos_file']) all_neg_points = helper.LoadDataFile(mesh_info['neg_file']) satisfied_pos = np.zeros((0, 3)) # Major loop starts here. part_file = os.path.join(point_output_dir, 'part_0.data') shutil.copy(mesh_info['vol_pos_file'], part_file) todo = [part_file] solutions = [] while len(todo) > 0: # Pop the first element. part_file = todo[0] # Extract idx from the file name part_XX.data. idx = int(part_file[part_file.rfind('_') + 1:-len('.data')]) volumes = helper.LoadDataFile(part_file) todo = todo[1:] print('Attempt to solve part %d...' % idx) # Compute the bounding box of volume. Intentionally enlarge it a bit. box_min = volumes.min(axis=0) - 0.01 box_max = volumes.max(axis=0) + 0.01 prim_roi = EnlargeBoundingBox((box_min[0], box_max[0], box_min[1], \ box_max[1], box_min[2], box_max[2]), 1.1) # Merge volumes to get positive constraints. cpp_exe = os.environ['CSG_CPP_EXE'] new_pos_file = os.path.join(point_output_dir, 'pos_%d.data' % idx) helper.Run('%s equiv-class -e %f -i %s -p %s -o %s' % (cpp_exe, eps, \ part_file, mesh_info['primitive_file'], new_pos_file)) # Subtract satisfied_pos from pos_idx.data. tmp_data_file = os.path.join(point_output_dir, '.tmp_%d.data' % idx) helper.SaveDataFile(tmp_data_file, satisfied_pos) helper.Run('%s remove-equiv-class -e %f -i %s -o %s -p %s -r %s' % (\ cpp_exe, eps, new_pos_file, new_pos_file, \ mesh_info['primitive_file'], tmp_data_file)) os.remove(tmp_data_file) pos_points = helper.LoadDataFile(new_pos_file) if pos_points.size == 0: helper.PrintWithGreenColor('Part %d has been resolved.' % idx) continue solution, done = SolveOnePartWithOuterLoop(idx, pos_points, \ all_neg_points, prim_roi, mesh_info) if done: helper.PrintWithGreenColor('Part %d is done.' % idx) # Generate current solution. solutions.append(solution) csg_file = os.path.join(csg_output_dir, 'solution_%d.scad' % idx) f = open(csg_file, 'w') # Enclose this solution with the bounding box. x_min, x_max, y_min, y_max, z_min, z_max = mesh_info[ 'bounding_box'] f.write('intersection() {\n') f.write('translate([%f, %f, %f])\n' % (x_min, y_min, z_min)) f.write('cube(size = [%f, %f, %f], center = false);\n' % \ (x_max - x_min, y_max - y_min, z_max - z_min)) f.write('union() {\n') for s in solutions: f.write(s) f.write('\n') f.write('}\n') f.write('}\n') f.close() # Check if all point constraints can be satisfied. tmp_pos_file = os.path.join(csg_output_dir, '.pos.data') tmp_neg_file = os.path.join(csg_output_dir, '.neg.data') helper.Run('%s csg-flag -d %s -e %f -i %s -n %s -p %s' % \ (cpp_exe, mesh_info['pos_file'], eps, csg_file, \ tmp_neg_file, tmp_pos_file)) satisfied_pos = helper.LoadDataFile(tmp_pos_file) unsatisfied_pos = helper.LoadDataFile(tmp_neg_file) os.remove(tmp_pos_file) os.remove(tmp_neg_file) if unsatisfied_pos.size == 0: # We have found the solution. helper.PrintWithGreenColor('All constraints were satisfied. Result is ' \ 'in %s.' % csg_file) return else: # Segment the volume. point_cloud_seg.SegmentPointCloud(part_file, seg_num, \ part_file[:-len('.data')]) # Get the last idx. last_part_file = todo[-1] if len(todo) > 0 else part_file last_idx = int(last_part_file[last_part_file.rfind('_') + 1 \ : -len('.data')]) new_idx = last_idx + 1 for i in range(seg_num): new_part_file = \ part_file[:part_file.rfind('_') + 1] + str(new_idx + i) + '.data' shutil.copyfile(part_file[:-len('.data')] + '_' + str(i) + '.data' , \ new_part_file) todo.append(new_part_file)
def SolveOnePart(idx, all_pos_constraints, all_neg_constraints, primitive_roi, \ mesh_info): # Call this function to solve all_pos_constraints and all_neg_constraints # using primitives inside primitive_roi. # Returns a string that describes the csg tree, and done to indicate whether # the problem is solved. # Call Sketch to satisfy pos_constraints and neg_constraints. xmin, xmax, ymin, ymax, zmin, zmax = primitive_roi helper.PrintWithGreenColor('Part %d, roi (%f, %f, %f, %f, %f, %f)' \ % (idx, xmin, xmax, ymin, ymax, zmin, zmax)) print('Constraints: %d positive, %d negative.' % \ (all_pos_constraints.shape[0], all_neg_constraints.shape[0])) # Save them for debugging purposes. They are duplicated in data.sk. pos_constraints_file = os.path.join(point_output_dir, 'pos_%d.data' % idx) helper.SaveDataFile(pos_constraints_file, all_pos_constraints) neg_constraints_file = os.path.join(point_output_dir, 'neg_%d.data' % idx) helper.SaveDataFile(neg_constraints_file, all_neg_constraints) # Prepare the data file. sketch_data_file = os.path.join(sketch_harness_dir, 'data_%d.sk' % idx) sketch_idx_file = os.path.join(sketch_harness_dir, 'idx_%d.sk' % idx) helper.SavePointToSketch(sketch_data_file, sketch_idx_file, \ all_pos_constraints, all_neg_constraints) # Prepare the primitive file. prim_file = os.path.join(point_output_dir, 'surface_primitives_%d.prim' % idx) unsat_code = 1 def UnsatHandler(command, exit_code): if exit_code != unsat_code: helper.DefaultExceptionHandle(command, exit_code) else: helper.PrintWithGreenColor('UNSAT detected.') while True: xmin, xmax, ymin, ymax, zmin, zmax = primitive_roi helper.Run('%s primitive-local -p %s -o %s -i %s -s %f %f %f %f %f %f' % ( \ os.environ['CSG_CPP_EXE'], mesh_info['primitive_file'], prim_file, \ '.dummy.meta', xmin, xmax, ymin, ymax, zmin, zmax)) # See if the problem is SAT. code = helper.Run('%s remove-prim -e %f -i %s -o %s -n %s -p %s -v' % ( \ os.environ['CSG_CPP_EXE'], eps, prim_file, prim_file, \ neg_constraints_file, pos_constraints_file), UnsatHandler) if code == 0: break elif code == unsat_code: # Try to enlarge the roi. if Enclose(primitive_roi, mesh_info['bounding_box']): helper.PrintWithRedColor('Roi is already larger than the bounding ' \ 'box but the problem is still UNSAT. Should never happen.') sys.exit(-1) helper.PrintWithGreenColor( 'Enlarge the primitive roi and retry...') primitive_roi = EnlargeBoundingBox(primitive_roi, 1.1) else: # Should never happen. helper.PrintWithRedColor('See exit code other than 1. ' \ 'Should never happen.') sys.exit(-1) # Now the surface primitives are stored in prim_file and all of them are # necessary. We can count the number of solid primitives and terminate it # early if we are sure the solution is too big for sketch to solve. estimated_prim_num = \ surface_primitive_to_sketch.CountMinimumNumberOfSolidPrimitives(prim_file) if estimated_prim_num > max_prim_num: # Call segmentation. helper.PrintWithRedColor('Problem seems to require a deeper CSG tree. ' \ 'Call segmentation.') return '', False prim_sketch_file = os.path.join(sketch_harness_dir, \ 'primitives_%d.sk' % idx) surface_primitive_to_sketch.WriteSurfacePrimitivesToSolidSketch( \ prim_file, prim_sketch_file, mesh_info['max_offsets'] + 10 * eps) sketch_harness_file_name = '%s_%d' % (output_dir.split('/')[-1], idx) sketch_harness_file = os.path.join(sketch_harness_dir, \ sketch_harness_file_name) + '.sk' sketch_solver_file = os.path.join(sketch_harness_dir, \ 'csg_solver_%d.sk' % idx) # Sketch harness file. CreateSketch(sketch_harness_file, sketch_solver_file, \ os.path.basename(sketch_data_file), sketch_idx_file, \ os.path.basename(prim_sketch_file)) # Run Sketch and get its log. sketch_output_file = os.path.join(sketch_output_dir, \ sketch_harness_file_name + '.log') sketch_done = GetSketch(sketch_harness_file, sketch_output_file, \ timeout) # Check if it succeeded. if not sketch_done or '[SKETCH] DONE' not in open( sketch_output_file).read(): helper.PrintWithRedColor('Problem is too hard. Need segmentation.') return '', False helper.PrintWithGreenColor('Sketch succeeded.') # Display the solution. sketch_solution = GetSketchCompile(sketch_harness_file) # Save the results into a scad file. csg_file = os.path.join(csg_output_dir, 'csg_%d.scad' % idx) f = open(csg_file, 'w') f.write(sketch_solution) f.close() # As a sanity check. unsatisfied_pos, unsatisfied_neg = CheckPointConstraints(csg_file, \ all_pos_constraints, all_neg_constraints) if unsatisfied_pos.size + unsatisfied_neg.size > 0: helper.PrintWithRedColor('Still see unsatisfied constraints. ' \ 'Should never happen.') sys.exit(-1) # Done. return sketch_solution, True
def Preprocessing(): mesh_info = {} # Bounding box of the mesh. mesh_bounding_box = helper.GetOffMeshBoundingBox(mesh_file_loc) print('Bounding box of the mesh: ' + str(mesh_bounding_box)) # Enlarge the bounding box a bit. box_min = np.array(mesh_bounding_box[::2]) box_max = np.array(mesh_bounding_box[1::2]) box_diag = box_max - box_min box_min -= box_diag * 0.1 box_max += box_diag * 0.1 enlarged_bounding_box = (box_min[0], box_max[0], box_min[1], box_max[1], \ box_min[2], box_max[2]) mesh_info['bounding_box'] = enlarged_bounding_box mesh_info['max_offsets'] = max([abs(x) for x in enlarged_bounding_box]) * 3.0 # Compute the level-set. cpp_exe = os.environ['CSG_CPP_EXE'] level_set_file = os.path.join(point_output_dir, 'levelset.ls') print('Computing the level set...') # Enlarge eps a bit to avoid numerical issues. bigger_eps = eps * 1.1 helper.Run('%s level-set -i %s -d %f -o %s' % (cpp_exe, mesh_file_loc, \ bigger_eps, level_set_file)) mesh_info['level_set_file'] = level_set_file # Get surface primitives. # init_prim_file includes all detected primitives and auxiliary planes. init_prim_file = os.path.join(point_output_dir, 'init_primitives.prim') # cluster_file and ransac_config_file are used by RANSAC. cluster_file = os.path.join(point_output_dir, 'primitives.clu') ransac_config_file = os.path.join(os.path.dirname( \ os.path.realpath(mesh_file_loc)), 'ransac.conf') dummy_meta_file = os.path.join(point_output_dir, '.tmp.meta') print('Getting all primitives...') helper.Run('%s primitive -i %s -o %s -c %s -l %s -m %s -v' % (cpp_exe, \ mesh_file_loc, init_prim_file, ransac_config_file, cluster_file, \ dummy_meta_file)) # Get auxiliary primitives. aux_prim_file = os.path.join(point_output_dir, 'aux_primitives.prim') init_and_aux_prim_file = os.path.join(point_output_dir, \ 'init_and_aux_primitives.prim') surface_primitive_to_sketch.AddAuxiliaryPrimitives( \ init_prim_file, aux_prim_file, init_and_aux_prim_file) os.remove(dummy_meta_file) # Sample points. surface_sample_file = os.path.join(point_output_dir, 'surface_sample.data') print('Surface sampling...') helper.Run('%s surface-sample -b %f -d %f -e %f -i %s -l %s -o %s -p %s -v' \ % (cpp_exe, 10 * bigger_eps, surface_density, bigger_eps, \ mesh_file_loc, level_set_file, surface_sample_file, \ init_and_aux_prim_file)) init_vol_pos_file = os.path.join(point_output_dir, 'init_vol_pos.data') init_vol_neg_file = os.path.join(point_output_dir, 'init_vol_neg.data') print('Volume sampling...') helper.Run('%s volume-sample -d %f -e %f -i %s -l %s -n %s -p %s -r %s -v' % \ (cpp_exe, volume_density, bigger_eps, mesh_file_loc, \ level_set_file, init_vol_neg_file, init_vol_pos_file, \ init_and_aux_prim_file)) surface_sample = helper.LoadDataFile(surface_sample_file) pos_sample = helper.LoadDataFile(init_vol_pos_file) neg_sample = helper.LoadDataFile(init_vol_neg_file) all_samples = np.vstack((surface_sample, pos_sample, neg_sample)) tmp_sample_file = os.path.join(point_output_dir, '.tmp.data') helper.SaveDataFile(tmp_sample_file, all_samples) equiv_pos_file = os.path.join(point_output_dir, 'equiv_pos.data') equiv_neg_file = os.path.join(point_output_dir, 'equiv_neg.data') all_pos_file = os.path.join(point_output_dir, 'all_pos.data') all_neg_file = os.path.join(point_output_dir, 'all_neg.data') print('Calling equiv-class-flag...') helper.Run('%s equiv-class-flag -d %f -e %s -i %s -l %s -m %s -n %s -o %s ' \ '-p %s -q %s -v' % (cpp_exe, bigger_eps, equiv_pos_file, \ tmp_sample_file, level_set_file, mesh_file_loc, all_neg_file, \ all_pos_file, init_and_aux_prim_file, equiv_neg_file)) os.remove(tmp_sample_file) # The problem is resolved as long as all points in equiv_pos_file and # equiv_neg_file are satisifed using detected primitives. mesh_info['pos_file'] = equiv_pos_file mesh_info['neg_file'] = equiv_neg_file # Now we can filter redundant primitives. final_prim_file = os.path.join(point_output_dir, 'final_primitives.prim') helper.Run('%s add-separator -a %s -e %f -i %s -o %s -n %s -p %s -v' % \ (cpp_exe, aux_prim_file, eps, init_prim_file, final_prim_file, \ equiv_neg_file, equiv_pos_file)) # Do it one more time. helper.Run('%s remove-prim -e %f -i %s -o %s -n %s -p %s -v' % (cpp_exe, \ eps, final_prim_file, final_prim_file, equiv_neg_file, equiv_pos_file)) # Add a giant bounding sphere to allow for negation. surface_primitive_to_sketch.AddBoundingSphere(final_prim_file, \ final_prim_file, mesh_info['max_offsets'] + 10 * eps) helper.Run('%s equiv-class -e %f -i %s -p %s -o %s -v' % (cpp_exe, eps, \ equiv_pos_file, final_prim_file, equiv_pos_file)) helper.Run('%s equiv-class -e %f -i %s -p %s -o %s -v' % (cpp_exe, eps, \ equiv_neg_file, final_prim_file, equiv_neg_file)) mesh_info['primitive_file'] = final_prim_file # Clean up volumetric samples. print('Filtering volumetric samples (%d positive, %d negative before).' % \ (pos_sample.shape[0], neg_sample.shape[0])) final_vol_pos_file = os.path.join(point_output_dir, 'final_vol_pos.data') final_vol_neg_file = os.path.join(point_output_dir, 'final_vol_neg.data') helper.IntersectPointSetFiles(all_neg_file, init_vol_neg_file, \ final_vol_neg_file) helper.IntersectPointSetFiles(all_pos_file, init_vol_pos_file, \ final_vol_pos_file) print('Filtering volumtric samples (%d positive, %d negative after).' % \ (helper.LoadDataFile(final_vol_pos_file).shape[0], \ helper.LoadDataFile(final_vol_neg_file).shape[0])) final_vol_pos_points = helper.LoadDataFile(final_vol_pos_file) equiv_pos_points = helper.LoadDataFile(equiv_pos_file) diff_points = helper.SubtractPointSets(equiv_pos_points, final_vol_pos_points) if diff_points.size > 0: final_vol_pos_points = np.vstack((final_vol_pos_points, diff_points)) helper.SaveDataFile(final_vol_pos_file, final_vol_pos_points) mesh_info['vol_pos_file'] = final_vol_pos_file mesh_info['vol_neg_file'] = final_vol_neg_file print('Preprocessing done.') return mesh_info
def main(): parser = argparse.ArgumentParser() parser.add_argument('-d', '--build_dir', default='', help='build directory path.') parser.add_argument('-dp', '--deps', action='store_false', help='Disable apt-get & py3 dependencies.') parser.add_argument('-eg', '--eigen', action='store_false', help='Disable Eigen install.') parser.add_argument('-cg', '--cgal', action='store_false', help='Disable CGAL install.') parser.add_argument('-c', '--cpp', action='store_false', help='Disable source cpp compilation.') parser.add_argument('-sk', '--sketch', action='store_false', help='Disable sketch installation.') args = parser.parse_args() print('Arguments:', args) # Usage: python3 install.py -d <build folder> if not args.build_dir: print('Usage: python3 install.py -d <build_folder>') sys.exit(-1) build_folder = os.path.realpath(args.build_dir) root_folder = HERE if not os.path.exists(build_folder): os.makedirs(build_folder) helper.PrintWithGreenColor('Build folder created :{}'.format(build_folder)) # Add a new environment variable to save the location of the root folder. env_variables['CSG_ROOT'] = os.environ['CSG_ROOT'] = root_folder # Check all C++ dependencies. if args.deps: print('Attempt to install build-essential, autoconf, libtool, flex, bison, ' 'mecurial, zsh, and cmake. Asking for sudo privilege.') # This works for Ubuntu 17.04 and 16.04. exit_code = helper.Run('sudo apt-get install gcc-6 g++-6 -y', None) if exit_code != 0: # This works for Ubuntu 14.04. helper.Run('sudo apt-get update') helper.Run('sudo apt-get install build-essential ' \ 'software-properties-common -y') helper.Run('sudo add-apt-repository ppa:ubuntu-toolchain-r/test -y') helper.Run('sudo apt-get update') helper.Run('sudo apt-get install gcc-snapshot -y') helper.Run('sudo apt-get update') helper.Run('sudo apt-get install gcc-6 g++-6 -y') helper.Run('sudo apt-get install autoconf libtool flex bison ' 'mercurial zsh cmake') # Install python dependencies. helper.Run('python3 -m pip install -U pip setuptools') helper.Run('python3 -m pip install --upgrade pip') helper.Run('python3 -m pip install numpy scipy matplotlib ipython ' 'jupyter pandas sympy nose') helper.Run('python3 -m pip install -U scikit-learn') # Install CGAL. InstallCGAL(build_folder, args.eigen) # Install Eigen-3.3.4. InstallEigen(root_folder, args.cgal) # Compile cpp. if args.cpp: cpp_build_folder = os.path.join(build_folder, 'cpp') if not os.path.exists(cpp_build_folder): os.makedirs(cpp_build_folder) os.chdir(cpp_build_folder) os.environ['CC'] = '/usr/bin/gcc-6' os.environ['CXX'] = '/usr/bin/g++-6' helper.Run('cmake -DCGAL_DIR=%s %s' % (env_variables['CGAL_DIR'], \ os.path.join(root_folder, 'cpp'))) helper.Run('make') helper.PrintWithGreenColor('C++ program compiled successfully.') env_variables['CSG_CPP_EXE'] = os.path.join(cpp_build_folder, 'csg_cpp_command') # Install Sketch. # Try calling Sketch. If it is successful, we are done. if CheckSketch(build_folder): SaveCustomizedEnvironmentVariables(env_variables, os.path.join( build_folder, 'ENVIRONMENT')) helper.PrintWithGreenColor('Installation Done.') sys.exit(0) # If we are here, Sketch is not properly installed. # First, install Oracle JDK 8. print('Attempt to install Oracle JDK 8. Asking for sudo privilege.') InstallJava() # Next, install maven. InstallMaven() # Download sketch-backend. sketch_folder = os.path.join(build_folder, 'sketch') if not os.path.exists(sketch_folder): os.makedirs(sketch_folder) if args.sketch: # Sketch-backend. os.chdir(sketch_folder) helper.Run('hg clone https://bitbucket.org/gatoatigrado/sketch-backend') helper.Run('mv sketch-backend sketch-backend-default') # Use this version of sketch. helper.Run('hg clone -r 04b3403 sketch-backend-default sketch-backend') sketch_backend_folder = os.path.join(sketch_folder, 'sketch-backend') env_variables['CSG_SKETCH_BACKEND'] = sketch_backend_folder if args.sketch: os.chdir(sketch_backend_folder) helper.Run('bash autogen.sh') helper.Run('./configure') helper.Run('make -j2') # Interestingly, I need to manually do the following copy and paste work to # avoid an error in sketch-frontend. sketch_solver_folder = os.path.join(sketch_backend_folder, 'src/SketchSolver') shutil.copyfile(os.path.join(sketch_solver_folder, 'libcegis.a'), \ os.path.join(sketch_solver_folder, '.libs/libcegis.a')) shutil.copyfile(os.path.join(sketch_solver_folder, 'cegis'), \ os.path.join(sketch_solver_folder, '.libs/cegis')) # Download sketch-frontend. os.chdir(sketch_folder) if args.sketch: helper.Run('hg clone https://bitbucket.org/gatoatigrado/sketch-frontend') helper.Run('mv sketch-frontend sketch-frontend-default') # Use this version of sketch. helper.Run('hg clone -r 42c057c sketch-frontend-default sketch-frontend') sketch_frontend_folder = os.path.join(sketch_folder, 'sketch-frontend') env_variables['CSG_SKETCH_FRONTEND'] = sketch_frontend_folder os.chdir(sketch_frontend_folder) if args.sketch: helper.Run('make system-install DESTDIR=/usr/bin SUDOINSTALL=1') # Now check Sketch again. if not CheckSketch(build_folder): helper.PrintWithRedColor('Failed to install Sketch. Please fix.') sys.exit(-1) SaveCustomizedEnvironmentVariables(env_variables, os.path.join( build_folder, 'ENVIRONMENT')) helper.PrintWithGreenColor('Installation Done.')