简体   繁体   中英

Plotting raster images using custom colours in R

This might sound like a strange process, but its the best I can think of to control rasterised colour gradients with respect to discrete objects (points, lines, polygons). I'm 95% there but can't quite plot correctly.

This should illustrate proof of concept:

require(raster)
r = matrix(56:255, ncol=20)         # reds
b = t(matrix(56:255, ncol=10))      # blues
col = matrix(rgb(r, 0, b, max=255), ncol=20) # matrix of colour strings
ras = raster(r)                     # data raster object
extent(ras) = extent(1,200,1,100)   # set extent for aspect
plot(ras, col = col, axes=F, asp=T) # overwrite data with custom colours

在此输入图像描述

Here I want to clip a raster to a triangle and create colour gradient of pixels inside based on their distances to one of the sides. Sorry for length but its the most minimal example I can design.

require(raster); require(reshape2); require(rgeos)
# equilateral triangle
t_s = 100                            # half side
t_h = floor(tan(pi*60/180) * t_s)    # height
corners = cbind(c(0, -t_s, t_s, 0), c(t_h, 0, 0, t_h))
trig = SpatialPolygons(list(Polygons(list(Polygon(corners)),"triangle")))

# line to measure pixel distances to
redline = SpatialLines(list(Lines(Line(corners[1:2,]), ID='redline')))
plot(trig); plot(redline, add=T, col='red', lwd=3)

在此输入图像描述

# create a blank raster and clip to triangle
r = raster(mat.or.vec(nc = t_s*2 + 1, nr = t_h))
extent(r) = extent(-t_s, t_s, 0, t_h)
r = mask(r, trig)
image(r, asp=T)

在此输入图像描述

# extract cell coordinates into d.f.
cells = as.data.frame(coordinates(rasterToPoints(r, spatial=T)))

# calculate distance of each pixel to redline with apply
dist_to_line = function(xy, line){
  point = readWKT(paste('POINT(', xy[1], xy[2], ')'))
  gDistance(point, line) / t_h
}

cells$dists = apply(cells, 1, dist_to_line, line=redline)
cells$cols = rgb(1 - cells$dists, 0, 0)
length(unique(cells$cols)) # count unique colours

# use custom colours to colour triangle pixels
image(r, col = cells$cols, asp=T)
plot(r, col = cells$cols, asp=T)

在此输入图像描述

As you can see the plotting fails to overwrite as in the first example, but the data seems fine. Trying to convert to matrix also fails:

# try convertying colours to matrix
col_ras = acast(cells, y~x, value.var='cols')
col_ras = apply(col_ras, 1, rev) # rotate acw to match r
plot(r, col = col_ras, asp=T)

Very grateful for any assistance on what's going wrong.


Edit:

To show Spacedman's plotRGB method:

b = brick(draster, 1-draster, 1-draster)
plotRGB(b, scale=1)
plot(trig, col=NA, border='white', lwd=5, add=T)

在此输入图像描述

Easy way is to go from your points to a spatial pixels data frame to a raster, then do the colour mapping...

Start with:

> head(cells)
           x     y        dists
1  0.0000000 172.5 0.0014463709
2  0.0000000 171.5 0.0043391128
3 -0.9950249 170.5 0.0022523089
4  0.0000000 170.5 0.0072318546
5  0.9950249 170.5 0.0122114004

convert:

> coordinates(cells)=~x+y
> draster = raster(as(cells,"SpatialPixelsDataFrame"))

colourise:

> cols=draster
> cols[!is.na(draster)]= rgb(1-draster[!is.na(draster)],0,0)
> plot(cols, col=cols)

在此输入图像描述

I'm not sure this is the right way to do things though, you might be better off creating an RGB raster stack and using plotRGB if you want fine colour control.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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