Search code examples
rplotaxis-labels

X-Y Axis Formatting in R


I am trying to plot a graph and format the y-axis such that the numbers have proper spacing (5,000 apart) and are formatted to have commas (eg 350,000). Also I am trying to get the x-axis (the date) to show more refinement such that I have more dates on the x-axis for the viewer to see. Every time I plot the graph I get numbers on the x-axis, not dates.

This is what I have so far

plot(date,sales,type="s",ylab="Sales",yaxt="n")
axis(1, at = seq(min(date), max(date), length.out = 1)
axis(2, at = seq(min(sales), max(sales), length.out = 20), labels = formatC(seq(min(revenue), max(revenue), length.out = 20),small.mark = " ", format = "d"), las = 2)

Here is the data I am using:

sales <- c(76103, 57300, 49875, 52113, 47891, 43531, 50909, 54182, 55884, 
63780, 57165, 59841, 65952, 67602, 70693, 76375, 83365, 82051, 
88568, 100717, 99344, 88980, 99034, 99593, 110497, 87223, 98350, 
102337, 116642, 116854, 138072, 137737, 84696, 64028, 74457, 
82260, 89841, 90251, 92486, 95298, 105186, 114004, 125486, 125330, 
121609, 124053, 127363, 115706, 115173, 108807, 106469, 112372, 
110860, 106773, 111647, 107490, 86029, 67618, 74113, 67344)

date <- structure(c(11292, 11382, 11474, 11566, 11657, 11747, 11839, 
11931, 12022, 12112, 12204, 12296, 12387, 12478, 12570, 12662, 
12753, 12843, 12935, 13027, 13118, 13208, 13300, 13392, 13483, 
13573, 13665, 13757, 13848, 13939, 14031, 14123, 14214, 14304, 
14396, 14488, 14579, 14669, 14761, 14853, 14944, 15034, 15126, 
15218, 15309, 15400, 15492, 15584, 15675, 15765, 15857, 15949, 
16040, 16130, 16222, 16314, 16405, 16495, 16587, 16679), class = "Date")

Solution

  • Unless your plot is enormous (much bigger than your screen), the number of labels you're asking for will be unreadable, because they'll overlay each other. Following the spirit of what you're asking for (y-ticks every 5000, commas in y labels, more x labels that make sense):

    # enlarge left margin to accommodate transposed labels
    par(mar = c(5.1, 6.1, 2.1, 2.1))
    
    # a sequence for tick marks
    y_seq <- seq((min(sales) %/% 5000) * 5000, 
                (max(sales) %/% 5000 + 1) * 5000,
                by = 5000)
    
    # a sequence for labels
    y_labs <- prettyNum(y_seq, big.mark = ',')
    y_labs[seq(1, length(y_labs), 2)] <- NA
    
    plot(date, sales, type="s", ylab=NA, xaxt = 'n', yaxt = 'n')
    
    # `axis.Date` makes sequencing and formatting easy; adapt as you like
    axis.Date(1, date, at = seq.Date(min(date), max(date), by = 'year'), format = '%Y')
    axis(2, at = y_seq, labels = y_labs, las = 2)
    
    # add y label in a readable location
    title(ylab = 'Sales', mgp = c(4.5, 1, 0))
    

    which produces plot with fixed axis labels

    If you want more labels, the approach is pretty customizable from here.

    One last point: While you can always fight base R graphics until they do what you want, sometimes the fight isn't worth it when ggplot2 has much better defaults.

    Just two lines:

    library(ggplot2)
    qplot(date, sales, geom = 'step')
    

    makes

    ggplot version