Exemple #1
0
    def test_point_mutate(self):
        # Modify coordinates
        p = Point(3.0, 4.0)
        p.coords = (2.0, 1.0)
        self.assertEqual(p.__geo_interface__, {
            'type': 'Point',
            'coordinates': (2.0, 1.0)
        })

        # Alternate method
        p.coords = ((0.0, 0.0), )
        self.assertEqual(p.__geo_interface__, {
            'type': 'Point',
            'coordinates': (0.0, 0.0)
        })
Exemple #2
0
def test_point_immutable():
    p = Point(3.0, 4.0)

    with pytest.raises(AttributeError):
        p.coords = (2.0, 1.0)

    with pytest.raises(TypeError):
        p.coords[0] = (2.0, 1.0)
Exemple #3
0
    def test_point_empty_mutate(self):
        # Check that we can set coordinates of a null geometry
        p_null = Point()
        p_null.coords = (1, 2)
        self.assertEqual(p_null.coords[:], [(1.0, 2.0)])

        # Passing > 3 arguments to Point is erroneous
        with self.assertRaises(TypeError):
            Point(1.0, 2.0, 3.0, 4.0)
Exemple #4
0
    def seed_neurons(self,
                     neurons=None,
                     container=None,
                     on_area=None,
                     xmin=None,
                     xmax=None,
                     ymin=None,
                     ymax=None,
                     soma_radius=0,
                     unit=None,
                     return_quantity=None):
        '''
        Return the positions of the neurons inside the
        :class:`Shape`.

        Parameters
        ----------
        neurons : int, optional (default: None)
            Number of neurons to seed. This argument is considered only if the
            :class:`Shape` has no `parent`, otherwise, a position is generated
            for each neuron in `parent`.
        container : :class:`Shape`, optional (default: None)
            Subshape acting like a mask, in which the neurons must be
            contained. The resulting area where the neurons are generated is
            the :func:`~shapely.Shape.intersection` between of the current
            shape and the `container`.
        on_area : str or list, optional (default: None)
            Area(s) where the seeded neurons should be.
        xmin : double, optional (default: lowest abscissa of the Shape)
            Limit the area where neurons will be seeded to the region on the
            right of `xmin`.
        xmax : double, optional (default: highest abscissa of the Shape)
            Limit the area where neurons will be seeded to the region on the
            left of `xmax`.
        ymin : double, optional (default: lowest ordinate of the Shape)
            Limit the area where neurons will be seeded to the region on the
            upper side of `ymin`.
        ymax : double, optional (default: highest ordinate of the Shape)
            Limit the area where neurons will be seeded to the region on the
            lower side of `ymax`.
        unit : string (default: None)
            Unit in which the positions of the neurons will be returned, among
            'um', 'mm', 'cm', 'dm', 'm'.
        return_quantity : bool, optional (default: False)
            Whether the positions should be returned as ``pint.Quantity``
            objects (requires Pint).

        .. versionchanged:: 0.5
            Accepts `pint` units and `return_quantity` argument.

        Note
        ----
        If both `container` and `on_area` are provided, the intersection of
        the two is used.

        Returns
        -------
        positions : array of double with shape (N, 2) or `pint.Quantity` if
                    `return_quantity` is `True`.
        '''
        return_quantity = (self._return_quantity
                           if return_quantity is None else return_quantity)

        if return_quantity:
            unit = self._unit if unit is None else unit
            if not _unit_support:
                raise RuntimeError("`return_quantity` requested but Pint is "
                                   "not available. Please install it first.")
        if _unit_support:
            from .units import Q_
            if isinstance(xmin, Q_):
                xmin = xmin.m_as(unit)
            if isinstance(xmax, Q_):
                xmax = xmax.m_as(unit)
            if isinstance(ymin, Q_):
                ymin = ymin.m_as(unit)
            if isinstance(ymax, Q_):
                ymax = ymax.m_as(unit)
            if isinstance(soma_radius, Q_):
                soma_radius = soma_radius.m_as(unit)

        positions = None
        if neurons is None and self._parent is not None:
            neurons = self._parent.node_nb()
        if neurons is None:
            raise ValueError("`neurons` cannot be None if `parent` is None.")
        if on_area is not None:
            if not hasattr(on_area, '__iter__'):
                on_area = [on_area]

        min_x, min_y, max_x, max_y = self.bounds

        custom_shape = (container is not None)
        if container is None and on_area is None:
            # set min/max
            if xmin is None:
                xmin = -np.inf
            if ymin is None:
                ymin = -np.inf
            if xmax is None:
                xmax = np.inf
            if ymax is None:
                ymax = np.inf
            min_x = max(xmin, min_x)  # smaller that Shape max x
            assert min_x <= self.bounds[2], "`min_x` must be inside Shape."
            min_y = max(ymin, min_y)  # smaller that Shape max y
            assert min_y <= self.bounds[3], "`min_y` must be inside Shape."
            max_x = min(xmax, max_x)  # larger that Shape min x
            assert max_x >= self.bounds[0], "`max_x` must be inside Shape."
            max_y = min(ymax, max_y)  # larger that Shape min y
            assert max_y >= self.bounds[1], "`max_y` must be inside Shape."
            # remaining tests
            if self._geom_type == "Rectangle":
                xx = uniform(min_x + soma_radius,
                             max_x - soma_radius,
                             size=neurons)
                yy = uniform(min_y + soma_radius,
                             max_y - soma_radius,
                             size=neurons)
                positions = np.vstack((xx, yy)).T
            elif (self._geom_type == "Disk"
                  and (xmin, ymin, xmax, ymax) == self.bounds):
                theta = uniform(0, 2 * np.pi, size=neurons)
                # take some precaution to stay inside the shape
                r = (self.radius - soma_radius) *\
                    np.sqrt(uniform(0, 0.99, size=neurons))
                positions = np.vstack((r * np.cos(theta) + self.centroid[0],
                                       r * np.sin(theta) + self.centroid[1])).T
            else:
                custom_shape = True
                container = Polygon([(min_x, min_y), (min_x, max_y),
                                     (max_x, max_y), (max_x, min_y)])
        elif on_area is not None:
            custom_shape = True
            area_shape = Polygon()
            for area in on_area:
                area_shape = area_shape.union(self._areas[area])
            if container is not None:
                container = container.intersection(area_shape)
            else:
                container = area_shape
            assert container.area > 0, "`container` and `on_area` have " +\
                                       "empty intersection."

        # enter here only if Polygon or `container` is not None
        if custom_shape:
            seed_area = self.intersection(container)
            area_buffer = seed_area.buffer(-soma_radius)
            if not area_buffer.is_empty:
                seed_area = area_buffer
            assert not seed_area.is_empty, "Empty area for seeding, check " +\
                "your `container` and min/max values."

            if not isinstance(seed_area, (Polygon, MultiPolygon)):
                raise ValueError("Invalid boundary value for seed region; "
                                 "check that the min/max values you requested "
                                 "are inside the shape.")

            if _opengl_support:
                triangles = []

                if isinstance(seed_area, MultiPolygon):
                    for g in seed_area.geoms:
                        triangles.extend((Polygon(v) for v in triangulate(g)))
                else:
                    triangles = [Polygon(v) for v in triangulate(seed_area)]

                positions = rnd_pts_in_tr(triangles, neurons)
            else:
                logger.warning("Random point generation can be very slow "
                               "without advanced triangulation methods. "
                               "Please install PyOpenGL for faster seeding "
                               "inside complex shapes.")
                points = []
                p = Point()
                while len(points) < neurons:
                    new_x = uniform(min_x, max_x, neurons - len(points))
                    new_y = uniform(min_y, max_y, neurons - len(points))
                    for x, y in zip(new_x, new_y):
                        p.coords = (x, y)
                        if seed_area.contains(p):
                            points.append((x, y))
                positions = np.array(points)

        if unit is not None and unit != self._unit:
            positions *= conversion_magnitude(unit, self._unit)

        if _unit_support and return_quantity:
            from .units import Q_
            return positions * Q_("um" if unit is None else unit)

        return positions
Exemple #5
0
    def test_point(self):

        # Test 2D points
        p = Point(1.0, 2.0)
        self.assertEqual(p.x, 1.0)
        self.assertEqual(p.y, 2.0)
        self.assertEqual(p.coords[:], [(1.0, 2.0)])
        self.assertEqual(str(p), p.wkt)
        self.assertFalse(p.has_z)
        with self.assertRaises(DimensionError):
            p.z

        # Check 3D
        p = Point(1.0, 2.0, 3.0)
        self.assertEqual(p.coords[:], [(1.0, 2.0, 3.0)])
        self.assertEqual(str(p), p.wkt)
        self.assertTrue(p.has_z)
        self.assertEqual(p.z, 3.0)

        # From coordinate sequence
        p = Point((3.0, 4.0))
        self.assertEqual(p.coords[:], [(3.0, 4.0)])

        # From another point
        q = Point(p)
        self.assertEqual(q.coords[:], [(3.0, 4.0)])

        # Coordinate access
        self.assertEqual(p.x, 3.0)
        self.assertEqual(p.y, 4.0)
        self.assertEqual(tuple(p.coords), ((3.0, 4.0), ))
        self.assertEqual(p.coords[0], (3.0, 4.0))
        with self.assertRaises(IndexError):  # index out of range
            p.coords[1]

        # Bounds
        self.assertEqual(p.bounds, (3.0, 4.0, 3.0, 4.0))

        # Geo interface
        self.assertEqual(p.__geo_interface__, {
            'type': 'Point',
            'coordinates': (3.0, 4.0)
        })

        # Modify coordinates
        p.coords = (2.0, 1.0)
        self.assertEqual(p.__geo_interface__, {
            'type': 'Point',
            'coordinates': (2.0, 1.0)
        })

        # Alternate method
        p.coords = ((0.0, 0.0), )
        self.assertEqual(p.__geo_interface__, {
            'type': 'Point',
            'coordinates': (0.0, 0.0)
        })

        # Adapt a coordinate list to a point
        coords = [3.0, 4.0]
        pa = asPoint(coords)
        self.assertEqual(pa.coords[0], (3.0, 4.0))
        self.assertEqual(pa.distance(p), 5.0)

        # Move the coordinates and watch the distance change
        coords[0] = 1.0
        self.assertEqual(pa.coords[0], (1.0, 4.0))
        self.assertAlmostEqual(pa.distance(p), 4.123105625617661)

        # Test Non-operability of Null geometry
        p_null = Point()
        self.assertEqual(p_null.wkt, 'GEOMETRYCOLLECTION EMPTY')
        self.assertEqual(p_null.coords[:], [])
        self.assertEqual(p_null.area, 0.0)

        # Check that we can set coordinates of a null geometry
        p_null.coords = (1, 2)
        self.assertEqual(p_null.coords[:], [(1.0, 2.0)])

        # Passing > 3 arguments to Point is erroneous
        with self.assertRaises(TypeError):
            Point(1.0, 2.0, 3.0, 4.0)
Exemple #6
0
    def test_point(self):

        # Test 2D points
        p = Point(1.0, 2.0)
        self.assertEqual(p.x, 1.0)
        self.assertEqual(p.y, 2.0)
        self.assertEqual(p.coords[:], [(1.0, 2.0)])
        self.assertEqual(str(p), p.wkt)
        self.assertFalse(p.has_z)
        with self.assertRaises(DimensionError):
            p.z

        # Check 3D
        p = Point(1.0, 2.0, 3.0)
        self.assertEqual(p.coords[:], [(1.0, 2.0, 3.0)])
        self.assertEqual(str(p), p.wkt)
        self.assertTrue(p.has_z)
        self.assertEqual(p.z, 3.0)

        # From coordinate sequence
        p = Point((3.0, 4.0))
        self.assertEqual(p.coords[:], [(3.0, 4.0)])

        # From another point
        q = Point(p)
        self.assertEqual(q.coords[:], [(3.0, 4.0)])

        # Coordinate access
        self.assertEqual(p.x, 3.0)
        self.assertEqual(p.y, 4.0)
        self.assertEqual(tuple(p.coords), ((3.0, 4.0),))
        self.assertEqual(p.coords[0], (3.0, 4.0))
        with self.assertRaises(IndexError):  # index out of range
            p.coords[1]

        # Bounds
        self.assertEqual(p.bounds, (3.0, 4.0, 3.0, 4.0))

        # Geo interface
        self.assertEqual(p.__geo_interface__,
                         {'type': 'Point', 'coordinates': (3.0, 4.0)})

        # Modify coordinates
        p.coords = (2.0, 1.0)
        self.assertEqual(p.__geo_interface__,
                         {'type': 'Point', 'coordinates': (2.0, 1.0)})

        # Alternate method
        p.coords = ((0.0, 0.0),)
        self.assertEqual(p.__geo_interface__,
                         {'type': 'Point', 'coordinates': (0.0, 0.0)})

        # Adapt a coordinate list to a point
        coords = [3.0, 4.0]
        pa = asPoint(coords)
        self.assertEqual(pa.coords[0], (3.0, 4.0))
        self.assertEqual(pa.distance(p), 5.0)

        # Move the coordinates and watch the distance change
        coords[0] = 1.0
        self.assertEqual(pa.coords[0], (1.0, 4.0))
        self.assertAlmostEqual(pa.distance(p), 4.123105625617661)

        # Test Non-operability of Null geometry
        p_null = Point()
        self.assertEqual(p_null.wkt, 'GEOMETRYCOLLECTION EMPTY')
        self.assertEqual(p_null.coords[:], [])
        self.assertEqual(p_null.area, 0.0)

        # Check that we can set coordinates of a null geometry
        p_null.coords = (1, 2)
        self.assertEqual(p_null.coords[:], [(1.0, 2.0)])

        # Passing > 3 arguments to Point is erroneous
        with self.assertRaises(TypeError):
            Point(1.0, 2.0, 3.0, 4.0)
Exemple #7
0
def test_point_mutability_deprecated():
    p = Point(3.0, 4.0)
    with pytest.warns(ShapelyDeprecationWarning, match="Setting"):
        p.coords = (2.0, 1.0)