def toLabelFile(self, image_path, samples): shapes = [] for sample in samples: shapes.append({ 'label': sample.label, 'line_color': None, 'fill_color': None, 'points': sample.points, 'shape_type': sample.shape_type, }) self.checkAborted() local_image_path = os.path.basename(image_path) image_data = LabelFile.load_image_file(image_path) label_file_name = os.path.splitext(image_path)[0] + LabelFile.suffix label_file = LabelFile() label_file.save( label_file_name, shapes, local_image_path, sample.image_size[0], sample.image_size[1], imageData=image_data, lineColor=None, fillColor=None, otherData=None, flags=None, )
def main(): parser = argparse.ArgumentParser() parser.add_argument('json_file') args = parser.parse_args() label_file = LabelFile(args.json_file) img = utils.img_data_to_arr(label_file.imageData) label_name_to_value = {'_background_': 0} for shape in sorted(label_file.shapes, key=lambda x: x['label']): label_name = shape['label'] if label_name in label_name_to_value: label_value = label_name_to_value[label_name] else: label_value = len(label_name_to_value) label_name_to_value[label_name] = label_value lbl, _ = utils.shapes_to_label(img.shape, label_file.shapes, label_name_to_value) label_names = [None] * (max(label_name_to_value.values()) + 1) for name, value in label_name_to_value.items(): label_names[value] = name lbl_viz = imgviz.label2rgb( label=lbl, img=imgviz.asgray(img), label_names=label_names, font_size=30, loc='rb', ) plt.subplot(121) plt.imshow(img) plt.subplot(122) plt.imshow(lbl_viz) plt.show()
def main(): parser = argparse.ArgumentParser() parser.add_argument( '--input', '-I', '-i', help='input json file of labelme generated (if it ends with .json it is ' 'recognized as file, else as directory)') args = parser.parse_args() config_from_args = args.__dict__ filename = config_from_args.pop('input') #print(filename) labelFile = LabelFile(filename) #print(f"len(labelFile.shapes) = {len(labelFile.shapes)}") i = 1 for s in labelFile.shapes: pointslen = len(s['points']) if pointslen < 10: print("{} line in {}".format(i, filename))
def addFromLabelFile(self, label_file, root_folder): lf = LabelFile(label_file) image_size = (lf.imageHeight, lf.imageWidth) image_dir = os.path.dirname(os.path.relpath(label_file, root_folder)) for s in lf.shapes: image_path = os.path.normpath(os.path.join(image_dir, lf.imagePath)) self.addSample(image_path, image_size, s[0], s[1], s[4]) self.checkAborted()
def main(): parser = argparse.ArgumentParser() parser.add_argument( '--input', '-I', '-i', help='input json file of labelme generated (if it ends with .json it is ' 'recognized as file, else as directory)') args = parser.parse_args() config_from_args = args.__dict__ filename = config_from_args.pop('input') #print(filename) labelFile = LabelFile(filename) #print(f"len(labelFile.shapes) = {len(labelFile.shapes)}") sameShape = {} plen = [] for s in labelFile.shapes: pointslen = len(s['points']) plen.append(pointslen) for i in range(len(plen) - 1, -1, -1): for j in range(i - 1, -1, -1): if plen[i] == plen[j]: #print(f"{j} and {i} len is the same {plen[i]}") shapei = labelFile.shapes[i] shapej = labelFile.shapes[j] kstep = 0 for k in range(0, plen[i]): dx = math.fabs( float(shapei['points'][k][0]) - float(shapej['points'][k][0])) dy = math.fabs( float(shapei['points'][k][1]) - float(shapej['points'][k][1])) if dx > 2.0 or dy > 2.0: break kstep = kstep + 1 if kstep == plen[i]: #print(f"{j} and {i} shape is the same") sameShape[j] = i print(sameShape)
def make_label_visualize_image(self, json_file): label_file = LabelFile(json_file) img = utils.img_data_to_arr(label_file.imageData) label_name_to_value = {"_background_": 0} for shape in sorted(label_file.shapes, key=lambda x: x["label"]): label_name = shape["label"] if label_name in label_name_to_value: label_value = label_name_to_value[label_name] else: label_value = len(label_name_to_value) label_name_to_value[label_name] = label_value lbl, _ = utils.shapes_to_label( img.shape, label_file.shapes, label_name_to_value ) label_names = [None] * (max(label_name_to_value.values()) + 1) for name, value in label_name_to_value.items(): label_names[value] = name lbl_viz = imgviz.label2rgb( label=lbl, img=imgviz.asgray(img), label_names=label_names, font_size=30, loc="rb", ) return lbl_viz fig = plt.figure() ax1 = fig.add_subplot(111) ax1.imshow(img) ax2 = fig.add_subplot(111) ax2.imshow(lbl_viz) fig.canvas.draw() data = np.fromstring(fig.canvas.tostring_rgb(), dtype=np.uint8, sep='') data = data.reshape(fig.canvas.get_width_height()[::-1] + (3,)) # plt.subplot(121) # plt.imshow(img) # plt.subplot(122) # plt.imshow(lbl_viz) # plt.show() # # plt.draw() return data
def saveLabels(self, filename): lf = LabelFile() def format_shape(s): return dict(label=str(s.label), line_color=s.line_color.getRgb() if s.line_color != self.lineColor else None, fill_color=s.fill_color.getRgb() if s.fill_color != self.fillColor else None, points=[(p.x(), p.y()) for p in s.points]) shapes = [format_shape(shape) for shape in self.labelList.shapes] flags = {} for i in range(self.flag_widget.count()): item = self.flag_widget.item(i) key = item.text() flag = item.checkState() == Qt.Checked flags[key] = flag try: imagePath = os.path.relpath( self.imagePath, os.path.dirname(filename)) imageData = self.imageData if self._config['store_data'] else None lf.save( filename=filename, shapes=shapes, imagePath=imagePath, imageData=imageData, lineColor=self.lineColor.getRgb(), fillColor=self.fillColor.getRgb(), otherData=self.otherData, flags=flags, ) self.labelFile = lf items = self.fileListWidget.findItems( self.imagePath, Qt.MatchExactly ) if len(items) > 0: if len(items) != 1: raise RuntimeError('There are duplicate files.') items[0].setCheckState(Qt.Checked) # disable allows next and previous image to proceed # self.filename = filename return True except LabelFileError as e: self.errorMessage('Error saving label data', '<b>%s</b>' % e) return False
def main(): parser = argparse.ArgumentParser() parser.add_argument( '--input', '-I', '-i', help='input json file of labelme generated (if it ends with .json it is ' 'recognized as file, else as directory)' ) args = parser.parse_args() config_from_args = args.__dict__ filename = config_from_args.pop('input') #print(filename) labelFile = LabelFile(filename) #print(f"len(labelFile.shapes) = {len(labelFile.shapes)}") fshape = labelFile.shapes[0] newPoints = [] newPoints.append(fshape['points'][0]) pointslen = len(fshape['points']) keepPointIndex = 0; for i in range(1, pointslen): dx = math.fabs(float(fshape['points'][i][0]) - float(fshape['points'][keepPointIndex][0])) dy = math.fabs(float(fshape['points'][i][1]) - float(fshape['points'][keepPointIndex][1])) if dx > 2.0 or dy > 2.0: keepPointIndex = i newPoints.append(fshape['points'][keepPointIndex]) print(newPoints)
def loadFile(self, filename=None): """Load the specified file, or the last opened file if None.""" # changing fileListWidget loads file if (filename in self.imageList and self.fileListWidget.currentRow() != self.imageList.index(filename)): self.fileListWidget.setCurrentRow(self.imageList.index(filename)) return self.resetState() self.canvas.setEnabled(False) if filename is None: filename = self.settings.value('filename', '') filename = str(filename) if not QtCore.QFile.exists(filename): self.errorMessage('Error opening file', 'No such file: <b>%s</b>' % filename) return False # assumes same name, but json extension self.status("Loading %s..." % os.path.basename(str(filename))) label_file = os.path.splitext(filename)[0] + '.json' if QtCore.QFile.exists(label_file) and \ LabelFile.isLabelFile(label_file): try: self.labelFile = LabelFile(label_file) # FIXME: PyQt4 installed via Anaconda fails to load JPEG # and JSON encoded images. # https://github.com/ContinuumIO/anaconda-issues/issues/131 if QtGui.QImage.fromData(self.labelFile.imageData).isNull(): raise LabelFileError( 'Failed loading image data from label file.\n' 'Maybe this is a known issue of PyQt4 built on' ' Anaconda, and may be fixed by installing PyQt5.') except LabelFileError as e: self.errorMessage( 'Error opening file', "<p><b>%s</b></p>" "<p>Make sure <i>%s</i> is a valid label file." % (e, label_file)) self.status("Error reading %s" % label_file) return False self.imageData = self.labelFile.imageData self.imagePath = os.path.join(os.path.dirname(label_file), self.labelFile.imagePath) self.lineColor = QtGui.QColor(*self.labelFile.lineColor) self.fillColor = QtGui.QColor(*self.labelFile.fillColor) self.otherData = self.labelFile.otherData else: # Load image: # read data first and store for saving into label file. self.imageData = read(filename, None) if self.imageData is not None: # the filename is image not JSON self.imagePath = filename self.labelFile = None image = QtGui.QImage.fromData(self.imageData) if image.isNull(): formats = [ '*.{}'.format(fmt.data().decode()) for fmt in QtGui.QImageReader.supportedImageFormats() ] self.errorMessage( 'Error opening file', '<p>Make sure <i>{0}</i> is a valid image file.<br/>' 'Supported image formats: {1}</p>'.format( filename, ','.join(formats))) self.status("Error reading %s" % filename) return False self.image = image self.filename = filename if self._config['keep_prev']: prev_shapes = self.canvas.shapes self.canvas.loadPixmap(QtGui.QPixmap.fromImage(image)) if self._config['flags']: self.loadFlags({k: False for k in self._config['flags']}) if self._config['keep_prev']: self.loadShapes(prev_shapes) if self.labelFile: self.loadLabels(self.labelFile.shapes) if self.labelFile.flags is not None: self.loadFlags(self.labelFile.flags) self.setClean() self.canvas.setEnabled(True) self.adjustScale(initial=True) self.paintCanvas() self.addRecentFile(self.filename) self.toggleActions(True) self.status("Loaded %s" % os.path.basename(str(filename))) return True
def test_data_to_sever(): ''' Check that the data that is sent from the labeling tool is correct when it is sent to the server This test assumes that a development server is running and is specified in the config file ''' config = labelme.config.get_config( config_file="labelme/config/config_unittests.yaml") with tempfile.TemporaryDirectory() as tmpdir: # Attempt to login to the server and download 3 images to label try: ih = ImageHandler(config["server"], config["port"], config["username"], config["password"], tmpdir) ih.get_new_hits(max_number_hits=4, max_images_downloaded=3) except: EnvironmentError( "Could not connect to server, is it running at the location specified in the config_unittests.yaml file?" ) # Go through and get the file locations and store basic data about the images labels_to_test = [ { "top_left_x": 671.9, "top_left_y": 106.9, "top_right_x": 1186.7, "top_right_y": 138.3, "bottom_left_x": 703.5, "bottom_left_y": 1101.7, "bottom_right_x": 1211.9, "bottom_right_y": 1122.2, "image_id": None, "hit_id": None, "results": { "slope_left": 31.481013, "slope_right": 39.043651, "slope": 35.262332, "intercept_left": -21045.192405, "intercept_right": -46194.800397, "intercept": -32653.94157, "intercept_percent": -27.211617975, "center_x": 943.044318, "center_x_percent": 0.5894026988, "width_horizontal": 510.961816, "width_horizontal_percent": 0.319351135, "width_normal": 510.7564755382, "width_normal_percent": 0.3192227972, } }, { "top_left_x": 694.0, "top_left_y": 94.3, "top_right_x": 1200.9, "top_right_y": 108.4, "bottom_left_x": 679.9, "bottom_left_y": 1139.5, "bottom_right_x": 1186.7, "bottom_right_y": 1136.4, "image_id": None, "hit_id": None, "results": { "slope_left": -74.127660, "slope_right": -72.394366, "slope": -73.261013, "intercept_left": 51538.895745, "intercept_right": 87046.794366, "intercept": 69512.510279, # note this is inverted so need to add image_height to the inventor calc "intercept_percent": 57.9270918992, "center_x": 940.643701, "center_x_percent": 0.5879023131, "width_horizontal": 506.931431, "width_horizontal_percent": 0.3168321444, "width_normal": 506.8842124439, "width_normal_percent": 0.3168026328, } }, { "top_left_x": 690.9, "top_left_y": 78.5, "top_right_x": 1208.8, "top_right_y": 72.2, "bottom_left_x": 734.9, "bottom_left_y": 1167.9, "bottom_right_x": 1243.4, "bottom_right_y": 1136.4, "image_id": None, "hit_id": None, "results": { "slope_left": 24.759091, "slope_right": 30.757225, "slope": 27.758158, "intercept_left": -17027.555909, "intercept_right": -37107.134104, "intercept": -26296.5888881, "intercept_percent": -21.9138240734, "center_x": 968.961583, "center_x_percent": 0.6056009894, "width_horizontal": 513.997225, "width_horizontal_percent": 0.3212482656, "width_normal": 513.6640081061, "width_normal_percent": 0.3210400051, } } ] images = {} for root, _, files in os.walk(tmpdir): for fname in files: if len(images) >= 3: # only want first 3 images break if fname[-5:] == ".jpeg": images[fname[:-5]] = { 'root': root, 'path': os.path.join(root, fname), 'hit_id': root.split(os.sep)[-1].split("_")[-1], 'image_id': fname[:-5], 'label': labels_to_test[len(images)], 'solution': labels_to_test[len(images)]['results'] } assert len( images) == 3, "Did not get 3 images to label from the server!" # Generate labels for each image, save the path to the label in the images dict for image_id in images: image = images[image_id] label = image['label'] result_fname = os.path.join(image["root"], "{}.json".format(image["image_id"])) images[image_id]["result_fname"] = result_fname result = LabelFile() result.save( filename=result_fname, shapes=[{ "label": "edge", "line_color": None, "fill_color": None, "points": [[label["top_left_x"], label["top_left_y"]], [label["top_right_x"], label["top_right_y"]], [label["bottom_right_x"], label["bottom_right_y"]], [label["bottom_left_x"], label["bottom_left_y"]]], "shape_type": "polygon", "flags": {} }], imagePath=image["path"], imageHeight=1200, imageWidth=1600) # upload the result to the server and verfiy ImageHandler._convert_labelme_to_edges() for image_id in images: image = images[image_id] label = image['label'] result_fname = images[image_id]["result_fname"] response = ih.submit_label_file(result_fname) images[image_id]['railedge_id'] = response[ "server_response_created_object_id"] # Verify the updated saved data is correct. # ImageHandler converts the locations in the shape key to the 4 locations needed. Verify it did it correctly # This tests the ImageHandler._convert_labelme_to_edges function for vert in ['top', 'bottom']: for lat in ['left', 'right']: for coord in ['x', 'y']: floatsClose( response["{}_{}_{}".format(vert, lat, coord)], label["{}_{}_{}".format(vert, lat, coord)], msg="Occured in {}_{}_{}".format(vert, lat, coord)) # download the results from the server and verify the result is correct for image_id in images: image = images[image_id] result_correct = image['label']['results'] railedge_id = image['railedge_id'] response = ih.client.get("{}?id={}".format(ih.url_api_edge, railedge_id)) response_json = response.json() assert len( response_json ) == 1, "Got {} railedge labels, should only get 1!".format( len(response_json)) result = response_json[0] for key in result_correct: floatsClose(result[key], result_correct[key], msg="key: {}".format(key))
def run(self): logger.debug('Start import from directory') try: import ptvsd ptvsd.debug_this_thread() except: pass data = Map(self.data) num_images = len(data.images) pattern = data.pattern output_dir = data.output_dir filters = data.filters filter_label_func = self.acceptAll if 'label' in filters and not filters['label'] == StatisticsModel.STATISTICS_FILTER_ALL: filter_label_func = self.acceptLabel image_count = 0 all_shapes = [] items = [] self.checkAborted() for i, filename in enumerate(data.images): self.thread.update.emit(None, i, num_images) self.checkAborted() # Search pattern if pattern and pattern.lower() not in filename.lower(): # re.search(pattern, filename, re.IGNORECASE) == None: continue label_file = os.path.splitext(filename)[0] + '.json' if output_dir: label_file_without_path = os.path.basename(label_file) label_file = os.path.normpath(os.path.join(output_dir, label_file_without_path)) # ListItem item = QtWidgets.QListWidgetItem(filename) item.setFlags(Qt.ItemIsEnabled | Qt.ItemIsSelectable) item.setCheckState(Qt.Unchecked) self.checkAborted() shapes = [] has_labels = False labels_for_image = set([]) label_file_exists = os.path.isfile(label_file) # Labels if label_file_exists: labelFile = LabelFile(label_file) for label, points, line_color, fill_color, shape_type, flags in labelFile.shapes: if filter_label_func(label): has_labels = True shape = Shape(label=label, shape_type=shape_type) shapes.append(shape) labels_for_image.add(label) # Filters if 'label' in filters and not filters['label'] == StatisticsModel.STATISTICS_FILTER_ALL: if not filters['label'] in labels_for_image: continue if 'has_label' in filters: if filters['has_label'] == StatisticsModel.STATISTICS_FILTER_LABELED and not has_labels: continue if filters['has_label'] == StatisticsModel.STATISTICS_FILTER_UNLABELED and has_labels: continue image_count += 1 items.append(item) if has_labels: item.setCheckState(Qt.Checked) all_shapes.append(shapes) if image_count % data['update_interval'] == 0: self.thread.data.emit({ 'items': items, 'num_images': image_count, 'all_shapes': all_shapes, }) image_count = 0 all_shapes = [] items = [] self.checkAborted() self.thread.data.emit({ 'num_images': image_count, 'all_shapes': all_shapes, 'items': items, })