将直接标签添加到 geom_smooth 而不是 geom_line
Add directlabels to geom_smooth rather than geom_line
我知道这个问题与 this one 非常相似,但那里的解决方案不再有效(使用 method="last.qp"
),所以我再问一次。
基本问题是我想使用 directlabels
(或等同物)来标记每个组(来自 stat_smooth()
)的平滑均值,而不是实际数据。下面的示例显示了我所得到的最接近的结果,但标签无法识别分组,甚至无法识别平滑线。相反,我在最后一点得到了标签。我想要的是每条平滑线末尾颜色协调的文本,而不是图右侧的图例。
这是一个例子:
library(ggplot2)
library(directlabels)
## Data
set.seed(10)
d <- data.frame(x=seq(1,100,1), y=rnorm(100, 3, 0.5))
d$z <- ifelse(d$y>3,1,0)
## Plot
p <- ggplot(d, aes(x=x, y=y, colour=as.factor(z))) +
stat_smooth(inherit.aes=T, se=F, span=0.8, show.legend = T) +
geom_line(colour="grey50") +
scale_x_continuous(limits=c(0,110)) +
geom_dl(label="text", method="maxvar.points", inherit.aes=T)
p
这使得这个情节:
你需要告诉 geom_dl
你想在情节中出现什么。下面的代码应该可以简单地满足您的需求;
p <- ggplot(d, aes(x=x, y=y, colour=as.factor(z))) +
stat_smooth(inherit.aes=T, se=F, span=0.8, method = "loess", show.legend = F) +
geom_line(colour="grey50") +
scale_x_continuous(limits=c(0,110)) +
geom_dl(label=as.factor(d$z), method="maxvar.points", inherit.aes=T)
如果你想要不同的文本而不是 0
和 1
你只需要根据 d$z
来制作它而不是 as.factor(d$z)
.
为了将标签放在 geom_smooth
的最后一个点旁边而不是最后一个数据点,我在 geom_dl
中找不到任何方法可以这样做,因此想出了一个解决方法:
p <- ggplot(d, aes(x=x, y=y, colour=as.factor(z))) +
stat_smooth(inherit.aes=T, aes(label=as.factor(z)), se=F,
span=0.8, method = "loess", show.legend = F) +
geom_line(colour="grey50") +
scale_x_continuous(limits=c(0,110))
library(data.table)
smooth_dat <- setDT(ggplot_build(p)$data[[1]])
smooth_lab <- smooth_dat[smooth_dat[, .I[x == max(x)], by=group]$V1]
p + annotate("text", x = smooth_lab$x, y=smooth_lab$y,
label=smooth_lab$label,colour=smooth_lab$colour,
hjust=-1)
基于this answer
使用ggrepel
包的解决方案
library(tidyverse)
library(ggrepel)
set.seed(123456789)
d <- data.frame(x = seq(1, 100, 1), y = rnorm(100, 3, 0.5))
d$z <- ifelse(d$y > 3, 1, 0)
labelInfo <-
split(d, d$z) %>%
lapply(function(t) {
data.frame(
predAtMax = loess(y ~ x, span = 0.8, data = t) %>%
predict(newdata = data.frame(x = max(t$x)))
, max = max(t$x)
)}) %>%
bind_rows
labelInfo$label = levels(factor(d$z))
labelInfo
#> predAtMax max label
#> 1 2.538433 99 0
#> 2 3.293859 100 1
ggplot(d, aes(x = x, y = y, color = factor(z))) +
geom_point(shape = 1) +
geom_line(colour = "grey50") +
stat_smooth(inherit.aes = TRUE, se = FALSE, span = 0.8, show.legend = TRUE) +
geom_label_repel(data = labelInfo,
aes(x = max, y = predAtMax,
label = label,
color = label),
nudge_x = 5) +
theme_classic()
#> `geom_smooth()` using method = 'loess' and formula 'y ~ x'
由 reprex package (v0.2.0) 创建于 2018-06-11。
我知道这个问题与 this one 非常相似,但那里的解决方案不再有效(使用 method="last.qp"
),所以我再问一次。
基本问题是我想使用 directlabels
(或等同物)来标记每个组(来自 stat_smooth()
)的平滑均值,而不是实际数据。下面的示例显示了我所得到的最接近的结果,但标签无法识别分组,甚至无法识别平滑线。相反,我在最后一点得到了标签。我想要的是每条平滑线末尾颜色协调的文本,而不是图右侧的图例。
这是一个例子:
library(ggplot2)
library(directlabels)
## Data
set.seed(10)
d <- data.frame(x=seq(1,100,1), y=rnorm(100, 3, 0.5))
d$z <- ifelse(d$y>3,1,0)
## Plot
p <- ggplot(d, aes(x=x, y=y, colour=as.factor(z))) +
stat_smooth(inherit.aes=T, se=F, span=0.8, show.legend = T) +
geom_line(colour="grey50") +
scale_x_continuous(limits=c(0,110)) +
geom_dl(label="text", method="maxvar.points", inherit.aes=T)
p
这使得这个情节:
你需要告诉 geom_dl
你想在情节中出现什么。下面的代码应该可以简单地满足您的需求;
p <- ggplot(d, aes(x=x, y=y, colour=as.factor(z))) +
stat_smooth(inherit.aes=T, se=F, span=0.8, method = "loess", show.legend = F) +
geom_line(colour="grey50") +
scale_x_continuous(limits=c(0,110)) +
geom_dl(label=as.factor(d$z), method="maxvar.points", inherit.aes=T)
如果你想要不同的文本而不是 0
和 1
你只需要根据 d$z
来制作它而不是 as.factor(d$z)
.
为了将标签放在 geom_smooth
的最后一个点旁边而不是最后一个数据点,我在 geom_dl
中找不到任何方法可以这样做,因此想出了一个解决方法:
p <- ggplot(d, aes(x=x, y=y, colour=as.factor(z))) +
stat_smooth(inherit.aes=T, aes(label=as.factor(z)), se=F,
span=0.8, method = "loess", show.legend = F) +
geom_line(colour="grey50") +
scale_x_continuous(limits=c(0,110))
library(data.table)
smooth_dat <- setDT(ggplot_build(p)$data[[1]])
smooth_lab <- smooth_dat[smooth_dat[, .I[x == max(x)], by=group]$V1]
p + annotate("text", x = smooth_lab$x, y=smooth_lab$y,
label=smooth_lab$label,colour=smooth_lab$colour,
hjust=-1)
基于this answer
使用ggrepel
包的解决方案
library(tidyverse)
library(ggrepel)
set.seed(123456789)
d <- data.frame(x = seq(1, 100, 1), y = rnorm(100, 3, 0.5))
d$z <- ifelse(d$y > 3, 1, 0)
labelInfo <-
split(d, d$z) %>%
lapply(function(t) {
data.frame(
predAtMax = loess(y ~ x, span = 0.8, data = t) %>%
predict(newdata = data.frame(x = max(t$x)))
, max = max(t$x)
)}) %>%
bind_rows
labelInfo$label = levels(factor(d$z))
labelInfo
#> predAtMax max label
#> 1 2.538433 99 0
#> 2 3.293859 100 1
ggplot(d, aes(x = x, y = y, color = factor(z))) +
geom_point(shape = 1) +
geom_line(colour = "grey50") +
stat_smooth(inherit.aes = TRUE, se = FALSE, span = 0.8, show.legend = TRUE) +
geom_label_repel(data = labelInfo,
aes(x = max, y = predAtMax,
label = label,
color = label),
nudge_x = 5) +
theme_classic()
#> `geom_smooth()` using method = 'loess' and formula 'y ~ x'
由 reprex package (v0.2.0) 创建于 2018-06-11。