我在这里使用@jan-glx 解释的 ndodge 函数; https://stackoverflow.com/a/60650595/13399047
我可能应该使用 theme(axis.ticks.length=) 但我不确定如何以偶数/奇数方式进行。
请帮忙!
我在这里使用@jan-glx 解释的 ndodge 函数; https://stackoverflow.com/a/60650595/13399047
我可能应该使用 theme(axis.ticks.length=) 但我不确定如何以偶数/奇数方式进行。
请帮忙!
据我所知,在 ggplot 中没有内置的方法可以做到这一点,尽管当他们重写指南系统时这可能会改变。
这既不漂亮也不容易,但这里有一个例子,你可以通过在 gtable / 网格中乱搞来做到这一点。
library(ggplot2)
library(grid)
data(diamonds)
diamonds$cut <- paste("Super Dee-Duper",as.character(diamonds$cut))
g <- ggplot(diamonds, aes(cut, carat)) +
geom_boxplot() +
scale_x_discrete(guide = guide_axis(n.dodge = 2))
# Convert to gtable
gt <- ggplotGrob(g)
# Grab bottom axis
is_axis <- grep("axis-b", gt$layout$name)
axisgrob <- gt$grobs[is_axis][[1]]
axis <- axisgrob$children$axis
# Grab tickmarks
is_ticks <- which(vapply(axis$grobs, inherits, logical(1), "polyline"))
ticks <- axis$grobs[[is_ticks]]
# Modify tickmarks
labelheight <- axis$heights[[2]] # First row of labels
modify <- which(seq_along(ticks$y) %% 4 == 0) - 1 # Change every the 3rd item in every quadruplet
ticks$y[modify] <- ticks$y[modify] - labelheight
# Insert ticks back into axis back into table
axis$grobs[[is_ticks]] <- ticks
axisgrob$children$axis <- axis
gt$grobs[[is_axis]] <- axisgrob
# Plot
grid.newpage()
grid.draw(gt)
由reprex 包(v0.3.0)于 2020-05-18 创建
这是一个只使用 ggplot2 东西而不修改任何 grobs 的解决方案。它需要 ggplot2 3.0.0 并且基于https://stackoverflow.com/a/51312611/6615512
library(ggplot2)
data(diamonds)
diamonds$cut <- paste("Super Dee-Duper",as.character(diamonds$cut))
tick_min_pos_odd = -0.6
tick_min_pos_even = -0.4
custom_ticks = data.frame(cut = sort(unique(diamonds$cut)))
n_discrete_x_values = nrow(custom_ticks)
# Alternate tick lengths
custom_ticks$tick_min_pos = ifelse(1:n_discrete_x_values %% 2 == 0, tick_min_pos_odd, tick_min_pos_even)
ggplot(diamonds, aes(cut, carat)) +
geom_boxplot() +
scale_x_discrete(guide = guide_axis(n.dodge = 2)) +
geom_linerange(data = custom_ticks, # The custom tickmarks
aes(x=cut, ymax=-0.25, ymin=tick_min_pos),
size=0.5, color='black',
inherit.aes = F) +
coord_cartesian(clip='off', ylim=c(0,NA)) + # Clip off makes it so the geoms can be drawn outside the plot
# ylim sets the y-axis from 0 to the max.
theme(plot.margin = margin(0,0,20,0), # Add some whitespace to the bottom of the plot
axis.title.x = element_text(vjust=-1.5), # nudge the x-axis title and text down a tad
axis.text.x = element_text(vjust=-1.5))