I\'m having a bit of difficulty figuring out how to recreate the following graphic of a spider (or radar) chart, using plotly. Actually, I can\'t even recreate it in the most re
The options available with polar plots are still limited. There is not, so far as I can tell, any way to add text to a polar plot for the category labels around the circumference. Neither text scatter points, nor annotations nor tick labels (except at the four quarter points) are compatible with polar coordinates in plotly at the moment.
So, we need to get a little creative.
One type of polar coordinate system that does work nicely is a projected map of a sperical earth using an azimuthal projection. Here is a demonstration of how you might adapt that to this problem.
First, convert the values to plot into latitude and longitudes centred on the South pole:
scale <- 10 # multiply latitudes by a factor of 10 to scale plot to good size in initial view
d$lat <- scale*d$Proportion - 90
d$long <- (as.numeric(d$Response)-1) * 360/24
Plot using an azimuthal equidistant projection
p <- plot_ly(d[c(1:24,1,25:48,25),], lat=lat, lon=long, color = factor(Year), colors=c('#F8756B','#00BDC2'),
type = 'scattergeo', mode = 'lines+markers', showlegend=T) %>%
layout(geo = list(scope='world', showland=F, showcoastlines=F, showframe=F,
projection = list(type = 'azimuthal equidistant', rotation=list(lat=-90), scale=5)),
legend=list(x=0.7,y=0.85))
Put some labels on
p %<>% add_trace(type="scattergeo", mode = "text", lat=rep(scale*1.1-90,24), lon=long,
text=Response, showlegend=F, textfont=list(size=10)) %>%
add_trace(type="scattergeo", mode = "text", showlegend=F, textfont=list(size=12),
lat=seq(-90, -90+scale,length.out = 5), lon=rep(0,5),
text=c("","25%","50%","75%","100%"))
Finally, add grid lines
l1 <- list(width = 0.5, color = rgb(.5,.5,.5), dash = "3px")
l2 <- list(width = 0.5, color = rgb(.5,.5,.5))
for (i in c(0.1, 0.25, 0.5, 0.75, 1))
p <- add_trace(lat=rep(-90, 100)-scale*i, lon=seq(0,360, length.out=100), type='scattergeo', mode='lines', line=l1, showlegend=F, evaluate=T)
for (i in 1:24)
p <- add_trace(p,lat=c(-90+scale*0.1,-90+scale), lon=rep(i*360/24,2), type='scattergeo', mode='lines', line=l2, showlegend=F, evaluate=T)
Breaking changes in the updates to plotly mean that the original version no longer works without a few modifications to bring it up to date. here is an updated version:
library(data.table)
gridlines1 = data.table(lat = -90 + scale*(c(0.1, 0.25, 0.5, 0.75, 1)))
gridlines1 = gridlines1[, .(long = c(seq(0,360, length.out=100), NA)), by = lat]
gridlines1[is.na(long), lat := NA]
gridlines2 = data.table(long = seq(0,360, length.out=25)[-1])
gridlines2 = gridlines2[, .(lat = c(NA, -90, -90+scale, NA)), by = long]
gridlines2[is.na(lat), long := NA]
text.labels = data.table(
lat=seq(-90, -90+scale,length.out = 5),
long = 0,
text=c("","25%","50%","75%","100%"))
p = plot_ly() %>%
add_trace(type="scattergeo", data = d[c(1:24, 1, 25:48, 25),],
lat=~lat, lon=~long,
color = factor(d[c(1:24, 1, 25:48, 25),]$Year),
mode = 'lines+markers')%>%
layout(geo = list(scope='world', showland=F, showcoastlines=F, showframe=F,
projection = list(type = 'azimuthal equidistant', rotation=list(lat=-90), scale=5)),
legend = list(x=0.7, y=0.85)) %>%
add_trace(data = gridlines1, lat=~lat, lon=~long,
type='scattergeo', mode='lines', line=l1,
showlegend=F, inherit = F) %>%
add_trace(data = gridlines2, lat=~lat, lon=~long,
type='scattergeo', mode='lines', line=l2, showlegend=F) %>%
add_trace(data = text.labels, lat=~lat, lon=~long,
type="scattergeo", mode = "text", text=~text, textfont = list(size = 12),
showlegend=F, inherit=F) %>%
add_trace(data = d, lat=-90+scale*1.2, lon=~long,
type="scattergeo", mode = "text", text=~Response, textfont = list(size = 10),
showlegend=F, inherit=F)
p