コード例 #1
0
def get_blob_crops_from_scale_space_imgs(img,
                                         scale_space,
                                         t_key,
                                         min_radius,
                                         max_radius,
                                         response_threshold=100):
    blob_arrs = []
    t_range = get_t_range(min_radius, max_radius)
    start_index = -1

    for i in range(0, len(scale_space)):
        if t_key[i] > t_range[0] and t_key[i] < t_range[1]:
            if start_index == -1:
                start_index = i
            append_img = KernelMath.convolute_array(scale_space[i],
                                                    BLOB_KERNEL)
            arr = numpy.array(append_img)
            arr = numpy.abs(arr) * t_key[i]
            blob_arrs.append(arr)

    scale_fit_blob_arrs(blob_arrs, scale_space)
    maxes = get_rel_maxes(blob_arrs, response_threshold, t_key[start_index:])
    #draw_maxes_to_img(img, blob_arrs, maxes).show()
    blob_rects = get_blob_rectangles(img.size, blob_arrs, maxes)

    copy_img = img.convert('RGB')
    copy_image = copy_img.load()
    for i in range(0, len(blob_rects)):
        blob_rects[i].draw(copy_img, copy_image, (255, 0, 0))
    copy_img.show()

    blob_rect_clusters = cluster_blob_rects(blob_rects)
    biggest_cluster = sorted(blob_rect_clusters,
                             key=lambda cluster: len(cluster),
                             reverse=True)

    bounded_clustered_blob_rects = get_cluster_bounding_boxes(
        blob_rect_clusters)

    img_copy = img.convert('RGB')
    image_copy = img_copy.load()
    for i in range(0, len(bounded_clustered_blob_rects)):
        bounded_clustered_blob_rects[i].draw(img_copy, image_copy, (0, 0, 255))
    img_copy.show()

    crops = []
    for i in range(0, len(bounded_clustered_blob_rects)):
        crops.append(
            Crop.get_img_cropped_to_bounds(img,
                                           bounded_clustered_blob_rects[i]))
    return crops
コード例 #2
0
def get_target_crops_from_img(img, geo_stamps, ppsi):
    '''takes the full image, geostamps, and ppsi and finds the targets,
    crops them, and instantiates a list of TargetCrop objects and returns them'''

    '''notes: ppsi of the image should be used in picking a reasonable max crop size'''
    img_downsized = Scale.get_img_scaled_to_one_bound(img, DOWNSCALE_CONSTRAINT).convert('RGB')

    #img.show()
    #img = Image.fromarray(cv2.GaussianBlur(numpy.array(img), (5,5), 3))
    #img = Image.fromarray(cv2.GaussianBlur(numpy.array(img), (7,7), 2))
    #img = img.resize((img.size[0]//5, img.size[1]//5))
    img_downsized = Image.fromarray(cv2.bilateralFilter(numpy.array(img_downsized), 15, 40, 40))
    #img_downsized.show()
    img_downsized.show()
    #img.show()
    image = numpy.array(img_downsized)


    kernel_size = 3
    kernel_margin = (kernel_size - 1)//2
    variance_map = numpy.zeros(img.size)


    var_img = numpy.zeros((image.shape[0], image.shape[1]))
    for x in range(kernel_margin, var_img.shape[0]-kernel_margin):
        for y in range(kernel_margin, var_img.shape[1]-kernel_margin):
            sub_arr = image[x-kernel_margin:x+kernel_margin+1, y-kernel_margin:y+kernel_margin+1]

            mean, std_dev = (cv2.meanStdDev(sub_arr))
            '''for some reason porting to this hasn't been the same as it functioned before'''
            var_img[x,y] = numpy.linalg.norm(std_dev)**2
    Image.fromarray(255*var_img/numpy.amax(var_img)).show()
    #pil_var_img = Image.fromarray(255*var_img/numpy.amax(var_img))
    #pil_var_img.show()
    #threshold_img = ImageMath.get_binary_bw_img(pil_var_img, pil_var_img.load(), 40)
    #threshold_img.show()
    var_img = var_img.T
    threshold_img = Image.new('L', (var_img.shape[0], var_img.shape[1]))
    threshold_image = threshold_img.load()

    for x in range(0, threshold_img.size[0]):
        for y in range(0, threshold_img.size[1]):
            if var_img[x,y] > VARIANCE_THRESHOLD:
                threshold_image[x,y] = 255
    threshold_img.show()

    threshold_connected_components_map = ImageMath.get_bw_connected_components_map(threshold_img, threshold_img.load())
    threshold_connected_components = ImageMath.convert_connected_component_map_into_clusters(threshold_connected_components_map)
    resize_ratio = float(img.size[0])/float(img_downsized.size[0])
    min_crop_size = (int((1.0/resize_ratio) * MAX_SQUARE_CROP_BOUNDS), int((1.0/resize_ratio) * MAX_SQUARE_CROP_BOUNDS))
    min_cluster_size = 38
    max_cluster_size = 200

    crops = []
    for i in range(0, len(threshold_connected_components)):
        if len(threshold_connected_components[i]) > min_cluster_size:
            crop_img = ImageMath.get_connected_component_mask(threshold_img.size, threshold_connected_components[i])
            crops.append(crop_img)


    color_crops = []
    crop_margin = 5
    for i in range(0, len(crops)):



        crop_img = crops[i]
        #crop_img.show()
        crop_img_mean_pixel = ImageMath.get_bw_img_mean_pixel(crop_img, crop_img.load())
        #crop_img.show()

        bilat_crop_img = img_downsized.crop((crop_img_mean_pixel[0]-(100 * (1.0/resize_ratio)), crop_img_mean_pixel[1]-(100 * (1.0/resize_ratio)), crop_img_mean_pixel[0]+(100 * (1.0/resize_ratio)), crop_img_mean_pixel[1]+ (100 * (1.0/resize_ratio)))).convert('L')
        bilat_crop_canny_img = Image.fromarray(cv2.Canny(numpy.array(bilat_crop_img), 40, 80))

        #bilat_crop_canny_img.show()

        bilat_start_x = crop_img_mean_pixel[0]-(100 * (1.0/resize_ratio))
        bilat_start_y = crop_img_mean_pixel[1]-(100 * (1.0/resize_ratio))
        bilat_bounding_rect = Crop.get_bw_img_bounds(bilat_crop_canny_img, bilat_crop_canny_img.load())
        bounding_rect = Crop.get_bw_img_bounds(crop_img, crop_img.load())
        bounding_rect.set_x(int(bounding_rect.get_x() * resize_ratio) - crop_margin)
        bounding_rect.set_y(int(bounding_rect.get_y() * resize_ratio) - crop_margin)
        bounding_rect.set_width(int(bounding_rect.get_width() * resize_ratio) + 3*crop_margin)
        bounding_rect.set_height(int(bounding_rect.get_height() * resize_ratio) + 3*crop_margin)
        append_img = Crop.get_img_cropped_to_bounds(img, bounding_rect)

        color_crops.append((numpy.asarray(crop_img_mean_pixel), append_img))

    '''kills crops in the same list whose center are very close to each other (sometimes the same target pops up twice)'''
    min_dist_threshold = 15

    min_area = 1600
    max_area = 48400*3
    i = 0
    while i < len(color_crops):
        sorted_crops = sorted(color_crops, key = lambda crop : numpy.linalg.norm(crop[0]-color_crops[i][0]))
        '''sorted_crops[1][0] so that it excludes a measurement to itself'''
        if numpy.linalg.norm(sorted_crops[1][0] - color_crops[i][0]) < min_dist_threshold:
            if not (color_crops[i][1].size[0]*color_crops[i][1].size[1] > sorted_crops[1][1].size[0]*sorted_crops[1][1].size[1]):
                del color_crops[i]
            else:
                i+=1
        else:
            i+=1

    i = 0
    while i < len(color_crops):
        area = color_crops[i][1].size[0]*color_crops[i][1].size[1]
        if area < min_area or area > max_area:
            del color_crops[i]
        else:
            i += 1

    i = 0
    KMEANS_RUN_TIMES = 10
    MIN_TOTAL_CLUSTER_DISTANCE_SUM = 370
    '''maybe, instead of summing the distance, use the area of the triangle that the three points make and threshold that'''
    while i < len(color_crops):
        #print('color crops[i][1]: ', color_crops[i][1])
        colors = numpy.array(color_crops[i][1].convert('RGB')).reshape((-1, 3))
        colors = numpy.float32(colors)

        criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, KMEANS_RUN_TIMES, 1.0)
        ret, labels, color_clusters = cv2.kmeans(colors, 3, None, criteria, 10, cv2.KMEANS_RANDOM_CENTERS)
        #print("color clusters: ", color_clusters)
        dist_sum = 0
        dist_sum += numpy.linalg.norm(color_clusters[1]-color_clusters[0])
        dist_sum += numpy.linalg.norm(color_clusters[2]-color_clusters[1])
        dist_sum += numpy.linalg.norm(color_clusters[0]-color_clusters[2])
        print("dist sum is: ", dist_sum)
        if not dist_sum > MIN_TOTAL_CLUSTER_DISTANCE_SUM:
            del color_crops[i]
        else:
            i += 1



    target_crops = []



    for i in range(0, len(color_crops)):
        target_crops.append(TargetCrop(img, color_crops[i][1], geo_stamps, color_crops[i][0], ppsi))
    return target_crops
コード例 #3
0
    connected_components_map = connected_components_map[1]
<<<<<<< HEAD
=======
    #print("THRESHOLDED IMG & CONNECTED COMPONENTS COMPLETED")
>>>>>>> committed so I don't lose everything during a rebase

    connected_components = ImageMath.convert_connected_component_map_into_clusters(connected_components_map)
    crop_masks = []
    for i in range(0, len(connected_components)):
        if len(connected_components[i]) > CONNECTED_COMPONENT_SIZE_THRESHOLDS[0] and len(connected_components[i]) < CONNECTED_COMPONENT_SIZE_THRESHOLDS[1]:
            crop_masks.append(ImageMath.get_connected_component_mask(thresholded_local_variance_img.size, connected_components[i]))
    #new_img = parent_img.crop((100,100,200,200))
    color_target_rects = []
    pixel_crop_margin = int(float(CROP_MARGIN_INCHES) * sqrt(ppsi))+1
    for i in range(0, len(crop_masks)):
        mask_bounding_rect = Crop.get_bw_img_bounds(crop_masks[i], crop_masks[i].load())
        '''for some reason adding a crop margin to the right and bottom edge to the crop requires more than just
        2* the crop margin. The *3 is to mitigate this, and seems to work'''
        parent_img_bounding_rect = Rectangle(int(upscale_multiplier * mask_bounding_rect.get_x()) - pixel_crop_margin, int(upscale_multiplier * mask_bounding_rect.get_y()) - pixel_crop_margin, int(upscale_multiplier * mask_bounding_rect.get_width()) + (3 * pixel_crop_margin), int(upscale_multiplier * mask_bounding_rect.get_height()) + (3 * pixel_crop_margin))
        #append_img = Crop.get_img_cropped_to_bounds(parent_img, parent_img_bounding_rect)
        crop_midpoint = parent_img_bounding_rect.get_center()
        color_target_rects.append((crop_midpoint, parent_img_bounding_rect))

    removal_start_time = timeit.default_timer()
    print("len before first remove step: ", len(color_target_rects))
    remove_duplicate_imgs_by_proximity(color_target_rects, ppsi)
    print("len before second remove step: ", len(color_target_rects))
    remove_crops_by_area(color_target_rects, ppsi)

    color_target_crops = []
    for i in range(0, len(color_target_rects)):
コード例 #4
0
ファイル: Main.py プロジェクト: liyu711/SUAS-Competition
def resize_img_to_PCA_specs(img, img_dim):
    crop_img = img
    crop_img = Crop.get_bw_img_cropped_to_bounds(img.convert('L'),
                                                 img.convert('L').load())
    crop_img = crop_img.resize(img_dim)
    return crop_img
コード例 #5
0
def get_target_crops_from_img(parent_img, geo_stamps, ppsi, get_centers=False):
    downsized_parent_image = numpy.array(
        Scale.get_img_scaled_to_one_bound(parent_img,
                                          DOWNSCALE_CONSTRAINT).convert('RGB'))

    downscale_multiplier = float(DOWNSCALE_CONSTRAINT) / float(
        parent_img.size[0])
    upscale_multiplier = 1.0 / downscale_multiplier
    img = Image.fromarray(downsized_parent_image)

    downsized_parent_image = cv2.bilateralFilter(downsized_parent_image,
                                                 BILAT_FILTER_THRESHOLDS[0],
                                                 BILAT_FILTER_THRESHOLDS[1],
                                                 BILAT_FILTER_THRESHOLDS[2])
    for i in range(0, MEDIAN_BLUR_RUN_TIMES):
        downsized_parent_image = cv2.medianBlur(downsized_parent_image, 3)

    start_time = timeit.default_timer()

    #var_image = create_local_variance_image(cv2.cvtColor(downsized_parent_image, cv2.COLOR_RGB2GRAY))
    #Image.fromarray(255*var_image/numpy.amax(var_image)).show()
    #print("var image shape: ", var_image.shape)

    print("time elapsed creating var image: ",
          timeit.default_timer() - start_time)
    start_time = timeit.default_timer()

    gaussian_blurred_downsized_image = cv2.GaussianBlur(
        downsized_parent_image, (5, 5), 3.0)
    thresh_var_img = Image.fromarray(
        cv2.Canny(gaussian_blurred_downsized_image, 100, 150, apertureSize=3)
    )  #create_thresholded_local_variance_img(var_image)#Image.fromarray(cv2.Canny(gaussian_blurred_downsized_image, 20, 40, apertureSize = 3))
    #thresh_var_img.show()
    print("time elapsed thresholding variance img: ",
          timeit.default_timer() - start_time)
    downsized_canny_image = numpy.uint8(numpy.array(thresh_var_img))

    contour_image, contours, hierarchy = cv2.findContours(
        downsized_canny_image, cv2.RETR_CCOMP, cv2.CHAIN_APPROX_SIMPLE)
    print("contours shape: ", len(contours), ", hierarchy shape: ",
          hierarchy.shape)

    drawn_contour_image = numpy.array(
        Image.new('RGB', tuple(contour_image.T.shape)))
    good_contours = []
    for i in range(0, hierarchy.shape[1]):
        if hierarchy[0][i][2] >= 0:  # and hierarchy[0][i][0] >= 0:
            good_contours.append(contours[i])

    print("good contours shape: ", len(good_contours))
    drawn_contour_image = cv2.drawContours(drawn_contour_image, good_contours,
                                           -1, (0, 255, 0), 1)
    '''print("hierarchy is: ", hierarchy)
    for i in range(0, hierarchy.shape[0]):
        print("hierarchy [i,0,2] is: ", hierarchy[i][0][2])
        if hierarchy[i][0][2] == -1:
            drawn_contour_image = cv2.drawContours(drawn_contour_image, contours[i], -1, (0,255,0), 3)
    #drawn_contour_image = cv2.drawContours(numpy.array(Image.new('RGB', tuple(contour_image.T.shape))), contours, -1, (0,255,0), 3)'''

    crop_masks = []
    for i in range(0, len(good_contours)):
        iter_contour_image = numpy.zeros(
            (downsized_parent_image.shape[0], downsized_parent_image.shape[1]))
        iter_contour_image = cv2.drawContours(iter_contour_image,
                                              good_contours, i, 255, 3)
        iter_contour_img = Image.fromarray(iter_contour_image)
        crop_masks.append(iter_contour_img)

    color_target_rects = []
    pixel_crop_margin = int(float(CROP_MARGIN_INCHES) * sqrt(ppsi)) + 1
    for i in range(0, len(crop_masks)):
        mask_bounding_rect = Crop.get_bw_img_bounds(crop_masks[i],
                                                    crop_masks[i].load())
        '''for some reason adding a crop margin to the right and bottom edge to the crop requires more than just
        2* the crop margin. The *3 is to mitigate this, and seems to work'''
        parent_img_bounding_rect = Rectangle(
            int(upscale_multiplier * mask_bounding_rect.get_x()) -
            pixel_crop_margin,
            int(upscale_multiplier * mask_bounding_rect.get_y()) -
            pixel_crop_margin,
            int(upscale_multiplier * mask_bounding_rect.get_width()) +
            (2 * pixel_crop_margin),
            int(upscale_multiplier * mask_bounding_rect.get_height()) +
            (2 * pixel_crop_margin))
        crop_midpoint = parent_img_bounding_rect.get_center()
        color_target_rects.append((crop_midpoint, parent_img_bounding_rect))

    print("len before first remove step: ", len(color_target_rects))
    remove_duplicate_imgs_by_proximity(color_target_rects, ppsi)
    print("len before second remove step: ", len(color_target_rects))
    remove_crops_by_area(color_target_rects, ppsi)

    color_target_crops = []
    for i in range(0, len(color_target_rects)):
        color_target_crops.append(
            (color_target_rects[i][0],
             Crop.get_img_cropped_to_bounds(
                 parent_img,
                 color_target_rects[i][1],
                 min_size=(sqrt(ppsi) * MIN_CROP_SIZE_INCHES,
                           sqrt(ppsi) * MIN_CROP_SIZE_INCHES))))

    print("len before third remove step: ", len(color_target_crops))
    '''needs to remove bad crops through kmeans.
    Run kmeans on the image and find where the clusetres are. Two of these cluseters should be
    near valid target and letter colors'''
    '''crop removal with false crop catcher needs a more aggressive threshold to be set.
    Rather than only training off of random crops selected from images as false positives,
    instead use actual false positives that were found in the images it was run on.'''

    #remove_crops_with_false_crop_catcher(color_target_crops)
    remove_crops_with_width_length_ratio(color_target_crops)
    ''' TO KILL REMAINDER OF FALSE POSITIVES:
    Train a decision tree or random forest
    Vector would be an assemblage of responses to various shape algorithm responses
    i.e. number harris corners, circle response score, etc.
    Possibly train a model that uses the colors present in the image as well'''

    print("final len: ", len(color_target_crops))

    centers = []
    for i in range(0, len(color_target_crops)):
        centers.append(color_target_rects[i][1].get_center())

    target_crops = []
    for i in range(0, len(color_target_crops)):
        target_crops.append(
            TargetCrop(parent_img, color_target_crops[i][1], image_timestamp,
                       geo_stamps, color_target_crops[i][0], ppsi))
    '''target_crop_index = 0
    KMEANS_RUN_TIMES = 4
    MIN_DIST_TO_TARGET_COLOR = 20
    MIN_DIST_TO_ELIMINATE_CLUSTER_COLOR = 20
    target_colors = TargetColorReader.target_colors
    while target_crop_index < len(target_crops):
        num_valid_colors = 0
        crop_colors = numpy.array(target_crops[target_crop_index].crop_img).reshape((-1, 3))
        crop_colors = numpy.float32(crop_colors)
        criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, KMEANS_RUN_TIMES, 1.0)
        ret, labels, color_clusters = cv2.kmeans(crop_colors, 3, None, criteria, 10, cv2.KMEANS_RANDOM_CENTERS)

        i = 0
        new_color_clusters = []
        while i < len(color_clusters):
            smallest_dist = numpy.linalg.norm(color_clusters[i] - color_clusters[0])
            for j in range(1, len(color_clusters)):
                if i != j:
                    dist_to_color = numpy.linalg.norm(color_clusters[i] - color_clusters[j])
                    if dist_to_color < smallest_dist:
                        dist_to_color = smallest_dist
            if not smallest_dist < MIN_DIST_TO_ELIMINATE_CLUSTER_COLOR:
                new_color_clusters.append(color_clusters[i])
            i+=1

        color_clusters = numpy.asarray(new_color_clusters)

        for i in range(0, len(color_clusters)):
            closest_color = sorted(target_colors, key = lambda target_color: numpy.linalg.norm(numpy.array(target_color) - color_clusters[i]))[0]
            dist_to_closest_color = numpy.linalg.norm(color_clusters[i] - numpy.array(closest_color))
            if dist_to_closest_color < MIN_DIST_TO_TARGET_COLOR:
                num_valid_colors += 1
        if num_valid_colors < 2:
            del target_crops[target_crop_index]
        else:
            target_crop_index += 1'''

    if get_centers:
        return target_crops, centers

    return target_crops
コード例 #6
0
 def get_img_resized_to_PCA_specs(self, img_in):
     img = ImageOps.invert(img_in)
     image = img.load()
     img = Crop.get_bw_img_cropped_to_bounds(img, image, margin=0)
     img = img.resize(LetterGenerator.PCA_DIM)
     return img
コード例 #7
0
ファイル: TargetTwo.py プロジェクト: liyu711/SUAS-Competition
 def get_letter_img_resized_to_PCA_dims(self, letter_img):
     out_img = Crop.get_bw_img_cropped_to_bounds(letter_img,
                                                 letter_img.load(),
                                                 margin=0)
     out_img = out_img.resize(TargetTwo.PCA_LETTER_DIM)
     return out_img