Search code examples
rggplot2linespolar-coordinates

r - Using geom_segment with coord_polar


I want to do something similar to the answer in this post, but with geom_segment() instead of geom_path() because now I want to add arrows to my lines.

Setup:

example <- data.frame(r=c(5,4,3),theta=c(0.9,1.1,0.6))

is.linear.polar2 <- function(x) TRUE
coord_polar2 <- coord_polar(theta="y", start = 3/2*pi, direction=-1) 
class(coord_polar2) <- c("polar2", class(coord_polar2))

myplot <- ggplot(example, aes(r, theta)) + geom_point(size=3.5) +
  scale_x_continuous(breaks=seq(0,max(example$r)), lim=c(0, max(example$r))) + 
  scale_y_continuous(breaks=round(seq(0, 2*pi, by=pi/4),2), expand=c(0,0), lim=c(0,2*pi)) +
  geom_text(aes(label=rownames(example)), size=4.4, hjust=0.5, vjust=-1)

myplot + coord_polar2 + geom_path()

enter image description here

I want a plot that looks like this, but with arrows in the direction of the next point in the sequence.

These are my attempts:

myplot + coord_polar2 + 
geom_segment(data=example,aes(x=r, y=theta, xend=c(tail(r, n=-1), NA), 
                              yend=c(tail(theta, n=-1), NA)),
             arrow=arrow(length=unit(0.3,"cm"), type="closed"))

enter image description here

myplot + coord_polar(theta="y", start = 3/2*pi, direction=-1) + 
geom_segment(data=example,aes(x=r, y=theta, xend=c(tail(r, n=-1), NA), 
                              yend=c(tail(theta, n=-1), NA)),
             arrow=arrow(length=unit(0.3,"cm"), type="closed"))

enter image description here


Solution

  • Well, this solution is even hackier than the answer to your first question. Instead of using geom_segment I use geom_path, but this will produce only the last arrow, so we will add the group aesthetic to connect segments one by one. This means our original data frame has to be slightly modified:

    tweak_data <- function(df) 
    {
      if (nrow(df) == 1) return(df)
      idx_x2 <- c(1, rep(2:(nrow(df) - 1), each=2), nrow(df))
      gr <- rep(seq.int(nrow(df) - 1), each=2)
      df_res <- data.frame(r = df$r[idx_x2], theta = df$theta[idx_x2], 
                           label = rownames(df)[idx_x2], group = gr)
      df_res
    }
    
    example_tw <- tweak_data(example)
    myplot2 <- ggplot(example2, aes(r, theta)) + geom_point(size=3.5) +
      scale_x_continuous(breaks=seq(0,max(example$r)), lim=c(0, max(example$r))) + 
      scale_y_continuous(breaks=round(seq(0, 2*pi, by=pi/4), 2), 
                         expand=c(0, 0), lim=c(0, 2*pi)) +
      geom_text(aes(label=label), size=4.4, hjust=0.5, vjust=-1)
    myplot2 + coord_polar2 + 
      geom_path(aes(group=group), arrow=arrow(length=unit(0.3,"cm"), type="closed"))
    

    enter image description here