labelme的开源标注工具非常好用,但是有个问题就是在使用语义分割的的标注后,对一个文件夹的标注好的图片没有批量转换的工具,而且用labelme_json_to_dataset
转化多张图片为dataset后,也会存在相同类型的label在不同图片中可能掩模颜色不一致。下面介绍我解决这些问题的代码。
labelme_batch
Label标注工具的批量转化处理与颜色和标签的对应
内有更多干货教程
我自己用python自己写了一个可以批量转换的脚本,原理很简单,就是使用python的os模块来运行转化命令,代码如下:
import os, argparse
parser = argparse.ArgumentParser()
parser.add_argument("-p", "--path", help="dir path of imamges")
args = parser.parse_args()
json_names = list(filter(lambda x: '.json' in x, os.listdir(args.path)))
os.chdir(args.path)
if not os.path.exists('../labels'):
os.mkdir('../labels')
for n in json_names:
os.system('labelme_json_to_dataset {} -o ../labels/{}'.format(n, os.path.splitext(n)[0]))
运行的方法为:
python py文件的路径(绝对/相对) -p 图片文件夹路径(绝对/相对)
其中图片文件夹的路径,是通过label工具标注过后的图片文件夹路径,即既有图片又有相对应的json文件的那个文件夹。
最后运行后会在图片文件夹所在的目录下面生成一个名字叫labels的文件夹,里面就是每个标注图片转化而来的dataset。
使用1 中的批量转化json脚本后,可以很方便的批量将json转为dataset,但是labelme官方的转化命令有个问题就是在批量转化的dataset中,可能在不同的图片中生成的掩模图片中的label颜色就不一样,大概去github项目中看了源码,发现不太好改,所以还是自己写一个脚本。代码如下:
# -*- coding: utf-8 -*-
import json
import cv2
import numpy as np
import os
import argparse
def cvt_one(json_path, img_path, save_path, label_color):
# load img and json
data = json.load(open(json_path))
img = cv2.imread(img_path)
# get background data
img_h = data['imageHeight']
img_w = data['imageWidth']
color_bg = (0, 0, 0)
points_bg = [(0, 0), (0, img_h), (img_w, img_h), (img_w, 0)]
img = cv2.fillPoly(img, [np.array(points_bg)], color_bg)
# draw roi
for i in range(len(data['shapes'])):
name = data['shapes'][i]['label']
points = data['shapes'][i]['points']
color = data['shapes'][i]['fill_color']
# data['shapes'][i]['fill_color'] = label_color[name] # 修改json文件中的填充颜色为我们设定的颜色
if label_color:
img = cv2.fillPoly(img, [np.array(points, dtype=int)], label_color[name])
else:
img = cv2.fillPoly(img, [np.array(points, dtype=int)], (color[0], color[1], color[2]))
cv2.imwrite(save_path, img)
if __name__ == '__main__':
parser = argparse.ArgumentParser()
parser.add_argument("-p", "--path", help="dir path of imamges")
args = parser.parse_args()
# path
file_dir = args.path
save_dir = os.path.join(os.path.split(args.path)[0], 'labels')
files = os.listdir(file_dir)
if not os.path.exists(save_dir):
os.mkdir(save_dir)
img_files = list(filter(lambda x: '.png' in x, files))
label_color = {
'forest': (225, 225, 0),
'building': (225, 0, 0),
'farm': (0, 255, 0),
'road': (0, 0, 255)
}
for i in range(len(img_files)):
img_path = file_dir + '/' + img_files[i]
json_path = img_path.replace('.png', '.json')
save_path = save_dir + '/' + img_files[i]
print('Processing {}'.format(img_path))
cvt_one(json_path, img_path, save_path, label_color)
运行的方法与上面的脚本一样:
python py文件的路径(绝对/相对) -p 图片文件夹路径(绝对/相对)
其中图片文件夹的路径,是通过label工具标注过后的图片文件夹路径,即既有图片又有相对应的json文件的那个文件夹。
最后运行后会在图片文件夹所在的目录下面生成一个名字叫labels的文件夹,里面就是每个标注图片转化而来的掩模图像。
还有一点不同就是,可以修改代码中的label_color
来配置相应的label对应的颜色,而没有在label_color中配置的label默认使用json文件里面对应的fill_color
颜色。
参考:
语义分割标注:通过labelme生成的json文件,生成标注图像 ; 更新批量处理操作