是否可以将geom_ribbon扩展为xlimits?

时间:2016-12-19 10:23:43

标签: r ggplot2

我有以下代码(作为示例)我想调整,使得功能区延伸到整个xrange,如geom_hline()所做的那样。功能区指示接受范围内的值。在我的实际应用程序中,有时没有上限或下限,因此hline本身不足以确定值是否在边界内。

library(ggplot2)
set.seed(2016-12-19)
dates <- seq(as.Date('2016-01-01'), as.Date('2016-12-31'), by = 1)
values <- rexp(length(dates), 1)
groups <- rpois(length(dates), 5)
temp <- data.frame(
    date = dates,
    value = values,
    group = groups,
    value.min = 0,
    value.max = 2
)
ggplot(temp, aes(date, value)) +
    geom_ribbon(aes(ymin = value.min, ymax = value.max), fill = '#00cc33', alpha = 0.6) +
    geom_hline(aes(yintercept = value.min)) +
    geom_hline(aes(yintercept = value.max)) +
    geom_point() +
    facet_wrap(~group)

我也尝试将x中的geom_ribbon设置为dates,但之后只会填充范围的一小部分。 我也尝试过这个:

geom_ribbon(aes(ymin = -Inf, ymax = 2, x = dates), data = data.frame(), fill = '#00cc33', alpha = 0.6)

然后数据似乎被覆盖整个情节,我得到错误Error in eval(expr, envir, enclos) : object 'value' not found。即使它能够工作,那么当xlimits扩展时,范围实际上仍然太窄。

2 个答案:

答案 0 :(得分:3)

这是一种方法:

ggplot(temp, aes(as.numeric(date), value)) +
  geom_rect(aes(xmin=-Inf, xmax=Inf, ymin = value.min, ymax = value.max), temp[!duplicated(temp$group),], fill = '#00cc33', alpha = 0.6) + 
  geom_hline(aes(yintercept = value.min)) +
  geom_hline(aes(yintercept = value.max)) +
  geom_point() +
  scale_x_continuous(labels = function(x) format(as.Date(x, origin = "1970-01-01"), "%b %y")) + 
  facet_wrap(~group)

enter image description here

请注意,我使用了as.numeric(date),否则Inf-Inf会产生

  

错误:输入无效:date_trans仅适用于类Date的对象

要获取数值的日期标签,我相应地调整了scale_x_continuous标签。 (虽然它们在这里并不精确。您可能希望使用确切的日期而不是月/年来调整它,或者使用breaks参数设置手动中断,例如seq.Date。)

另请注意,我使用temp[!duplicated(temp$group),]来避免过度绘图,从而保持所需的Alpha透明度。

答案 1 :(得分:1)

根据lukeA的回答,我制作了以下代码,我认为这个代码更简单:

library(ggplot2)
set.seed(2016-12-19)
dates <- seq(as.Date('2016-01-01'), as.Date('2016-12-31'), by = 1)
values <- rexp(length(dates), 1)
groups <- rpois(length(dates), 5)
temp <- data.frame(
    date = dates,
    value = values,
    group = groups,
    value.min = 1,
    value.max = 2
)
bounds <- data.frame(
    xmin = -Inf,
    xmax = Inf,
    ymin = temp$value.min[1],
    ymax = temp$value.max[1]
)
ggplot(temp, aes(date, value)) +
    geom_rect(
        aes(
            xmin = as.Date(xmin, origin = '1970-01-01'),
            xmax = as.Date(xmax, origin = '1970-01-01'),
            ymin = ymin,
            ymax = ymax
        ),
        data = bounds,
        fill = '#00cc33',
        alpha = 0.3,
        inherit.aes = FALSE
    ) +
    geom_point() +
    facet_wrap(~group)

我创建了一个包含矩形边界的临时数据框,并添加了inherit.aes = FALSE,因为显然边界否则会覆盖temp data.frame(对我来说似乎仍然是一个错误)。通过将-InfInf转换为正确的数据类型,我不需要自定义标签(如果您处理POSIXt使用正确的as.POSIXct/lt,则自动转换失败)。