Adding a polar background to a ggplot without using polar coordinates - r

I'd like make a plot using cartesian coordinate system, but then have it overlaid on a polar plot background, like that produced by coord_polar. Panel.background from theme.R only has element_rect; Ideally I could use something like element_polar.
Any way to do this?
Simply using coord_polar doesn't work because I'm also plotting various other geoms that map idiosyncratically onto coord_polar (geom_ellispis from the ggforce package, for example).
Reproducible example code:
library(ggplot2)
library(ggforce) # NB this is the github version #install_github("thomasp85/ggforce"). Includes 'geom_ellipsis'
#### Make example data
r<-runif(50,-100,100) # radial coordinates
theta<-runif(50,0,2) # theta
a<-runif(50,1,20)
b<-runif(50,1,20)
# Convert r and theta to cartesian:
x<-r*cos(theta*pi) # x-coordinate of ellipse foci
y<-r*sin(theta*pi) # y-coordinate of ellipse foci
angle.random<-runif(50,min=0,max=2) # random angle for ellipsis rotation
df<-as.data.frame(cbind(r,theta,x,y,a,b,angle.random))
# Make plots
# Plot should look like this:
ggplot(df,aes(x,y))+
geom_point(aes(x,y))+
geom_ellipsis(data=df,aes(x0=x,y0=y,a=a,b=b,angle=angle.random,fill=T))
# But I want the panel background in polar coordinates (and auto-adjusing to scale), like this:
ggplot(df,aes(x,y))+
geom_point(aes(x,y))+
coord_polar()
# However, using geom_ellipsis (among other functions) has idiosyncratic effects in non-cartesian coordinate systems:
ggplot(df,aes(r,theta))+
geom_point(aes(x,y))+
geom_ellipsis(data=df,aes(x0=x,y0=y,a=a,b=b,angle=angle.random,fill=T))+
coord_polar()
I would like the polar background from the 3rd plot, with the un-distorted ellipses from the first plot. Is there any way to do this?

Related

How to plot colored circles knowing X/Y coordinates, radius and a continuous 3rd parameter in R

In a telecommunication project I have a data basis of a list of antennas with their XY coordinates, emission radius and frequencies. I would like to represent with circles the covered area of each antennas, with a specific color depending on the frequency.
Ive been looking for libraries, but I'm very new to R and programmation in general, and I don't find any easy and simple ones. What would you recommend ?
Thank you for any help
You can do it with ggplot2 and ggforce package, like this:
# First generate a sample data
data <- data.frame(x=rnorm(50),y=rnorm(50),radius = rnorm(50,sd=0.1),freq = factor(1:5,levels=1:5))
# Load the package
library(ggplot2)
library(ggforce)
# Plot
ggplot(data=data,aes(x0=x,y0=y,col=freq,r=radius)) + geom_circle() +
coord_fixed()

Getting "npc" coordinates of ggplot2 grob

The grid package used for generating graphics in the R language uses so-called "normal parent coordinates" (npc) to position graphical objects ("grobs").
Is it possible to get the npc coordinates of a ggplot2 grob?
This would be of major help for drawing lines (for connecting data points) across facets (ggplot, drawing line between points across facets contains a solution, but this is very hard to follow for beginners)
library(ggplot2)
library(grid)
# Generate some sample data
df <- data.frame(y=c(1,2,3),x=1,Set=LETTERS[1:3])
# Plot
ggplot(df,aes(x,y)) +
geom_point(aes(fill=Set),color="black",shape=21,size=3) +
facet_grid(~Set)
# It is easy to list the grobs, but I can't see their npc coordinates
grid.ls(grid.force())

How to make a ggplot2 contour plot analogue to lattice:filled.contour()?

I've been learning ggplot2, and hope to use it for all my R graphing. However, I've yet to find a way to make a contour plot that looks analogous to a conventional contour plot, like what can be obtained using lattice:filled.contour(). For example:
#define data
x<-seq(1,11,1)
y<-seq(1,11,1)
xyz.func<-function(x,y) {-10.4+6.53*x+6.53*y-0.167*x^2-0.167*y^2+0.0500*x*y}
#contour plot using lattice graphics and R Color Brewer
library(lattice) #for filled.contour()
library(RColorBrewer) #for brewer.pal()
z.lattice<-outer(x,y,xyz.func)
filled.contour(x,y,z.lattice,nlevels=6,col=brewer.pal(6,"YlOrRd"))
This gives me a nice contour plot.
Now, let's try the same thing in ggplot2. The best I can come up with, based on everything I've read (particularly Drawing labels on flat section of contour lines in ggplot2) is:
#contour plot using ggplot2
library(ggplot2)
library(reshape2) #for melt()
z.molten<-melt(z.lattice)
names(z.molten) <- c("x", "y", "z")
v<-ggplot(z.molten, aes(x,y,z=z))+
geom_tile(aes(fill=z))+
stat_contour(bins=6,aes(x,y,z=z), color="black", size=0.6)+
scale_fill_gradientn(colours=brewer.pal(6,"YlOrRd"))
v
This graph has the same basic idea as filled.contour(), but the colored tiles don't conform to the contours very well.
I haven't been successful with changing the sizes of the tiles, either.
Any suggestions on how to make ggplot2's output closer to filled.contour()'s output?
The essence of your question, it seems, is how to produce a contour plot in ggplot with discrete filled contours, rather than continuous contours as you would get using the conventional geom_tile(...) approach. Here is one way.
x<-seq(1,11,.03) # note finer grid
y<-seq(1,11,.03)
xyz.func<-function(x,y) {-10.4+6.53*x+6.53*y-0.167*x^2-0.167*y^2+0.0500*x*y}
gg <- expand.grid(x=x,y=y)
gg$z <- with(gg,xyz.func(x,y)) # need long format for ggplot
library(ggplot2)
library(RColorBrewer) #for brewer.pal()
brks <- cut(gg$z,breaks=seq(0,100,len=6))
brks <- gsub(","," - ",brks,fixed=TRUE)
gg$brks <- gsub("\\(|\\]","",brks) # reformat guide labels
ggplot(gg,aes(x,y)) +
geom_tile(aes(fill=brks))+
scale_fill_manual("Z",values=brewer.pal(6,"YlOrRd"))+
scale_x_continuous(expand=c(0,0))+
scale_y_continuous(expand=c(0,0))+
coord_fixed()
The use of, e.g., scale_x_continuos(...) is just to get rid of the extra space ggplot puts around the axis limits; fine for most things but distracting in contour plots. The use of coord_fixed(...) is just to set the aspect ratio to 1:1. These are optional.

Add a curve to a log/log scatterplot

I have a scatterplot in a log/log space
plot(a,b,log="xy")
or in ggplot2
qplot(a,b,data="time",log="xy")
Now I would like to impose upon this scatter plot the curve f(x)=x*x+2. Butthe function woudl need to be plotted in the logarithmic space as well. How would I do this? Is there an way to do this in ggplot2?
As you guessed, curve is the command that you're looking for in base graphics.
#Make up some data
set.seed(0)
a <- 1:10
b <-(a^2+2)*exp(0.1*rnorm(10))
plot(a,b,log='xy')
curve(x^2+2,add=TRUE)
in ggplot2 world:
qplot(a,b,data=time)+stat_function(fun=function(x){x^2+2}) + coord_trans(xtrans = "log10",ytrans="log10")
from Plotting in R using stat_function on a logarithmic scale seems to do what you're after.

Making a wireframe plot from an x,y,z data.frame

I have a data.frame of x/y/z points. I know how to make a 3d scatterplot using the rgl package but I would like to connect each point in the scatterplot to make a wireframe or surface plot.
This code returns the scatter plot
library(rgl)
Data <- expand.grid(x=seq(0,10),y=seq(0,10))
Data$z <- Data$x^2+Data$y^2
plot3d(Data)
While this code returns a blank graph:
plot3d(Data,type='wire')
I can make the plot I want with lattice:
library(lattice)
wireframe(z~x+y,Data)
I can even make it rotate:
library(TeachingDemos)
rotate.wireframe(z~x+y,Data)
But I prefer rgl over lattice because it renders much quicker and lets you rotate the plot with the mouse.
Whats the proper way to make a wireframe plot in rgl?
The surface drawing plot function in rgl is persp3d and like base::persp, it needs a matrix as input to the z argument
zmat <- matrix(Data$z, 11,11)
persp3d(x=seq(0,10), y=seq(0,10), z=zmat)
I did spin this graphic a bit before capturing it with a screen grabbing program I use:

Resources