简体   繁体   English

使用R和Lattice的XYZ图中的高程数据的颜色渐变

[英]Color gradient for elevation data in a XYZ plot with R and Lattice

I have a bunch of XYZ data where X and Y are coordinates and Z is supposed to be the elevation (LiDAR points). 我有一堆XYZ数据,其中X和Y是坐标,Z应该是高程(LiDAR点)。 I am trying to plot this point cloud with a gradient based on the Z value. 我试图用基于Z值的渐变来绘制这个点云。

Here is what I have so far: 这是我到目前为止:

# Read the CSV file with the LiDAR point cloud (which was conveniently converted to CSV)
myData <- read.csv("./52I212_plot10.las.csv")
# We don't need all attributes, let's keep only X, Y and Z.
myData <- subset(myData, select=c(X,Y,Z))
# We want a normalized version of Z (between 0 and 1)
myData$normalZ <- (myData$Z-min(myData$Z))/(max(myData$Z)-min(myData$Z))
str(myData)

With this I try to create the plot with 有了这个我尝试创建情节

library(lattice)
ramp <- colorRampPalette(c("lightblue", "red"))
cloud(myData$Z ~ myData$X + myData$Y, xlab="X", ylab="Y", zlab="Z",pch=20,
  col.point=ramp(10)[myData$normalZ*10]) 

I expected Z values to have one of ten possible colors between lightblue and red. 我希望Z值在浅蓝色和红色之间有十种可能的颜色之一。 XYZ图,不同颜色

When I change the plot command to 当我将plot命令更改为

cloud(myData$Z ~ myData$X + myData$Y, xlab="X", ylab="Y", zlab="Z",pch=20,
  col.point=gray(myData$normalZ))

I get something that is much closer to what I need: 我得到了一些更接近我需要的东西:

好多了!

I suspect I am doing something wrong on the color ramp, but cannot figure out what. 我怀疑我在颜色渐变上做错了什么,但无法弄清楚是什么。

thanks in advance 提前致谢

Rafael 拉斐尔

EDIT 编辑

This question: How to match vector values with colours from a colour ramp in R? 这个问题: 如何将矢量值与R中颜色渐变的颜色相匹配? helped me a lot, but I still don't understand what I did wrong. 帮助了我很多,但我仍然不明白我做错了什么。 This code works: 此代码有效:

myData$normalZ <- (myData$Z-min(myData$Z))/(max(myData$Z)-min(myData$Z))
ramp <- colorRamp(c("lightblue", "red"))
cols <- ramp(myData$normalZ)
cloud(myData$Z ~ myData$X + myData$Y, xlab="X", ylab="Y", zlab="Z",pch=20,
      col.point=rgb(cols,maxColorValue = 256))

啊哈!

Please point what could be changed on the original code to make it work -- I cannot figure out why in the first figure colors appear to be randomish. 请指出原始代码可以更改的内容使其工作 - 我无法弄清楚为什么在第一个图中颜色看起来是随机的。

thanks Rafael 谢谢拉斐尔

Can't confirm without data, but I think 0's are throwing you off. 没有数据就无法确认,但我认为0会让你失望。 Your normalZ is between 0 and 1, so 10 * normalZ is between 0 and 10. You're passing these non-integers to [ and they get rounded down. 你的normalZ介于0和1之间,所以10 * normalZ介于0和10之间。你将这些非整数传递给[并且它们向下舍入。 (I had to look this up, but from ?"[" : "Numeric values [of i] are coerced to integer as by as.integer (and hence truncated towards zero)". (我不得不查看它,但是来自?"[" :“数字值[of i]被强制转换为整数,因为as.integer(因此被截断为零)”。

Giving 0 (or anything less than 1) as a subset index messes with your color vector's length and hence how things match up: 0 (或任何小于1)作为子集索引会混淆颜色向量的长度,从而使事物匹配:

ramp(10)[c(0, 0.4, 0.8, 1.2, 1.6)]
# [1] "#ACD8E5" "#ACD8E5"

and then the too-short vector gets recycled. 然后太短的矢量被回收。 So, your code will probably work with 所以,你的代码可能会使用

col.point = ramp(10)[ceiling(myData$normalZ * 10)]

There's a small bug in the mapping of z-values to indices in the color ramp. 将z值映射到颜色渐变中的索引有一个小错误。

library(lattice)

N <- 500
myData <- data.frame(X = runif(N,0,30),
                     Y = runif(N,0,30),
                     Z = runif(N,0,300))

myData$normalZ <- (myData$Z-min(myData$Z))/(max(myData$Z)-min(myData$Z))

ramp <- colorRampPalette(c("lightblue", "red"))

cloud(myData$Z ~ myData$X + myData$Y, xlab="X", ylab="Y", zlab="Z",pch=20,
      col.point=ramp(10)[myData$normalZ*10])

Here myData$normalZ*10 maps Z-values in (0,1) onto color indices (0,10). 这里myData$normalZ*10将(0,1)中的Z值映射到颜色索引(0,10)。 (The floating point values get truncated to integers when indexing.) But ramp(10) only returns 10 (not 11) elements, and R vector indexing must start at 1 not 0, so for small Z-values NULL will be returned. (索引时浮点值会被截断为整数。)但是ramp(10)只返回10(而不是11)个元素,并且R向量索引必须从1开始而不是0,因此对于小的Z值,将返回NULL。 Both effects ruin correct color interpolation. 两种效果都会破坏正确的颜色插值。

The cloud then looks like this, with incorrect colouring along the Z-axis: 然后云看起来像这样,沿Z轴的颜色不正确:

在此输入图像描述

Correct interpolation like this 像这样正确插值

cloud(myData$Z ~ myData$X + myData$Y, xlab="X", ylab="Y", zlab="Z",pch=20,
      col.point=ramp(10)[myData$normalZ*9+1])

returns a result as expected: 按预期返回结果:

在此输入图像描述

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM