Example #1
0
def reproj_convert_layer(geojson_path,
                         output_path,
                         file_format,
                         output_crs,
                         input_crs="epsg:4326"):
    layer_name = output_path.split('/')
    layer_name = layer_name[len(layer_name) - 1].split('.')[0]

    in_driver = GetDriverByName("GeoJSON")
    out_driver = GetDriverByName(file_format)

    inSpRef = SpatialReference()
    inSpRef.ImportFromEPSG(int(input_crs.split("epsg:")[1]))

    outSpRef = SpatialReference()
    ret_val = outSpRef.ImportFromProj4(output_crs)
    if not ret_val == 0:
        raise ValueError("Error when importing the output crs")

    coords_transform = CoordinateTransformation(inSpRef, outSpRef)

    f_in = in_driver.Open(geojson_path)
    input_layer = f_in.GetLayer()
    f_out = out_driver.CreateDataSource(output_path)
    output_layer = f_out.CreateLayer(layer_name, outSpRef)

    input_lyr_defn = input_layer.GetLayerDefn()
    for i in range(input_lyr_defn.GetFieldCount()):
        fieldDefn = input_lyr_defn.GetFieldDefn(i)
        output_layer.CreateField(fieldDefn)

    output_lyr_defn = output_layer.GetLayerDefn()

    for inFeature in input_layer:
        geom = inFeature.GetGeometryRef()
        outFeature = OgrFeature(output_lyr_defn)
        if geom:
            geom.Transform(coords_transform)
            outFeature.SetGeometry(geom)
        else:
            outFeature.SetGeometry(None)

        for i in range(output_lyr_defn.GetFieldCount()):
            outFeature.SetField(
                output_lyr_defn.GetFieldDefn(i).GetNameRef(),
                inFeature.GetField(i))
        output_layer.CreateFeature(outFeature)
        outFeature.Destroy()
        inFeature.Destroy()
    f_in.Destroy()
    f_out.Destroy()

    if "Shapefile" in file_format:
        outSpRef.MorphToESRI()
        with open(output_path.replace(".shp", ".prj"), 'w') as file_proj:
            file_proj.write(outSpRef.ExportToWkt())
        with open(output_path.replace(".shp", ".cpg"), "w") as encoding_file:
            encoding_file.write("ISO-8859-1")
    return 0
Example #2
0
    def write(self, fpath, polygons, spatial_reference=None, driver_name=None):
        """ Convert SCHISM polygon YAML file to a shapefile

        Parameters
        ----------
        fpath: str
            output file name
        polygons: array of schism_polygon.SchismPolygon
            polygons to write
        spatial_reference: osgeo.osr.SpatialReference or proj4 string
            default: NAD83, UTM zone 10N, meter
        driver_name: osgeo.ogr Driver name
            default: ESRI Shapefile
        """
        if spatial_reference is None:
            # Not sure if this changed. it should be EPSG 26910 
            #spatial_reference = '+proj=utm +zone=10N +ellps=NAD83 +datum=NAD83 +units=m'
            spatial_reference= '+proj=utm +zone=10 +ellps=GRS80 +towgs84=0,0,0,0,0,0,0 +units=m +no_defs'
        if isinstance(spatial_reference, str):
            spatial_reference_obj = SpatialReference()
            try:
                spatial_reference_obj.ImportFromProj4(spatial_reference)
            except:
                raise ValueError("spatial reference could not be created from string: {}".format(spatial_reference))
        elif isinstance(spatial_reference, SpatialReference):
            spatial_reference_obj = spatial_reference
        else:
            raise ValueError('Not support spatial_reference type')
        if driver_name is None:
            driver_name = 'ESRI Shapefile'
        driver = GetDriverByName(driver_name)
        if driver is None:
            print('%s is not available.' % driver_name)
            raise RuntimeError()
        datasource = driver.CreateDataSource(str(fpath))
        if datasource is None:
            raise RuntimeError("Cannot create a GIS file")
        layer = datasource.CreateLayer('layer',
                                       spatial_reference_obj,
                                       wkbPolygon)
        fields = ('name', 'type', 'attribute')
        for field in fields:
            layer.CreateField(FieldDefn(field))
        feature_defn = layer.GetLayerDefn()
        feature = Feature(feature_defn)
        for i, polygon in enumerate(polygons):
            feature.SetGeometry(CreateGeometryFromWkb(polygon.wkb))
            feature.SetField(0, polygon.name)
            feature.SetField(1, polygon.type)
            feature.SetField(2, polygon.attribute)
            layer.CreateFeature(feature)
        datasource.Destroy()
    def write(self,
              fpath,
              lines,
              spatial_reference=None,
              driver_name=None,
              **kwargs):
        """
            Parameters
            ----------
            fpath: str
                output file name
            lines: array of schism_linestring.LineString
                list of LineStrings
            spatial_reference: osgeo.osr.SpatialReference
            default: NAD83, UTM zone 10N, meter
        """
        # Boilerplate to create a SHP file
        if spatial_reference is None:
            spatial_reference = SpatialReference()
            spatial_reference.ImportFromProj4(
                '+proj=utm +zone=10N +ellps=NAD83 +datum=NAD83 +units=m')
        if driver_name is None:
            driver_name = 'ESRI Shapefile'
        driver = GetDriverByName(driver_name)
        if driver is None:
            print('%s is not available.' % driver_name)
            raise RuntimeError()
        datasource = driver.CreateDataSource(fpath)
        if datasource is None:
            raise RuntimeError("Cannot create a GIS file")
        layer = datasource.CreateLayer('layer', spatial_reference,
                                       wkbLineString)
        fields = []
        for l in lines:
            if l.prop is not None:
                for k in l.prop:
                    if k not in fields and k != 'coordinates':
                        fields.append(k)
        map(layer.CreateField, [FieldDefn(field) for field in fields])
        feature_defn = layer.GetLayerDefn()
        feature = Feature(feature_defn)

        for i, line in enumerate(lines):
            feature.SetGeometry(CreateGeometryFromWkb(line.wkb))
            for j, f in enumerate(fields):
                val = line.prop.get(f)
                if val is not None:
                    feature.SetField(j, val)
            layer.CreateFeature(feature)
        datasource.Destroy()
def get_zip_style(feature: Feature) -> str:
    zippy: str = feature.GetField("zip")

    if int(zippy[-1]) % 2 == 0:
        return 'PEN(w:2px,c:#0000FF,id:"mapinfo-pen-1,ogr-pen-0");BRUSH(fc:#FFFF00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-2")'
    else:
        return 'PEN(w:2px,c:#0000FF,id:"mapinfo-pen-1,ogr-pen-0");BRUSH(fc:#E8BEFF,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-2")'
 def _ogr_feat_to_row(self, feat: ogr.Feature) -> dict:
     ''' ogr feature to table row (dict with field names as keys and field
     values as values) '''
     if self.field_names is not None:
         items = OrderedDict([(f, feat[f]) for f in self.field_names
                              if hasattr(feat, f)])
     else:
         items = OrderedDict(self._cursor.items())
     items[self.id_field] = feat.GetFID()
     geom = feat.geometry()
     if geom:
         qgeom = QgsGeometry()
         qgeom.fromWkb(geom.ExportToWkb())
         if not qgeom.isGeosValid():
             qgeom = qgeom.makeValid()
         geom = qgeom
     items[self.geom_field] = geom
     return items
Example #6
0
def convert_ogr_to_geojson(file_path, file_format):

    regex_field_name = re.compile("[^a-zA-Z0-9_-ëêàáâãæêéèñòóô]+")

    in_driver = GetDriverByName(file_format)
    out_driver = GetDriverByName('MEMORY')

    f_in = in_driver.Open(file_path)
    input_layer = f_in.GetLayer()

    outSpRef = SpatialReference()
    outSpRef.ImportFromEPSG(4326)
    coords_transform = CoordinateTransformation(input_layer.GetSpatialRef(),
                                                outSpRef)

    f_out = out_driver.CreateDataSource('')
    output_layer = f_out.CreateLayer('', outSpRef)

    input_lyr_defn = input_layer.GetLayerDefn()
    for i in range(input_lyr_defn.GetFieldCount()):
        fieldDefn = input_lyr_defn.GetFieldDefn(i)
        fieldDefn.SetName(regex_field_name.sub('_', fieldDefn.GetNameRef()))
        output_layer.CreateField(fieldDefn)

    output_lyr_defn = output_layer.GetLayerDefn()
    nb_field = output_lyr_defn.GetFieldCount()
    field_names = [
        output_lyr_defn.GetFieldDefn(i).GetNameRef() for i in range(nb_field)
    ]

    res = []
    for inFeature in input_layer:
        geom = inFeature.GetGeometryRef()
        outFeature = OgrFeature(output_lyr_defn)
        # Don't try to transform empty geometry :
        if geom:
            geom.Transform(coords_transform)
            outFeature.SetGeometry(geom)
        else:
            outFeature.SetGeometry(None)
        outFeature.SetFID(inFeature.GetFID())
        for i in range(output_lyr_defn.GetFieldCount()):
            outFeature.SetField(field_names[i], inFeature.GetField(i))
        res.append(outFeature.ExportToJson())
        outFeature.Destroy()
        inFeature.Destroy()

    f_in.Destroy()
    f_out.Destroy()

    return ''.join([
        '''{"type":"FeatureCollection","features":[''', ','.join(res), ''']}'''
    ]).encode()
def get_fire_style(feature: Feature) -> str:
    """Function that determines which style to use, based on the feature description"""
    riskdesc: str = feature.GetField("riskdesc")
    risktype: str = feature.GetField("risktype")
    description: str = " ".join([risktype, riskdesc])

    if description == "IF Smoke Risk":
        return 'PEN(w:2px,c:#0000FF,id:"mapinfo-pen-1,ogr-pen-0");BRUSH(fc:#FFFF00,bc:#FFFFFF,id:"mapinfo-brush-1,ogr-brush-0")'

    if description == "IF Low":
        return 'PEN(w:2px,c:#0000FF,id:"mapinfo-pen-1,ogr-pen-0");BRUSH(fc:#E8BEFF,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "IF Moderate":
        return 'PEN(w:2px,c:#0000FF,id:"mapinfo-pen-1,ogr-pen-0");BRUSH(fc:#C500FF,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "IF High":
        return 'PEN(w:2px,c:#0000FF,id:"mapinfo-pen-1,ogr-pen-0");BRUSH(fc:#4C0073,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "IM Low":
        return 'PEN(w:1px,c:#000000,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#55FF00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "IM Moderate":
        return 'PEN(w:1px,c:#000000,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#FFFF00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "IM High":
        return 'PEN(w:1px,c:#000000,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#FFAA00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "IM Very High":
        return 'PEN(w:1px,c:#000000,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#E60000,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "WL Low":
        return 'PEN(w:1px,c:#FFFFFF,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#55FF00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "WL Moderate":
        return 'PEN(w:1px,c:#FFFFFF,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#FFFF00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "WL High":
        return 'PEN(w:1px,c:#FFFFFF,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#FFAA00,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'

    if description == "WL Very High":
        return 'PEN(w:1px,c:#FFFFFF,id:"mapinfo-pen-2,ogr-pen-0");BRUSH(fc:#E60000,bc:#FFFFFF,id:"mapinfo-brush-2,ogr-brush-0")'
def write_foglio(foglio,
                 destination,
                 point_borders=False,
                 format_name='ESRI Shapefile'):

    cassini_soldener = ''
    #Imposto alcune variabile a seconda del codice_comune:
    #ATTENZIONE: Prima di modificare qui lo SRID controllare che su Postgres le tavole siano impostate adeguatamente nella tavola geometry_columns!!!
    #ATTENZIONE: se nella definizione della cassini_soldener si inseriscono dei valori fissi di x_0 e y_0 ricordarsi di definire successivamente la local_cassini_soldener in maniera adeguata, cioe' togliendo il riferimento al vettore shift_cassini prima definito. In pratica aggiungere il codice_comune nell'array del primo "if" (verso rigo 103...)
    if foglio['CODICE COMUNE'] == 'G087':
        cassini_soldener = '+proj=cass +lat_0=45.007336 +lon_0=7.53725 +x_0=%f +y_0=%f +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'B305':
        cassini_soldener = '+proj=cass +lat_0=45.067618 +lon_0=7.436827 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I785':
        cassini_soldener = '+proj=cass +lat_0=37.267029 +lon_0=14.692473 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'G535':
        cassini_soldener = '+proj=cass +lat_0=44.759075 +lon_0=9.917936 +x_0=-15.5 +y_0=10.5 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'G476':
        cassini_soldener = '+proj=cass +lat_0=40.535328 +lon_0=15.324016 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'L380':
        cassini_soldener = '+proj=tmerc +lat_0=0 +lon_0=9 +k=0.9996 +x_0=1500000 +y_0=0 +ellps=intl +towgs84=-104.1,-49.1,-9.9,0.971,-2.917,0.714,-11.68 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I258':
        cassini_soldener = '+proj=cass +lat_0=45.099116 +lon_0=7.356182 +x_0=-1.5 +y_0=0.5 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'C261':
        cassini_soldener = '+proj=cass +lat_0=45.31413 +lon_0=9.502994 +x_0=1 +y_0=1 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'C722':
        cassini_soldener = "+proj=cass +lat_0=45.235812 +lon_0=7.602194 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs +wktext"
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'A484':
        cassini_soldener = '+proj=cass +lat_0=40.535328 +lon_0=15.324016 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'G793':
        cassini_soldener = '+proj=cass +lat_0=40.535328 +lon_0=15.324016 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I089':
        cassini_soldener = '+proj=cass +lat_0=40.535328 +lon_0=15.324016 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I143':
        cassini_soldener = '+proj=cass +lat_0=40.535328 +lon_0=15.324016 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I307':
        cassini_soldener = '+proj=cass +lat_0=40.535328 +lon_0=15.324016 +x_0=0 +y_0=0 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'G226':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'B266':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'B868':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'F618':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'F625':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'H683':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I410':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'I451':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'C370':
        cassini_soldener = '+proj=cass +lat_0=45.558239 +lon_0=10.76357 +x_0=+0.45 +y_0=-1.90 +ellps=intl +units=m +no_defs'
        t_srs = '4326'
    elif foglio['CODICE COMUNE'] == 'D292':
        cassini_soldener = '+proj=cass +lat_0=40.283555 +lon_0=15.483897 +x_0=8.9958 +y_0=-8.3549 +ellps=bessel +towgs84=668.8,146.4,506.5,5.187,-2.54,5.256,0 +units=m +no_defs'
    target_srs = SpatialReference()
    try:
        target_srs.ImportFromEPSG(int(t_srs))
    except TypeError:
        raise
        target_srs.ImportFromProj4(t_srs)

    shifts = ((0., 0.), (0., 0.))
    shifts = comuni_shift.get(foglio['CODICE COMUNE'], shifts)
    shifts = comuni_shift.get(
        (foglio['CODICE COMUNE'], foglio['NUMERO FOGLIO']), shifts)

    shift_cassini, shift_gauss_boaga = shifts
    ##### Parte eventualmente da MODIFICARE:
    if foglio['CODICE COMUNE'] in [
            'G535', 'I258', 'L380', 'G476', 'C261', 'A484', 'B266', 'B868',
            'F618', 'F625', 'G226', 'G793', 'I307', 'I410', 'I451', 'D292',
            'I143', 'I089', 'H683', 'C722', 'B305', 'I785', 'C370'
    ]:
        local_cassini_soldener = cassini_soldener
    else:
        local_cassini_soldener = cassini_soldener % (-shift_cassini[0],
                                                     -shift_cassini[1])

    source_srs = SpatialReference()
    source_srs.ImportFromProj4(local_cassini_soldener)

    trasformation = CoordinateTransformation(source_srs, target_srs)

    f_comune = FieldDefn('COMUNE', OFTString)
    f_comune.SetWidth(4)
    f_foglio = FieldDefn('FOGLIO', OFTString)
    f_foglio.SetWidth(11)
    f_tipo = FieldDefn('tipo', OFTString)
    f_tipo.SetWidth(11)
    f_part = FieldDefn('PARTICELLA', OFTString)
    f_part.SetWidth(8)
    f_numero = FieldDefn('NUMERO', OFTString)
    f_part.SetWidth(8)
    f_dimensione = FieldDefn('DIMENSIONE', OFTInteger)
    f_area = FieldDefn('AREA', OFTInteger)
    f_angolo = FieldDefn('ANGOLO', OFTReal)
    f_pos_x = FieldDefn('POSIZIONEX', OFTReal)
    f_pos_y = FieldDefn('POSIZIONEY', OFTReal)
    f_interno_x = FieldDefn('P_INTERNOX', OFTReal)
    f_interno_y = FieldDefn('P_INTERNOY', OFTReal)
    f_simbolo = FieldDefn('SIMBOLO', OFTInteger)
    f_etichetta = FieldDefn('etichetta', OFTString)
    f_etichetta.SetWidth(32)
    f_testo = FieldDefn('TESTO', OFTString)
    f_testo.SetWidth(256)

    create_options = []
    if format_name == 'PostgreSQL':
        #Per passare i parametri del driver nella forma "parametro=valore". Sfortunatamente NON POSSO PASSARE "-APPEND"!!!!
        #vedi anche: http://www.gdal.org/gdal_tutorial.html
        papszOptions = ['OVERWRITE=yes']
    elif format_name == 'SQLite':  #IN SVILUPPO!
        #per maggiori info vedere: http://www.gdal.org/drv_sqlite.html
        create_options = [
            'SPATIALITE=YES', 'INIT_WITH_EPSG=YES',
            'OGR_SQLITE_SYNCHRONOUS=OFF', 'OVERWRITE=yes'
        ]
        #l'opzione Overwrite sul DB non funziona: ho messo una IF oltre
        papszOptions = ['FORMAT=SPATIALITE', 'OVERWRITE=yes']  #default
    else:
        papszOptions = []

    if (format_name == 'SQLite') and (os.path.exists(destination)):
        ds = GetDriverByName(format_name).Open(destination, update=1)
    #Pensavo in questo modo di ovviare all'errore che mi restituisce lo script nel caso di DB:
    #ERROR 1: PostgreSQL driver doesn't currently support database creation. Please create database with the `createdb' command.
    #ma non ho risolto niente... Invece aggiungendo "PG:" il plugin genera le tabelle!
    elif (format_name == 'PostgreSQL'):
        #    ds = GetDriverByName(format_name).Open(destination)
        #destination = "PG:%s" % (destination)
        ds = GetDriverByName(format_name).CreateDataSource(
            destination, options=create_options)
    else:
        ds = GetDriverByName(format_name).CreateDataSource(
            destination, options=create_options)
    #per evitare sovrascritture aggiungo anche l'allegato
    pedice = "%s_%s_%s_%s" % (foglio['CODICE COMUNE'], foglio['NUMERO FOGLIO'],
                              foglio['CODICE ALLEGATO'],
                              foglio['CODICE SVILUPPO'])

    #PLUGIN QGIS:
    #Decodifico alcuni campi in modo tale che vengano riconosciuti corretti anche dalle librerie interne di QGis:
    comune_decode = remove_accents(foglio['CODICE COMUNE'])
    #oppure potrebbe essere:
    #comune_decode = foglio['CODICE COMUNE'].encode('utf-8')
    codice_foglioXX = foglio['CODICE FOGLIO'][5:
                                              9]  #cosi' dovrebbe essere "0036"
    foglio_intero = int(codice_foglioXX.lstrip('0'))

    # tipo BORDO
    #bordi = ds.CreateLayer('CATASTO_BORDI', target_srs, wkbPolygon)
    nome_layer_not_utf = "CATASTO_BORDI_%s" % (pedice)
    nome_layer = nome_layer_not_utf.encode('utf-8')  #serve per plugin QGis
    bordi = ds.CreateLayer(nome_layer, target_srs, wkbPolygon25D, papszOptions)

    bordi.CreateField(f_comune)
    bordi.CreateField(f_foglio)
    bordi.CreateField(f_tipo)
    bordi.CreateField(f_part)
    bordi.CreateField(f_dimensione)
    bordi.CreateField(f_angolo)
    bordi.CreateField(f_pos_x)
    bordi.CreateField(f_pos_y)
    bordi.CreateField(f_interno_x)
    bordi.CreateField(f_interno_y)
    bordi.CreateField(f_area)
    bordi.CreateField(f_etichetta)

    for oggetto in foglio['oggetti']['BORDO']:
        poly = Geometry(wkbPolygon)
        tabisole = map(int, oggetto['TABISOLE'])

        # contorno esterno
        vertici_contorno = int(oggetto['NUMEROVERTICI']) - sum(tabisole)
        ring = Geometry(wkbLinearRing)
        for vertice in range(vertici_contorno):
            x, y = map(float, oggetto['VERTICI'][vertice])
            if True:
                x, y = trasformation.TransformPoint(x, y)[:2]
            ring.AddPoint(x + shift_gauss_boaga[0], y + shift_gauss_boaga[1])
        ring.CloseRings()
        poly.AddGeometry(ring)

        # isole
        for isola in range(int(oggetto['NUMEROISOLE'])):
            ring = Geometry(wkbLinearRing)
            for vertice in range(vertice + 1, vertice + 1 + tabisole[isola]):
                x, y = map(float, oggetto['VERTICI'][vertice])
                if True:
                    x, y = trasformation.TransformPoint(x, y)[:2]
                ring.AddPoint(x + shift_gauss_boaga[0],
                              y + shift_gauss_boaga[1])
            ring.CloseRings()
            poly.AddGeometry(ring)

        etichetta = oggetto['CODICE IDENTIFICATIVO']
        if oggetto['CODICE IDENTIFICATIVO'][-1] == '+':
            etichetta = ''

        feat = Feature(bordi.GetLayerDefn())
        feat.SetField('COMUNE',
                      comune_decode)  #plugin in QGis necessita di decodifica
        #codice_foglioXX = foglio['CODICE FOGLIO'][5:9] #cosi' dovrebbe essere "0036"
        #feat.SetField('FOGLIO', codice_foglioXX.lstrip('0'))
        feat.SetField('FOGLIO',
                      foglio_intero)  #plugin in QGis necessita di decodifica
        feat.SetField('tipo', oggetto['tipo'])
        #feat.SetField('PARTICELLA', oggetto['CODICE IDENTIFICATIVO']) #voglio togliere il "+"
        feat.SetField('PARTICELLA',
                      oggetto['CODICE IDENTIFICATIVO'].rstrip('+'))
        feat.SetField('DIMENSIONE', int(oggetto['DIMENSIONE']))
        feat.SetField('ANGOLO', float(oggetto['ANGOLO']))
        pos_x, pos_y = map(float,
                           (oggetto['POSIZIONEX'], oggetto['POSIZIONEY']))
        interno_x, interno_y = map(
            float, (oggetto['PUNTOINTERNOX'], oggetto['PUNTOINTERNOY']))
        if True:
            pos_x, pos_y = trasformation.TransformPoint(pos_x, pos_y)[:2]
            interno_x, interno_y = trasformation.TransformPoint(
                interno_x, interno_y)[:2]
        feat.SetField('POSIZIONEX', pos_x + shift_gauss_boaga[0])
        feat.SetField('POSIZIONEY', pos_y + shift_gauss_boaga[1])
        feat.SetField('P_INTERNOX', interno_x + shift_gauss_boaga[0])
        feat.SetField('P_INTERNOY', interno_y + shift_gauss_boaga[1])
        feat.SetField('AREA', oggetto.get('AREA', -1))
        feat.SetField('etichetta', etichetta.encode('utf-8'))
        feat.SetGeometry(poly)
        bordi.CreateFeature(feat)
        feat.Destroy()

    if point_borders:
        # tipo BORDO_PUNTO
        #bordi = ds.CreateLayer('CATASTO_PARTICELLE', target_srs, wkbPoint)
        #nome_layer = "CATASTO_PARTICELLE_%s" % (pedice)
        nome_layer_not_utf = "CATASTO_PARTICELLE_%s" % (pedice)
        nome_layer = nome_layer_not_utf.encode('utf-8')  #serve per plugin QGis
        bordi = ds.CreateLayer(nome_layer, target_srs, wkbPoint, papszOptions)

        bordi.CreateField(f_comune)
        bordi.CreateField(f_foglio)
        bordi.CreateField(f_tipo)
        bordi.CreateField(f_part)
        bordi.CreateField(f_dimensione)
        bordi.CreateField(f_angolo)
        bordi.CreateField(f_area)
        bordi.CreateField(f_etichetta)

        for oggetto in foglio['oggetti']['BORDO']:
            etichetta = oggetto['CODICE IDENTIFICATIVO']
            if oggetto['CODICE IDENTIFICATIVO'][-1] == '+':
                etichetta = ''

            feat = Feature(bordi.GetLayerDefn())
            #feat.SetField('COMUNE', foglio['CODICE COMUNE'])
            feat.SetField(
                'COMUNE',
                comune_decode)  #plugin in QGis necessita di decodifica
            #feat.SetField('FOGLIO', foglio['CODICE FOGLIO'])
            feat.SetField(
                'FOGLIO',
                foglio_intero)  #plugin in QGis necessita di decodifica
            feat.SetField('tipo', oggetto['tipo'])
            feat.SetField('PARTICELLA', oggetto['CODICE IDENTIFICATIVO'])
            feat.SetField('DIMENSIONE', int(oggetto['DIMENSIONE']))
            feat.SetField('ANGOLO', float(oggetto['ANGOLO']))
            pos_x, pos_y = map(
                float, (oggetto['PUNTOINTERNOX'], oggetto['PUNTOINTERNOY']))
            if True:
                pos_x, pos_y = trasformation.TransformPoint(pos_x, pos_y)[:2]
            feat.SetField('AREA', oggetto.get('AREA', -1))
            feat.SetField('etichetta', etichetta.encode('utf-8'))
            pt = Geometry(wkbPoint)
            pt.SetPoint_2D(0, pos_x + shift_gauss_boaga[0],
                           pos_y + shift_gauss_boaga[1])
            feat.SetGeometry(pt)
            bordi.CreateFeature(feat)
            feat.Destroy()

    # tipo TESTO
    #testi = ds.CreateLayer('CATASTO_TESTI', target_srs, wkbPoint)
    #nome_layer = "CATASTO_TESTI_%s" % (pedice)
    nome_layer_not_utf = "CATASTO_TESTI_%s" % (pedice)
    nome_layer = nome_layer_not_utf.encode('utf-8')  #serve per plugin QGis
    testi = ds.CreateLayer(nome_layer, target_srs, wkbPoint, papszOptions)

    testi.CreateField(f_comune)
    testi.CreateField(f_foglio)
    testi.CreateField(f_testo)
    testi.CreateField(f_dimensione)
    testi.CreateField(f_angolo)
    testi.CreateField(f_etichetta)

    for oggetto in foglio['oggetti']['TESTO']:
        x, y = map(float, (oggetto['POSIZIONEX'], oggetto['POSIZIONEY']))
        if True:
            x, y = trasformation.TransformPoint(x, y)[:2]
        # FIXME: many texts are useless, prun them from etichetta
        etichetta = remove_accents(oggetto['TESTO'])

        feat = Feature(testi.GetLayerDefn())
        #feat.SetField('COMUNE', foglio['CODICE COMUNE'])
        feat.SetField('COMUNE',
                      comune_decode)  #plugin in QGis necessita di decodifica
        #feat.SetField('FOGLIO', foglio['CODICE FOGLIO'])
        feat.SetField('FOGLIO',
                      foglio_intero)  #plugin in QGis necessita di decodifica
        #feat.SetField('TESTO', oggetto['TESTO'])
        feat.SetField('TESTO', etichetta)
        feat.SetField('DIMENSIONE', int(oggetto['DIMENSIONE']))
        feat.SetField('ANGOLO', float(oggetto['ANGOLO']))
        feat.SetField('etichetta', etichetta.encode('utf-8'))
        pt = Geometry(wkbPoint)
        pt.SetPoint_2D(0, x + shift_gauss_boaga[0], y + shift_gauss_boaga[1])
        feat.SetGeometry(pt)
        testi.CreateFeature(feat)

    # tipo SIMBOLO
    #simboli = ds.CreateLayer('CATASTO_SIMBOLI', target_srs, wkbPoint)
    #nome_layer = "CATASTO_SIMBOLI_%s" % (pedice)
    nome_layer_not_utf = "CATASTO_SIMBOLI_%s" % (pedice)
    nome_layer = nome_layer_not_utf.encode('utf-8')  #serve per plugin QGis
    simboli = ds.CreateLayer(nome_layer, target_srs, wkbPoint, papszOptions)

    simboli.CreateField(f_comune)
    simboli.CreateField(f_foglio)
    simboli.CreateField(f_simbolo)
    simboli.CreateField(f_angolo)

    for oggetto in foglio['oggetti']['SIMBOLO']:
        x, y = map(float, (oggetto['POSIZIONEX'], oggetto['POSIZIONEY']))
        if True:
            x, y = trasformation.TransformPoint(x, y)[:2]

        feat = Feature(simboli.GetLayerDefn())
        #feat.SetField('COMUNE', foglio['CODICE COMUNE'])
        feat.SetField('COMUNE',
                      comune_decode)  #plugin in QGis necessita di decodifica
        #feat.SetField('FOGLIO', foglio['CODICE FOGLIO'])
        feat.SetField('FOGLIO',
                      foglio_intero)  #plugin in QGis necessita di decodifica
        feat.SetField('SIMBOLO', oggetto['CODICE SIMBOLO'])
        feat.SetField('ANGOLO', float(oggetto['ANGOLO']))
        pt = Geometry(wkbPoint)
        pt.SetPoint_2D(0, x + shift_gauss_boaga[0], y + shift_gauss_boaga[1])
        feat.SetGeometry(pt)
        simboli.CreateFeature(feat)

    # tipo FIDUCIALE
    #fiduciali = ds.CreateLayer('CATASTO_FIDUCIALI', target_srs, wkbPoint)
    #nome_layer = "CATASTO_FIDUCIALI_%s" % (pedice)
    nome_layer_not_utf = "CATASTO_FIDUCIALI_%s" % (pedice)
    nome_layer = nome_layer_not_utf.encode('utf-8')  #serve per plugin QGis
    fiduciali = ds.CreateLayer(nome_layer, target_srs, wkbPoint, papszOptions)

    fiduciali.CreateField(f_comune)
    fiduciali.CreateField(f_foglio)
    fiduciali.CreateField(f_numero)
    fiduciali.CreateField(f_simbolo)
    fiduciali.CreateField(f_pos_x)
    fiduciali.CreateField(f_pos_y)
    fiduciali.CreateField(f_etichetta)

    print 'corrections', shift_cassini, shift_gauss_boaga
    for oggetto in foglio['oggetti']['FIDUCIALE']:
        x, y = map(float, (oggetto['POSIZIONEX'], oggetto['POSIZIONEY']))
        pos_x, pos_y = map(float, (oggetto['PUNTORAPPRESENTAZIONEX'],
                                   oggetto['PUNTORAPPRESENTAZIONEY']))
        if True:
            x, y = trasformation.TransformPoint(x, y)[:2]
            pos_x, pos_y = trasformation.TransformPoint(pos_x, pos_y)[:2]
        etichetta = 'PF%02d/%s%s/%s' % (int(oggetto['NUMERO IDENTIFICATIVO']),
                                        foglio['CODICE NUMERO FOGLIO'][1:],
                                        foglio['CODICE ALLEGATO'],
                                        foglio['CODICE COMUNE'])

        feat = Feature(fiduciali.GetLayerDefn())
        #feat.SetField('COMUNE', foglio['CODICE COMUNE'])
        feat.SetField('COMUNE',
                      comune_decode)  #plugin in QGis necessita di decodifica
        #feat.SetField('FOGLIO', foglio['CODICE FOGLIO'])
        feat.SetField('FOGLIO',
                      foglio_intero)  #plugin in QGis necessita di decodifica
        feat.SetField('NUMERO', oggetto['NUMERO IDENTIFICATIVO'])
        feat.SetField('SIMBOLO', oggetto['CODICE SIMBOLO'])
        feat.SetField('POSIZIONEX', pos_x + shift_gauss_boaga[0])
        feat.SetField('POSIZIONEY', pos_y + shift_gauss_boaga[1])
        feat.SetField('etichetta', etichetta.encode('utf-8'))
        pt = Geometry(wkbPoint)
        pt.SetPoint_2D(0, x + shift_gauss_boaga[0], y + shift_gauss_boaga[1])
        feat.SetGeometry(pt)
        fiduciali.CreateFeature(feat)

        print etichetta, oggetto['CODICE SIMBOLO'], \
            float(oggetto['POSIZIONEX']) + shift_cassini[0], float(oggetto['POSIZIONEY']) + shift_cassini[1], \
            x + shift_gauss_boaga[0], y + shift_gauss_boaga[1]

    # tipo LINEA
    #linee = ds.CreateLayer('CATASTO_LINEE', target_srs, wkbLineString)
    #nome_layer = "CATASTO_LINEE_%s" % (pedice)
    nome_layer_not_utf = "CATASTO_LINEE_%s" % (pedice)
    nome_layer = nome_layer_not_utf.encode('utf-8')  #serve per plugin QGis
    linee = ds.CreateLayer(nome_layer, target_srs, wkbLineString25D,
                           papszOptions)

    linee.CreateField(f_comune)
    linee.CreateField(f_foglio)
    linee.CreateField(f_simbolo)

    for oggetto in foglio['oggetti']['LINEA']:
        # contorno esterno
        vertici = int(oggetto['NUMEROVERTICI'])
        linea = Geometry(wkbLineString)
        for vertice in range(vertici):
            x, y = map(float, oggetto['VERTICI'][vertice])
            if True:
                x, y = trasformation.TransformPoint(x, y)[:2]
            linea.AddPoint(x + shift_gauss_boaga[0], y + shift_gauss_boaga[1])

        feat = Feature(linee.GetLayerDefn())
        #feat.SetField('COMUNE', foglio['CODICE COMUNE'])
        feat.SetField('COMUNE',
                      comune_decode)  #plugin in QGis necessita di decodifica
        #feat.SetField('FOGLIO', foglio['CODICE FOGLIO'])
        feat.SetField('FOGLIO',
                      foglio_intero)  #plugin in QGis necessita di decodifica
        feat.SetField('SIMBOLO', oggetto['CODICE TIPO DI TRATTO'])
        feat.SetGeometry(linea)
        linee.CreateFeature(feat)
        feat.Destroy()

    ds.Destroy()
Example #9
0
File: geo.py Project: vinber/magrit
def reproj_convert_layer(geojson_path, output_path, file_format, output_crs):
    """
    Concert GeoJSON to GML or Shapefile and write it to disk.

    Convert a GeoJSON FeatureCollection to GML or ESRI Shapefile format and
    reproject the geometries if needed (used when the user requests an export).

    Parameters
    ----------
    geojson_path: str
        Path of the input GeoJSON FeatureCollection to be converted.

    output_path: str
        Path for the resulting Shapefile/GML (should be in a directory
        created by tempfile.TemporaryDirectory).

    file_format: str
        The format of the expected result ('ESRI Shapefile' or 'GML' is expected).

    output_crs: str
        The output srs to use (in proj4 string format).

    Returns
    -------
    result_code: int
        Should return 0 if everything went fine..
    """
    ## TODO : Use VectorTranslate to make the conversion?
    input_crs = "epsg:4326"
    layer_name = output_path.split('/')
    layer_name = layer_name[len(layer_name) - 1].split('.')[0]

    in_driver = GetDriverByName("GeoJSON")
    out_driver = GetDriverByName(file_format)

    inSpRef = SpatialReference()
    inSpRef.ImportFromEPSG(int(input_crs.split("epsg:")[1]))

    outSpRef = SpatialReference()
    ret_val = outSpRef.ImportFromProj4(output_crs)
    if not ret_val == 0:
        raise ValueError("Error when importing the output crs")

    coords_transform = CoordinateTransformation(inSpRef, outSpRef)

    f_in = in_driver.Open(geojson_path)
    input_layer = f_in.GetLayer()
    f_out = out_driver.CreateDataSource(output_path)
    output_layer = f_out.CreateLayer(layer_name, outSpRef)

    input_lyr_defn = input_layer.GetLayerDefn()
    for i in range(input_lyr_defn.GetFieldCount()):
        fieldDefn = input_lyr_defn.GetFieldDefn(i)
        output_layer.CreateField(fieldDefn)

    output_lyr_defn = output_layer.GetLayerDefn()

    for inFeature in input_layer:
        geom = inFeature.GetGeometryRef()
        outFeature = OgrFeature(output_lyr_defn)
        if geom:
            geom.Transform(coords_transform)
            outFeature.SetGeometry(geom)
        else:
            outFeature.SetGeometry(None)

        for i in range(output_lyr_defn.GetFieldCount()):
            outFeature.SetField(
                output_lyr_defn.GetFieldDefn(i).GetNameRef(),
                inFeature.GetField(i))
        output_layer.CreateFeature(outFeature)
        outFeature.Destroy()
        inFeature.Destroy()
    f_in.Destroy()
    f_out.Destroy()

    if "Shapefile" in file_format:
        outSpRef.MorphToESRI()
        with open(output_path.replace(".shp", ".prj"), 'w') as file_proj:
            file_proj.write(outSpRef.ExportToWkt())
        with open(output_path.replace(".shp", ".cpg"), "w") as encoding_file:
            encoding_file.write("ISO-8859-1")
    return 0
Example #10
0
File: geo.py Project: vinber/magrit
def convert_ogr_to_geojson(file_path, file_format):
    """
    Convert a layer (in a format supported by ogr) to a GeoJSON layer.
    Used in fallback, if the conversion failed with 'VectorTranslate'.

    Parameters
    ----------
    file_path: str
        Path of the input file.
    file_format: str
        Format of the input layer

    Returns
    -------
    raw_geojson: bytes
        The resulting GeoJSON FeatureCollection.
    """
    regex_field_name = re.compile("[^a-zA-Z0-9_-ëêàáâãæêéèñòóô]+")

    in_driver = GetDriverByName(file_format)
    out_driver = GetDriverByName('MEMORY')

    f_in = in_driver.Open(file_path)
    input_layer = f_in.GetLayer()

    outSpRef = SpatialReference()
    outSpRef.ImportFromEPSG(4326)
    coords_transform = CoordinateTransformation(input_layer.GetSpatialRef(),
                                                outSpRef)

    f_out = out_driver.CreateDataSource('')
    output_layer = f_out.CreateLayer('', outSpRef)

    input_lyr_defn = input_layer.GetLayerDefn()
    for i in range(input_lyr_defn.GetFieldCount()):
        fieldDefn = input_lyr_defn.GetFieldDefn(i)
        fieldDefn.SetName(regex_field_name.sub('_', fieldDefn.GetNameRef()))
        output_layer.CreateField(fieldDefn)

    output_lyr_defn = output_layer.GetLayerDefn()
    nb_field = output_lyr_defn.GetFieldCount()
    field_names = [
        output_lyr_defn.GetFieldDefn(i).GetNameRef() for i in range(nb_field)
    ]

    res = []
    for inFeature in input_layer:
        geom = inFeature.GetGeometryRef()
        outFeature = OgrFeature(output_lyr_defn)
        # Don't try to transform empty geometry :
        if geom:
            geom.Transform(coords_transform)
            outFeature.SetGeometry(geom)
        else:
            outFeature.SetGeometry(None)
        outFeature.SetFID(inFeature.GetFID())
        for i in range(output_lyr_defn.GetFieldCount()):
            outFeature.SetField(field_names[i], inFeature.GetField(i))
        res.append(outFeature.ExportToJson())
        outFeature.Destroy()
        inFeature.Destroy()

    f_in.Destroy()
    f_out.Destroy()

    return ''.join([
        '''{"type":"FeatureCollection","features":[''', ','.join(res), ''']}'''
    ]).encode()
def get_predom(const: dict, ft: ogr.Feature) -> int:
    '''Derive the predominant ice value'''
    # get fields
    e_ct = ft.GetField('E_CT')
    e_ca = ft.GetField('E_CA')
    e_cb = ft.GetField('E_CB')
    e_cc = ft.GetField('E_CC')
    e_sa = ft.GetField('E_SA')
    e_sb = ft.GetField('E_SB')
    e_sc = ft.GetField('E_SC')
    e_sd = ft.GetField('E_SD')
    pnt_type = ft.GetField('PNT_TYPE')

    # set icebergs to open water
    e_sa = '0' if e_sa == 'L' else e_sa
    e_sb = '0' if e_sb == 'L' else e_sb
    e_sc = '0' if e_sc == 'L' else e_sc

    # find predominant
    key = ''
    if pnt_type in ['123', '128', '133']:  # nodata
        key = 'ND'
    elif pnt_type in ['900', '400']:  # land
        key = 'LD'
    elif pnt_type in ['101', '107', '115',
                      '146']:  # icefree/openwater/bergywater
        key = 'NI'
    else:
        # derive cd
        ca, cb, cc = 0, 0, 0
        cd = 10 if e_ct == '9+' else int(float(e_ct)) if e_ct else 0

        if e_ca is None:
            ca = 10 if e_ct == '9+' else int(float(e_ct))
        if e_cb:
            cb = int(float(e_cb))
        if e_cc:
            cc = int(float(e_cc))

        cd -= ca + cb + cc

        # 1x icetype
        e_ca = e_ct if e_ca is None else e_ca
        ca = 10 if e_ca == '9+' else int(float(e_ca))
        cb = 0 if e_cb is None else int(float(e_cb))
        cc = 0 if e_cc is None else int(float(e_cc))

        # 3x icetypes, pick the middle icetype
        if ca == cb and ca == cc:
            key = e_sa

        # choose predominance from column a to d
        elif ca >= cb and ca >= cc and ca >= cd:
            key = e_sa
        elif cb > ca and cb >= cc and cb >= cd:
            key = e_sb
        elif cc > ca and cc > cb and cc >= cd:
            key = e_sc
        elif cd > ca and cd > cb and cd > cc:
            key = e_sd

        # verify old ice predominance
        oipredom = False
        sypredom = False
        mypredom = False
        oi = 0

        # check column a
        if e_sa in ['7.', '8.', '9.']:
            oi += ca
        if e_sa == '7.' and ca >= 4:
            oipredom = True
        elif e_sa == '8.' and ca >= 4:
            sypredom = True
        elif e_sa == '9.' and ca >= 4:
            mypredom = True

        # check colum b
        if e_sb in ['7.', '8.', '9.']:
            oi += cb
        if e_sb == '7.' and cb >= 4:
            oipredom = True
        elif e_sb == '8.' and cb >= 4:
            sypredom = True
        elif e_sb == '9.' and cb >= 4:
            mypredom = True

        # check colum c
        if e_sc in ['7.', '8.', '9.']:
            oi += cc
        if e_sc == '7.' and cc >= 4:
            oipredom = True
        elif e_sc == '8.' and cc >= 4:
            sypredom = True
        elif e_sc == '9.' and cc >= 4:
            mypredom = True

        # find predominant, order MY->SY->OLD.
        # preference given to oldice subcategories
        if oi >= 4:
            key = '7.'
        elif oipredom:
            key = '7.'
        elif sypredom:
            key = '8.'
        elif mypredom:
            key = '9.'

    # return predominant
    stage = PREDOMINANTS.get(key)
    if stage is None:
        try:
            stage = int(float(key))
        except:
            stage = const['water']

    logging.info(f'predominant = {stage}')
    return stage
Example #12
0
def getfiddo(feature: Feature) -> int:
    return feature.GetFID()
 def title_provider(feature: ogr.Feature) -> str:
     name = feature.GetFieldAsString("MAP_LABEL")
     status = " (retired)" if feature.GetFieldAsString(
         'LIFE_CYCLE_STATUS_CODE') == "RETIRED" else ""
     return f"{name}{status}"
 def get_xyz_url_for_feature(feature: ogr.Feature) -> str:
     return feature.GetFieldAsString("xyz_url")
 def get_profile_names_for_feature(feature: ogr.Feature) -> List[str]:
     return list(
         map(
             lambda profile_names_part: profile_names_part.strip(),
             feature.GetFieldAsString("profile").split(","),
         ))