Commit 1c0f457a authored by jay's avatar jay
Browse files

Merge remote-tracking branch 'upstream/dev'

parents f76bed03 c298c90a
Loading
Loading
Loading
Loading
+4 −4
Changes for autocnet/cg/cg.py: 4 added lines, 4 removed lines.
Original line number Diff line number Diff line
@@ -70,13 +70,13 @@ def two_poly_overlap(poly1, poly2):
                   The total area of overalap

    """
    a_o = poly2.Intersection(poly1).GetArea()
    overlap_area_polygon = poly2.Intersection(poly1)
    overlap_area = overlap_area_polygon.GetArea()
    area1 = poly1.GetArea()
    area2 = poly2.GetArea()

    overlap_area = a_o
    overlap_percn = (a_o / (area1 + area2 - a_o)) * 100
    return overlap_percn, overlap_area
    overlap_percn = (overlap_area / (area1 + area2 - overlap_area)) * 100
    return overlap_percn, overlap_area, overlap_area_polygon


def get_area(poly1, poly2):
+30 −8
Changes for autocnet/graph/edge.py: 30 added lines, 8 removed lines.
Original line number Diff line number Diff line
@@ -14,6 +14,7 @@ from autocnet.matcher.feature import FlannMatcher
from autocnet.transformation.decompose import coupled_decomposition
from autocnet.transformation.transformations import FundamentalMatrix, Homography
from autocnet.vis.graph_view import plot_edge
from autocnet.vis.graph_view import plot_node
from autocnet.cg import cg


@@ -354,7 +355,7 @@ class Edge(dict, MutableMapping):
    def ratio_check(self, clean_keys=[], **kwargs):
        if hasattr(self, 'matches'):

            matches, mask = self._clean(clean_keys)
            matches, mask = self.clean(clean_keys)

            self.distance_ratio = od.DistanceRatio(matches)
            self.distance_ratio.compute(mask=mask, **kwargs)
@@ -389,7 +390,7 @@ class Edge(dict, MutableMapping):
        if not hasattr(self, 'matches'):
            raise AttributeError('Matches have not been computed for this edge')
            return
        matches, mask = self._clean(clean_keys)
        matches, mask = self.clean(clean_keys)

        # TODO: Homogeneous is horribly inefficient here, use Numpy array notation
        s_keypoints = self.source.get_keypoint_coordinates(index=matches['source_idx'],
@@ -440,7 +441,7 @@ class Edge(dict, MutableMapping):
        else:
            raise AttributeError('Matches have not been computed for this edge')

        matches, mask = self._clean(clean_keys)
        matches, mask = self.clean(clean_keys)

        s_keypoints = self.source.get_keypoint_coordinates(index=matches['source_idx'])
        d_keypoints = self.destination.get_keypoint_coordinates(index=matches['destination_idx'])
@@ -498,7 +499,7 @@ class Edge(dict, MutableMapping):
                self.matches[column] = default

        # Build up a composite mask from all of the user specified masks
        matches, mask = self._clean(clean_keys)
        matches, mask = self.clean(clean_keys)

        # Grab the full images, or handles
        if tiled is True:
@@ -568,7 +569,7 @@ class Edge(dict, MutableMapping):
        if not hasattr(self, 'matches'):
            raise AttributeError('This edge does not yet have any matches computed.')

        matches, mask = self._clean(clean_keys)
        matches, mask = self.clean(clean_keys)
        domain = self.source.geodata.raster_size

        # Massage the dataframe into the correct structure
@@ -589,10 +590,31 @@ class Edge(dict, MutableMapping):
        mask[mask] = self.suppression.mask
        self.masks = ('suppression', mask)

    def plot(self, ax=None, clean_keys=[], **kwargs):
    def plot_source(self, ax=None, clean_keys=[], **kwargs):  # pragma: no cover
        matches, mask = self.clean(clean_keys=clean_keys)
        indices = pd.Index(matches['source_idx'].values)
        return plot_node(self.source, index_mask=indices, **kwargs)

    def plot_destination(self, ax=None, clean_keys=[], **kwargs):  # pragma: no cover
        matches, mask = self.clean(clean_keys=clean_keys)
        indices = pd.Index(matches['destination_idx'].values)
        return plot_node(self.destination, index_mask=indices, **kwargs)

    def plot(self, ax=None, clean_keys=[], node=None, **kwargs):  # pragma: no cover
        dest_keys = [0, '0', 'destination', 'd', 'dest']
        source_keys = [1, '1', 'source', 's']

        # If node is not none, plot a single node
        if node in source_keys:
            return self.plot_source(self, clean_keys=clean_keys, **kwargs)

        elif node in dest_keys:
            return self.plot_destination(self, clean_keys=clean_keys, **kwargs)

        # Else, plot the whole edge
        return plot_edge(self, ax=ax, clean_keys=clean_keys, **kwargs)

    def _clean(self, clean_keys, pid=None):
    def clean(self, clean_keys, pid=None):
        """
        Given a list of clean keys and a provenance id compute the
        mask of valid matches
@@ -652,7 +674,7 @@ class Edge(dict, MutableMapping):
        if self.matches is None:
            raise AttributeError('Edge needs to have features extracted and matched')
            return
        matches, mask = self._clean(clean_keys)
        matches, mask = self.clean(clean_keys)
        source_array = self.source.get_keypoint_coordinates(index=matches['source_idx']).values

        source_coords = self.source.geodata.latlon_corners
+10 −3
Changes for autocnet/graph/node.py: 10 added lines, 3 removed lines.
Original line number Diff line number Diff line
@@ -264,8 +264,10 @@ class Node(dict, MutableMapping):

        allkps = pd.DataFrame(data=clean_kps, columns=columns, index=index)

        if 'response' in allkps.columns:
            self._keypoints = allkps.sort_values(by='response', ascending=False)

        elif 'size' in allkps.columns:
            self._keypoints = allkps.sort_values(by='size', ascending=False)
        if isinstance(in_path, str):
            hdf = None

@@ -312,7 +314,7 @@ class Node(dict, MutableMapping):
        if isinstance(out_path, str):
            hdf = None

    def group_correspondences(self, cg, *args, clean_keys=['fundamental'], deepen=False, **kwargs):
    def group_correspondences(self, cg, *args, deepen=False, **kwargs):
        """

        Parameters
@@ -332,12 +334,17 @@ class Node(dict, MutableMapping):
             # TODO: Add dangling correspondences to control network anyway.  Subgraphs handle this segmentation if req.
            return

        try:
            clean_keys = kwargs['clean_keys']
        except:
            clean_keys = []

        # Grab all the incident edge matches and concatenate into a group match set.
        # All share the same source node
        edge_matches = []
        for e in incident_edges:
            edge = cg[e[0]][e[1]]
            matches, mask = edge._clean(clean_keys=clean_keys)
            matches, mask = edge.clean(clean_keys=clean_keys)
            # Add a depth mask that initially mirrors the fundamental mask
            edge_matches.append(matches)
        d = pd.concat(edge_matches)
+16 −8
Changes for autocnet/matcher/ciratefi.py: 16 added lines, 8 removed lines.
Original line number Diff line number Diff line
@@ -481,8 +481,8 @@ def tefi(template, search_image, candidate_pixels, best_scales, best_angles,

    # check for upsampling
    if upsampling > 1:
        template = zoom(template, upsampling, order=3)
        search_image = zoom(search_image, upsampling, order=3)
        u_template = zoom(template, upsampling, order=3)
        u_search_image = zoom(search_image, upsampling, order=3)

    alpha_list = np.arange(0, 2*math.pi, alpha)
    candidate_pixels *= int(upsampling)
@@ -505,13 +505,13 @@ def tefi(template, search_image, candidate_pixels, best_scales, best_angles,

        max_coeff = -math.inf
        for j in range(scalesxalphas.shape[0]):
            transformed_template = imresize(template, scalesxalphas[j][0])
            transformed_template = imresize(u_template, scalesxalphas[j][0])
            transformed_template = rotate(transformed_template, scalesxalphas[j][1])

            y_window, x_window = (math.floor(transformed_template.shape[0]/2),
                                  math.floor(transformed_template.shape[1]/2))

            cropped_search = search_image[y-y_window:y+y_window+1, x-x_window:x+x_window+1]
            cropped_search = u_search_image[y-y_window:y+y_window+1, x-x_window:x+x_window+1]

            if(y < y_window or x < x_window or cropped_search.shape < transformed_template.shape or
               cropped_search.shape != transformed_template.shape):
@@ -531,16 +531,24 @@ def tefi(template, search_image, candidate_pixels, best_scales, best_angles,
    if use_percentile:
        thresh = np.percentile(tefi_coeffs, int(thresh))

    candidate_pixels = candidate_pixels/upsampling
    result_points = candidate_pixels[np.where(tefi_coeffs >= thresh)]
    result_coeffs = tefi_coeffs[np.where(tefi_coeffs >= thresh)]

    results = candidate_pixels[np.where(tefi_coeffs >= thresh)]
    x = result_points[0][1]
    y = result_points[0][0]

    ideal_y = u_search_image.shape[0] / 2
    ideal_x = u_search_image.shape[1] / 2

    if verbose:  # pragma: no cover
        plt.imshow(image_pixels, interpolation='none')
        plt.scatter(y=results[:, 0], x=results[:, 1], c='w', s=80)
        plt.scatter(y=y/upsampling, x=x/upsampling, c='w', s=80)
        plt.show()

    return results
    x = (ideal_x - x)/upsampling
    y = (ideal_y - y)/upsampling

    return x, y, result_coeffs[0]


def ciratefi(template, search_image, upsampling=1, cifi_thresh=95, rafi_thresh=95, tefi_thresh=100,
+7 −2
Changes for autocnet/matcher/subpixel.py: 7 added lines, 2 removed lines.
Original line number Diff line number Diff line
import numpy as np

from autocnet.matcher import naive_template
from autocnet.matcher import ciratefi


# TODO: look into KeyPoint.size and perhaps use to determine an appropriately-sized search/template.

@@ -49,7 +51,7 @@ def clip_roi(img, center, img_size):
    return clipped_img


def subpixel_offset(template, search, **kwargs):
def subpixel_offset(template, search, method='naive', **kwargs):
    """
    Uses a pattern-matcher on subsets of two images determined from the passed-in keypoints and optional sizes to
    compute an x and y offset from the search keypoint to the template keypoint and an associated strength.
@@ -74,7 +76,10 @@ def subpixel_offset(template, search, **kwargs):
               Strength of the correspondence in the range [-1, 1]
    """

    x_offset, y_offset, strength = naive_template.pattern_match(template, search, **kwargs)
    functions = { 'naive' : naive_template.pattern_match,
                  'ciratefi' : ciratefi.ciratefi}

    x_offset, y_offset, strength = functions[method](template, search, **kwargs)
    return x_offset, y_offset, strength

'''
Loading