I am trying to draw a line with R's ggplot that starts on one facet and ends on another.
I believe this question was not asked yet (at least I could not find it) but I have found some example code that achieves exactly this: http://rstudio-pubs-static.s3.amazonaws.com/410976_f8eb6b218bfa42038a8b7bc9a6f9a193.html
However, documentation is weak and I did not manage to untangle the code.
Can someone please provide an easily understandable version that illustrates the trick?
Here's some code as an example:
library(ggplot2)
df <- data.frame(x = 1:6, y = 1:6, facet = c(rep('A', times = 3), rep('B', times = 3)))
gg <- ggplot(data = df, mapping = aes(x = x, y = y)) + facet_grid(~ facet) +
geom_line()
gg
line <- data.frame(x = 3, y = 3,
xend = 4, yend = 4,
facet = 'A')
gg_line <- gg + geom_segment(data = line, mapping = aes(x = x, y = y,
xend = xend, yend = yend),
inherit.aes = FALSE, color = 'red')
gg_line
Obviously, in gg_line, the red geom_segment reaches the respective coordinates in facet A.
However, I would like the end points to refer to the coordinates in facet B.
Any nudges to a working solution are highly appreciated!
Related
I have been searching for days for an answer but I could not find anything to help me out.
I have a large dataset with points defining longitude and latitude and a value. I wanted to plot them on a map with hexagons. The code I used for it was this:
ggplot(data = df, aes(lon, lat, group = value))+
geom_polygon(data = df.shp,aes(x=long, y=lat, group=group), fill = "grey", show.legend = FALSE)+
stat_summary_hex(bins = 50, binwidth = 0.5, aes(z = value), fun = "mean", colour = "black")+
xlim(-20,50)+
ylim(24,72)+
scale_fill_viridis(
option = "A",
breaks = c(0,1,2,3,4))
I used two files, the df.shp to create a background map and df with my point data. The result I get is this:
I like the way the map looks but it feels a bit too clustered. What I would like to do somehow is define a minimum threshold of points that have to be included in one of the hexagons to show a value and if that threshold is not met I would like the hexagon to not appear basically. Is there anyway this could be done?
If I understood correctly, you can change bins argument.
See example below with fake data
# Library
library(dplyr)
library(tidyr)
library(ggplot2)
library(hexbin)
# Fake data
set.seed(123)
df <- data.frame(x = rnorm(1000), y = rnorm(1000), z = rnorm(1000))
# Change bins = 5
ggplot(data = df, aes(x = x, y = y, z = z)) +
stat_summary_hex(bins = 5)
# Change bins = 30
ggplot(data = df, aes(x = x, y = y, z = z)) +
stat_summary_hex(bins = 30)
Created on 2022-12-10 with reprex v2.0.2
I've been trying to recreate some heatmaps from this, but my y ticks are quite far apart from the remainder of geom_tile.
Here is my code
library(tidyverse)
library(ggthemes)
library(viridis)
d <-c('Sunday','Monday','Tuesday','Wednesday','Thursday','Friday','Saturday')
days <- factor(d, levels = d,ordered=TRUE)
L = rnorm(7*24,0,20)
df <- data.frame(days,L) %>%arrange(days)
df['Time'] = c(0:23)
gg <- ggplot(data = df, aes(x = Time, y = days, fill = L))+
geom_tile(color = 'white',size = 0.1)+
scale_fill_viridis('')+
coord_equal()+
labs(x = NULL, y = NULL, title = 'Practice HeatMap')+
theme_tufte(base_family="Helvetica")+
theme(axis.ticks=element_blank())
print(gg)
and the resulting plot
Even using hjust wont move the labels closer. How can I achieve a cleaner look?
When mapping colour to lines in ggplot2, e.g.:
x = data.frame(x = 1:6, y = c(0,0,10,10,0,0))
ggplot(x, aes(x, y, col=y)) + geom_line(size=5)
.. the lines colours are mapped to the first data point of each line segment. Is there any easy way to get ggplot to calculate the mean value of both points instead (ie. so the sloping lines are both scaled to the colour for 5)?
Similar idea as #Richard, but use the zoo package.
library(zoo)
x = data.frame(x = 1:6, y = c(0,0,10,10,0,0))
ggplot(x, aes(x, y, col=rollmean(y, 2, fill = 0))) + geom_line(size=5)
Does this do what you want?
x = data.frame(x = 1:6, y = c(0,0,10,10,0,0))
x$c <- rowMeans(cbind(x$y, c(x$y[-1], NA)))
ggplot(x, aes(x, y, col=c)) + geom_line(size=5)
Using R's standard plot or better still GGPLOT,
is there a way to create a plot like this?
Note especially the horizontal lines across selected bar
with asterisk on top of it.
I don't know of an easy way to annotate graphs like this in ggplot2. Here's a relatively generic approach to make the data you'd need to plot. You can use a similar approach to annotate the relationships as necessary. I'll use the iris dataset as an example:
library(ggplot2)
library(plyr) #for summarizing data
#summarize average sepal length by species
dat <- ddply(iris, "Species", summarize, length = mean(Sepal.Length))
#Create the data you'll need to plot for the horizontal lines
horzlines <- data.frame(x = 1,
xend = seq_along(dat$Species)[-1],
y = seq(from = max(dat$length), by = 0.5, length.out = length(unique(dat$Species))-1),
yend = seq(from = max(dat$length), by = 0.5, length.out = length(unique(dat$Species))-1),
label = c("foo", "bar")
)
ggplot() +
geom_histogram(data = dat, aes(Species, length), stat = "identity") +
geom_segment(data = horzlines, aes(x = x, xend = xend, y = y, yend = yend)) +
geom_text(data = horzlines, aes(x = (x + xend)/2, y = y + .25, label = label))
Giving you something like this:
Let us say I have the following graph plotted using ggplot:
Is there anyway to extend how much line length is displayed in the legend? Sometimes, it just gets impossible to identify which line correspond to which line in the graph using the legend.
here is an option legend.key.width:
# sample data frame
df <- data.frame(x = c(rnorm(100, -3), rnorm(100), rnorm(100, 3)),
g = gl(3, 100))
df <- ddply(df, .(g), summarize, x = x, y = ecdf(x)(x))
ggplot(df, aes(x, y, colour = g, linetype = g)) +
geom_line() +
theme(legend.key.width = unit(10, "line"))
opts is not working with ggplot2. You need to use theme, so instead you need to type:
+ theme(legend.key.width = unit(10, "line"))