def hist_equalize(pixel_array): ''' pixel_array: original input image ''' hist_equalized = cv2.equalizeHist(pixel_array) hist_equalized = np.stack((hist_equalized,)*3, axis=-1) data = plt.make_image(hist_equalized, "Histogram Equalized\n") return data
def clahe_hist_equalize(pixel_array): ''' pixel_array: original input image ''' clahe = cv2.createCLAHE(clipLimit=3.0, tileGridSize=(8,8)) clahe_hist_equalized = clahe.apply(pixel_array) clahe_hist_equalized = np.stack((clahe_hist_equalized,)*3, axis=-1) data = plt.make_image(clahe_hist_equalized, "Clahe Histogram Equalized\n") return data
def clustering(pixel_array): ''' pixel_array: original input image ''' clusters = slic(pixel_array, compactness=0.01, n_segments=10, sigma=20) img = mark_boundaries(pixel_array, clusters, color=(0, 0, 0), mode='outer') data = plt.make_image(img, "Super Pixel + Clustering\n") return data
def plot_canny(pixel_array): ''' pixel_array: original input image ''' h, w = pixel_array.shape res = cv2.resize(pixel_array, dsize=(int(512 * w / h), 512), interpolation=cv2.INTER_CUBIC) canny_array = cv2.Canny(res.astype(np.uint8), 100, 200) canny_array = np.stack((canny_array,)*3, axis=-1) data = plt.make_image(canny_array, "Canny Edge Detection\n") return data
def black_white_windowing(dicom_pixel_array): threshold = 80 lut_min = np.linspace(255, 255, num=15, endpoint=True) lut_mid = np.linspace(0, 0, num=threshold - 15, endpoint=True) lut_max = np.linspace(255, 255, num=256 - threshold, endpoint=True) lut = np.concatenate((lut_min, lut_mid, lut_max)) dicom_pixel_array = lut[dicom_pixel_array] pixel_array = np.stack((dicom_pixel_array, ) * 3, axis=-1) data = plt.make_image(img=pixel_array, title="Windowing to Gray Scale\n") return data
def metadata(file_path, pixel_array): ''' file_path: input image file path pixel_array: original input image ''' pixel_array = np.stack((pixel_array, ) * 3, axis=-1) img_data = pydicom.dcmread(file_path) info = 'ID: {}\nModality: {} Age: {} Sex: {}\nBody Part Examined: {}\nView Position: {}'.format( img_data.PatientID, img_data.Modality, img_data.PatientAge, img_data.PatientSex, img_data.BodyPartExamined, img_data.ViewPosition) data = plt.make_image(pixel_array, info) return (data, info)
def landmark(img, pixel_array): ''' img: mask image pixel_array: original input image ''' # make mask to red border line img = np.stack([img, img / 512, img / 512, img], axis=-1) pixel_array = np.stack((pixel_array, ) * 3, axis=-1) # make overlapped image data = plt.make_image(img=pixel_array, img2=img, title="Landmark Extraction\n", ticks=[0, len(img) - 1]) return data
def bc_control(pixel_array, br, ct): ''' pixel_array: input image br: brightness value ct: contrast value ''' img = Image.fromarray(pixel_array) enhancer_ct = ImageEnhance.Contrast(img) img = np.array(enhancer_ct.enhance(ct)) img = Image.fromarray(img) enhancer_br = ImageEnhance.Brightness(img) img = np.array(enhancer_br.enhance(br)) img = np.stack((img, ) * 3, axis=-1) data = plt.make_image(img=img, title="Brightness Contrast Control\n") return data
def coord(img, pixel_array): ''' img: mask image pixel_array: original input image ''' h, w = pixel_array.shape # make image 1/16 resolution dst = np.array([[img[i][j] for j in range(0, len(img[i]), int(w / 64))] for i in range(0, len(img), int(h / 64))]) # initialize start index and end index of landmark start_idx = -1 end_idx = len(dst) # BFS code for finding largest two clusters group_table = dict() map = [[0 if dst[i][j] <= 200 else -1 for j in range(0, len(dst[i]))] for i in range(0, len(dst))] group_num = 0 total_num = -sum([sum(map[i]) for i in range(len(map))]) checked_num = 0 while checked_num < total_num: group_num += 1 x, y = (-1, -1) for i in range(len(map)): for j in range(len(map[i])): if map[i][j] == -1: x, y = (i, j) break if x != -1 and y != -1: break queue = deque() queue.append((x, y)) while queue: item = queue.popleft() # print(item) if map[item[0]][item[1]] == -1: map[item[0]][item[1]] = group_num checked_num += 1 group_table[ group_num] = 0 if group_num not in group_table else group_table[ group_num] + 1 if item[0] > 0 and map[item[0] - 1][item[1]] == -1: queue.append((item[0] - 1, item[1])) if item[0] < len(map) - 1 and map[item[0] + 1][item[1]] == -1: queue.append((item[0] + 1, item[1])) if item[1] > 0 and map[item[0]][item[1] - 1] == -1: queue.append((item[0], item[1] - 1)) if item[1] < len(map[0]) - 1 and map[item[0]][item[1] + 1] == -1: queue.append((item[0], item[1] + 1)) sorted_group_table = sorted(group_table.items(), key=(lambda x: x[1]), reverse=True) it = iter(sorted_group_table) start_idx_1, end_idx_1 = (len(map), -1) start_idx_2, end_idx_2 = (len(map), -1) fst_group = next(it, None) if fst_group: for i, j in zip(range(len(map)), reversed(range(len(map)))): if start_idx_1 == len(map) and fst_group[0] in map[i]: start_idx_1 = i if end_idx_1 == -1 and fst_group[0] in map[j]: end_idx_1 = j if start_idx_1 != len(map) and end_idx_1 != -1: break snd_group = next(it, None) if snd_group: for i, j in zip(range(len(map)), reversed(range(len(map)))): if start_idx_2 == len(map) and snd_group[0] in map[i]: start_idx_2 = i if end_idx_2 == -1 and snd_group[0] in map[j]: end_idx_2 = j if start_idx_2 != len(map) and end_idx_2 != -1: break # multiply 16 to start index and end index as BFS runned in 1/16 resolution start_idx = min(start_idx_1, start_idx_2) * int(h / 64) end_idx = max(end_idx_1, end_idx_2) * int(h / 64) pixel_array = np.stack((pixel_array, ) * 3, axis=-1) # make line on input image for j in range(0, len(pixel_array[0])): for k in range(0, 15): if start_idx + k - 7 >= 0 and start_idx + k - 7 < len( pixel_array ) and end_idx + k - 7 >= 0 and end_idx + k - 7 < len(pixel_array): pixel_array[start_idx + k - 7][j] = [255, 0, 0] pixel_array[end_idx + k - 7][j] = [255, 0, 0] data = plt.make_image(img=pixel_array, title="Anatomical Imaging Range\n", ticks=[0, start_idx, end_idx, len(pixel_array) - 1]) # return output image and tuple of start index and end index return (data, (start_idx, end_idx))
def coord_windowing(pixel_array): ''' pixel_array: original input image ''' # control brightness and contrast to make image clear img = Image.fromarray(pixel_array) enhancer_ct = ImageEnhance.Contrast(img) img = enhancer_ct.enhance(5) enhancer_br = ImageEnhance.Brightness(img) img = np.array(enhancer_br.enhance(5)) # find first index of white pixel for each row white_pixel_coord_list = [0 for _ in range(img.shape[0])] for i in range(img.shape[0]): for j in range(img.shape[1]): if img[i][j] >= 255 and img[i][j + 1] >= 255 and img[i][j + 5] >= 255: white_pixel_coord_list[i] = j break # find start index of while pixel appearing start = 0 for i in range(len(white_pixel_coord_list)): if white_pixel_coord_list[i] != 0: start = i break for i in range(start): white_pixel_coord_list[i] = white_pixel_coord_list[start] # find index of minimum index of white pixel start min = 100000 min_idx = 0 end = 0 for i in range(len(white_pixel_coord_list)): if white_pixel_coord_list[i] <= min and white_pixel_coord_list[i] != 0: min = white_pixel_coord_list[i] min_idx = i # find inflection point after minimum index of white pixel start for i in range(min_idx, len(white_pixel_coord_list) - 50): flag = True for j in range(50): if white_pixel_coord_list[i] < white_pixel_coord_list[i + j]: flag = False if flag: end = i break # draw landmark coordinate line on original input image img = np.stack((pixel_array, ) * 3, axis=-1) for i in range(img.shape[1]): for j in range(5): img[start + j - 1][i] = [255, 255, 0] img[end + j - 1][i] = [255, 255, 0] data = plt.make_image(img=img, title="Anatomical Imaging Range\n", ticks=[0, start, end, len(img) - 1]) return data
def clustering_coord(pixel_array): ''' pixel_array: original input image ''' h, w = pixel_array.shape clusters = slic(pixel_array, compactness=0.01, n_segments=10, sigma=20) cnt = len(np.unique(clusters)) min = [(0, 0) for _ in range(cnt)] max = [(0, 0) for _ in range(cnt)] score = [0 for _ in range(cnt)] for i in range(cnt): for row_idx, row in enumerate(clusters): if i in row: min[i] = (row_idx, i) break for row_idx, row in enumerate(reversed(clusters)): if i in row: max[i] = (len(clusters) - 1 - row_idx, i) break min = sorted(min) max = sorted(max, reverse=True) # print(min, max) for k, (i, j) in enumerate(zip(min, max)): score[i[1]] += k score[j[1]] += k # print(score) fst_cluster, score_max = -1, -1 for i, x in enumerate(score): if x > score_max: score_max = x fst_cluster = i # print(fst_cluster) start_idx = 0 end_idx = 0 for i, row in enumerate(pixel_array): if sum(row) / len(row) > 30: start_idx = i break for i in max: if i[1] == fst_cluster: end_idx = i[0] break pixel_array = np.stack((pixel_array, ) * 3, axis=-1) for j in range(0, len(pixel_array[0])): for k in range(0, 5): if start_idx + k - 2 >= 0 and start_idx + k - 2 < len( pixel_array ) and end_idx + k - 2 >= 0 and end_idx + k - 2 < len(pixel_array): pixel_array[start_idx + k - 2][j] = [255, 128, 0] pixel_array[end_idx + k - 2][j] = [255, 128, 0] data = plt.make_image(img=pixel_array, title="Anatomical Imaging Range\n", ticks=[0, start_idx, end_idx, len(pixel_array) - 1]) return data
def coord_windowing(dicom_pixel_array): pixel_array = resize(dicom_pixel_array, (512, 512), preserve_range=True) pixel_mean = int(sum([sum(row) for row in pixel_array]) / (512 * 512)) pixel_mean = 75 if pixel_mean < 140 else pixel_mean - 16 for i in range(len(pixel_array)): for j in range(len(pixel_array[i])): if pixel_array[i][j] <= pixel_mean: pixel_array[i][j] = 255 else: break for j in reversed(range(len(pixel_array[i]))): if pixel_array[i][j] <= pixel_mean: pixel_array[i][j] = 255 else: break for i in range(len(pixel_array[0])): for j in range(len(pixel_array)): if pixel_array[j][i] <= pixel_mean or pixel_array[j][i] == 255: pixel_array[j][i] = 255 else: break for j in reversed(range(len(pixel_array))): if pixel_array[j][i] <= pixel_mean or pixel_array[j][i] == 255: pixel_array[j][i] = 255 else: break lut_min = np.linspace(255, 255, num=(pixel_mean - 40), endpoint=True) lut_mid = np.linspace(0, 0, num=80, endpoint=True) lut_max = np.linspace(255, 255, num=256 - (pixel_mean + 20), endpoint=True) lut = np.concatenate((lut_min, lut_mid, lut_max)) pixel_array = lut[pixel_array.astype(np.uint8)] pixel_array = [[ pixel_array[i][j] for j in range(0, len(pixel_array[i]), 8) ] for i in range(0, len(pixel_array), 8)] xs = [x for x in range(len(pixel_array))] y = [sum(row) / len(pixel_array[0]) for row in pixel_array] start_idx = -1 end_idx = len(pixel_array) for i, x in enumerate(y): if i == 0 or i == len(pixel_array) - 1: continue if y[i] <= 180 and y[i - 1] >= 180: start_idx = i if y[i] <= 220 and y[i + 1] >= 220: end_idx = i start_idx = max(0, int(start_idx * len(dicom_pixel_array) / 64)) end_idx = min(len(dicom_pixel_array), int(end_idx * len(dicom_pixel_array) / 64)) pixel_array = np.stack((dicom_pixel_array, ) * 3, axis=-1) for j in range(0, len(pixel_array[0])): for k in range(0, 15): if start_idx + k - 7 >= 0 and start_idx + k - 7 < len(pixel_array): pixel_array[start_idx + k - 7][j] = [255, 255, 0] if end_idx + k - 7 >= 0 and end_idx + k - 7 < len(pixel_array): pixel_array[end_idx + k - 7][j] = [255, 255, 0] data = plt.make_image(img=pixel_array, title="Anatomical Imaging Range\n", ticks=[0, start_idx, end_idx, len(pixel_array) - 1]) return data