Lisp routine to obtain the lowest z value of all point cloud nodes within a selection

Lisp routine to obtain the lowest z value of all point cloud nodes within a selection

dlbsurveysuk
Collaborator Collaborator
3,300 Views
16 Replies
Message 1 of 17

Lisp routine to obtain the lowest z value of all point cloud nodes within a selection

dlbsurveysuk
Collaborator
Collaborator

Hi,

 

I'd like to be able to make a rectangular selection of a point cloud in the xy plane and extract the z-value of the point cloud node with the lowest z-value within that selection.

 

This would be very useful when adding ground levels to a drawing where there might be foliage/twigs/debris etc above or on the ground.

 

I already have a Lisp routine for picking a point cloud node and drawing a cross with the level value but this just picks the node nearest the picker, which might not be the lowest point within the selected area.

 

Any help much appreciated.

Thanks.

0 Likes
3,301 Views
16 Replies
Replies (16)
Message 2 of 17

ronjonp
Mentor
Mentor

Maybe post an example point cloud to test on.

0 Likes
Message 3 of 17

pbejse
Mentor
Mentor

@ronjonp wrote:

Maybe post an example point cloud to test on.


Was wondering about that, is it only accessible if you have RECAP installed? guessing it can also be imported to Civil3D? 

 

0 Likes
Message 4 of 17

dlbsurveysuk
Collaborator
Collaborator

Here is a Dropbox link to a small point cloud sample that has uneven ground with some small trees, clumps of foliage, and some debris on the ground.

 

My present workflow is to chop clouds up into small areas then clip them as near to ground as possible. I then enable the previously mentioned Lisp routine for adding a cross with level (with 3D object snap node enabled) and move the picker around while keeping an eye on the running z-value until I decide it's a good point and then click.

 

https://www.dropbox.com/sh/3nzf3qwuxq3g6kp/AABM8J0BpRp8Bdpntu4FmA0Ma?dl=0

0 Likes
Message 5 of 17

ronjonp
Mentor
Mentor

I've never messed with point clouds so I'm a bit intrigued 🙂

0 Likes
Message 6 of 17

dlbsurveysuk
Collaborator
Collaborator

The above point cloud is a recap pro file which can be attached directly to an Autocad drawing. It will attach at the co-ordinates in the 500,500,25 range that it has been controlled to.

0 Likes
Message 7 of 17

hak_vz
Advisor
Advisor

Try this

 

 

 

(defun c:pc_pt_with_min_z (/ pco)
(setq pco (vlax-ename->vla-object (car (entsel "\nSelect point cloud :"))))
(and (= "AcDbPointCloudEx"  (vla-get-objectname pco))(vla-getboundingbox pco 'minpt  'maxpt))
(setq p1 (vlax-safearray->list minpt))
)

 

 

 

Point with min z stored in global variable  p1. Z value should be minimal Z in pointcloud. This is not actual point with min z.

Miljenko Hatlak

EESignature

Did you find this post helpful? Feel free to Like this post.
Did your question get successfully answered? Then click on the ACCEPT SOLUTION button.
0 Likes
Message 8 of 17

hak_vz
Advisor
Advisor

@dlbsurveysuk 

Is it possible to obtain a good quality lidar aerial survey record of a mountainous area covered with deciduous forest

and  remove forest layer to retain only ground levels to create terrain model? Have you got any experience with this kind of work? 

Miljenko Hatlak

EESignature

Did you find this post helpful? Feel free to Like this post.
Did your question get successfully answered? Then click on the ACCEPT SOLUTION button.
0 Likes
Message 9 of 17

dlbsurveysuk
Collaborator
Collaborator

That sounds like an expensive undertaking and I'm afraid that kind of stuff is out of my league. I'm using a Leica BLK360 in combination with a Theodolite to survey small/medium Topo and buildings.

 

There are various software packages such as Leica Cloudworx, Virtual Surveyor etc. that can do this with a combination of lowest point of a selection (Smart Pick in Cloudworx) and interpolating between visible low points.

 

These software packages cost 1000s though and I'm running on a minimal budget with regards to point clouds using Register360, Recap Pro, and Autocad.

 

Any special survey drawing functions I use are achieved using Lisp routines.

 

Thanks for the code. I'm currently trying to figure out how to combine it with the code I use to pick a point and add a cross and level text. I'll let you know how I get on...

0 Likes
Message 10 of 17

ronjonp
Mentor
Mentor

Can you post the code you're currently using?

0 Likes
Message 11 of 17

hak_vz
Advisor
Advisor

If points from a part of a pointcloud can be extracted to some kind of txt file then working with them analyzing data could be done easy and autolisp can be used for it.

 

I have been testing with UK survey .asc files from https://environment.data.gov.uk/DefraDataDownload/?Mode=survey  Here in attachment is my code to to load .asc files to autocad , maybe you can find some use for it.

Works well with sets up to 300 000 points.

 

Thanks for info about lidar. It was one of ideas to present it to my client about terrain survey for future  aggregate exploitation. 

Miljenko Hatlak

EESignature

Did you find this post helpful? Feel free to Like this post.
Did your question get successfully answered? Then click on the ACCEPT SOLUTION button.
0 Likes
Message 12 of 17

dlbsurveysuk
Collaborator
Collaborator

You need to have a block called "CROSS" defined. I have a layer called "LTEXT" for all level text and a layer called "LX" for level crosses.

 

(defun C:LP (/ lyr txtSize osm3D pt ptXY ptXY2 zStr)
  ;;initial prep
;
  (setvar "cmdecho" 0)
  (setq lyr (getvar 'CLAYER))
  (setq txtSize (getvar "textsize"))
;
  ;;user select point
;
  (setq osm3D (getvar '3DOSMODE))
  (setvar '3DOSMODE 128)
  (initget 1) (setq pt (getpoint "\nSelect Point: "))
  (setvar '3DOSMODE osm3D)
;
  ;;prep for work
;
  (setq ptXY (list (car pt) (cadr pt)))
  (setq ptXY2 (list (car pt) (- (cadr pt) (* 2 txtSize))))
  (setq zStr (rtos (caddr pt) 2 2))
;
  ;;block/text creation
;
  (command "-LAYER" "M" "LX" "")
  (command "-INSERT" "CROSS" "non" ptXY txtSize "" 0.0)
  (command "-LAYER" "M" "LTEXT" "")
  (command "TEXT" "non" ptXY2 "" 0.0 zStr)
;
  ;;finish up
;
  (setvar 'CLAYER lyr)
  (setvar 'CMDECHO 1)
  (princ)
);defun

 

0 Likes
Message 13 of 17

dlbsurveysuk
Collaborator
Collaborator

Your code seems to let me pick an entire point cloud, not a selection of that point cloud. It then returns the z-value corresponding to the lowest point of the bounding box, not the z-value of the lowest point within in the cloud.

 

I incorporated it into my code and the above seems to be the result I get.

 

PS I don't really know what I'm doing...

 

(defun c:LOW (/ pco p1 pt ptXY ptXY2 zStr)
;
  (setvar "cmdecho" 0)
  (setq lyr (getvar 'CLAYER))
  (setq txtSize (getvar "textsize"))
;
  (setq pco (vlax-ename->vla-object (car (entsel "\nSelect point cloud :"))))
  (and (= "AcDbPointCloudEx"  (vla-get-objectname pco))(vla-getboundingbox pco 'minpt  'maxpt))
  (setq p1 (vlax-safearray->list minpt))
;
  (setq pt(getpoint "Whereabouts...?"))
;
  (setq ptXY (list (car pt) (cadr pt)))
  (setq ptXY2 (list (car pt) (- (cadr pt) (* 2 txtSize))))
  (setq zStr (rtos (caddr p1) 2 2))
;
  (command "-LAYER" "M" "LX" "")
  (command "-INSERT" "CROSS" "non" ptXY txtSize "" 0.0)
  (command "-LAYER" "M" "LTEXT" "")
  (command "TEXT" "non" ptXY2 "" 0.0 zStr)
;
  (setvar 'CLAYER lyr)
  (setvar 'CMDECHO 1)
  (princ)
);defun

 

0 Likes
Message 14 of 17

hak_vz
Advisor
Advisor

@dlbsurveysuk 

 

This is definitively not a solution. I don't use Recap, but if you can extract part of a pointcloud you are working on it can be done with easy. Actually data can be filtered out from txt file without even loading PC in acad. Unfortunately there is no much options. Instead of picking points you would have to extract part of  a cloud to txt file, and process with lisp. Sorting points for min Z can be done during reading file and there is not need to create any object on the screen. That's the way I would tackle this problem. Sorry, I don't have much experience working with pointclouds.

 

 

Miljenko Hatlak

EESignature

Did you find this post helpful? Feel free to Like this post.
Did your question get successfully answered? Then click on the ACCEPT SOLUTION button.
0 Likes
Message 15 of 17

dlbsurveysuk
Collaborator
Collaborator

OK thanks for your help. You've given me some ideas for further research.

0 Likes
Message 16 of 17

samZZ9WW
Participant
Participant

Any joy with this?

0 Likes
Message 17 of 17

dlbsurveysuk
Collaborator
Collaborator

Not exactly, I abandoned the idea of any kind of automated picking of pointcloud points. I'm pretty sure you have to get involved with ObjectARX (or buy some additional software) and this is beyond my Lisp knowledge, plus I just haven't got the time. It's not a deal breaker for me.

 

If I ever do want to be sure of picking the lowest point of a point cloud I have written a Lisp routine where you can select a small portion of the cloud in plan view, by square or circle (eg. an area of ground with a lot of vegetation, but the scanner has penetrated to some extent) . Then the code auto opens a second viewport, flips this viewport by 90 degrees, and adjusts the point size for visibility. I can then continue to visually pick the lowest point on the second viewport and auto add a level cross and text on the original plan view. It then auto reverts everything to one view  with the point cloud uncropped to its previous state.

 

I've written a few combined routines for quickly going around a plan and adding floor levels, beam levels, sill and head levels etc. in the same way. Also, in Register 360 you can move around the panoramic photos and add "pick points", these can then be exported to a CSV file, then you can use a Lisp routine to read the CSV file and auto add multiple annotations of any kind you like.

 

I use a combination of all the above.

0 Likes