问题
I'm trying to replicate using ggplot2
, an earlier question i had using leaflet. I'm trying to merge two palettes where one is used if my variable is below a certain threshold and another if above a certain threshold. As I did with my leaflet
question my final plot doesn't seem to be correct. I also want to convert the factor legend to a continuous one. Example code:
library(sf)
library(leaflet)
library(RColorBrewer)
# preparing the shapefile
nc <- st_read(system.file("gpkg/nc.gpkg", package="sf"), quiet = TRUE) %>%
st_transform(st_crs(4326)) %>%
st_cast('POLYGON')
# Create 108 categories
mutate(nc, category = ntile(PERIMETER, n = 108)) -> nc
x <- sum(nc$PERIMETER < 1.3)
x # number of values below threshold = 21
### Create an asymmetric color range
## Make vector of colors for values smaller than 1.3 (21 colors)
rc1 <- colorRampPalette(colors = c("#006837", "#1A9850"), space = "Lab")(x) #21
## Make vector of colors for values larger than 1.3
rc2 <- colorRampPalette(colors = c("#FDAE61", "#A50026"), space = "Lab")(length(nc$PERIMETER) - x)
## Combine the two color palettes
rampcols <- c(rc1, rc2)
mypal <- colorFactor(palette = rampcols, domain = nc$category)
previewColors(colorNumeric(palette = rampcols, domain = NULL), values = 1:length(nc$PERIMETER))
nc %>%
ggplot() +
geom_sf(aes(fill = factor(category))) +
scale_fill_manual(values = mypal(nc$category), guide = FALSE)
gives this plot:
but the leaflet plot (correct coloring)
leaflet() %>%
addTiles() %>%
addPolygons(data = nc,
fillOpacity = 0.7,
fillColor = ~mypal(nc$category),
popup = paste("PERIMETER: ", nc$PERIMETER)) %>%
addLegend( pal = mypal, values = nc$category)
gives this correct plot:
You can see the ggplot
figure is not the same which I can't fix.
Additionally when I add a legend to the ggplot
, I get a factor legend for the new palette but I want a continuous one (even if the variable is a factor):
nc %>%
ggplot() +
geom_sf(aes(fill = factor(category))) +
scale_fill_manual(values = mypal(nc$category))
Would anyone know how to fix the coloring issue and alter the associated legend in continuous form? Thanks
回答1:
I think is caused by the use of factor()
, using the following code:
nc %>%
ggplot() +
geom_sf(aes(fill = factor(category))) +
scale_fill_manual(values = mypal(levels(factor(nc$category))), guide = FALSE)
gives you a map with the same coloring as leaflet does.
回答2:
For anyone coming to this, the closest answer I could find was to use scales
package following this question instead of scale_fill_manual
. Using this approach, I no longer use mypal
but enter the colours manually at the cut point with the trick of putting in 1.299
instead of 1.3
(rescale(c(.999, 1.2999, 1.3, 3.640))
instead of rescale(c(.999, 1.2999, 1.3, 3.640))
)
library("scales")
range(nc$PERIMETER)
#[1] 0.999 3.640
nc %>%
ggplot() +
geom_sf(aes(fill = PERIMETER)) +
scale_fill_gradientn(colours = c("#006837", "#1A9850", "#FDAE61", "#A50026"),
values = rescale(c(.999, 1.2999, 1.3, 3.640))
#guide = "colorbar"
#limits=c(-.1,.3)
)
giving:
来源:https://stackoverflow.com/questions/60327158/merging-palette-colors-colorramppalette-and-plotting-with-ggplot