Monday 25 February 2019

Extracting coordinates - user friendly tool (4) (QGIS Plugin) - creating points, line, polygon

We have reach point when we are able to get WKT representation of plain text - for points, line and  polygon. Now it's time to visualize this 'horrible' string. I will show how to create spatial features from plain text in this post. If you familiar with one of the post dealing with creating 'asirpsace-like' polygons, you probably got idea how to do it. It is easy - actually we already got it and we only need to add very little code.

First we want to clear WKT string and table with extracted point, than extract coordinates - create table with points, to make sure that feature are created from current plain text:

self.dlg.textEditRawTextWKRTString.clear()
self.dlg.tableWidgetCoordinates.setRowCount(0)
self.extract_coordinates()


Because we will create features, it is a good idea to name points, lines and polygon.
For lines and polygon user will give name directly; for point name will be combination of name given by user (such as prefix) and number of extracted coordinates pair (beginning from 1).
To get name of created feature:

feat_name = self.dlg.lineEditFeatureName.text()

All features will be kept in memory layer, called POINT, LINE, POLYGON.
Note 1:
Notice that at this stage I am not going to check if such layer exist, attributes of this layer match to this in memory layer, which can lead to unexpected results and failures. So far, the whole idea of this plugins is to build tool that is able to create point, line and polygons from plain text such as NOTAM or  parts of AIP.
Assigning names for memory layers:

if self.point_mlyr_name == '':
    self.point_mlyr_name = 'POINT'

if self.line_mlyr_name = '':
    self.line_mlyr_name == 'POINT'

if self.polygon_mlyr_name == '':
    self.polygon_mlyr_name = 'POLYGON'

Just like in previous post, if there is no such layer in layer list create layer and add it into list (remmber about Note 1).
Firstly, get list of layer names:

layers = QgsProject.instance().layerTreeRoot().children()
layers_list = []  # List of layers in current (opened) QGIS project
for layer in layers:
    layers_list.append(layer.name())

We also need QgsFeature() object in order to add features (points, lines, polygons) into layers, so, let's add following line before we start writing code that adds features into layers:

feat = QgsFeature()

Adding WKT string points and creating point features will be done in following steps:
  • create WKT string for extracted points
  • create point memory layer 'POINT' if it does not exist
  • set POINT layer as active
  • add points from list into POINT layer
  • commit changes and updated extent for POINT layer
wkt_str = ''.join([point_item.asWkt() for point_item in points])

if self.point_mlyr_name not in layers_list:
    self.create_mlyr(self.point_mlyr_name, 'POINT')
# Set POINT layer as active
out_lyr = QgsProject.instance().mapLayersByName(self.point_mlyr_name)[0]
self.iface.setActiveLayer(out_lyr)

# There might be many points so first started editing of the point layer
# add points in the loop to layer and at the and commit changes
out_lyr.startEditing()
out_prov = out_lyr.dataProvider()
point_nr = 0
for point_item in points:
    point_nr += 1
    point_name = '{}-{}'.format(feat_name, point_nr)
    point_geom = QgsGeometry.fromPointXY(point_item)
    feat.setGeometry(point_geom)
    feat.setAttributes([point_name])
    out_prov.addFeatures([feat])

out_lyr.commitChanges()
out_lyr.updateExtents()
self.iface.mapCanvas().setExtent(out_lyr.extent())
self.iface.mapCanvas().refresh()




No comments:

Post a Comment