Пользовательский импортер LiDAR Houdini в Python с использованием модуля Laspy - PullRequest
0 голосов
/ 11 июля 2020

Я пытаюсь создать собственный импортер LiDAR для Houdini с Python. Модуль Laspy (https://pypi.org/project/laspy) до сих пор делает хорошую и быструю работу, читая и записывая файлы *. * Las внутри Houdini, а также фильтруя классификации.

Но я должен прочитать и напишите файл *. * las и снова импортируйте вместо того, чтобы мгновенно получать точки внутри Houdini.

Теперь мне интересно, могу ли я получить координаты точек LiDAR xyz, чтобы скормить им точки внутри Houdini.

Я пытался найти полезную информацию в руководстве по Laspy, но не смог найти ни одного примера или функции.

Я сделал нечто подобное с файлом *. * Csv, в котором есть позиции xyz для создать простой GPS-ридер для вывода позиций в виде точек в Houdini (с модулем csv).

Я прилагаю снимок экрана с исходным .las (серый) и отфильтрованным выводом ..las (красные крыши) и пример скрипта из мануала Ласпи.

Может, вместо Ласпи есть более изящное Решение? Я использую Python 3 в Houdini, но 2.7 тоже работает.

Обновление, ответ здесь работает почти идеально https://forums.odforce.net/topic/46475-custom-lidar-importer-with-python/?tab=comments#comment -217104 :

from laspy.file import File
import numpy as np

node = hou.pwd()
geo = node.geometry()

file_path = geo.attribValue("file_path")
inFile = File(file_path, mode='r')

# --- load point position
coords = np.vstack((inFile.x, inFile.y, inFile.z)).transpose()
scale = np.array(inFile.header.scale)
offset = np.array(inFile.header.offset) # there is no offset in simple.las example from laspy library
# offset = np.array([1000, 20000, 100000])  # just for testing that offset works

# geo.setPointFloatAttribValues("P", np.concatenate(coords))    # same as Lidar Import SOP - seems that it ignores scale (and offset?)
geo.setPointFloatAttribValues("P", np.concatenate(coords*scale+offset))

# --- load color
color = np.vstack((inFile.red, inFile.green, inFile.blue)).transpose()
geo.addAttrib(hou.attribType.Point, "Cd", (1.0,1.0,1.0), False, False)  # add color atttribute
geo.setPointFloatAttribValues("Cd", np.concatenate(color / 255.0)) # transform from 1-255 to 0.0-1.0 range)

Единственное, что пока не работает, это inFile.classifications == x Это вызывает сбой Houdini.

1 Ответ

0 голосов
/ 11 июля 2020

Петр из Odforce закончил Импортер LiDAR. https://forums.odforce.net/topic/46475-custom-lidar-importer-with-python/

Для загрузки и чтения точек:

from laspy.file import File
node = hou.pwd()
geo = node.geometry()
geo.createPoint()   # dummy point for point generate

classification = hou.evalParm("classification")
file_path = hou.evalParm("lidar_file")
inFile = File(file_path, mode='r')
# store how many points lidar attribute has
geo.addAttrib(hou.attribType.Global, "nb_of_points", 0, False, False)
geo.setGlobalAttribValue("nb_of_points", len(inFile.points[inFile.Classification == classification]))

# store file path
geo.addAttrib(hou.attribType.Global, "file_path", "", False, False)
geo.setGlobalAttribValue("file_path", file_path)

# store classification
geo.addAttrib(hou.attribType.Global, "classification", 0, False, False)
geo.setGlobalAttribValue("classification", classification)

# find availible information
pointformat = inFile.point_format
for spec in inFile.point_format:
    print(spec.name)

и для загрузки атрибутов:

from laspy.file import File
import numpy as np

node = hou.pwd()
geo = node.geometry()

file_path = geo.attribValue("file_path")
inFile = File(file_path, mode='r')
classification = geo.attribValue("classification")

selection = inFile.Classification == classification
points = inFile.points[selection]



# --- load point position
coords = np.vstack((inFile.x, inFile.y, inFile.z)).transpose()
scale = np.array(inFile.header.scale)
offset = np.array(inFile.header.offset) # there is no offset in simple.las example from laspy library
# offset = np.array([1000, 20000, 100000])  # just for testing that offset works

# geo.setPointFloatAttribValues("P", np.concatenate(coords))    # same as Lidar Import SOP - seems that it ignores scale (and offset?)
geo.setPointFloatAttribValues("P", np.concatenate(coords[selection]*scale+offset))

# --- load color
missing_color = ["red", "green", "blue"]
for spec in inFile.point_format:
    if spec.name in missing_color:
        missing_color.remove(spec.name)

if not missing_color:       
    color = np.vstack((inFile.red, inFile.green, inFile.blue)).transpose()
    geo.addAttrib(hou.attribType.Point, "Cd", (1.0,1.0,1.0), False, False)  # add color atttribute
    geo.setPointFloatAttribValues("Cd", np.concatenate(color[selection] / 255.0)) # transform from 1-255 to 0.0-1.0 range)

# --- load intensity
geo.addAttrib(hou.attribType.Point, "intensity", 0.0, False, False)  # add intensity atttribute
geo.setPointFloatAttribValues("intensity", inFile.intensity[selection] / 512.0) # transform from 1-255 to 0.0-1.0 range)
...