测试gitnore

This commit is contained in:
ladeng07
2022-05-06 15:45:57 +08:00
parent 12f390949b
commit 51552904f9
2347 changed files with 120102 additions and 53549 deletions
@@ -3,10 +3,7 @@ The GeoDjango GEOS module. Please consult the GeoDjango documentation
for more details: https://docs.djangoproject.com/en/dev/ref/contrib/gis/geos/
"""
from .collections import ( # NOQA
GeometryCollection,
MultiLineString,
MultiPoint,
MultiPolygon,
GeometryCollection, MultiLineString, MultiPoint, MultiPolygon,
)
from .error import GEOSException # NOQA
from .factory import fromfile, fromstr # NOQA
@@ -2,6 +2,8 @@
This module houses the Geometry Collection objects:
GeometryCollection, MultiPoint, MultiLineString, and MultiPolygon
"""
from ctypes import byref, c_int, c_uint
from django.contrib.gis.geos import prototypes as capi
from django.contrib.gis.geos.geometry import GEOSGeometry, LinearGeometryMixin
from django.contrib.gis.geos.libgeos import GEOM_PTR
@@ -46,15 +48,12 @@ class GeometryCollection(GEOSGeometry):
# ### Methods for compatibility with ListMixin ###
def _create_collection(self, length, items):
# Creating the geometry pointer array.
geoms = (GEOM_PTR * length)(
*[
# this is a little sloppy, but makes life easier
# allow GEOSGeometry types (python wrappers) or pointer types
capi.geom_clone(getattr(g, "ptr", g))
for g in items
]
)
return capi.create_collection(self._typeid, geoms, length)
geoms = (GEOM_PTR * length)(*[
# this is a little sloppy, but makes life easier
# allow GEOSGeometry types (python wrappers) or pointer types
capi.geom_clone(getattr(g, 'ptr', g)) for g in items
])
return capi.create_collection(c_int(self._typeid), byref(geoms), c_uint(length))
def _get_single_internal(self, index):
return capi.get_geomn(self.ptr, index)
@@ -62,9 +61,7 @@ class GeometryCollection(GEOSGeometry):
def _get_single_external(self, index):
"Return the Geometry from this Collection at the given index (0-based)."
# Checking the index and returning the corresponding GEOS geometry.
return GEOSGeometry(
capi.geom_clone(self._get_single_internal(index)), srid=self.srid
)
return GEOSGeometry(capi.geom_clone(self._get_single_internal(index)), srid=self.srid)
def _set_list(self, length, items):
"Create a new collection, and destroy the contents of the previous pointer."
@@ -81,13 +78,12 @@ class GeometryCollection(GEOSGeometry):
@property
def kml(self):
"Return the KML for this Geometry Collection."
return "<MultiGeometry>%s</MultiGeometry>" % "".join(g.kml for g in self)
return '<MultiGeometry>%s</MultiGeometry>' % ''.join(g.kml for g in self)
@property
def tuple(self):
"Return a tuple of all the coordinates in this Geometry Collection"
return tuple(g.tuple for g in self)
coords = tuple
@@ -109,12 +105,4 @@ class MultiPolygon(GeometryCollection):
# Setting the allowed types here since GeometryCollection is defined before
# its subclasses.
GeometryCollection._allowed = (
Point,
LineString,
LinearRing,
Polygon,
MultiPoint,
MultiLineString,
MultiPolygon,
)
GeometryCollection._allowed = (Point, LineString, LinearRing, Polygon, MultiPoint, MultiLineString, MultiPolygon)
@@ -20,7 +20,7 @@ class GEOSCoordSeq(GEOSBase):
def __init__(self, ptr, z=False):
"Initialize from a GEOS pointer."
if not isinstance(ptr, CS_PTR):
raise TypeError("Coordinate sequence should initialize with a CS_PTR.")
raise TypeError('Coordinate sequence should initialize with a CS_PTR.')
self._ptr = ptr
self._z = z
@@ -50,9 +50,7 @@ class GEOSCoordSeq(GEOSBase):
elif numpy and isinstance(value, numpy.ndarray):
pass
else:
raise TypeError(
"Must set coordinate with a sequence (list, tuple, or numpy array)."
)
raise TypeError('Must set coordinate with a sequence (list, tuple, or numpy array).')
# Checking the dims of the input
if self.dims == 3 and self._z:
n_args = 3
@@ -61,7 +59,7 @@ class GEOSCoordSeq(GEOSBase):
n_args = 2
point_setter = self._set_point_2d
if len(value) != n_args:
raise TypeError("Dimension of value does not match.")
raise TypeError('Dimension of value does not match.')
self._checkindex(index)
point_setter(index, value)
@@ -69,7 +67,7 @@ class GEOSCoordSeq(GEOSBase):
def _checkindex(self, index):
"Check the given index."
if not (0 <= index < self.size):
raise IndexError("invalid GEOS Geometry index: %s" % index)
raise IndexError('invalid GEOS Geometry index: %s' % index)
def _checkdim(self, dim):
"Check the given dimension."
@@ -182,13 +180,11 @@ class GEOSCoordSeq(GEOSBase):
# Getting the substitution string depending on whether the coordinates have
# a Z dimension.
if self.hasz:
substr = "%s,%s,%s "
substr = '%s,%s,%s '
else:
substr = "%s,%s,0 "
return (
"<coordinates>%s</coordinates>"
% "".join(substr % self[i] for i in range(len(self))).strip()
)
substr = '%s,%s,0 '
return '<coordinates>%s</coordinates>' % \
''.join(substr % self[i] for i in range(len(self))).strip()
@property
def tuple(self):
@@ -8,7 +8,7 @@ def fromfile(file_h):
"""
# If given a file name, get a real handle.
if isinstance(file_h, str):
with open(file_h, "rb") as file_h:
with open(file_h, 'rb') as file_h:
buf = file_h.read()
else:
buf = file_h.read()
@@ -14,7 +14,9 @@ from django.contrib.gis.geos.error import GEOSException
from django.contrib.gis.geos.libgeos import GEOM_PTR
from django.contrib.gis.geos.mutable_list import ListMixin
from django.contrib.gis.geos.prepared import PreparedGeometry
from django.contrib.gis.geos.prototypes.io import ewkb_w, wkb_r, wkb_w, wkt_r, wkt_w
from django.contrib.gis.geos.prototypes.io import (
ewkb_w, wkb_r, wkb_w, wkt_r, wkt_w,
)
from django.utils.deconstruct import deconstructible
from django.utils.encoding import force_bytes, force_str
@@ -36,15 +38,12 @@ class GEOSGeometryBase(GEOSBase):
if GEOSGeometryBase._GEOS_CLASSES is None:
# Inner imports avoid import conflicts with GEOSGeometry.
from .collections import (
GeometryCollection,
MultiLineString,
MultiPoint,
GeometryCollection, MultiLineString, MultiPoint,
MultiPolygon,
)
from .linestring import LinearRing, LineString
from .point import Point
from .polygon import Polygon
GEOSGeometryBase._GEOS_CLASSES = {
0: Point,
1: LineString,
@@ -63,9 +62,7 @@ class GEOSGeometryBase(GEOSBase):
"Perform post-initialization setup."
# Setting the coordinate sequence for the geometry (will be None on
# geometries that do not have coordinate sequences)
self._cs = (
GEOSCoordSeq(capi.get_cs(self.ptr), self.hasz) if self.has_cs else None
)
self._cs = GEOSCoordSeq(capi.get_cs(self.ptr), self.hasz) if self.has_cs else None
def __copy__(self):
"""
@@ -88,7 +85,7 @@ class GEOSGeometryBase(GEOSBase):
def __repr__(self):
"Short-hand representation because WKT may be very large."
return "<%s object at %s>" % (self.geom_type, hex(addressof(self.ptr)))
return '<%s object at %s>' % (self.geom_type, hex(addressof(self.ptr)))
# Pickling support
def _to_pickle_wkb(self):
@@ -107,7 +104,7 @@ class GEOSGeometryBase(GEOSBase):
wkb, srid = state
ptr = self._from_pickle_wkb(wkb)
if not ptr:
raise GEOSException("Invalid Geometry loaded from pickled state.")
raise GEOSException('Invalid Geometry loaded from pickled state.')
self.ptr = ptr
self._post_init()
self.srid = srid
@@ -120,17 +117,17 @@ class GEOSGeometryBase(GEOSBase):
def from_ewkt(ewkt):
ewkt = force_bytes(ewkt)
srid = None
parts = ewkt.split(b";", 1)
parts = ewkt.split(b';', 1)
if len(parts) == 2:
srid_part, wkt = parts
match = re.match(rb"SRID=(?P<srid>\-?\d+)", srid_part)
match = re.match(br'SRID=(?P<srid>\-?\d+)', srid_part)
if not match:
raise ValueError("EWKT has invalid SRID part.")
srid = int(match["srid"])
raise ValueError('EWKT has invalid SRID part.')
srid = int(match['srid'])
else:
wkt = ewkt
if not wkt:
raise ValueError("Expected WKT but got an empty string.")
raise ValueError('Expected WKT but got an empty string.')
return GEOSGeometry(GEOSGeometry._from_wkt(wkt), srid=srid)
@staticmethod
@@ -152,11 +149,7 @@ class GEOSGeometryBase(GEOSBase):
other = GEOSGeometry.from_ewkt(other)
except (ValueError, GEOSException):
return False
return (
isinstance(other, GEOSGeometry)
and self.srid == other.srid
and self.equals_exact(other)
)
return isinstance(other, GEOSGeometry) and self.srid == other.srid and self.equals_exact(other)
def __hash__(self):
return hash((self.srid, self.wkt))
@@ -321,7 +314,7 @@ class GEOSGeometryBase(GEOSBase):
two Geometries match the elements in pattern.
"""
if not isinstance(pattern, str) or len(pattern) > 9:
raise GEOSException("invalid intersection matrix pattern")
raise GEOSException('invalid intersection matrix pattern')
return capi.geos_relatepattern(self.ptr, other.ptr, force_bytes(pattern))
def touches(self, other):
@@ -360,7 +353,7 @@ class GEOSGeometryBase(GEOSBase):
Return the EWKT (SRID + WKT) of the Geometry.
"""
srid = self.srid
return "SRID=%s;%s" % (srid, self.wkt) if srid else self.wkt
return 'SRID=%s;%s' % (srid, self.wkt) if srid else self.wkt
@property
def wkt(self):
@@ -393,7 +386,6 @@ class GEOSGeometryBase(GEOSBase):
Return GeoJSON representation of this Geometry.
"""
return self.ogr.json
geojson = json
@property
@@ -418,7 +410,7 @@ class GEOSGeometryBase(GEOSBase):
def kml(self):
"Return the KML representation of this Geometry."
gtype = self.geom_type
return "<%s>%s</%s>" % (gtype, self.coord_seq.kml, gtype)
return '<%s>%s</%s>' % (gtype, self.coord_seq.kml, gtype)
@property
def prepared(self):
@@ -492,7 +484,7 @@ class GEOSGeometryBase(GEOSBase):
self._post_init()
self.srid = g.srid
else:
raise GEOSException("Transformed WKB was invalid.")
raise GEOSException('Transformed WKB was invalid.')
# #### Topology Routines ####
def _topology(self, gptr):
@@ -514,9 +506,7 @@ class GEOSGeometryBase(GEOSBase):
"""
return self._topology(capi.geos_buffer(self.ptr, width, quadsegs))
def buffer_with_style(
self, width, quadsegs=8, end_cap_style=1, join_style=1, mitre_limit=5.0
):
def buffer_with_style(self, width, quadsegs=8, end_cap_style=1, join_style=1, mitre_limit=5.0):
"""
Same as buffer() but allows customizing the style of the buffer.
@@ -525,9 +515,7 @@ class GEOSGeometryBase(GEOSBase):
Mitre ratio limit only affects mitered join style.
"""
return self._topology(
capi.geos_bufferwithstyle(
self.ptr, width, quadsegs, end_cap_style, join_style, mitre_limit
),
capi.geos_bufferwithstyle(self.ptr, width, quadsegs, end_cap_style, join_style, mitre_limit),
)
@property
@@ -618,7 +606,7 @@ class GEOSGeometryBase(GEOSBase):
the Geometry.
"""
if not isinstance(other, GEOSGeometry):
raise TypeError("distance() works only on other GEOS Geometries.")
raise TypeError('distance() works only on other GEOS Geometries.')
return capi.geos_distance(self.ptr, other.ptr, byref(c_double()))
@property
@@ -628,7 +616,6 @@ class GEOSGeometryBase(GEOSBase):
(xmin, ymin, xmax, ymax).
"""
from .point import Point
env = self.envelope
if isinstance(env, Point):
xmin, ymin = env.tuple
@@ -655,7 +642,6 @@ class LinearGeometryMixin:
"""
Used for LineString and MultiLineString.
"""
def interpolate(self, distance):
return self._topology(capi.geos_interpolate(self.ptr, distance))
@@ -664,16 +650,14 @@ class LinearGeometryMixin:
def project(self, point):
from .point import Point
if not isinstance(point, Point):
raise TypeError("locate_point argument must be a Point")
raise TypeError('locate_point argument must be a Point')
return capi.geos_project(self.ptr, point.ptr)
def project_normalized(self, point):
from .point import Point
if not isinstance(point, Point):
raise TypeError("locate_point argument must be a Point")
raise TypeError('locate_point argument must be a Point')
return capi.geos_project_normalized(self.ptr, point.ptr)
@property
@@ -717,9 +701,9 @@ class GEOSGeometry(GEOSGeometryBase, ListMixin):
wkt_m = wkt_regex.match(geo_input)
if wkt_m:
# Handle WKT input.
if wkt_m["srid"]:
input_srid = int(wkt_m["srid"])
g = self._from_wkt(force_bytes(wkt_m["wkt"]))
if wkt_m['srid']:
input_srid = int(wkt_m['srid'])
g = self._from_wkt(force_bytes(wkt_m['wkt']))
elif hex_regex.match(geo_input):
# Handle HEXEWKB input.
g = wkb_r().read(force_bytes(geo_input))
@@ -729,7 +713,7 @@ class GEOSGeometry(GEOSGeometryBase, ListMixin):
g = ogr._geos_ptr()
input_srid = ogr.srid
else:
raise ValueError("String input unrecognized as WKT EWKT, and HEXEWKB.")
raise ValueError('String input unrecognized as WKT EWKT, and HEXEWKB.')
elif isinstance(geo_input, GEOM_PTR):
# When the input is a pointer to a geometry (GEOM_PTR).
g = geo_input
@@ -739,14 +723,14 @@ class GEOSGeometry(GEOSGeometryBase, ListMixin):
elif isinstance(geo_input, GEOSGeometry):
g = capi.geom_clone(geo_input.ptr)
else:
raise TypeError("Improper geometry input type: %s" % type(geo_input))
raise TypeError('Improper geometry input type: %s' % type(geo_input))
if not g:
raise GEOSException("Could not initialize GEOS Geometry with given input.")
raise GEOSException('Could not initialize GEOS Geometry with given input.')
input_srid = input_srid or capi.geos_get_srid(g) or None
if input_srid and srid and input_srid != srid:
raise ValueError("Input geometry already has SRID: %d." % input_srid)
raise ValueError('Input geometry already has SRID: %d.' % input_srid)
super().__init__(g, None)
# Set the SRID, if given.
@@ -5,13 +5,10 @@ reader and writer classes.
"""
from django.contrib.gis.geos.geometry import GEOSGeometry
from django.contrib.gis.geos.prototypes.io import (
WKBWriter,
WKTWriter,
_WKBReader,
_WKTReader,
WKBWriter, WKTWriter, _WKBReader, _WKTReader,
)
__all__ = ["WKBWriter", "WKTWriter", "WKBReader", "WKTReader"]
__all__ = ['WKBWriter', 'WKTWriter', 'WKBReader', 'WKTReader']
# Public classes for (WKB|WKT)Reader, which return GEOSGeometry
@@ -15,14 +15,13 @@ from django.core.exceptions import ImproperlyConfigured
from django.utils.functional import SimpleLazyObject, cached_property
from django.utils.version import get_version_tuple
logger = logging.getLogger("django.contrib.gis")
logger = logging.getLogger('django.contrib.gis')
def load_geos():
# Custom library path set?
try:
from django.conf import settings
lib_path = settings.GEOS_LIBRARY_PATH
except (AttributeError, ImportError, ImproperlyConfigured, OSError):
lib_path = None
@@ -30,12 +29,12 @@ def load_geos():
# Setting the appropriate names for the GEOS-C library.
if lib_path:
lib_names = None
elif os.name == "nt":
elif os.name == 'nt':
# Windows NT libraries
lib_names = ["geos_c", "libgeos_c-1"]
elif os.name == "posix":
lib_names = ['geos_c', 'libgeos_c-1']
elif os.name == 'posix':
# *NIX libraries
lib_names = ["geos_c", "GEOS"]
lib_names = ['geos_c', 'GEOS']
else:
raise ImportError('Unsupported OS "%s"' % os.name)
@@ -52,7 +51,8 @@ def load_geos():
if lib_path is None:
raise ImportError(
'Could not find the GEOS library (tried "%s"). '
"Try setting GEOS_LIBRARY_PATH in your settings." % '", "'.join(lib_names)
'Try setting GEOS_LIBRARY_PATH in your settings.' %
'", "'.join(lib_names)
)
# Getting the GEOS C library. The C interface (CDLL) is used for
# both *NIX and Windows.
@@ -82,7 +82,7 @@ def notice_h(fmt, lst):
warn_msg = fmt % lst
except TypeError:
warn_msg = fmt
logger.warning("GEOS_NOTICE: %s\n", warn_msg)
logger.warning('GEOS_NOTICE: %s\n', warn_msg)
notice_h = NOTICEFUNC(notice_h)
@@ -96,7 +96,7 @@ def error_h(fmt, lst):
err_msg = fmt % lst
except TypeError:
err_msg = fmt
logger.error("GEOS_ERROR: %s\n", err_msg)
logger.error('GEOS_ERROR: %s\n', err_msg)
error_h = ERRORFUNC(error_h)
@@ -135,7 +135,6 @@ class GEOSFuncFactory:
"""
Lazy loading of GEOS functions.
"""
argtypes = None
restype = None
errcheck = None
@@ -155,7 +154,6 @@ class GEOSFuncFactory:
@cached_property
def func(self):
from django.contrib.gis.geos.prototypes.threadsafe import GEOSFunc
func = GEOSFunc(self.func_name)
func.argtypes = self.argtypes or []
func.restype = self.restype
@@ -29,15 +29,11 @@ class LineString(LinearGeometryMixin, GEOSGeometry):
else:
coords = args
if not (
isinstance(coords, (tuple, list))
or numpy
and isinstance(coords, numpy.ndarray)
):
raise TypeError("Invalid initialization input for LineStrings.")
if not (isinstance(coords, (tuple, list)) or numpy and isinstance(coords, numpy.ndarray)):
raise TypeError('Invalid initialization input for LineStrings.')
# If SRID was passed in with the keyword arguments
srid = kwargs.get("srid")
srid = kwargs.get('srid')
ncoords = len(coords)
if not ncoords:
@@ -46,8 +42,7 @@ class LineString(LinearGeometryMixin, GEOSGeometry):
if ncoords < self._minlength:
raise ValueError(
"%s requires at least %d points, got %s."
% (
'%s requires at least %d points, got %s.' % (
self.__class__.__name__,
self._minlength,
ncoords,
@@ -58,7 +53,7 @@ class LineString(LinearGeometryMixin, GEOSGeometry):
if numpy_coords:
shape = coords.shape # Using numpy's shape.
if len(shape) != 2:
raise TypeError("Too many dimensions.")
raise TypeError('Too many dimensions.')
self._checkdim(shape[1])
ndim = shape[1]
else:
@@ -68,15 +63,13 @@ class LineString(LinearGeometryMixin, GEOSGeometry):
# Incrementing through each of the coordinates and verifying
for coord in coords:
if not isinstance(coord, (tuple, list, Point)):
raise TypeError(
"Each coordinate should be a sequence (list or tuple)"
)
raise TypeError('Each coordinate should be a sequence (list or tuple)')
if ndim is None:
ndim = len(coord)
self._checkdim(ndim)
elif len(coord) != ndim:
raise TypeError("Dimension mismatch.")
raise TypeError('Dimension mismatch.')
# Creating a coordinate sequence object because it is easier to
# set the points using its methods.
@@ -129,21 +122,20 @@ class LineString(LinearGeometryMixin, GEOSGeometry):
self._post_init()
else:
# can this happen?
raise GEOSException("Geometry resulting from slice deletion was invalid.")
raise GEOSException('Geometry resulting from slice deletion was invalid.')
def _set_single(self, index, value):
self._cs[index] = value
def _checkdim(self, dim):
if dim not in (2, 3):
raise TypeError("Dimension mismatch.")
raise TypeError('Dimension mismatch.')
# #### Sequence Properties ####
@property
def tuple(self):
"Return a tuple version of the geometry from the coordinate sequence."
return self._cs.tuple
coords = tuple
def _listarr(self, func):
@@ -189,5 +181,7 @@ class LinearRing(LineString):
@property
def is_counterclockwise(self):
if self.empty:
raise ValueError("Orientation of an empty LinearRing cannot be determined.")
raise ValueError(
'Orientation of an empty LinearRing cannot be determined.'
)
return self._cs.is_counterclockwise
@@ -60,10 +60,10 @@ class ListMixin:
# ### Python initialization and special list interface methods ###
def __init__(self, *args, **kwargs):
if not hasattr(self, "_get_single_internal"):
if not hasattr(self, '_get_single_internal'):
self._get_single_internal = self._get_single_external
if not hasattr(self, "_set_single"):
if not hasattr(self, '_set_single'):
self._set_single = self._set_single_rebuild
self._assign_extended_slice = self._assign_extended_slice_rebuild
@@ -72,9 +72,7 @@ class ListMixin:
def __getitem__(self, index):
"Get the item(s) at the specified index/slice."
if isinstance(index, slice):
return [
self._get_single_external(i) for i in range(*index.indices(len(self)))
]
return [self._get_single_external(i) for i in range(*index.indices(len(self)))]
else:
index = self._checkindex(index)
return self._get_single_external(index)
@@ -93,9 +91,9 @@ class ListMixin:
indexRange = range(*index.indices(origLen))
newLen = origLen - len(indexRange)
newItems = (
self._get_single_internal(i) for i in range(origLen) if i not in indexRange
)
newItems = (self._get_single_internal(i)
for i in range(origLen)
if i not in indexRange)
self._rebuild(newLen, newItems)
@@ -110,28 +108,28 @@ class ListMixin:
# ### Special methods for arithmetic operations ###
def __add__(self, other):
"add another list-like object"
'add another list-like object'
return self.__class__([*self, *other])
def __radd__(self, other):
"add to another list-like object"
'add to another list-like object'
return other.__class__([*other, *self])
def __iadd__(self, other):
"add another list-like object to self"
'add another list-like object to self'
self.extend(other)
return self
def __mul__(self, n):
"multiply"
'multiply'
return self.__class__(list(self) * n)
def __rmul__(self, n):
"multiply"
'multiply'
return self.__class__(list(self) * n)
def __imul__(self, n):
"multiply"
'multiply'
if n <= 0:
del self[:]
else:
@@ -181,16 +179,16 @@ class ListMixin:
for i in range(0, len(self)):
if self[i] == val:
return i
raise ValueError("%s not found in object" % val)
raise ValueError('%s not found in object' % val)
# ## Mutating ##
def append(self, val):
"Standard list append method"
self[len(self) :] = [val]
self[len(self):] = [val]
def extend(self, vals):
"Standard list extend method"
self[len(self) :] = vals
self[len(self):] = vals
def insert(self, index, val):
"Standard list insert method"
@@ -219,9 +217,9 @@ class ListMixin:
# ### Private routines ###
def _rebuild(self, newLen, newItems):
if newLen and newLen < self._minlength:
raise ValueError("Must have at least %d items" % self._minlength)
raise ValueError('Must have at least %d items' % self._minlength)
if self._maxlength is not None and newLen > self._maxlength:
raise ValueError("Cannot have more than %d items" % self._maxlength)
raise ValueError('Cannot have more than %d items' % self._maxlength)
self._set_list(newLen, newItems)
@@ -234,19 +232,19 @@ class ListMixin:
return index
if -length <= index < 0:
return index + length
raise IndexError("invalid index: %s" % index)
raise IndexError('invalid index: %s' % index)
def _check_allowed(self, items):
if hasattr(self, "_allowed"):
if hasattr(self, '_allowed'):
if False in [isinstance(val, self._allowed) for val in items]:
raise TypeError("Invalid type encountered in the arguments.")
raise TypeError('Invalid type encountered in the arguments.')
def _set_slice(self, index, values):
"Assign values to a slice of the object"
try:
valueList = list(values)
except TypeError:
raise TypeError("can only assign an iterable to a slice")
raise TypeError('can only assign an iterable to a slice')
self._check_allowed(valueList)
@@ -261,14 +259,13 @@ class ListMixin:
self._assign_extended_slice(start, stop, step, valueList)
def _assign_extended_slice_rebuild(self, start, stop, step, valueList):
"Assign an extended slice by rebuilding entire list"
'Assign an extended slice by rebuilding entire list'
indexList = range(start, stop, step)
# extended slice, only allow assigning slice of same size
if len(valueList) != len(indexList):
raise ValueError(
"attempt to assign sequence of size %d "
"to extended slice of size %d" % (len(valueList), len(indexList))
)
raise ValueError('attempt to assign sequence of size %d '
'to extended slice of size %d'
% (len(valueList), len(indexList)))
# we're not changing the length of the sequence
newLen = len(self)
@@ -284,20 +281,19 @@ class ListMixin:
self._rebuild(newLen, newItems())
def _assign_extended_slice(self, start, stop, step, valueList):
"Assign an extended slice by re-assigning individual items"
'Assign an extended slice by re-assigning individual items'
indexList = range(start, stop, step)
# extended slice, only allow assigning slice of same size
if len(valueList) != len(indexList):
raise ValueError(
"attempt to assign sequence of size %d "
"to extended slice of size %d" % (len(valueList), len(indexList))
)
raise ValueError('attempt to assign sequence of size %d '
'to extended slice of size %d'
% (len(valueList), len(indexList)))
for i, val in zip(indexList, valueList):
self._set_single(i, val)
def _assign_simple_slice(self, start, stop, valueList):
"Assign a simple slice; Can assign slice of any length"
'Assign a simple slice; Can assign slice of any length'
origLen = len(self)
stop = max(start, stop)
newLen = origLen - stop + start + len(valueList)
@@ -32,7 +32,7 @@ class Point(GEOSGeometry):
else:
coords = [x, y]
else:
raise TypeError("Invalid parameters given for Point initialization.")
raise TypeError('Invalid parameters given for Point initialization.')
point = self._create_point(len(coords), coords)
@@ -47,9 +47,7 @@ class Point(GEOSGeometry):
return self._create_empty() if wkb is None else super()._from_pickle_wkb(wkb)
def _ogr_ptr(self):
return (
gdal.geometries.Point._create_empty() if self.empty else super()._ogr_ptr()
)
return gdal.geometries.Point._create_empty() if self.empty else super()._ogr_ptr()
@classmethod
def _create_empty(cls):
@@ -64,7 +62,7 @@ class Point(GEOSGeometry):
return capi.create_point(None)
if ndim < 2 or ndim > 3:
raise TypeError("Invalid point dimension: %s" % ndim)
raise TypeError('Invalid point dimension: %s' % ndim)
cs = capi.create_cs(c_uint(1), c_uint(ndim))
i = iter(coords)
@@ -86,7 +84,7 @@ class Point(GEOSGeometry):
self._post_init()
else:
# can this happen?
raise GEOSException("Geometry resulting from slice deletion was invalid.")
raise GEOSException('Geometry resulting from slice deletion was invalid.')
def _set_single(self, index, value):
self._cs.setOrdinate(index, 0, value)
@@ -144,7 +142,7 @@ class Point(GEOSGeometry):
def z(self, value):
"Set the Z component of the Point."
if not self.hasz:
raise GEOSException("Cannot set Z on 2D Point.")
raise GEOSException('Cannot set Z on 2D Point.')
self._cs.setOrdinate(2, 0, value)
# ### Tuple setting and retrieval routines. ###
@@ -1,3 +1,5 @@
from ctypes import byref, c_uint
from django.contrib.gis.geos import prototypes as capi
from django.contrib.gis.geos.geometry import GEOSGeometry
from django.contrib.gis.geos.libgeos import GEOM_PTR
@@ -32,8 +34,7 @@ class Polygon(GEOSGeometry):
ext_ring, *init_holes = args
n_holes = len(init_holes)
# If initialized as Polygon(shell, (LinearRing, LinearRing))
# [for backward-compatibility]
# If initialized as Polygon(shell, (LinearRing, LinearRing)) [for backward-compatibility]
if n_holes == 1 and isinstance(init_holes[0], (tuple, list)):
if not init_holes[0]:
init_holes = ()
@@ -60,10 +61,8 @@ class Polygon(GEOSGeometry):
x0, y0, x1, y1 = bbox
for z in bbox:
if not isinstance(z, (float, int)):
return GEOSGeometry(
"POLYGON((%s %s, %s %s, %s %s, %s %s, %s %s))"
% (x0, y0, x0, y1, x1, y1, x1, y0, x0, y0)
)
return GEOSGeometry('POLYGON((%s %s, %s %s, %s %s, %s %s, %s %s))' %
(x0, y0, x0, y1, x1, y1, x1, y0, x0, y0))
return Polygon(((x0, y0), (x0, y1), (x1, y1), (x1, y0), (x0, y0)))
# ### These routines are needed for list-like operation w/ListMixin ###
@@ -86,11 +85,12 @@ class Polygon(GEOSGeometry):
n_holes = length - 1
if n_holes:
holes_param = (GEOM_PTR * n_holes)(*[self._clone(r) for r in rings])
holes = (GEOM_PTR * n_holes)(*[self._clone(r) for r in rings])
holes_param = byref(holes)
else:
holes_param = None
return capi.create_polygon(shell, holes_param, n_holes)
return capi.create_polygon(shell, holes_param, c_uint(n_holes))
def _clone(self, g):
if isinstance(g, GEOM_PTR):
@@ -98,14 +98,8 @@ class Polygon(GEOSGeometry):
else:
return capi.geom_clone(g.ptr)
def _construct_ring(
self,
param,
msg=(
"Parameter must be a sequence of LinearRings or objects that can "
"initialize to LinearRings"
),
):
def _construct_ring(self, param, msg=(
'Parameter must be a sequence of LinearRings or objects that can initialize to LinearRings')):
"Try to construct a ring from the given parameter."
if isinstance(param, LinearRing):
return param
@@ -144,9 +138,7 @@ class Polygon(GEOSGeometry):
return capi.get_intring(self.ptr, index - 1)
def _get_single_external(self, index):
return GEOSGeometry(
capi.geom_clone(self._get_single_internal(index)), srid=self.srid
)
return GEOSGeometry(capi.geom_clone(self._get_single_internal(index)), srid=self.srid)
_set_single = GEOSGeometry._set_single_rebuild
_assign_extended_slice = GEOSGeometry._assign_extended_slice_rebuild
@@ -174,17 +166,13 @@ class Polygon(GEOSGeometry):
def tuple(self):
"Get the tuple for each ring in this Polygon."
return tuple(self[i].tuple for i in range(len(self)))
coords = tuple
@property
def kml(self):
"Return the KML representation of this Polygon."
inner_kml = "".join(
inner_kml = ''.join(
"<innerBoundaryIs>%s</innerBoundaryIs>" % self[i + 1].kml
for i in range(self.num_interior_rings)
)
return "<Polygon><outerBoundaryIs>%s</outerBoundaryIs>%s</Polygon>" % (
self[0].kml,
inner_kml,
)
return "<Polygon><outerBoundaryIs>%s</outerBoundaryIs>%s</Polygon>" % (self[0].kml, inner_kml)
@@ -8,7 +8,6 @@ class PreparedGeometry(GEOSBase):
At the moment this includes the contains covers, and intersects
operations.
"""
ptr_type = capi.PREPGEOM_PTR
destructor = capi.prepared_destroy
@@ -18,7 +17,6 @@ class PreparedGeometry(GEOSBase):
# See #21662
self._base_geom = geom
from .geometry import GEOSGeometry
if not isinstance(geom, GEOSGeometry):
raise TypeError
self.ptr = capi.geos_prepare(geom.ptr)
@@ -5,61 +5,22 @@
"""
from django.contrib.gis.geos.prototypes.coordseq import ( # NOQA
create_cs,
cs_clone,
cs_getdims,
cs_getordinate,
cs_getsize,
cs_getx,
cs_gety,
cs_getz,
cs_is_ccw,
cs_setordinate,
cs_setx,
cs_sety,
cs_setz,
create_cs, cs_clone, cs_getdims, cs_getordinate, cs_getsize, cs_getx,
cs_gety, cs_getz, cs_is_ccw, cs_setordinate, cs_setx, cs_sety, cs_setz,
get_cs,
)
from django.contrib.gis.geos.prototypes.geom import ( # NOQA
create_collection,
create_empty_polygon,
create_linearring,
create_linestring,
create_point,
create_polygon,
destroy_geom,
geom_clone,
geos_get_srid,
geos_normalize,
geos_set_srid,
geos_type,
geos_typeid,
get_dims,
get_extring,
get_geomn,
get_intring,
get_nrings,
get_num_coords,
create_collection, create_empty_polygon, create_linearring,
create_linestring, create_point, create_polygon, destroy_geom, geom_clone,
geos_get_srid, geos_normalize, geos_set_srid, geos_type, geos_typeid,
get_dims, get_extring, get_geomn, get_intring, get_nrings, get_num_coords,
get_num_geoms,
)
from django.contrib.gis.geos.prototypes.misc import * # NOQA
from django.contrib.gis.geos.prototypes.predicates import ( # NOQA
geos_contains,
geos_covers,
geos_crosses,
geos_disjoint,
geos_equals,
geos_equalsexact,
geos_hasz,
geos_intersects,
geos_isclosed,
geos_isempty,
geos_isring,
geos_issimple,
geos_isvalid,
geos_overlaps,
geos_relatepattern,
geos_touches,
geos_within,
geos_contains, geos_covers, geos_crosses, geos_disjoint, geos_equals,
geos_equalsexact, geos_hasz, geos_intersects, geos_isclosed, geos_isempty,
geos_isring, geos_issimple, geos_isvalid, geos_overlaps,
geos_relatepattern, geos_touches, geos_within,
)
from django.contrib.gis.geos.prototypes.topology import * # NOQA
@@ -1,14 +1,16 @@
from ctypes import POINTER, c_byte, c_double, c_int, c_uint
from django.contrib.gis.geos.libgeos import CS_PTR, GEOM_PTR, GEOSFuncFactory
from django.contrib.gis.geos.prototypes.errcheck import GEOSException, last_arg_byref
from django.contrib.gis.geos.prototypes.errcheck import (
GEOSException, last_arg_byref,
)
# ## Error-checking routines specific to coordinate sequences. ##
def check_cs_op(result, func, cargs):
"Check the status code of a coordinate sequence operation."
if result == 0:
raise GEOSException("Could not set value on coordinate sequence")
raise GEOSException('Could not set value on coordinate sequence')
else:
return result
@@ -47,9 +49,7 @@ class CsOperation(GEOSFuncFactory):
else:
argtypes = [CS_PTR, c_uint, dbl_param]
super().__init__(
*args, **{**kwargs, "errcheck": errcheck, "argtypes": argtypes}
)
super().__init__(*args, **{**kwargs, 'errcheck': errcheck, 'argtypes': argtypes})
class CsOutput(GEOSFuncFactory):
@@ -59,7 +59,7 @@ class CsOutput(GEOSFuncFactory):
def errcheck(result, func, cargs):
if not result:
raise GEOSException(
"Error encountered checking Coordinate Sequence returned from GEOS "
'Error encountered checking Coordinate Sequence returned from GEOS '
'C function "%s".' % func.__name__
)
return result
@@ -68,28 +68,26 @@ class CsOutput(GEOSFuncFactory):
# ## Coordinate Sequence ctypes prototypes ##
# Coordinate Sequence constructors & cloning.
cs_clone = CsOutput("GEOSCoordSeq_clone", argtypes=[CS_PTR])
create_cs = CsOutput("GEOSCoordSeq_create", argtypes=[c_uint, c_uint])
get_cs = CsOutput("GEOSGeom_getCoordSeq", argtypes=[GEOM_PTR])
cs_clone = CsOutput('GEOSCoordSeq_clone', argtypes=[CS_PTR])
create_cs = CsOutput('GEOSCoordSeq_create', argtypes=[c_uint, c_uint])
get_cs = CsOutput('GEOSGeom_getCoordSeq', argtypes=[GEOM_PTR])
# Getting, setting ordinate
cs_getordinate = CsOperation("GEOSCoordSeq_getOrdinate", ordinate=True, get=True)
cs_setordinate = CsOperation("GEOSCoordSeq_setOrdinate", ordinate=True)
cs_getordinate = CsOperation('GEOSCoordSeq_getOrdinate', ordinate=True, get=True)
cs_setordinate = CsOperation('GEOSCoordSeq_setOrdinate', ordinate=True)
# For getting, x, y, z
cs_getx = CsOperation("GEOSCoordSeq_getX", get=True)
cs_gety = CsOperation("GEOSCoordSeq_getY", get=True)
cs_getz = CsOperation("GEOSCoordSeq_getZ", get=True)
cs_getx = CsOperation('GEOSCoordSeq_getX', get=True)
cs_gety = CsOperation('GEOSCoordSeq_getY', get=True)
cs_getz = CsOperation('GEOSCoordSeq_getZ', get=True)
# For setting, x, y, z
cs_setx = CsOperation("GEOSCoordSeq_setX")
cs_sety = CsOperation("GEOSCoordSeq_setY")
cs_setz = CsOperation("GEOSCoordSeq_setZ")
cs_setx = CsOperation('GEOSCoordSeq_setX')
cs_sety = CsOperation('GEOSCoordSeq_setY')
cs_setz = CsOperation('GEOSCoordSeq_setZ')
# These routines return size & dimensions.
cs_getsize = CsInt("GEOSCoordSeq_getSize")
cs_getdims = CsInt("GEOSCoordSeq_getDimensions")
cs_getsize = CsInt('GEOSCoordSeq_getSize')
cs_getdims = CsInt('GEOSCoordSeq_getDimensions')
cs_is_ccw = GEOSFuncFactory(
"GEOSCoordSeq_isCCW", restype=c_int, argtypes=[CS_PTR, POINTER(c_byte)]
)
cs_is_ccw = GEOSFuncFactory('GEOSCoordSeq_isCCW', restype=c_int, argtypes=[CS_PTR, POINTER(c_byte)])
@@ -8,7 +8,7 @@ from django.contrib.gis.geos.libgeos import GEOSFuncFactory
# Getting the `free` routine used to free the memory allocated for
# string pointers returned by GEOS.
free = GEOSFuncFactory("GEOSFree")
free = GEOSFuncFactory('GEOSFree')
free.argtypes = [c_void_p]
@@ -29,19 +29,14 @@ def check_dbl(result, func, cargs):
def check_geom(result, func, cargs):
"Error checking on routines that return Geometries."
if not result:
raise GEOSException(
'Error encountered checking Geometry returned from GEOS C function "%s".'
% func.__name__
)
raise GEOSException('Error encountered checking Geometry returned from GEOS C function "%s".' % func.__name__)
return result
def check_minus_one(result, func, cargs):
"Error checking on routines that should not return -1."
if result == -1:
raise GEOSException(
'Error encountered in GEOS C function "%s".' % func.__name__
)
raise GEOSException('Error encountered in GEOS C function "%s".' % func.__name__)
else:
return result
@@ -53,9 +48,7 @@ def check_predicate(result, func, cargs):
elif result == 0:
return False
else:
raise GEOSException(
'Error encountered on GEOS C predicate function "%s".' % func.__name__
)
raise GEOSException('Error encountered on GEOS C predicate function "%s".' % func.__name__)
def check_sized_string(result, func, cargs):
@@ -65,9 +58,7 @@ def check_sized_string(result, func, cargs):
This frees the memory allocated by GEOS at the result pointer.
"""
if not result:
raise GEOSException(
'Invalid string pointer returned by GEOS C function "%s"' % func.__name__
)
raise GEOSException('Invalid string pointer returned by GEOS C function "%s"' % func.__name__)
# A c_size_t object is passed in by reference for the second
# argument on these routines, and its needed to determine the
# correct size.
@@ -84,10 +75,7 @@ def check_string(result, func, cargs):
This frees the memory allocated by GEOS at the result pointer.
"""
if not result:
raise GEOSException(
'Error encountered checking string return value in GEOS C function "%s".'
% func.__name__
)
raise GEOSException('Error encountered checking string return value in GEOS C function "%s".' % func.__name__)
# Getting the string value at the pointer address.
s = string_at(result)
# Freeing the memory allocated within GEOS
@@ -1,10 +1,8 @@
from ctypes import POINTER, c_char_p, c_int, c_ubyte, c_uint
from ctypes import POINTER, c_char_p, c_int, c_ubyte
from django.contrib.gis.geos.libgeos import CS_PTR, GEOM_PTR, GEOSFuncFactory
from django.contrib.gis.geos.prototypes.errcheck import (
check_geom,
check_minus_one,
check_string,
check_geom, check_minus_one, check_string,
)
# This is the return type used by binary output (WKB, HEX) routines.
@@ -46,45 +44,38 @@ class StringFromGeom(GEOSFuncFactory):
# ### ctypes prototypes ###
# The GEOS geometry type, typeid, num_coordinates and number of geometries
geos_normalize = IntFromGeom("GEOSNormalize")
geos_type = StringFromGeom("GEOSGeomType")
geos_typeid = IntFromGeom("GEOSGeomTypeId")
get_dims = GEOSFuncFactory("GEOSGeom_getDimensions", argtypes=[GEOM_PTR], restype=c_int)
get_num_coords = IntFromGeom("GEOSGetNumCoordinates")
get_num_geoms = IntFromGeom("GEOSGetNumGeometries")
geos_normalize = IntFromGeom('GEOSNormalize')
geos_type = StringFromGeom('GEOSGeomType')
geos_typeid = IntFromGeom('GEOSGeomTypeId')
get_dims = GEOSFuncFactory('GEOSGeom_getDimensions', argtypes=[GEOM_PTR], restype=c_int)
get_num_coords = IntFromGeom('GEOSGetNumCoordinates')
get_num_geoms = IntFromGeom('GEOSGetNumGeometries')
# Geometry creation factories
create_point = GeomOutput("GEOSGeom_createPoint", argtypes=[CS_PTR])
create_linestring = GeomOutput("GEOSGeom_createLineString", argtypes=[CS_PTR])
create_linearring = GeomOutput("GEOSGeom_createLinearRing", argtypes=[CS_PTR])
create_point = GeomOutput('GEOSGeom_createPoint', argtypes=[CS_PTR])
create_linestring = GeomOutput('GEOSGeom_createLineString', argtypes=[CS_PTR])
create_linearring = GeomOutput('GEOSGeom_createLinearRing', argtypes=[CS_PTR])
# Polygon and collection creation routines need argument types defined
# for compatibility with some platforms, e.g. macOS ARM64. With argtypes
# defined, arrays are automatically cast and byref() calls are not needed.
create_polygon = GeomOutput(
"GEOSGeom_createPolygon",
argtypes=[GEOM_PTR, POINTER(GEOM_PTR), c_uint],
)
create_empty_polygon = GeomOutput("GEOSGeom_createEmptyPolygon", argtypes=[])
create_collection = GeomOutput(
"GEOSGeom_createCollection",
argtypes=[c_int, POINTER(GEOM_PTR), c_uint],
)
# Polygon and collection creation routines are special and will not
# have their argument types defined.
create_polygon = GeomOutput('GEOSGeom_createPolygon')
create_empty_polygon = GeomOutput('GEOSGeom_createEmptyPolygon')
create_collection = GeomOutput('GEOSGeom_createCollection')
# Ring routines
get_extring = GeomOutput("GEOSGetExteriorRing", argtypes=[GEOM_PTR])
get_intring = GeomOutput("GEOSGetInteriorRingN", argtypes=[GEOM_PTR, c_int])
get_nrings = IntFromGeom("GEOSGetNumInteriorRings")
get_extring = GeomOutput('GEOSGetExteriorRing', argtypes=[GEOM_PTR])
get_intring = GeomOutput('GEOSGetInteriorRingN', argtypes=[GEOM_PTR, c_int])
get_nrings = IntFromGeom('GEOSGetNumInteriorRings')
# Collection Routines
get_geomn = GeomOutput("GEOSGetGeometryN", argtypes=[GEOM_PTR, c_int])
get_geomn = GeomOutput('GEOSGetGeometryN', argtypes=[GEOM_PTR, c_int])
# Cloning
geom_clone = GEOSFuncFactory("GEOSGeom_clone", argtypes=[GEOM_PTR], restype=GEOM_PTR)
geom_clone = GEOSFuncFactory('GEOSGeom_clone', argtypes=[GEOM_PTR], restype=GEOM_PTR)
# Destruction routine.
destroy_geom = GEOSFuncFactory("GEOSGeom_destroy", argtypes=[GEOM_PTR])
destroy_geom = GEOSFuncFactory('GEOSGeom_destroy', argtypes=[GEOM_PTR])
# SRID routines
geos_get_srid = GEOSFuncFactory("GEOSGetSRID", argtypes=[GEOM_PTR], restype=c_int)
geos_set_srid = GEOSFuncFactory("GEOSSetSRID", argtypes=[GEOM_PTR, c_int])
geos_get_srid = GEOSFuncFactory('GEOSGetSRID', argtypes=[GEOM_PTR], restype=c_int)
geos_set_srid = GEOSFuncFactory('GEOSSetSRID', argtypes=[GEOM_PTR, c_int])
@@ -3,14 +3,10 @@ from ctypes import POINTER, Structure, byref, c_byte, c_char_p, c_int, c_size_t
from django.contrib.gis.geos.base import GEOSBase
from django.contrib.gis.geos.libgeos import (
GEOM_PTR,
GEOSFuncFactory,
geos_version_tuple,
GEOM_PTR, GEOSFuncFactory, geos_version_tuple,
)
from django.contrib.gis.geos.prototypes.errcheck import (
check_geom,
check_sized_string,
check_string,
check_geom, check_sized_string, check_string,
)
from django.contrib.gis.geos.prototypes.geom import c_uchar_p, geos_char_p
from django.utils.encoding import force_bytes
@@ -39,43 +35,33 @@ WKB_READ_PTR = POINTER(WKBReader_st)
WKB_WRITE_PTR = POINTER(WKBReader_st)
# WKTReader routines
wkt_reader_create = GEOSFuncFactory("GEOSWKTReader_create", restype=WKT_READ_PTR)
wkt_reader_destroy = GEOSFuncFactory("GEOSWKTReader_destroy", argtypes=[WKT_READ_PTR])
wkt_reader_create = GEOSFuncFactory('GEOSWKTReader_create', restype=WKT_READ_PTR)
wkt_reader_destroy = GEOSFuncFactory('GEOSWKTReader_destroy', argtypes=[WKT_READ_PTR])
wkt_reader_read = GEOSFuncFactory(
"GEOSWKTReader_read",
argtypes=[WKT_READ_PTR, c_char_p],
restype=GEOM_PTR,
errcheck=check_geom,
'GEOSWKTReader_read', argtypes=[WKT_READ_PTR, c_char_p], restype=GEOM_PTR, errcheck=check_geom
)
# WKTWriter routines
wkt_writer_create = GEOSFuncFactory("GEOSWKTWriter_create", restype=WKT_WRITE_PTR)
wkt_writer_destroy = GEOSFuncFactory("GEOSWKTWriter_destroy", argtypes=[WKT_WRITE_PTR])
wkt_writer_create = GEOSFuncFactory('GEOSWKTWriter_create', restype=WKT_WRITE_PTR)
wkt_writer_destroy = GEOSFuncFactory('GEOSWKTWriter_destroy', argtypes=[WKT_WRITE_PTR])
wkt_writer_write = GEOSFuncFactory(
"GEOSWKTWriter_write",
argtypes=[WKT_WRITE_PTR, GEOM_PTR],
restype=geos_char_p,
errcheck=check_string,
'GEOSWKTWriter_write', argtypes=[WKT_WRITE_PTR, GEOM_PTR], restype=geos_char_p, errcheck=check_string
)
wkt_writer_get_outdim = GEOSFuncFactory(
"GEOSWKTWriter_getOutputDimension", argtypes=[WKT_WRITE_PTR], restype=c_int
'GEOSWKTWriter_getOutputDimension', argtypes=[WKT_WRITE_PTR], restype=c_int
)
wkt_writer_set_outdim = GEOSFuncFactory(
"GEOSWKTWriter_setOutputDimension", argtypes=[WKT_WRITE_PTR, c_int]
'GEOSWKTWriter_setOutputDimension', argtypes=[WKT_WRITE_PTR, c_int]
)
wkt_writer_set_trim = GEOSFuncFactory(
"GEOSWKTWriter_setTrim", argtypes=[WKT_WRITE_PTR, c_byte]
)
wkt_writer_set_precision = GEOSFuncFactory(
"GEOSWKTWriter_setRoundingPrecision", argtypes=[WKT_WRITE_PTR, c_int]
)
wkt_writer_set_trim = GEOSFuncFactory('GEOSWKTWriter_setTrim', argtypes=[WKT_WRITE_PTR, c_byte])
wkt_writer_set_precision = GEOSFuncFactory('GEOSWKTWriter_setRoundingPrecision', argtypes=[WKT_WRITE_PTR, c_int])
# WKBReader routines
wkb_reader_create = GEOSFuncFactory("GEOSWKBReader_create", restype=WKB_READ_PTR)
wkb_reader_destroy = GEOSFuncFactory("GEOSWKBReader_destroy", argtypes=[WKB_READ_PTR])
wkb_reader_create = GEOSFuncFactory('GEOSWKBReader_create', restype=WKB_READ_PTR)
wkb_reader_destroy = GEOSFuncFactory('GEOSWKBReader_destroy', argtypes=[WKB_READ_PTR])
class WKBReadFunc(GEOSFuncFactory):
@@ -89,12 +75,12 @@ class WKBReadFunc(GEOSFuncFactory):
errcheck = staticmethod(check_geom)
wkb_reader_read = WKBReadFunc("GEOSWKBReader_read")
wkb_reader_read_hex = WKBReadFunc("GEOSWKBReader_readHEX")
wkb_reader_read = WKBReadFunc('GEOSWKBReader_read')
wkb_reader_read_hex = WKBReadFunc('GEOSWKBReader_readHEX')
# WKBWriter routines
wkb_writer_create = GEOSFuncFactory("GEOSWKBWriter_create", restype=WKB_WRITE_PTR)
wkb_writer_destroy = GEOSFuncFactory("GEOSWKBWriter_destroy", argtypes=[WKB_WRITE_PTR])
wkb_writer_create = GEOSFuncFactory('GEOSWKBWriter_create', restype=WKB_WRITE_PTR)
wkb_writer_destroy = GEOSFuncFactory('GEOSWKBWriter_destroy', argtypes=[WKB_WRITE_PTR])
# WKB Writing prototypes.
@@ -104,8 +90,8 @@ class WKBWriteFunc(GEOSFuncFactory):
errcheck = staticmethod(check_sized_string)
wkb_writer_write = WKBWriteFunc("GEOSWKBWriter_write")
wkb_writer_write_hex = WKBWriteFunc("GEOSWKBWriter_writeHEX")
wkb_writer_write = WKBWriteFunc('GEOSWKBWriter_write')
wkb_writer_write_hex = WKBWriteFunc('GEOSWKBWriter_writeHEX')
# WKBWriter property getter/setter prototypes.
@@ -118,22 +104,17 @@ class WKBWriterSet(GEOSFuncFactory):
argtypes = [WKB_WRITE_PTR, c_int]
wkb_writer_get_byteorder = WKBWriterGet("GEOSWKBWriter_getByteOrder")
wkb_writer_set_byteorder = WKBWriterSet("GEOSWKBWriter_setByteOrder")
wkb_writer_get_outdim = WKBWriterGet("GEOSWKBWriter_getOutputDimension")
wkb_writer_set_outdim = WKBWriterSet("GEOSWKBWriter_setOutputDimension")
wkb_writer_get_include_srid = WKBWriterGet(
"GEOSWKBWriter_getIncludeSRID", restype=c_byte
)
wkb_writer_set_include_srid = WKBWriterSet(
"GEOSWKBWriter_setIncludeSRID", argtypes=[WKB_WRITE_PTR, c_byte]
)
wkb_writer_get_byteorder = WKBWriterGet('GEOSWKBWriter_getByteOrder')
wkb_writer_set_byteorder = WKBWriterSet('GEOSWKBWriter_setByteOrder')
wkb_writer_get_outdim = WKBWriterGet('GEOSWKBWriter_getOutputDimension')
wkb_writer_set_outdim = WKBWriterSet('GEOSWKBWriter_setOutputDimension')
wkb_writer_get_include_srid = WKBWriterGet('GEOSWKBWriter_getIncludeSRID', restype=c_byte)
wkb_writer_set_include_srid = WKBWriterSet('GEOSWKBWriter_setIncludeSRID', argtypes=[WKB_WRITE_PTR, c_byte])
# ### Base I/O Class ###
class IOBase(GEOSBase):
"Base class for GEOS I/O objects."
def __init__(self):
# Getting the pointer with the constructor.
self.ptr = self._constructor()
@@ -141,7 +122,6 @@ class IOBase(GEOSBase):
# __del__ is too late (import error).
self.destructor.func
# ### Base WKB/WKT Reading and Writing objects ###
@@ -203,7 +183,7 @@ class WKTWriter(IOBase):
@outdim.setter
def outdim(self, new_dim):
if new_dim not in (2, 3):
raise ValueError("WKT output dimension must be 2 or 3")
raise ValueError('WKT output dimension must be 2 or 3')
wkt_writer_set_outdim(self.ptr, new_dim)
@property
@@ -223,9 +203,7 @@ class WKTWriter(IOBase):
@precision.setter
def precision(self, precision):
if (not isinstance(precision, int) or precision < 0) and precision is not None:
raise AttributeError(
"WKT output rounding precision must be non-negative integer or None."
)
raise AttributeError('WKT output rounding precision must be non-negative integer or None.')
if precision != self._precision:
self._precision = precision
wkt_writer_set_precision(self.ptr, -1 if precision is None else precision)
@@ -243,37 +221,34 @@ class WKBWriter(IOBase):
def _handle_empty_point(self, geom):
from django.contrib.gis.geos import Point
if isinstance(geom, Point) and geom.empty:
if self.srid:
# PostGIS uses POINT(NaN NaN) for WKB representation of empty
# points. Use it for EWKB as it's a PostGIS specific format.
# https://trac.osgeo.org/postgis/ticket/3181
geom = Point(float("NaN"), float("NaN"), srid=geom.srid)
geom = Point(float('NaN'), float('NaN'), srid=geom.srid)
else:
raise ValueError("Empty point is not representable in WKB.")
raise ValueError('Empty point is not representable in WKB.')
return geom
def write(self, geom):
"Return the WKB representation of the given geometry."
from django.contrib.gis.geos import Polygon
geom = self._handle_empty_point(geom)
wkb = wkb_writer_write(self.ptr, geom.ptr, byref(c_size_t()))
if self.geos_version < (3, 6, 1) and isinstance(geom, Polygon) and geom.empty:
# Fix GEOS output for empty polygon.
# See https://trac.osgeo.org/geos/ticket/680.
wkb = wkb[:-8] + b"\0" * 4
wkb = wkb[:-8] + b'\0' * 4
return memoryview(wkb)
def write_hex(self, geom):
"Return the HEXEWKB representation of the given geometry."
from django.contrib.gis.geos.polygon import Polygon
geom = self._handle_empty_point(geom)
wkb = wkb_writer_write_hex(self.ptr, geom.ptr, byref(c_size_t()))
if self.geos_version < (3, 6, 1) and isinstance(geom, Polygon) and geom.empty:
wkb = wkb[:-16] + b"0" * 8
wkb = wkb[:-16] + b'0' * 8
return wkb
# ### WKBWriter Properties ###
@@ -284,9 +259,7 @@ class WKBWriter(IOBase):
def _set_byteorder(self, order):
if order not in (0, 1):
raise ValueError(
"Byte order parameter must be 0 (Big Endian) or 1 (Little Endian)."
)
raise ValueError('Byte order parameter must be 0 (Big Endian) or 1 (Little Endian).')
wkb_writer_set_byteorder(self.ptr, order)
byteorder = property(_get_byteorder, _set_byteorder)
@@ -299,7 +272,7 @@ class WKBWriter(IOBase):
@outdim.setter
def outdim(self, new_dim):
if new_dim not in (2, 3):
raise ValueError("WKB output dimension must be 2 or 3")
raise ValueError('WKB output dimension must be 2 or 3')
wkb_writer_set_outdim(self.ptr, new_dim)
# Property for getting/setting the include srid flag.
@@ -8,7 +8,7 @@ from django.contrib.gis.geos.libgeos import GEOM_PTR, GEOSFuncFactory
from django.contrib.gis.geos.prototypes.errcheck import check_dbl, check_string
from django.contrib.gis.geos.prototypes.geom import geos_char_p
__all__ = ["geos_area", "geos_distance", "geos_length", "geos_isvalidreason"]
__all__ = ['geos_area', 'geos_distance', 'geos_length', 'geos_isvalidreason']
class DblFromGeom(GEOSFuncFactory):
@@ -16,7 +16,6 @@ class DblFromGeom(GEOSFuncFactory):
Argument is a Geometry, return type is double that is passed
in by reference as the last argument.
"""
restype = c_int # Status code returned
errcheck = staticmethod(check_dbl)
@@ -24,11 +23,9 @@ class DblFromGeom(GEOSFuncFactory):
# ### ctypes prototypes ###
# Area, distance, and length prototypes.
geos_area = DblFromGeom("GEOSArea", argtypes=[GEOM_PTR, POINTER(c_double)])
geos_distance = DblFromGeom(
"GEOSDistance", argtypes=[GEOM_PTR, GEOM_PTR, POINTER(c_double)]
)
geos_length = DblFromGeom("GEOSLength", argtypes=[GEOM_PTR, POINTER(c_double)])
geos_area = DblFromGeom('GEOSArea', argtypes=[GEOM_PTR, POINTER(c_double)])
geos_distance = DblFromGeom('GEOSDistance', argtypes=[GEOM_PTR, GEOM_PTR, POINTER(c_double)])
geos_length = DblFromGeom('GEOSLength', argtypes=[GEOM_PTR, POINTER(c_double)])
geos_isvalidreason = GEOSFuncFactory(
"GEOSisValidReason", restype=geos_char_p, errcheck=check_string, argtypes=[GEOM_PTR]
'GEOSisValidReason', restype=geos_char_p, errcheck=check_string, argtypes=[GEOM_PTR]
)
@@ -22,26 +22,22 @@ class BinaryPredicate(UnaryPredicate):
# ## Unary Predicates ##
geos_hasz = UnaryPredicate("GEOSHasZ")
geos_isclosed = UnaryPredicate("GEOSisClosed")
geos_isempty = UnaryPredicate("GEOSisEmpty")
geos_isring = UnaryPredicate("GEOSisRing")
geos_issimple = UnaryPredicate("GEOSisSimple")
geos_isvalid = UnaryPredicate("GEOSisValid")
geos_hasz = UnaryPredicate('GEOSHasZ')
geos_isclosed = UnaryPredicate('GEOSisClosed')
geos_isempty = UnaryPredicate('GEOSisEmpty')
geos_isring = UnaryPredicate('GEOSisRing')
geos_issimple = UnaryPredicate('GEOSisSimple')
geos_isvalid = UnaryPredicate('GEOSisValid')
# ## Binary Predicates ##
geos_contains = BinaryPredicate("GEOSContains")
geos_covers = BinaryPredicate("GEOSCovers")
geos_crosses = BinaryPredicate("GEOSCrosses")
geos_disjoint = BinaryPredicate("GEOSDisjoint")
geos_equals = BinaryPredicate("GEOSEquals")
geos_equalsexact = BinaryPredicate(
"GEOSEqualsExact", argtypes=[GEOM_PTR, GEOM_PTR, c_double]
)
geos_intersects = BinaryPredicate("GEOSIntersects")
geos_overlaps = BinaryPredicate("GEOSOverlaps")
geos_relatepattern = BinaryPredicate(
"GEOSRelatePattern", argtypes=[GEOM_PTR, GEOM_PTR, c_char_p]
)
geos_touches = BinaryPredicate("GEOSTouches")
geos_within = BinaryPredicate("GEOSWithin")
geos_contains = BinaryPredicate('GEOSContains')
geos_covers = BinaryPredicate('GEOSCovers')
geos_crosses = BinaryPredicate('GEOSCrosses')
geos_disjoint = BinaryPredicate('GEOSDisjoint')
geos_equals = BinaryPredicate('GEOSEquals')
geos_equalsexact = BinaryPredicate('GEOSEqualsExact', argtypes=[GEOM_PTR, GEOM_PTR, c_double])
geos_intersects = BinaryPredicate('GEOSIntersects')
geos_overlaps = BinaryPredicate('GEOSOverlaps')
geos_relatepattern = BinaryPredicate('GEOSRelatePattern', argtypes=[GEOM_PTR, GEOM_PTR, c_char_p])
geos_touches = BinaryPredicate('GEOSTouches')
geos_within = BinaryPredicate('GEOSWithin')
@@ -1,11 +1,13 @@
from ctypes import c_byte
from django.contrib.gis.geos.libgeos import GEOM_PTR, PREPGEOM_PTR, GEOSFuncFactory
from django.contrib.gis.geos.libgeos import (
GEOM_PTR, PREPGEOM_PTR, GEOSFuncFactory,
)
from django.contrib.gis.geos.prototypes.errcheck import check_predicate
# Prepared geometry constructor and destructors.
geos_prepare = GEOSFuncFactory("GEOSPrepare", argtypes=[GEOM_PTR], restype=PREPGEOM_PTR)
prepared_destroy = GEOSFuncFactory("GEOSPreparedGeom_destroy", argtypes=[PREPGEOM_PTR])
geos_prepare = GEOSFuncFactory('GEOSPrepare', argtypes=[GEOM_PTR], restype=PREPGEOM_PTR)
prepared_destroy = GEOSFuncFactory('GEOSPreparedGeom_destroy', argtypes=[PREPGEOM_PTR])
# Prepared geometry binary predicate support.
@@ -15,12 +17,12 @@ class PreparedPredicate(GEOSFuncFactory):
errcheck = staticmethod(check_predicate)
prepared_contains = PreparedPredicate("GEOSPreparedContains")
prepared_contains_properly = PreparedPredicate("GEOSPreparedContainsProperly")
prepared_covers = PreparedPredicate("GEOSPreparedCovers")
prepared_crosses = PreparedPredicate("GEOSPreparedCrosses")
prepared_disjoint = PreparedPredicate("GEOSPreparedDisjoint")
prepared_intersects = PreparedPredicate("GEOSPreparedIntersects")
prepared_overlaps = PreparedPredicate("GEOSPreparedOverlaps")
prepared_touches = PreparedPredicate("GEOSPreparedTouches")
prepared_within = PreparedPredicate("GEOSPreparedWithin")
prepared_contains = PreparedPredicate('GEOSPreparedContains')
prepared_contains_properly = PreparedPredicate('GEOSPreparedContainsProperly')
prepared_covers = PreparedPredicate('GEOSPreparedCovers')
prepared_crosses = PreparedPredicate('GEOSPreparedCrosses')
prepared_disjoint = PreparedPredicate('GEOSPreparedDisjoint')
prepared_intersects = PreparedPredicate('GEOSPreparedIntersects')
prepared_overlaps = PreparedPredicate('GEOSPreparedOverlaps')
prepared_touches = PreparedPredicate('GEOSPreparedTouches')
prepared_within = PreparedPredicate('GEOSPreparedWithin')
@@ -1,12 +1,13 @@
import threading
from django.contrib.gis.geos.base import GEOSBase
from django.contrib.gis.geos.libgeos import CONTEXT_PTR, error_h, lgeos, notice_h
from django.contrib.gis.geos.libgeos import (
CONTEXT_PTR, error_h, lgeos, notice_h,
)
class GEOSContextHandle(GEOSBase):
"""Represent a GEOS context handle."""
ptr_type = CONTEXT_PTR
destructor = lgeos.finishGEOS_r
@@ -30,11 +31,10 @@ class GEOSFunc:
Serve as a wrapper for GEOS C Functions. Use thread-safe function
variants when available.
"""
def __init__(self, func_name):
# GEOS thread-safe function signatures end with '_r' and take an
# additional context handle parameter.
self.cfunc = getattr(lgeos, func_name + "_r")
self.cfunc = getattr(lgeos, func_name + '_r')
# Create a reference to thread_context so it's not garbage-collected
# before an attempt to call this object.
self.thread_context = thread_context
@@ -6,9 +6,7 @@ from ctypes import c_double, c_int
from django.contrib.gis.geos.libgeos import GEOM_PTR, GEOSFuncFactory
from django.contrib.gis.geos.prototypes.errcheck import (
check_geom,
check_minus_one,
check_string,
check_geom, check_minus_one, check_string,
)
from django.contrib.gis.geos.prototypes.geom import geos_char_p
@@ -21,52 +19,35 @@ class Topology(GEOSFuncFactory):
# Topology Routines
geos_boundary = Topology("GEOSBoundary")
geos_buffer = Topology("GEOSBuffer", argtypes=[GEOM_PTR, c_double, c_int])
geos_bufferwithstyle = Topology(
"GEOSBufferWithStyle", argtypes=[GEOM_PTR, c_double, c_int, c_int, c_int, c_double]
)
geos_centroid = Topology("GEOSGetCentroid")
geos_convexhull = Topology("GEOSConvexHull")
geos_difference = Topology("GEOSDifference", argtypes=[GEOM_PTR, GEOM_PTR])
geos_envelope = Topology("GEOSEnvelope")
geos_intersection = Topology("GEOSIntersection", argtypes=[GEOM_PTR, GEOM_PTR])
geos_linemerge = Topology("GEOSLineMerge")
geos_pointonsurface = Topology("GEOSPointOnSurface")
geos_preservesimplify = Topology(
"GEOSTopologyPreserveSimplify", argtypes=[GEOM_PTR, c_double]
)
geos_simplify = Topology("GEOSSimplify", argtypes=[GEOM_PTR, c_double])
geos_symdifference = Topology("GEOSSymDifference", argtypes=[GEOM_PTR, GEOM_PTR])
geos_union = Topology("GEOSUnion", argtypes=[GEOM_PTR, GEOM_PTR])
geos_boundary = Topology('GEOSBoundary')
geos_buffer = Topology('GEOSBuffer', argtypes=[GEOM_PTR, c_double, c_int])
geos_bufferwithstyle = Topology('GEOSBufferWithStyle', argtypes=[GEOM_PTR, c_double, c_int, c_int, c_int, c_double])
geos_centroid = Topology('GEOSGetCentroid')
geos_convexhull = Topology('GEOSConvexHull')
geos_difference = Topology('GEOSDifference', argtypes=[GEOM_PTR, GEOM_PTR])
geos_envelope = Topology('GEOSEnvelope')
geos_intersection = Topology('GEOSIntersection', argtypes=[GEOM_PTR, GEOM_PTR])
geos_linemerge = Topology('GEOSLineMerge')
geos_pointonsurface = Topology('GEOSPointOnSurface')
geos_preservesimplify = Topology('GEOSTopologyPreserveSimplify', argtypes=[GEOM_PTR, c_double])
geos_simplify = Topology('GEOSSimplify', argtypes=[GEOM_PTR, c_double])
geos_symdifference = Topology('GEOSSymDifference', argtypes=[GEOM_PTR, GEOM_PTR])
geos_union = Topology('GEOSUnion', argtypes=[GEOM_PTR, GEOM_PTR])
geos_unary_union = GEOSFuncFactory(
"GEOSUnaryUnion", argtypes=[GEOM_PTR], restype=GEOM_PTR
)
geos_unary_union = GEOSFuncFactory('GEOSUnaryUnion', argtypes=[GEOM_PTR], restype=GEOM_PTR)
# GEOSRelate returns a string, not a geometry.
geos_relate = GEOSFuncFactory(
"GEOSRelate",
argtypes=[GEOM_PTR, GEOM_PTR],
restype=geos_char_p,
errcheck=check_string,
'GEOSRelate', argtypes=[GEOM_PTR, GEOM_PTR], restype=geos_char_p, errcheck=check_string
)
# Linear referencing routines
geos_project = GEOSFuncFactory(
"GEOSProject",
argtypes=[GEOM_PTR, GEOM_PTR],
restype=c_double,
errcheck=check_minus_one,
'GEOSProject', argtypes=[GEOM_PTR, GEOM_PTR], restype=c_double, errcheck=check_minus_one
)
geos_interpolate = Topology("GEOSInterpolate", argtypes=[GEOM_PTR, c_double])
geos_interpolate = Topology('GEOSInterpolate', argtypes=[GEOM_PTR, c_double])
geos_project_normalized = GEOSFuncFactory(
"GEOSProjectNormalized",
argtypes=[GEOM_PTR, GEOM_PTR],
restype=c_double,
errcheck=check_minus_one,
)
geos_interpolate_normalized = Topology(
"GEOSInterpolateNormalized", argtypes=[GEOM_PTR, c_double]
'GEOSProjectNormalized', argtypes=[GEOM_PTR, GEOM_PTR], restype=c_double, errcheck=check_minus_one
)
geos_interpolate_normalized = Topology('GEOSInterpolateNormalized', argtypes=[GEOM_PTR, c_double])