예제 #1
0
파일: models.py 프로젝트: rcoup/traveldash
    def gtfs_generate(cls, source, reader):
        shape_id = None
        coords = []
        for row in reader:
            if (shape_id is not None) and (shape_id != row['shape_id']):
                path = geos.LineString(coords)
                coords = []
                yield Shape(source=source, shape_id=shape_id, path=path)

            shape_id = row['shape_id']
            coords.append(
                (float(row['shape_pt_lon']), float(row['shape_pt_lat'])))

        if shape_id is not None:
            path = geos.LineString(coords)
            yield Shape(source=source, shape_id=shape_id, path=path)
예제 #2
0
    def test_default_resolver(self):
        geometry = geos.LineString((0, 0), (0, 1))
        resolved = resolver.geometry_resolver(attname='type',
                                              default_value=geometry,
                                              root=None,
                                              info=None)

        self.assertEqual(resolved, 'LineString')
예제 #3
0
    def test_filter_distance(self):
        line = geos.LineString((0, 0), (1, 1), srid=4326)
        response = self.execute({
            'unit': 'km',
            'value': 100,
            'geometry': str(line),
        })

        self.assertTrue(response.data['places']['edges'])
예제 #4
0
def add_point_to_network(point, qs=Land.objects.all()):
    qs_coords = ()
    for item in qs:
        qs_coords += item.geometry.exterior_ring.coords
    qs_points = [geos.Point(p) for p in qs_coords]
    for qs_pnt in qs_points:
        line = geos.MultiLineString(geos.LineString(point, qs_pnt))
        if not line_crosses_land(line, qs):
            nw = Network(geometry=line)
            nw.save()
            nw_id = nw.pk
    assign_vertex_ids()
    return Network.objects.get(pk=nw_id).source
예제 #5
0
def add_geometry_to_network(qs):
    # gather polygon vertices from a query set (qs) and add the lines connecting those vertices that do not intersect
    # the geometries within the qs to the Network models.  This will typically be used with Land.objects.all() as the
    # qs but I decided to make it more general.
    coords = ()
    for item in qs:
        coords += item.geometry.exterior_ring.coords
    points = [geos.Point(p) for p in coords]
    matrix = []
    for point in points:
        for pnt in points:
            if point <> pnt and (
                    pnt, point
            ) not in matrix:  # if (1,2) has been dealt with, we don't need to consider (2,1)
                matrix.append((point, pnt))
                line = geos.MultiLineString(geos.LineString(point, pnt))
                if not line_crosses_land(line, qs):
                    nw = Network(geometry=line)
                    nw.save()
    assign_vertex_ids()
    def handle(self, *args, **options):
        # Validate the arguments
        if "shapefile" not in options or not options["shapefile"]:
            logger.error("No shapefile given!")
            return

        if not os.path.isfile(options["shapefile"]):
            logger.error("Invalid shapefile path!")
            return

        if "out" not in options or not options["out"]:
            logger.error("No output path given!")
            return

        if "width_field_name" not in options or not options["width_field_name"]:
            width_field_name = DEFAULT_WIDTH_FIELD_NAME
            logger.info(
                "No width field name given, using the default of {}".format(
                    DEFAULT_WIDTH_FIELD_NAME))
        else:
            width_field_name = options["width_field_name"]

        if "srid" not in options or not options["srid"]:
            input_srid = DEFAULT_INPUT_SRID
            logger.warn(
                "No input srid given! Assuming the default of {}".format(
                    DEFAULT_INPUT_SRID))
        else:
            input_srid = options["srid"]

        # Initialize the json_data with a generic line type
        # TODO: Expand! Make customizable with options and/or by reading and classifying from the shapefile
        json_data = [{
            "model": "linear.LineType",
            "fields": DEFAULT_LINE_TYPE_FIELDS
        }]

        logger.info("Parsing...")

        error_count = 0

        # Parse features from the shapefile into a json file in the fixture format
        for feature in fiona.open(options["shapefile"]):
            # The width field is -1 for some entries. Since those are very minor roads such as bike lanes, we ignore
            # them. TODO: Can we really just ignore them or should we handle them differently?
            if feature["properties"][width_field_name] < 0:
                continue

            try:
                # Convert the LineString from the original srid to WebMercator
                linestring = geos.LineString(
                    *feature["geometry"]["coordinates"], srid=input_srid)
                linestring.transform(WEBMERCATOR_SRID)

                fields = {
                    "type": 1,  # TODO: Change once we use more types
                    "width": feature["properties"][width_field_name],
                    "line": str(linestring)
                }

                json_data.append({
                    "model": "linear.LineSegment",
                    "fields": fields
                })
            except Exception:
                # FIXME: I get errors for about 0.03% of the entries, almost exclusively
                #  "TypeError: Dimension mismatch". What does it mean and how should we handle it?
                logger.error("Error while converting LineString:")
                traceback.print_exc()

                error_count += 1

        if error_count > 0:
            logger.error(
                "Encountered {} errors while parsing, this means that {} entries are now missing!"
                .format(error_count, error_count))

        logger.info("Writing the result...")

        # Write the result into a nicely human-readable json fixture
        with open(options["out"], "w+") as outfile:
            outfile.write(
                json.dumps(json_data,
                           sort_keys=False,
                           indent=4,
                           separators=(",", ": "),
                           ensure_ascii=False))

            logger.info("Success!")
예제 #7
0
    def fuzz(self):
        points = [fake.latlng() for _ in range(20)]  # pylint: disable=no-member

        return geos.LineString(points)
예제 #8
0
    def fuzz(self):
        points = [(random.random(), random.random()) for _ in range(20)]

        return geos.LineString(points)
예제 #9
0
    def test_filter_intersects(self):
        line = geos.LineString((0, 0), (0, 2), srid=4326)
        response = self.execute({'geometry': str(line)})

        self.assertTrue(response.data['places']['edges'])
예제 #10
0
    def linestring(faker, field, srid, *args, **kwargs):
        point_count = faker.random_int(min=2, max=10)

        points = [point(faker, field, srid) for _ in range(point_count)]
        return geos.LineString(*points)
def provide_default_geom(apps, schema_editor):
    segment_model = apps.get_model("tracks", "Segment")
    for segment in segment_model.objects.all():
        segment.geom = geos.LineString()
        segment.save()