22 votos

¿Cómo añadir la dirección y la distancia a la tabla de atributos?

Cualquiera que pueda ayudar. Sólo quiero añadir la dirección (Rumbo: i.e. N 25 35 E) y la distancia (Longitud: 125 metros) como mi nuevo campo en los datos de polilínea/línea. ¿Hay algún plug-in para generar estos campos? Intenté usar "exportar/añadir columnas de geometría" en mis datos de línea, pero sólo se añadió el valor de "Longitud".

Gracias

0 votos

Hasta ahora puedo usar el plugin mmqgis para darme la distancia. Estoy explorando el problema de la dirección.

1 votos

¿Qué aspecto tienen los datos de las polilíneas? La distancia es relativamente fácil de calcular, pero el rumbo puede cambiar a lo largo de la polilínea. ¿Está buscando el rumbo desde punto de partida a punto final ?

0 votos

Sí, estoy buscando el rumbo desde el punto de partida hasta el punto final... gracias

44voto

Puedes calcular el rumbo en la Calculadora de Campo en QGIS 1.9; la función xat(n) no parece funcionar en 1.7.x por el momento. Esto funciona en coordenadas UTM (métricas) en pequeñas distancias (cientos de km), pero se necesitaría algo más sofisticado para grandes distancias o para grados decimales.

Abre la tabla de atributos de tu capa de línea, cambia la edición y haz clic en el botón Calculadora de campo para abrir el cuadro de diálogo:

enter image description here

Crear un nuevo campo como decimal con una precisión de 1 o 2.

Pegue este código en la casilla "Expresión" y haga clic en "OK": (atan((xat(-1)-xat(0))/(yat(-1)-yat(0)))) * 180/3.14159 + (180 *(((yat(-1)-yat(0)) < 0) + (((xat(-1)-xat(0)) < 0 AND (yat(-1) - yat(0)) >0)*2)))

La primera parte calcula la tangente inversa de las diferencias x e y y la convierte en grados (180/pi). La segunda parte suma 180 o 360 a la cifra resultante para dar un rumbo de 0-360°.

2 votos

Una solución muy elegante, gracias. Me gustaría mencionar que si necesitas determinar el rumbo de cada segmento de una polilínea puedes hacerlo dividiendo el shapefile de la línea con el plug-in 'Split Feature'. Luego cargue el nuevo shapefile (dividido) y siga el procedimiento anterior.

1 votos

@arzandia - tenga en cuenta que DEBE utilizar QGIS 1.9 (véase la página de inicio para las descargas de la versión beta), ya que las funciones xat() y yat() no funcionan en la versión 1.7, que es la que estás utilizando.

0 votos

Ya he utilizado el plug in que has mencionado. como puedes ver en la imagen, el nombre de la capa es "splitted"...

24voto

GreyCat Puntos 146

No necesitas un plugin. Todo está en la clase QgsPoint de PyQGIS

Si examinas el contenido de una clase de puntos QGIS con la función incorporada de Python dir() en la consola de Python.

dir(point])
['__class__', '__delattr__', '__dict__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__'
, '__getitem__', '__gt__', '__hash__', '__init__', '__le__', '__len__', '__lt__', '__module__', 
'__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', 
'__str__', '__subclasshook__', '__weakref__', 'azimuth', 
'multiply', 'set', 'setX', 'setY', 'sqrDist', 'sqrDistToSegment', 'toDegreesMinutesSeconds', 'toString', 'wellKnownText', 'x', 'y']

Puedes ver que hay azimut y sqrDist funciones y después de unos pocos intentos:

- xy[0].azimuth(xy[1]) or xy[1].azimuth(xy[0]) gives the azimuth direction between two points(in degrees, +/- 180°)
- xy[0].sqrDist(xy[1]) give the square distance between two points (in the unit of the project)

El problema enter image description here

Así que en la consola Python

def select_all(layer):
     layer.select([])
     layer.setSelectedFeatures([obj.id() for obj in layer])

myline = qgis.utils.iface.activeLayer()
select_all(myline)
for elem in myline.selectedFeatures():
      xy = elem.geometry().asPolyline()

ahora xy contiene todos los nodos (puntos) de la línea

# first point
print "x=%2d y=%2d" % (xy[0].x(),xy[0].y())
x=112935 y=117784
# and others...

Usando todos los puntos de nodos de la línea:

1) punto de azimut i a punto i + 1 (+/- 180°) (nodos de una línea)

for i in range(len(xy)-1):
     print "x=%2d y=%2d azim=%6.1f azim2=%6.1f" % (xy[i].x(), xy[i].y(), xy[i].azimuth(xy[i+1]), xy[i+1].azimuth(xy[i]))

x=112935 y=117784 azim= 168.4 azim2= -11.6
x=113032 y=117312 azim=-167.5 azim2=  12.5
x=112926 y=116835 azim= 177.3 azim2=  -2.7
x=112943 y=116472 azim= 145.1 azim2= -34.9
[...]

2) distancia euclidiana entre el punto i y el punto i + 1

for i in range(len(xy)-1):
     print "x=%2d y=%2d dist=%6.1f" % (xy[i].x(), xy[i].y(), xy[i].sqrDist(xy[i+1]))

x=112935 y=117784 dist=232533.9
x=113032 y=117311 dist=238243.6
x=112926 y=116835 dist=131839.8
x=112943 y=116472 dist=209268.1
[...]

Después, no es muy difícil añadir estos valores a la tabla de atributos.

Utilizo esta técnica para analizar los lineamientos (geología) con matplotlib y el plugin script Runner

enter image description here

5 votos

+1 - ¡Buena solución! Debe ... aprender ... Python ...

0 votos

Esta es una gran solución y súper valiosa para los geólogos.. pero también es taaaan complicada

13voto

Giuseppe Maxia Puntos 236

La solución aportada por @Simbamangu es bastante efectiva pero no cubre todos los casos. Por ejemplo, si se aplica la fórmula con un desplazamiento horizontal el resultado será nulo, por lo que hay que utilizar esta fórmula en la calculadora de campos de QGIS

case
   when yat(-1)-yat(0) < 0 or yat(-1)-yat(0) > 0
       then (atan((xat(-1)-xat(0))/(yat(-1)-yat(0)))) * 180/3.14159 + 
       (180 * (((yat(-1)-yat(0)) < 0) + (((xat(-1)-xat(0)) < 0 AND (yat(-1) - yat(0)) > 0)*2)))
   when ((yat(-1)-yat(0)) = 0 and (xat(-1) - xat(0)) >0) then 90
   when ((yat(-1)-yat(0)) = 0 and (xat(-1) - xat(0)) <0) then 270
end

0 votos

¿es posible hacer esto en postgis? El comando de postGIS llamado ST_Azimuth sólo funciona en puntos, y no he podido encontrar ningún ejemplo de este mismo proceso en postgresql, postgis.

i-Ciencias.com

I-Ciencias es una comunidad de estudiantes y amantes de la ciencia en la que puedes resolver tus problemas y dudas.
Puedes consultar las preguntas de otros usuarios, hacer tus propias preguntas o resolver las de los demás.

Powered by:

X