ChatGPT解决这个技术问题 Extra ChatGPT

Center Plot title in ggplot2

This simple code (and all my scripts from this morning) has started giving me an off center title in ggplot2:

Ubuntu version: 16.04

R studio version: Version 0.99.896

R version: 3.3.2

GGPLOT2 version: 2.2.0

I have freshly installed the above this morning to try and fix this...

dat <- data.frame(
time = factor(c("Lunch","Dinner"), levels=c("Lunch","Dinner")),
total_bill = c(14.89, 17.23)
)

# Add title, narrower bars, fill color, and change axis labels
ggplot(data=dat, aes(x=time, y=total_bill, fill=time)) + 
  geom_bar(colour="black", fill="#DD8888", width=.8, stat="identity") + 
  guides(fill=FALSE) +
  xlab("Time of day") + ylab("Total bill") +
  ggtitle("Average bill for 2 people")

https://i.stack.imgur.com/v3zNm.png

use ... + theme(plot.title = element_text(hjust = 0.5))

H
Henrik

From the release news of ggplot 2.2.0: "The main plot title is now left-aligned to better work better with a subtitle". See also the plot.title argument in ?theme: "left-aligned by default".

As pointed out by @J_F, you may add theme(plot.title = element_text(hjust = 0.5)) to center the title.

ggplot() +
  ggtitle("Default in 2.2.0 is left-aligned")

https://i.stack.imgur.com/gCbQz.png

ggplot() +
  ggtitle("Use theme(plot.title = element_text(hjust = 0.5)) to center") +
  theme(plot.title = element_text(hjust = 0.5))

https://i.stack.imgur.com/hziol.png


When I instead use ... theme(plot.title = element_text(hjust = 'center')) I get the error warning messages: 1: In unit(rep(xp, n), "npc") : NAs introduced by coercionv2: In validDetails.text(x) : NAs introduced by coercion and no title. Is this a bug?
@JamesHirschorn This is not a bug. The value used for hjust must be numeric.
as of ggplot2 version 3.3.0, the title is centred by default.
I have added this code theme(plot.title = element_text(hjust = 0.5)), but it didn't work out, it's weird.
@ahbon I realize this is really late but the order you put it into ggplot seems to matter. I had the same problem until I moved it down to the bottom of the cue in all the inputs to ggplot and then it worked.
C
Community

As stated in the answer by Henrik, titles are left-aligned by default starting with ggplot 2.2.0. Titles can be centered by adding this to the plot:

theme(plot.title = element_text(hjust = 0.5))

However, if you create many plots, it may be tedious to add this line everywhere. One could then also change the default behaviour of ggplot with

theme_update(plot.title = element_text(hjust = 0.5))

Once you have run this line, all plots created afterwards will use the theme setting plot.title = element_text(hjust = 0.5) as their default:

theme_update(plot.title = element_text(hjust = 0.5))
ggplot() + ggtitle("Default is now set to centered")

https://i.stack.imgur.com/bceGQ.png

To get back to the original ggplot2 default settings you can either restart the R session or choose the default theme with

theme_set(theme_gray())

T
Thomas Neitmann

The ggeasy package has a function called easy_center_title() to do just that. I find it much more appealing than theme(plot.title = element_text(hjust = 0.5)) and it's so much easier to remember.

ggplot(data = dat, aes(time, total_bill, fill = time)) + 
  geom_bar(colour = "black", fill = "#DD8888", width = .8, stat = "identity") + 
  guides(fill = FALSE) +
  xlab("Time of day") +
  ylab("Total bill") +
  ggtitle("Average bill for 2 people") +
  ggeasy::easy_center_title()

https://i.stack.imgur.com/FpAJI.png

Note that as of writing this answer you will need to install the development version of ggeasy from GitHub to use easy_center_title(). You can do so by running remotes::install_github("jonocarroll/ggeasy").


R
Rtist

If you are working a lot with graphs and ggplot, you might be tired to add the theme() each time. If you don't want to change the default theme as suggested earlier, you may find easier to create your own personal theme.

personal_theme = theme(plot.title = 
element_text(hjust = 0.5))

Say you have multiple graphs, p1, p2 and p3, just add personal_theme to them.

p1 + personal_theme
p2 + personal_theme
p3 + personal_theme

dat <- data.frame(
  time = factor(c("Lunch","Dinner"), 
levels=c("Lunch","Dinner")),
  total_bill = c(14.89, 17.23)
)
p1 = ggplot(data=dat, aes(x=time, y=total_bill, 
fill=time)) + 
  geom_bar(colour="black", fill="#DD8888", 
width=.8, stat="identity") + 
  guides(fill=FALSE) +
  xlab("Time of day") + ylab("Total bill") +
  ggtitle("Average bill for 2 people")

p1 + personal_theme