Exemple #1
0
def upload_annotations(cytomine, img, y, term=None, proba=1.):
    points = np.transpose(y.nonzero())
    points = [Point(x, y) for x, y in points]

    if isinstance(img, Annotation):
        img_inst = cytomine.get_image_instance(img.image)
        crop_location = affine_transform(loads(img.location),
                                         [0, -1, 1, 0, img_inst.height, 0])
        offset, width, height = polygon_box(crop_location)
    else:
        offset = (0, 0)
        img_inst = img

    affine_matrix = [0, 1, -1, 0, offset[1], img_inst.height - offset[0]]
    points = [affine_transform(pt, affine_matrix) for pt in points]

    for point in points:
        annotation = cytomine.add_annotation(point.wkt, img_inst.id)
        if term is not None and annotation is not None:
            cytomine.add_annotation_term(
                annotation.id,
                term,
                term,
                proba,
                annotation_term_model=AlgoAnnotationTerm)
Exemple #2
0
 def test_affine_3d(self):
     g2 = load_wkt('LINESTRING(2.4 4.1, 2.4 3, 3 3)')
     g3 = load_wkt('LINESTRING(2.4 4.1 100.2, 2.4 3 132.8, 3 3 128.6)')
     # custom scale and translate
     matrix2d = (2, 0, 0, 2.5, -5, 4.1)
     matrix3d = (2, 0, 0, 0, 2.5, 0, 0, 0, 0.3048, -5, 4.1, 100)
     # Combinations of 2D and 3D geometries and matrices
     a22 = affinity.affine_transform(g2, matrix2d)
     a23 = affinity.affine_transform(g2, matrix3d)
     a32 = affinity.affine_transform(g3, matrix2d)
     a33 = affinity.affine_transform(g3, matrix3d)
     # Check dimensions
     self.assertFalse(a22.has_z)
     self.assertFalse(a23.has_z)
     self.assertTrue(a32.has_z)
     self.assertTrue(a33.has_z)
     # 2D equality checks
     expected2d = load_wkt('LINESTRING(-0.2 14.35, -0.2 11.6, 1 11.6)')
     expected3d = load_wkt('LINESTRING(-0.2 14.35 130.54096, '
                           '-0.2 11.6 140.47744, 1 11.6 139.19728)')
     expected32 = load_wkt('LINESTRING(-0.2 14.35 100.2, '
                           '-0.2 11.6 132.8, 1 11.6 128.6)')
     self.assertTrue(a22.almost_equals(expected2d))
     self.assertTrue(a23.almost_equals(expected2d))
     # Do explicit 3D check of coordinate values
     for a, e in zip(a32.coords, expected32.coords):
         for ap, ep in zip(a, e):
             self.assertAlmostEqual(ap, ep)
     for a, e in zip(a33.coords, expected3d.coords):
         for ap, ep in zip(a, e):
             self.assertAlmostEqual(ap, ep)
Exemple #3
0
def improved_buffer(input_geometry,
                    buffer_width,
                    separation_width,
                    simplify_length,
                    show_progress=False):
    buffer_width *= GEO.m_to_lat
    separation_width *= GEO.m_to_lat
    simplify_length *= GEO.m_to_lat
    if show_progress: UI.progress_bar(1, 0)
    input_geometry = affinity.affine_transform(input_geometry,
                                               [scalx, 0, 0, 1, 0, 0])
    output_geometry = input_geometry.buffer(buffer_width + separation_width,
                                            join_style=2,
                                            mitre_limit=1.5,
                                            resolution=1)
    if show_progress: UI.progress_bar(1, 40)
    if UI.red_flag: return geometry.Polygon()
    output_geometry = output_geometry.buffer(-1 * separation_width,
                                             join_style=2,
                                             mitre_limit=1.5,
                                             resolution=1)
    if show_progress: UI.progress_bar(1, 80)
    if UI.red_flag: return geometry.Polygon()
    if simplify_length:
        output_geometry = output_geometry.simplify(simplify_length)
    if show_progress: UI.progress_bar(1, 100)
    if UI.red_flag: return geometry.Polygon()
    output_geometry = affinity.affine_transform(output_geometry,
                                                [1 / scalx, 0, 0, 1, 0, 0])
    return output_geometry
Exemple #4
0
 def run(self, ips, imgs, para = None):
     shp = convert.roi2shape(ips.roi)
     m = ips.img.mat
     m = [m[0,1], 0, 0, m[1,2], m[0,0], m[1,0]]
     shp = affine_transform(shp, m)
     shp = affine_transform(shp, [0,1,1,0,0,0])
     gdf = gpd.GeoDataFrame([[shp]], columns=['geometry'], crs=ips.img.crs)
     gdf.to_file(para['path'])        
Exemple #5
0
def get_dataset(cytomine,
                working_path,
                id_project,
                id_term,
                id_roi_term,
                id_user=None,
                reviewed_only=False,
                id_roi_user=None,
                reviewed_only_roi=False,
                force_download=False):

    # Download ROI annotations
    crops_annotations = cytomine.get_annotations(
        id_project=id_project,
        id_term=id_roi_term,
        id_user=id_roi_user,
        reviewed_only=reviewed_only_roi,
        showWKT=True,
        showMeta=True)
    # Download ROI crops
    crops = cytomine.dump_annotations(
        annotations=crops_annotations,
        dest_path=os.path.join(working_path, CROPS_PATH, str(id_project)),
        override=force_download,
        desired_zoom=0,
        get_image_url_func=Annotation.get_annotation_alpha_crop_url).data()

    dataset = list()
    for crop in crops:
        gt_annots = cytomine.get_annotations(id_project=id_project,
                                             id_image=crop.image,
                                             id_bbox=crop.id,
                                             id_term=id_term,
                                             id_user=id_user,
                                             reviewed_only=reviewed_only,
                                             showWKT=True).data()

        img_inst = cytomine.get_image_instance(crop.image)
        crop_location = affine_transform(loads(crop.location),
                                         [0, -1, 1, 0, img_inst.height, 0])
        offset, width, height = polygon_box(crop_location)
        affine_matrix = [0, -1, 1, 0, img_inst.height - offset[0], -offset[1]]
        gt_locations = [
            affine_transform(loads(gt.location), affine_matrix)
            for gt in gt_annots
        ]

        groundtruth = mk_groundtruth_image(gt_locations, width, height)

        image_filename = crop.filename
        groundtruth_filename = save_groundtruth_image(
            groundtruth,
            os.path.join(working_path, GROUNDTRUTHS_PATH, str(crop.project)),
            "{}_{}.png".format(crop.image, crop.id))
        dataset.append((image_filename, groundtruth_filename))

    return zip(*dataset)
Exemple #6
0
def transform(shape, trans):
    if isinstance(shape, Collection):
        return Collection([transform(s, trans) for s in shape.geoms])
    elif isinstance(shape, Polygon):
        # shapely should not be used if the students are implementing this
        return Polygon(affine_transform(shape.poly, trans).exterior.coord)
    else:
        # shapely should not be used if the students are implementing this
        return Point(affine_transform(shape.point, trans).coords[0])
Exemple #7
0
def transform(shape, trans):
    if isinstance(shape, Collection):
        return Collection([transform(s, trans) for s in shape.geoms])
    elif isinstance(shape, Polygon):
        # shapely should not be used if the students are implementing this
        return Polygon(affine_transform(shape.poly, trans).exterior.coord)
    else:
        # shapely should not be used if the students are implementing this
        return Point(affine_transform(shape.point, trans).coords[0])
Exemple #8
0
def connect_IDL(df):
    logger = logging.getLogger('shippingroutes_connect_IDL')
    # do an affinity transform, then get nearest points, then reverse the affine transform, then V_inv to get the distance

    logger.info('intersecting boxes and taking affine transform')
    pos_box = geometry.box(178, -85, 180, 85)
    neg_box = geometry.box(-180, -85, -178, 85)

    df['pos_intersects'] = df['geometry'].apply(
        lambda el: wkt.loads(el).intersects(pos_box))
    df['neg_intersects'] = df['geometry'].apply(
        lambda el: wkt.loads(el).intersects(neg_box))

    df_pos = df[df['pos_intersects']]
    df_neg = df[df['neg_intersects']]

    DT = [1, 0, 0, 1, -360, 0]

    df_pos['geometry'] = df_pos['geometry'].apply(
        lambda el: affinity.affine_transform(wkt.loads(el), DT))
    df_neg['geometry'] = df_neg['geometry'].apply(lambda el: wkt.loads(el))

    DT = [1, 0, 0, 1, 360, 0]

    logger.info('Getting all nearest Points')
    records = []
    for idx_pos, row_pos in tqdm(df_pos.iterrows()):
        for idx_neg, row_neg in df_neg.iterrows():
            pt_pos, pt_neg = ops.nearest_points(row_pos['geometry'],
                                                row_neg['geometry'])
            records.append({
                'pt_pos': affinity.affine_transform(pt_pos, DT),
                'pt_neg': pt_neg,
                'id_pos': row_pos['unique_id'],
                'id_neg': row_neg['unique_id']
            })

    df_intersection = pd.DataFrame.from_records(records)

    logger.info('Getting distance between points')
    df_intersection['DISTANCE'] = df_intersection.progress_apply(
        lambda row: V_inv((row['pt_pos'].y, row['pt_pos'].x),
                          (row['pt_neg'].y, row['pt_neg'].x))[0] * 1000,
        axis=1)  #m
    df_intersection = df_intersection.rename(columns={
        'id_pos': 'START',
        'id_neg': 'END'
    })
    df_intersection = df_intersection[df_intersection['DISTANCE'] < 10000]
    df_intersection['PT_START'] = df_intersection['pt_pos'].apply(
        lambda el: el.wkt)
    df_intersection['PT_END'] = df_intersection['pt_neg'].apply(
        lambda el: el.wkt)

    return df_intersection[['START', 'END', 'PT_START', 'PT_END', 'DISTANCE']]
Exemple #9
0
 def test_geom(g2, g3=None):
     self.assertFalse(g2.has_z)
     a2 = affinity.affine_transform(g2, matrix2d)
     self.assertFalse(a2.has_z)
     self.assertTrue(g2.equals(a2))
     if g3 is not None:
         self.assertTrue(g3.has_z)
         a3 = affinity.affine_transform(g3, matrix3d)
         self.assertTrue(a3.has_z)
         self.assertTrue(g3.equals(a3))
     return
Exemple #10
0
 def test_geom(g2, g3=None):
     self.assertFalse(g2.has_z)
     a2 = affinity.affine_transform(g2, matrix2d)
     self.assertFalse(a2.has_z)
     self.assertTrue(g2.equals(a2))
     if g3 is not None:
         self.assertTrue(g3.has_z)
         a3 = affinity.affine_transform(g3, matrix3d)
         self.assertTrue(a3.has_z)
         self.assertTrue(g3.equals(a3))
     return
Exemple #11
0
def _make_polygon(elt_type,
                  instructions,
                  parent=None,
                  interpolate_curve=50,
                  return_points=False):
    container = None
    shell = []  # outer points defining the polygon's outer shell
    holes = []  # inner points defining holes
    idx_start = 0

    if elt_type == "path":  # build polygons from custom paths
        path_data = parse_path(instructions["path"])
        subpaths = [subpath for subpath in _get_closed_subpaths(path_data)]
        points = [_get_points(subpath) for subpath in subpaths]

        # get the container
        idx_container = _get_outer_shell(points)
        shell = np.array(points[idx_container])

        # get the holes and make the shape
        holes = [pp for i, pp in enumerate(points) if i != idx_container]
        container = Polygon(shell, holes=holes)
    elif elt_type == "ellipse":  # build ellipses
        circle = Point((instructions["cx"], instructions["cy"])).buffer(1)
        rx, ry = instructions["rx"], instructions["ry"]
        container = scale(circle, rx, ry)
    elif elt_type == "circle":  # build circles
        r = instructions["r"]
        container = Point((instructions["cx"], instructions["cy"])).buffer(r)
    elif elt_type == "rect":  # build rectangles
        x, y = instructions["x"], instructions["y"]
        w, h = instructions["width"], instructions["height"]
        shell = np.array([(x, y), (x + w, y), (x + w, y + h), (x, y + h)])
        container = Polygon(shell)
    else:
        raise RuntimeError("Unexpected element type: '{}'.".format(elt_type))

    # transforms
    nn, dd = instructions["transf"][::-1], instructions["transfdata"][::-1]
    for name, data in zip(nn, dd):
        if name == "matrix":
            container = affine_transform(container, data)
        elif name == "translate":
            container = translate(container, *data)

    # y axis is inverted in SVG, so make mirror transform
    container = affine_transform(container, (1, 0, 0, -1, 0, 0))
    shell = np.array(container.exterior.coords)

    if return_points:
        return container, shell

    return container
Exemple #12
0
 def test_affine_2d(self):
     g = load_wkt('LINESTRING(2.4 4.1, 2.4 3, 3 3)')
     # custom scale and translate
     expected2d = load_wkt('LINESTRING(-0.2 14.35, -0.2 11.6, 1 11.6)')
     matrix2d = (2, 0, 0, 2.5, -5, 4.1)
     a2 = affinity.affine_transform(g, matrix2d)
     self.assertTrue(a2.almost_equals(expected2d))
     self.assertFalse(a2.has_z)
     # Make sure a 3D matrix does not make a 3D shape from a 2D input
     matrix3d = (2, 0, 0, 0, 2.5, 0, 0, 0, 10, -5, 4.1, 100)
     a3 = affinity.affine_transform(g, matrix3d)
     self.assertTrue(a3.almost_equals(expected2d))
     self.assertFalse(a3.has_z)
Exemple #13
0
def normalize(line, end_idx):
    traj = LineString(line)
    start = line[0]  #shape [2,]
    #Translation normalization: start with (0.0, 0.0)
    #[a, b, c, d, x, y] is the planner transformation matrix[a, b, x; c, d, y; 0, 0, 1]
    g = [1, 0, 0, 1, -start[0], -start[1]]
    traj_trans = affine_transform(traj, g)

    #Rotation normalization:
    end = traj_trans.coords[end_idx]
    if end[0] == 0 and end[1] == 0:
        angle = 0.0
    elif end[0] == 0:
        angle = 90.0 if end[1] < 0 else -90.0
    elif end[1] == 0:
        angle = 0.0 if end[0] > 0 else 180.0
    else:
        angle = math.degrees(math.atan(end[1] / end[0]))
        if (end[0] > 0 and end[1] > 0) or (end[0] > 0 and end[1] < 0):
            angle = -angle
        else:
            angle = 180.0 - angle
    #Rotate normalization: end with y=0
    traj_rotate = rotate(traj_trans, angle, origin=(0, 0)).coords[:]

    #Transform to numpy
    traj_norm = np.array(traj_rotate)
    return traj_norm
Exemple #14
0
    def denormalize_xy(self, xy_locations, translation=None, rotation=None):
        """Reverse the Translate and rotate operations on the input data
            Args:
                xy_locations (numpy array): XY positions for the trajectory
            Returns:
                xy_locations_normalized (numpy array): denormalized XY positions
        """
        # Apply rotation
        num = xy_locations.shape[0]
        if xy_locations.shape[0] > 1:
            trajectory = LineString(xy_locations)
        else:
            trajectory = LineString(np.concatenate(([[0.0, 0.0]], xy_locations), axis=0))

        if rotation is not None:
            trajectory = rotate(trajectory, rotation, origin=(0, 0))

        if translation is not None:
            mat = [1, 0, 0, 1, translation[0], translation[1]]
            trajectory = affine_transform(trajectory, mat)

        output = np.array(trajectory.coords, dtype=np.float32)
        if num <= 1:
            output = output[1:]

        return output
Exemple #15
0
    def minimum_rotated_rectangle(self):
        """Returns the general minimum bounding rectangle of 
        the geometry. Can possibly be rotated. If the convex hull
        of the object is a degenerate (line or point) this same degenerate 
        is returned.
        """
        # first compute the convex hull
        hull = self.convex_hull
        try:
            coords = hull.exterior.coords
        except AttributeError:  # may be a Point or a LineString
            return hull
        # generate the edge vectors between the convex hull's coords
        edges = ((pt2[0] - pt1[0], pt2[1] - pt1[1])
                 for pt1, pt2 in zip(coords, islice(coords, 1, None)))

        def _transformed_rects():
            for dx, dy in edges:
                # compute the normalized direction vector of the edge vector
                length = math.sqrt(dx**2 + dy**2)
                ux, uy = dx / length, dy / length
                # compute the normalized perpendicular vector
                vx, vy = -uy, ux
                # transform hull from the original coordinate system to the coordinate system
                # defined by the edge and compute the axes-parallel bounding rectangle
                transf_rect = affine_transform(hull,
                                               (ux, uy, vx, vy, 0, 0)).envelope
                # yield the transformed rectangle and a matrix to transform it back
                # to the original coordinate system
                yield (transf_rect, (ux, vx, uy, vy, 0, 0))

        # check for the minimum area rectangle and return it
        transf_rect, inv_matrix = min(_transformed_rects(),
                                      key=lambda r: r[0].area)
        return affine_transform(transf_rect, inv_matrix)
Exemple #16
0
def calc_distance_and_angle(p: LocationLocal, ref_p: LocationLocal, rel_angle=0):
        # if type(p) is LocationGlobal or LocationGlobalRelative:
        #         p = latlon_to_xy()

        p = Point(p.east, p.north) 
        ref_p = Point(ref_p.east, ref_p.north)
        # transform to local coordinates
        p_local = affine_transform(p, [1,0,0,1, -ref_p.x, -ref_p.y])
        # alpha = -90 # plus 90 so north is a heading of 0 degrees.With shapely positive rotations are counter clockwise 
        # p_local = rotate(p_local, alpha, origin=(0,0)) # take into account the relative angle of the plane
        # # convert to polar coordinates
        # distance = math.sqrt(pow(p.x - ref_p.x, 2) + pow(p.y - ref_p.y, 2))
        # angle = math.atan((p.x - ref_p.x) / (p.y - ref_p.y))
        (distance, angle) = cmath.polar(complex(p_local.x, p_local.y)) # angle is in radians
        
        # convert to degrees and change axis
        # +90 to set north to heading 0
        angle = 90 - math.degrees(angle) - rel_angle

        # only positive angles
        if angle < 0:
            angle+=360

        # only angles under 360
        if angle > 360:
            angle-=360

        return (distance, angle)
Exemple #17
0
 def mapSuperPixels(segments=None,
                    GT=None,
                    proj={'init': 'epsg:32618'},
                    verbose=True):
     start = time.time()
     if verbose:
         print('---  Mapping superpixels to lat/lng coordinates  ---')
     seg_properties = regionprops(segments)
     polygons = [
         gpd.GeoSeries(Polygon(sp.coords)).convex_hull
         for sp in seg_properties if (sp.area >= 12)
     ]
     polygons = [
         affine_transform(p[0], GT) for p in polygons
         if p[0].geom_type == 'Polygon'
     ]
     if len(polygons) == 1:
         if verbose:
             print('---   Done - execution time: {} seconds'.format(
                 time.time() - start))
         return gpd.GeoDataFrame({'geometry': polygons},
                                 geometry='geometry',
                                 crs=proj,
                                 index=[0])
     else:
         if verbose:
             print('---   Done - execution time: {} seconds'.format(
                 time.time() - start))
         return gpd.GeoDataFrame({'geometry': polygons},
                                 geometry='geometry',
                                 crs=proj)
Exemple #18
0
    def minimum_rotated_rectangle(self):
        """Returns the general minimum bounding rectangle of 
        the geometry. Can possibly be rotated. If the convex hull
        of the object is a degenerate (line or point) this same degenerate 
        is returned.
        """
        # first compute the convex hull
        hull = self.convex_hull
        try:
            coords = hull.exterior.coords
        except AttributeError: # may be a Point or a LineString
            return hull
        # generate the edge vectors between the convex hull's coords
        edges = ((pt2[0]-pt1[0], pt2[1]-pt1[1]) for pt1, pt2 in zip(coords, islice(coords, 1, None)))

        def _transformed_rects():
            for dx, dy in edges:
                # compute the normalized direction vector of the edge vector
                length = math.sqrt(dx**2 + dy**2)
                ux, uy = dx/length, dy/length
                # compute the normalized perpendicular vector
                vx, vy = -uy, ux
                # transform hull from the original coordinate system to the coordinate system 
                # defined by the edge and compute the axes-parallel bounding rectangle
                transf_rect = affine_transform(hull, (ux,uy,vx,vy,0,0)).envelope
                # yield the transformed rectangle and a matrix to transform it back
                # to the original coordinate system
                yield (transf_rect, (ux,vx,uy,vy,0,0))

        # check for the minimum area rectangle and return it
        transf_rect, inv_matrix = min(_transformed_rects(), key=lambda r : r[0].area)
        return affine_transform(transf_rect, inv_matrix)
Exemple #19
0
 def run(self, ips, imgs, para = None):
     gdf = gpd.read_file(para['path']).to_crs(ips.img.crs)
     m = ips.img.mat
     m = [1/m[0,1], 0, 0, 1/m[1,2], -m[0,0]/m[0,1], -m[1,0]/m[1,2]]
     shp = affine_transform(gdf['geometry'][0], m)
     ips.roi = convert.shape2roi(shp)
     if 'back' in ips.data:ips.roi.fill(ips.data['back'], (0,0,80))
Exemple #20
0
def shp2raster(shape, scale, margin=0.05, style='lab', bounds=None):
    shapes = shape['shape'].values
    kmargin = margin/(1-2*margin)
    geoms = list(shape['shape'].values)
    bounds = bounds or GeometryCollection(geoms).bounds
    l,t,r,b = bounds
    w,h = r-l, b-t
    if isinstance(scale, tuple):
        W, H = np.array(scale) * (1-margin*2)
        scale = max(w/W, h/H)
    offsetx, offsety = l-w*kmargin, b+h*kmargin
    shp = np.array((h,w))*(1+(kmargin*2))/scale
    rst = np.zeros(shp.astype(np.int), dtype=np.int16)
    m = [1/scale, 0, 0, -1/scale, -offsetx/scale, offsety/scale]
    img = Image.fromarray(rst)
    draw = ImageDraw.Draw(img)
    for i in range(len(shapes)):
        gs = affine_transform(shapes[i], m)
        for g in gs:
            pts = np.array(g.exterior.xy).T.astype(np.int).ravel()
            if style=='lab': draw.polygon(list(pts), i+1)
            else: draw.line(list(pts), 255, style)
        
        #pgs = [np.array(g.exterior.xy).T.astype(np.int) for g in gs]
        #if style=='lab':cv2.fillPoly(rst, pgs, i+1)
        #else: cv2.drawContours(rst, pgs, -1, 255, style)
    rst = np.array(img)
    m = np.array([offsetx, scale, 0, offsety, 0, -scale]).reshape((2,3))
    return Raster([rst], shape.prj, m)
Exemple #21
0
 def _recalc(self):
     cache = _EdgeCorrect._recalc(self)
     if cache is not None:
         halfS = cache[2]
         m = list(halfS.flatten()) + [0, 0]
         geo = _saffinity.affine_transform(self._geo, m)
         self._cache = cache + (geo, )
def transform_csg(layerdef_from, layerdef_to, inshift, outshift, step,
                  geom_from, geoms_to, csg_laminate, scale_x, scale_y):
    from popupcad.filetypes.laminate import Laminate
    import shapely.affinity as aff
    from popupcad.algorithms.points import calctransformfrom2lines

    lsout = Laminate(layerdef_to)

    for layer_from, layer_to in zip(layerdef_from.layers[::step][inshift:],
                                    layerdef_to.layers[outshift:]):
        newgeoms = []
        for geom in geoms_to:
            for designgeom in csg_laminate.layer_sequence[layer_from].geoms:
                try:
                    from_line = geom_from.exteriorpoints(
                        scaling=popupcad.csg_processing_scaling)
                    to_line = geom.exteriorpoints(
                        scaling=popupcad.csg_processing_scaling)
                    transform = calctransformfrom2lines(from_line,
                                                        to_line,
                                                        scale_x=scale_x,
                                                        scale_y=scale_y)
                    transformed_geom = aff.affine_transform(
                        designgeom, transform)
                    newgeoms.append(transformed_geom)
                except IndexError:
                    pass
        result1 = popupcad.algorithms.csg_shapely.unary_union_safe(newgeoms)
        results2 = popupcad.algorithms.csg_shapely.condition_shapely_entities(
            result1)
        lsout.replacelayergeoms(layer_to, results2)

    return lsout
Exemple #23
0
def draw_pred_on_slide(slide_path,
                       preds,
                       value_fn,
                       color_fn,
                       opacity=127,
                       size=2048,
                       base_zl=2):
    level = determine_tissue_extract_level(slide_path,
                                           desired_processing_size=size)
    slide = pyvips.Image.new_from_file(slide_path, page=level)

    black = (0, 0, 0, 0)
    mask = Image.new('RGBA', (slide.width, slide.height), black)
    draw = ImageDraw.Draw(mask)
    zoom_ratio = 2**(base_zl - level)
    t_matrix = [zoom_ratio, 0, 0, zoom_ratio, 0, 0]

    for rect, probas in preds:
        color = color_fn(value_fn(probas))
        with_opacity = color + (opacity, )
        draw.rectangle(affine_transform(rect, t_matrix).bounds,
                       fill=with_opacity,
                       outline=black)

    np_image = np.ndarray(buffer=slide.write_to_memory(),
                          dtype=np.uint8,
                          shape=[slide.height, slide.width, slide.bands])
    pil_slide = Image.fromarray(np_image).convert("RGBA")
    img = Image.alpha_composite(pil_slide, mask)
    return pil_slide, img.convert("RGB")
Exemple #24
0
def normalized_to_map_coordinates(coords: np.ndarray,
                                  translation: List[List[float]],
                                  rotation: List[float]) -> np.ndarray:
    """Denormalize trajectory to bring it back to map frame.

    Args:
        coords (numpy array): Array of shape (num_tracks x seq_len x 2) containing normalized coordinates
        translation (list): Translation matrix used in normalizing trajectories
        rotation (list): Rotation angle used in normalizing trajectories 
    Returns:
        _ (numpy array: Array of shape (num_tracks x seq_len x 2) containing coordinates in map frame

    """
    abs_coords = []
    for i in range(coords.shape[0]):
        ls = LineString(coords[i])

        # Rotate
        ls_rotate = rotate(ls, -rotation[i], origin=(0, 0))

        # Translate
        M_inv = [1, 0, 0, 1, -translation[i][4], -translation[i][5]]

        ls_offset = affine_transform(ls_rotate, M_inv).coords[:]
        abs_coords.append(ls_offset)

    return np.array(abs_coords)
Exemple #25
0
def random_point_in_polygon(transforms, areas):
    transform = random.choices(transforms, weights=areas)
    x, y = [random.random() for _ in range(2)]
    if x + y > 1:
        p = Point(1 - x, 1 - y)
    else:
        p = Point(x, y)
    return affine_transform(p, transform[0])
Exemple #26
0
 def _to_shape(annot: ParsedAnnotation,
               is_grayscale: bool = True) -> Tuple[BaseGeometry, int]:
     geometry = affine_transform(annot.geometry, affine)
     if is_grayscale:
         value = annot.fill_color.as_rgb_tuple()[0]
     else:
         value = annot.fill_color.as_int()
     return geometry, value
def rotate_route(ls, running_right):
    #I wanted all routes to be seen as if they were running up from the left side of the ball
    #need to find where they were orignially run from and transform accordingly
    coords = list(ls.coords)
    centroidx, _ = ls.centroid.xy
    starting_point = coords[0]
    running_right = bool(running_right)
    high_field = starting_point[1] > 53.3 / 2

    #translate the points so the starting point is at 0, 0
    moved_coords = LineString([
        (c[0] - starting_point[0], c[1] - starting_point[1]) for c in coords
    ])

    #error checking
    #draw_routes(ls.coords)

    #routes are designed to be from 'left' side of the ball
    if high_field:
        if running_right:
            #do a 90 degree turn
            transformed_coords = affinity.rotate(moved_coords,
                                                 angle=90,
                                                 origin=(0, 0))
        else:
            #do a 270 degree turn and mirror
            transformed_coords = affinity.affine_transform(
                affinity.rotate(moved_coords, angle=270, origin=(0, 0)),
                (-1, 0, 0, 1, 0, 0))
    else:
        if running_right:
            #do a 90 degree turn and mirror
            transformed_coords = affinity.affine_transform(
                affinity.rotate(moved_coords, angle=90, origin=(0, 0)),
                (-1, 0, 0, 1, 0, 0))
            pass
        else:
            #do a 270 degree turn
            transformed_coords = affinity.rotate(moved_coords,
                                                 angle=270,
                                                 origin=(0, 0))

    #error checkign
    #draw_routes(transformed_coords)

    return transformed_coords
Exemple #28
0
 def add_line(poly_xy, idx, patch, patch_angle, patch_x, patch_y, line_list):
     points = [(p0, p1) for p0, p1 in zip(poly_xy[0, idx:idx + 2], poly_xy[1, idx:idx + 2])]
     line = LineString(points)
     line.intersection(patch)
     if not line.is_empty:
         line = affinity.rotate(line, -patch_angle, origin=(patch_x, patch_y), use_radians=False)
         line = affinity.affine_transform(line, [1.0, 0.0, 0.0, 1.0, -patch_x, -patch_y])
         line_list.append(line)
 def _transformed_rects():
     for dx, dy in edges:
         length = math.sqrt(dx**2 + dy**2)
         ux, uy = dx / length, dy / length
         vx, vy = -uy, ux
         transf_rect = affine_transform(poly,
                                        (ux, uy, vx, vy, 0, 0)).envelope
         yield (transf_rect, (ux, vx, uy, vy, 0, 0))
Exemple #30
0
def draw_lab(raster, shp, name, color, font, anc):
    gs = shp['geometry'].centroid
    m = raster.mat
    m = [
        1 / m[0, 1], 0, 0, -1 / m[0, 1], -m[0, 0] / m[0, 1], m[1, 0] / m[0, 1]
    ]
    pos = [(int(p.x), int(p.y)) for p in [affine_transform(i, m) for i in gs]]
    return draw_text(raster, shp[name], *list(zip(*pos)), color, font, anc)
Exemple #31
0
    def add_noise(self, x, rotation, translation):
        trajectory = LineString(x)
        mat = [1, 0, 0, 1, translation[0], translation[1]]
        trajectory_translated = affine_transform(trajectory, mat)

        # Apply rotation
        trajectory_rotated = np.array(rotate(trajectory_translated, rotation, origin=(0, 0)).coords, dtype=np.float32)
        return trajectory_rotated
Exemple #32
0
def reproject_geometry(input_geom, input_crs=None, target_crs=None,
                       affine_obj=None):
    """Reproject a geometry or coordinate into a new CRS.

    Arguments
    ---------
    input_geom : `str`, `list`, or `Shapely <https://shapely.readthedocs.io>`_ geometry
        A geometry object to re-project. This can be a 2-member ``list``, in
        which case `input_geom` is assumed to coorespond to ``[x, y]``
        coordinates in `input_crs`. It can also be a Shapely geometry object or
        a wkt string.
    input_crs : int, optional
        The coordinate reference system for `input_geom`'s coordinates, as an
        EPSG :class:`int`. Required unless `affine_transform` is provided.
    target_crs : int, optional
        The target coordinate reference system to re-project the geometry into.
        If not provided, the appropriate UTM zone will be selected by default,
        unless `affine_transform` is provided (and therefore CRSs are ignored.)
    affine_transform : :class:`affine.Affine`, optional
        An :class:`affine.Affine` object (or a ``[a, b, c, d, e, f]`` list to
        convert to that format) to use for transformation. Has no effect unless
        `input_crs` **and** `target_crs` are not provided.

    Returns
    -------
    output_geom : Shapely geometry
        A shapely geometry object:
        - in `target_crs`, if one was provided;
        - in the appropriate UTM zone, if `input_crs` was provided and
          `target_crs` was not;
        - with `affine_transform` applied to it if neither `input_crs` nor
          `target_crs` were provided.
    """
    input_geom = _check_geom(input_geom)

    if input_crs is not None:
        input_crs = _check_crs(input_crs)
        if target_crs is None:
            geom = reproject_geometry(input_geom, input_crs,
                                      target_crs=_check_crs(4326))
            target_crs = latlon_to_utm_epsg(geom.centroid.y, geom.centroid.x)
        target_crs = _check_crs(target_crs)
        gdf = gpd.GeoDataFrame(geometry=[input_geom], crs=input_crs.to_wkt())
        # create a new instance of the same geometry class as above with the
        # new coordinates
        output_geom = gdf.to_crs(target_crs.to_wkt()).iloc[0]['geometry']

    else:
        if affine_obj is None:
            raise ValueError('If an input CRS is not provided, '
                             'affine_transform is required to complete the '
                             'transformation.')
        elif isinstance(affine_obj, Affine):
            affine_obj = affine_to_list(affine_obj)

        output_geom = affine_transform(input_geom, affine_obj)

    return output_geom
Exemple #33
0
 def _to_shape(annot: ParsedAnnotation,
               is_grayscale: bool = True) -> Tuple[BaseGeometry, int]:
     width = _contour_width(annot.stroke_width)
     geometry = stretch_contour(affine_transform(
         contour(annot.geometry, point_style=point_style), affine),
                                width=width)
     value = annot.stroke_color.as_rgb_tuple(
     )[0] if is_grayscale else annot.stroke_color.as_int()
     return geometry, value
Exemple #34
0
 def test_affine_2d(self):
     g = load_wkt('LINESTRING(2.4 4.1, 2.4 3, 3 3)')
     # custom scale and translate
     expected2d = load_wkt('LINESTRING(-0.2 14.35, -0.2 11.6, 1 11.6)')
     matrix2d = (2, 0,
                 0, 2.5,
                 -5, 4.1)
     a2 = affinity.affine_transform(g, matrix2d)
     self.assertTrue(a2.almost_equals(expected2d))
     self.assertFalse(a2.has_z)
     # Make sure a 3D matrix does not make a 3D shape from a 2D input
     matrix3d = (2, 0, 0,
                 0, 2.5, 0,
                 0, 0, 10,
                 -5, 4.1, 100)
     a3 = affinity.affine_transform(g, matrix3d)
     self.assertTrue(a3.almost_equals(expected2d))
     self.assertFalse(a3.has_z)
def _upload_annotation(cytomine, img_inst, polygon, label=None, proba=1.0):
    """Upload an annotation and its term (if provided)"""
    image_id = img_inst.id

    # Transform polygon to match cytomine (bottom-left) origin point
    polygon = affine_transform(polygon, [1, 0, 0, -1, 0, img_inst.height])

    annotation = cytomine.add_annotation(polygon.wkt, image_id)
    if label is not None and annotation is not None:
        cytomine.add_annotation_term(annotation.id, label, label, proba, annotation_term_model=AlgoAnnotationTerm)
Exemple #36
0
    def operate(self,design):
        import shapely.affinity as aff
        subdesign = design.subdesigns[self.subdesignid]

        locateline = subdesign.findlocateline()

        try:
            designgeometry = subdesign.operations[subdesign.operation_index(self.subopid)].output[self.getoutputref()].csg
        except AttributeError:
            subdesign.reprocessoperations()
            designgeometry = subdesign.operations[subdesign.operation_index(self.subopid)].output[self.getoutputref()].csg
            
        sketch = design.sketches[self.sketchid]

        if self.transformtype==self.transformtypes.place:
            scale_x = 1.
            scale_y = 1.
        elif self.transformtype==self.transformtypes.stretch:
            scale_x = None
            scale_y = 1.
        if self.transformtype==self.transformtypes.scale:
            scale_x = None
            scale_y = None
        if self.transformtype==self.transformtypes.custom:
            scale_x = self.scalex
            scale_y = self.scaley

        lsout = Laminate(design.return_layer_definition())
        step = 1
        if self.flip:
            step = -1
        if self.shift > 0:
            outshift = self.shift
            inshift = 0
        elif self.shift <0:
            outshift = 0
            inshift = -self.shift
        else:
            outshift = 0
            inshift = 0
            
        for layerout,layerin in zip(design.return_layer_definition().layers[outshift:],subdesign.return_layer_definition().layers[::step][inshift:]):
            newgeoms = []
            for geom in sketch.operationgeometry:
                for designgeom in designgeometry.layer_sequence[layerin].geoms:
                    try:
                        newgeoms.append(aff.affine_transform(designgeom,calctransformfrom2lines(locateline.exteriorpoints(),geom.exteriorpoints(),scale_x = scale_x,scale_y = scale_y)))
                    except IndexError:
                        pass
            newgeoms = customshapely.unary_union_safe(newgeoms)
            newgeoms = popupcad.geometry.customshapely.multiinit(newgeoms)
            lsout.replacelayergeoms(layerout,newgeoms)
            
        return lsout
Exemple #37
0
    def test_affine_geom_types(self):

        # identity matrices, which should result with no transformation
        matrix2d = (1, 0,
                    0, 1,
                    0, 0)
        matrix3d = (1, 0, 0,
                    0, 1, 0,
                    0, 0, 1,
                    0, 0, 0)

        # empty in, empty out
        empty2d = load_wkt('MULTIPOLYGON EMPTY')
        self.assertTrue(affinity.affine_transform(empty2d, matrix2d).is_empty)

        def test_geom(g2, g3=None):
            self.assertFalse(g2.has_z)
            a2 = affinity.affine_transform(g2, matrix2d)
            self.assertFalse(a2.has_z)
            self.assertTrue(g2.equals(a2))
            if g3 is not None:
                self.assertTrue(g3.has_z)
                a3 = affinity.affine_transform(g3, matrix3d)
                self.assertTrue(a3.has_z)
                self.assertTrue(g3.equals(a3))
            return

        pt2d = load_wkt('POINT(12.3 45.6)')
        pt3d = load_wkt('POINT(12.3 45.6 7.89)')
        test_geom(pt2d, pt3d)
        ls2d = load_wkt('LINESTRING(0.9 3.4, 0.7 2, 2.5 2.7)')
        ls3d = load_wkt('LINESTRING(0.9 3.4 3.3, 0.7 2 2.3, 2.5 2.7 5.5)')
        test_geom(ls2d, ls3d)
        lr2d = load_wkt('LINEARRING(0.9 3.4, 0.7 2, 2.5 2.7, 0.9 3.4)')
        lr3d = load_wkt(
            'LINEARRING(0.9 3.4 3.3, 0.7 2 2.3, 2.5 2.7 5.5, 0.9 3.4 3.3)')
        test_geom(lr2d, lr3d)
        test_geom(load_wkt('POLYGON((0.9 2.3, 0.5 1.1, 2.4 0.8, 0.9 2.3), '
                           '(1.1 1.7, 0.9 1.3, 1.4 1.2, 1.1 1.7), '
                           '(1.6 1.3, 1.7 1, 1.9 1.1, 1.6 1.3))'))
        test_geom(load_wkt(
            'MULTIPOINT ((-300 300), (700 300), (-800 -1100), (200 -300))'))
        test_geom(load_wkt(
            'MULTILINESTRING((0 0, -0.7 -0.7, 0.6 -1), '
            '(-0.5 0.5, 0.7 0.6, 0 -0.6))'))
        test_geom(load_wkt(
            'MULTIPOLYGON(((900 4300, -1100 -400, 900 -800, 900 4300)), '
            '((1200 4300, 2300 4400, 1900 1000, 1200 4300)))'))
        # GeometryCollection fails, since it does not have a good constructor
        gc = load_wkt('GEOMETRYCOLLECTION(POINT(20 70),'
                      ' POLYGON((60 70, 13 35, 60 -30, 60 70)),'
                      ' LINESTRING(60 70, 50 100, 80 100))')
        self.assertRaises(TypeError, test_geom, gc)  # TODO: fix this
Exemple #38
0
 def _transformed_rects():
     for dx, dy in edges:
         # compute the normalized direction vector of the edge vector
         length = math.sqrt(dx**2 + dy**2)
         ux, uy = dx/length, dy/length
         # compute the normalized perpendicular vector
         vx, vy = -uy, ux
         # transform hull from the original coordinate system to the coordinate system 
         # defined by the edge and compute the axes-parallel bounding rectangle
         transf_rect = affine_transform(hull, (ux,uy,vx,vy,0,0)).envelope
         # yield the transformed rectangle and a matrix to transform it back
         # to the original coordinate system
         yield (transf_rect, (ux,vx,uy,vy,0,0))
Exemple #39
0
 def test_affine_3d(self):
     g2 = load_wkt('LINESTRING(2.4 4.1, 2.4 3, 3 3)')
     g3 = load_wkt('LINESTRING(2.4 4.1 100.2, 2.4 3 132.8, 3 3 128.6)')
     # custom scale and translate
     matrix2d = (2, 0,
                 0, 2.5,
                 -5, 4.1)
     matrix3d = (2, 0, 0,
                 0, 2.5, 0,
                 0, 0, 0.3048,
                 -5, 4.1, 100)
     # Combinations of 2D and 3D geometries and matrices
     a22 = affinity.affine_transform(g2, matrix2d)
     a23 = affinity.affine_transform(g2, matrix3d)
     a32 = affinity.affine_transform(g3, matrix2d)
     a33 = affinity.affine_transform(g3, matrix3d)
     # Check dimensions
     self.assertFalse(a22.has_z)
     self.assertFalse(a23.has_z)
     self.assertTrue(a32.has_z)
     self.assertTrue(a33.has_z)
     # 2D equality checks
     expected2d = load_wkt('LINESTRING(-0.2 14.35, -0.2 11.6, 1 11.6)')
     expected3d = load_wkt('LINESTRING(-0.2 14.35 130.54096, '
                           '-0.2 11.6 140.47744, 1 11.6 139.19728)')
     expected32 = load_wkt('LINESTRING(-0.2 14.35 100.2, '
                           '-0.2 11.6 132.8, 1 11.6 128.6)')
     self.assertTrue(a22.almost_equals(expected2d))
     self.assertTrue(a23.almost_equals(expected2d))
     # Do explicit 3D check of coordinate values
     for a, e in zip(a32.coords, expected32.coords):
         for ap, ep in zip(a, e):
             self.assertAlmostEqual(ap, ep)
     for a, e in zip(a33.coords, expected3d.coords):
         for ap, ep in zip(a, e):
             self.assertAlmostEqual(ap, ep)
Exemple #40
0
    def operate(self,design):
        from popupcad.filetypes.genericshapes import GenericLine
        import shapely.affinity as aff
        import popupcad.algorithms.points as points
        import popupcad
        import shapely.geometry as sg
        import numpy
        
        parent_ref,parent_index  = self.operation_links['source'][0]
        parent = design.op_from_ref(parent_ref).output[parent_index].csg
        
        sketch = design.sketches[self.sketch_links['cross_section'][0]]
        
        layerdef = design.return_layer_definition()
        laminate = Laminate(layerdef)
        for item in sketch.operationgeometry:
            if isinstance(item,GenericLine):
                line = item
                b = line.exteriorpoints()[0]
                c = numpy.array(b)+numpy.array([1,0])
                a = points.calctransformfrom2lines(line.exteriorpoints(),[b,c.tolist()],scale_x=1,scale_y=1)            
                sketch_csg = sketch.output_csg()
                
                for layer in layerdef.layers:
                    laminate.replacelayergeoms(layer,sketch_csg)
                result = parent.intersection(laminate)
                laminate2 = Laminate(layerdef)
                for ii,layerid in enumerate(layerdef.layers):
#                for ii,layer in enumerate(result):
                    yshift = layerdef.zvalue[layerid] * self.scale_value
                    layer = result.layer_sequence[layerid]
                    thickness = layerid.thickness*popupcad.internal_argument_scaling*self.scale_value
                    newgeoms = [item for item in layer.geoms]
                    newgeoms = [aff.affine_transform(item,a) for item in newgeoms]
#                    newgeoms = [item.buffer(bufferval) for item in newgeoms]
                    newgeoms2 = []
                    for geom in newgeoms:
                        newgeom = sg.box(geom.coords[0][0],geom.coords[0][1],geom.coords[-1][0],geom.coords[-1][1]+thickness)
                        newgeoms2.append(newgeom)
                    newgeoms = newgeoms2
                    newgeoms = [aff.translate(item,yoff = yshift) for item in newgeoms]
                    newgeoms = popupcad.geometry.customshapely.multiinit(*newgeoms)
                    laminate2[ii] = newgeoms
                return laminate2

        return laminate
def cross_section(layerdef, sketch, parent, scale_value):
    from popupcad.filetypes.laminate import Laminate
    from popupcad.filetypes.genericshapes import GenericLine
    import shapely.affinity as aff
    import popupcad.algorithms.points as points
    import shapely.geometry as sg
    import numpy

    laminate = Laminate(layerdef)
    for item in sketch.operationgeometry:
        if isinstance(item, GenericLine):
            line = item
            b = line.exteriorpoints(scaling = popupcad.csg_processing_scaling)[0]
            c = numpy.array(b) + numpy.array([1, 0])
            a = points.calctransformfrom2lines(
                line.exteriorpoints(scaling = popupcad.csg_processing_scaling), [
                    b, c.tolist()], scale_x=1, scale_y=1)
            sketch_csg = sketch.output_csg()

            for layer in layerdef.layers:
                laminate.replacelayergeoms(layer, sketch_csg)
            result = parent.intersection(laminate)
            laminate2 = Laminate(layerdef)
            for ii, layerid in enumerate(layerdef.layers):
                #                for ii,layer in enumerate(result):
                yshift = layerdef.zvalue[layerid] * popupcad.csg_processing_scaling * scale_value
                layer = result.layer_sequence[layerid]
                thickness = layerid.thickness * popupcad.csg_processing_scaling * scale_value
                newgeoms = [item for item in layer.geoms]
                newgeoms = [aff.affine_transform(item, a) for item in newgeoms]
#                    newgeoms = [item.buffer(bufferval) for item in newgeoms]
                newgeoms2 = []
                for geom in newgeoms:
                    newgeom = sg.box(geom.coords[0][0],
                                     geom.coords[0][1],
                                     geom.coords[-1][0],
                                     geom.coords[-1][1] + thickness)
                    newgeoms2.append(newgeom)
                newgeoms = newgeoms2
                newgeoms = [aff.translate(item,yoff=yshift) for item in newgeoms]
                newgeoms = popupcad.algorithms.csg_shapely.condition_shapely_entities(*newgeoms)
                laminate2[ii] = newgeoms
            return laminate2

    return laminate
def transform(
        layerdef,
        layerdef_subdesign,
        inshift,
        outshift,
        step,
        sketch,
        designgeometry,
        locateline,
        scale_x,
        scale_y):
    from popupcad.filetypes.laminate import Laminate
    import shapely.affinity as aff
    from popupcad.algorithms.points import calctransformfrom2lines

    lsout = Laminate(layerdef)

    for layerout, layerin in zip(
        layerdef.layers[
            outshift:], layerdef_subdesign.layers[
            ::step][
                inshift:]):
        newgeoms = []
        for geom in sketch.operationgeometry:
            if not geom.is_construction():
                for designgeom in designgeometry.layer_sequence[layerin].geoms:
                    try:
                        newgeoms.append(
                            aff.affine_transform(
                                designgeom,
                                calctransformfrom2lines(
                                    locateline.exteriorpoints(scaling = popupcad.csg_processing_scaling),
                                    geom.exteriorpoints(scaling = popupcad.csg_processing_scaling),
                                    scale_x=scale_x,
                                    scale_y=scale_y)))
                    except IndexError:
                        pass
        result1 = popupcad.algorithms.csg_shapely.unary_union_safe(newgeoms)
        results2 = popupcad.algorithms.csg_shapely.condition_shapely_entities(result1)
        lsout.replacelayergeoms(layerout, results2)

    return lsout
Exemple #43
0
def _locate(segmented, offset=None):
    """Inspired from: https://goo.gl/HYPrR1"""
    # CV_RETR_EXTERNAL to only get external contours.
    _, contours, hierarchy = cv2.findContours(segmented.copy(),
                                              cv2.RETR_CCOMP,
                                              cv2.CHAIN_APPROX_SIMPLE)

    # Note: points are represented as (col, row)-tuples apparently
    transform = identity
    if offset is not None:
        col_off, row_off = offset
        transform = lambda p: affine_transform(p, [1, 0, 0, 1, col_off, row_off])
    components = []
    if len(contours) > 0:
        top_index = 0
        tops_remaining = True
        while tops_remaining:
            exterior = contours[top_index][:, 0, :].tolist()

            interiors = []
            # check if there are childs and process if necessary
            if hierarchy[0][top_index][2] != -1:
                sub_index = hierarchy[0][top_index][2]
                subs_remaining = True
                while subs_remaining:
                    interiors.append(contours[sub_index][:, 0, :].tolist())

                    # check if there is another sub contour
                    if hierarchy[0][sub_index][0] != -1:
                        sub_index = hierarchy[0][sub_index][0]
                    else:
                        subs_remaining = False

            # add component tuple to components only if exterior is a polygon
            if len(exterior) == 1:
                components.append(Point(exterior[0]))
            elif len(exterior) == 2:
                components.append(LineString(exterior))
            elif len(exterior) > 2:
                polygon = Polygon(exterior, interiors)
                polygon = transform(polygon)
                if polygon.is_valid:  # some polygons might be invalid
                    components.append(polygon)
                else:
                    fixed = fix_geometry(polygon)
                    if fixed.is_valid and not fixed.is_empty:
                        components.append(fixed)
                    else:
                        warn("Attempted to fix invalidity '{}' in polygon but failed... "
                             "Output polygon still invalid '{}'".format(explain_validity(polygon),
                                                                        explain_validity(fixed)))

            # check if there is another top contour
            if hierarchy[0][top_index][0] != -1:
                top_index = hierarchy[0][top_index][0]
            else:
                tops_remaining = False

    del contours
    del hierarchy
    return components
Exemple #44
0
def getsvggeo(node):
    """
    Extracts and flattens all geometry from an SVG node
    into a list of Shapely geometry.

    :param node: xml.etree.ElementTree.Element
    :return: List of Shapely geometry
    :rtype: list
    """
    kind = re.search('(?:\{.*\})?(.*)$', node.tag).group(1)
    geo = []

    # Recurse
    if len(node) > 0:
        for child in node:
            subgeo = getsvggeo(child)
            if subgeo is not None:
                geo += subgeo

    # Parse
    elif kind == 'path':
        log.debug("***PATH***")
        P = parse_path(node.get('d'))
        P = path2shapely(P)
        geo = [P]

    elif kind == 'rect':
        log.debug("***RECT***")
        R = svgrect2shapely(node)
        geo = [R]

    elif kind == 'circle':
        log.debug("***CIRCLE***")
        C = svgcircle2shapely(node)
        geo = [C]

    elif kind == 'ellipse':
        log.debug("***ELLIPSE***")
        E = svgellipse2shapely(node)
        geo = [E]

    elif kind == 'polygon':
        log.debug("***POLYGON***")
        poly = svgpolygon2shapely(node)
        geo = [poly]

    elif kind == 'line':
        log.debug("***LINE***")
        line = svgline2shapely(node)
        geo = [line]

    elif kind == 'polyline':
        log.debug("***POLYLINE***")
        pline = svgpolyline2shapely(node)
        geo = [pline]

    else:
        log.warning("Unknown kind: " + kind)
        geo = None

    # Transformations
    if 'transform' in node.attrib:
        trstr = node.get('transform')
        trlist = parse_svg_transform(trstr)
        #log.debug(trlist)

        # Transformations are applied in reverse order
        for tr in trlist[::-1]:
            if tr[0] == 'translate':
                geo = [translate(geoi, tr[1], tr[2]) for geoi in geo]
            elif tr[0] == 'scale':
                geo = [scale(geoi, tr[0], tr[1], origin=(0, 0))
                       for geoi in geo]
            elif tr[0] == 'rotate':
                geo = [rotate(geoi, tr[1], origin=(tr[2], tr[3]))
                       for geoi in geo]
            elif tr[0] == 'skew':
                geo = [skew(geoi, tr[1], tr[2], origin=(0, 0))
                       for geoi in geo]
            elif tr[0] == 'matrix':
                geo = [affine_transform(geoi, tr[1:]) for geoi in geo]
            else:
                raise Exception('Unknown transformation: %s', tr)

    return geo
def cov_transform(p, obst_cov):
    ''' Returns the convex polygon p transformed by W, where W*cov*W^T = I'''
    W = np.linalg.inv( np.linalg.cholesky(obst_cov) )
    affine_params = np.concatenate((W.flatten(), np.zeros(2)))  
    return affinity.affine_transform(p, affine_params), W