3

I tried to shorten a given LineGeometry with some Python code.

from qgis.utils import iface

layer = iface.activeLayer()
fs = layer.selectedFeatures()

for f in fs:
    fg = f.geometry()
    geomSingleType = QgsWkbTypes.isSingleType(fg.wkbType())

    if fg.type() == QgsWkbTypes.LineGeometry:
        if geomSingleType:
            x = fg.asPolyline()
            print("length: ", fg.length())
        else:
            x = fg.asMultiPolyline()
            print("MultiLine: ", x, "length: ", fg.length())

    newLine = fg.extendLine(0,(-2.5))
    print("length: ", newLine .length())

That returns a line with an equal length:

length:  11.995677929842055
length:  11.995677929842055

When I use a value > 0 the length is updated:

length:  11.995677929842055
length:  14.495677929927327

So I'm able to make a line longer, but I want to make it shorter.

Does anyone have any advice for me?

The code is part of a bigger project - so solutions with QGIS UI will not help me.

2
  • 1
    I think extendLine intents only extend the lines not shrink. There is Line substring tool you may want to try out.
    – Nil
    Jan 11, 2021 at 11:51
  • 2
    extendLine uses extend behind the scene. And extend doesn't work with negative values. i.stack.imgur.com/QbKlg.png Jan 11, 2021 at 12:05

1 Answer 1

5

If you want to modify existing geometries (actually shorten line features) can use or modify the script below. You can test this on selected features of a line layer by running in the Python console but please make a backup copy of the layer first.

from qgis.utils import iface

l = iface.activeLayer()

#retrieve feature geometry and check its length
f = l.getFeature(1)
print(f.geometry().length())

def shorten_line(feat, length):
    '''Returns a linestring geometry shortened by the given length.
    Takes two arguments- a QgsFeature object and a double value'''
    g = feat.geometry()
    v = [v for v in g.vertices()]
    v.remove(v[-1])
    v.append(QgsPoint(g.interpolate(g.length()-length).asPoint()))
    n = QgsLineString(v)
    return QgsGeometry(n)
    

# example usage ! This will permanently modify the selected features in
# your active layer!
l.selectByIds([1])
with edit(l):
    for f in l.selectedFeatures():
        l.changeGeometry(f.id(), shorten_line(f, 100.00))

#retrieve feature geometry and check its new length
f = l.getFeature(1)
print(f.geometry().length())

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.