Say I have the following tibble:
df1 <- structure(list(var1 = structure(c("Didn't do a thing", "Almost did a thing",
"Once did a thing", "Have never done a thing", "Always do a thing"
), description = "This is the question i asked respondents (and the title of the plot)"),
wtd_pct = c(4L, 15L, 62L, 11L, 8L)), row.names = c(NA, -5L
), class = c("tbl_df", "tbl", "data.frame"))
I want to make a plot function that takes as inputs the name of the tibble (df1) and the name of a column inside it (in this case, there is only var1, but in my actual tibble I have many more columns).
Inside the plot function I want to pull out the attribute connected to var1 and make that the plot title. For example, outside a function this looks like this:
df1 %>%
ggplot(aes(y = var1, x = wtd_pct)) +
geom_col(aes(fill = var1)) +
geom_text(aes(label = paste0(round(wtd_pct, 0), "%")), size = 3.5, vjust = -.5, hjust = -.3, color = 'black') +
theme_minimal() + theme(legend.position = "none") +
labs(y = "",
x = "Weighted percent",
title = paste0("\"", str_wrap(attr(df1$var1, "description"), 100), "\""))
Note the title line above. However, when I put this inside a function and attempt to call it I get all sorts of errors. E.g.
plot_function <- function(.x, .y){
.x %>%
ggplot(aes(y = {{.y}}, x = wtd_pct)) +
geom_col(aes(fill = {{.y}})) +
geom_text(aes(label = paste0(round(wtd_pct, 0), "%")), size = 3.5, vjust = -.5, hjust = -.3, color = 'black') +
theme_minimal() + theme(legend.position = "none") +
labs(y = "",
x = "Weighted percent",
title = paste0("\"", str_wrap(attr({{.x$.y}}, "description"), 100), "\""))
}
plot_function(df1, var1)
This returns the plot but with no title + the error Warning message: Unknown or uninitialised column: .y.. I've tried various other things (wrapping in !!ensym(), .data[[]], extracting the attribute first into a separate string, etc., but I never get what I want.
It seems the crux of the issue is that you can't pipe df into attr(), but it also doesn't like the .x$.y syntax. Can anyone here point me in the right direction?

The
$operator uses non-standard evaluation without substituting, so.x$.ywill be interpreted as "the column called.yinsidedf1", which of course does not exist.The usual way round this is to use
[[instead of$, but this is a little trickier here because you want to pass an unquoted column name.One option is to use
.x[[deparse(substitute(.y))]](without the curly-curly operators)A pure tidyverse equivalent might be to use something like
in place of
.x[[deparse(substitute(.y))]]