I'm wondering how I can add an mtext() or a text() that can say: Note: CG[10] stands for central gravity? (of course, [10] is the subscript of CG.)
I'm trying the following mtext() but can't get the desired outcome:
plot(1:10, ty="n", ann=F)
mtext("Note:", bquote(bold(CG[10])), side = 1, line = 1, adj = 0, cex = 1.2, font = 2)
Well, a simple way is to use expression and * sign to separate the subscripted from ordinary (i.e., non-subscripted) text. So, in my case, this will be:
mtext(expression("Note: "*bold(CG[10])*" stand for Central Gravity"), side = 1, line = -5, adj = 0, cex = 1.2, font = 2)
And the desired outcome is:
Related
I'm having trouble writing a particular expression in R that uses complex subscripts. The expression should look like this: $(A_{1,2,L}, A_{1,2,U})$
I have an expression that produces the correct subscripts (example below) but I'm unable to add the comma between the entries. Do I need to use substitute() or group()?
plot(NULL, xlim = c(0, 2), ylim = c(0,2))
text(x = 1, y = 1, label = expression((A["1,2,L"]~A["1,2,U"])))
Output of example without comma
You need to put the two expressions in a list list(expr1, expr2).
plot(NULL, xlim = c(0, 2), ylim = c(0,2))
text(x = 1, y = 1, label = expression((list(A["1, 2, L"] , A["1, 2, U"]))))
?par says this about mgp[1:3]:
The margin line (in mex units) for the axis title, axis labels and axis line. Note that mgp[1] affects title whereas mgp[2:3] affect axis. The default is c(3, 1, 0).
?axis says something similar. However, it seems that tick labels are not in general placed at line mgp[2], but rather at line mgp[2] + (mgp[3] %% 1). Thus, axis seems to behave as documented only when mgp[3] is an integer. Is this a bug in axis, or is something else going on?
Here is an example showing expected and actual output of axis for integer and noninteger mgp[3]:
par(mar = c(5, 1, 5, 1))
plot.new()
plot.window(xlim = c(0, 1), ylim = c(0, 1))
box(lty = 3)
## 'axis' puts line and labels in right place when 'mgp[3]' is integer
mgp_bottom <- c(0, 2.5, 1) # 'mgp[1]' is arbitrary
axis(side = 1, mgp = mgp_bottom)
mtext(c("labels", "line"), side = 1, line = mgp_bottom[2:3])
## 'axis' puts line in right place when 'mgp[3]' is noninteger,
## but apparently not labels
mgp_top <- mgp_bottom - c(0, 0, 1e-3)
axis(side = 3, mgp = mgp_top)
mtext(c("labels", "line"), side = 3, line = mgp_top[2:3])
mtext("LABELS", side = 3, line = mgp_top[2] + (mgp_top[3] %% 1))
This does look like a bug. I think it happens here: https://github.com/wch/r-source/blob/6e61247f042985d5cb9f09034cb9e694a69082e0/src/library/graphics/src/plot.c#L944-L948 . In this context, gpptr(dd)->mgp[2] is the value of par("mgp")[3], and is a double. Here it's converted to an int, which loses the fractional part.
I don't really understand what the intention is in this calculation, so I'm not sure that simply changing lineoff to a double wouldn't cause problems elsewhere.
This has been reported to R's bugzilla, in PR#18194, i.e.,
https://bugs.r-project.org/show_bug.cgi?id=18194
and fixed in the R sources, svn 80947, now.
I have been unable to find a way to adjust the (vertical) distance between plot and main title in R using par. In this example:
plot(1, 1, main = "Title")
I can adjust the position of the axis titles using:
par(mgp = c(2.5, 1, 0))
But I see no way to similarly adjust the main title. I am aware that more manual control is possible using title or mtext, but I assume that there is a way setting the title distance using par as well, which would be more elegant for my purposes.
We can use title() function with negative line value to bring down the title.
See this example:
plot(1, 1)
title("Title", line = -2)
To summarize and explain visually how it works. Code construction is as follows:
par(mar = c(3,2,2,1))
barplot(...all parameters...)
title("Title text", adj = 0.5, line = 0)
explanation:
par(mar = c(low, left, top, right)) - margins of the graph area.
title("text" - title text
adj = from left (0) to right (1) with anything in between: 0.1, 0.2, etc...
line = positive values move title text up, negative - down)
Try this:
par(adj = 0)
plot(1, 1, main = "Title")
or equivalent:
plot(1, 1, main = "Title", adj = 0)
adj = 0 produces left-justified text, 0.5 (the default) centered text and 1 right-justified text. Any value in [0, 1] is allowed.
However, the issue is that this will also change the position of the label of the x-axis and y-axis.
I was wondering if I could shift the non-numeric values (e.g., "Trivial" see R code below) up on my axis on side 4 such that each non-numeric value be exactly positioned between the current tickmarks (I need to keep the current tickmarks) on this particular axis?
Note: you see I have placed " " for the highest non-numeric axis value, this is because I don't need it (may be there is way that " " could be deleted).
Here is the R code:
curve(dnorm(x),-3,3,bty="n")
axis(side=4,at = c(0,.1, .2, .3,.4),labels = c("Trivial", "Anecdotal", "Substantial","Strong", " "),las=1)
If you want them exactly between the tick marks, it may be easiest to put specify their positions exactly with a second call to axis to plot the labels.
curve(dnorm(x), -3, 3, bty = "n")
axis(side = 4, at = c(0, .1, .2, .3, .4),
labels = FALSE) # don't generate labels
axis(side = 4,
at = c(0.05, 0.15, 0.25, 0.35), # put the labels half-way between
labels = c("Trivial", "Anecdotal", "Substantial","Strong"),
tick = FALSE, # don't plot the tick marks
las = 1)
I am having problems with aligning my subtitle in chart_Series.
At present it is just writing over the top of the x axis.
Also is it possible to switch off the text that is automatically written at the top of a
chart_Series chart so I can replace it with my own
library(quantmod)
getSymbols("SPY", from="2013-01-01", to=Sys.Date())
chart_Series(SPY)
title("S&P Index", sub = "text1\n\text2\ntext3",
cex.main = 2, font.main= 4, col.main= "blue",
cex.sub = 0.75, font.sub = 3, col.sub = "red")
I would be grateful for your help.
The 'quantmod' graphics are object-oriented. Data is stored in an environment (named 'Env') inside another environment (named whatever you name it, 'cspy' in this case). Special charting functions are stored with along with the data in a 'proto'-object. It is a more object-oriented approach than is used in either the S3 or S4 programming paradigms that are much more common in R. The 'proto'-package should be consulted for more details. After nosing around the code in chartSeries and the object it creates, I can get the labeling at the top to go away with this:
cspy <- chart_Series(SPY, name = NULL)
cspy$Env$actions[[4]] <- NULL
cspy
The 'quantmod' code has this:
cs$Env$name <- name
text.exp <- c(expression(text(1 - 1/3, 0.5, name, font = 2,
col = "#444444", offset = 0, cex = 1.1, pos = 4)),
expression(text(NROW(xdata[xsubset]),
0.5, paste(start(xdata[xsubset]), end(xdata[xsubset]),
sep = " / "), col = 1, adj = c(0, 0), pos = 2)))
cs$add(text.exp, env = cs$Env, expr = TRUE)
... but I wasn't able to figure out a name for that leaf so I looked at :
cspy$Env$actions
... and saw that the name and date-range were in the 4th item. so I just deleted it. (To get rid of only the name it is trivial: chart_Series(SPY, name = NULL). (I don't know if the location of that graphical item in the object will be consistent and I do not see a method for access that object-leaf, so this is possibly an unstable hack.)
To make room for the margin text (subtitle):
png("out.png")
myoma <- par("oma")
myoma[1] <- 3
par("oma" =myoma)
cspy
title("S&P Index", cex.main = 2, font.main= 4, col.main= "blue")
mtext(text= "text1\ntext2\ntext3", side=1, cex = 0.75, font = 3, col = "red",line=7)
dev.off()
I am not familiar with chart_Series plot from before. Normally I would have used the plotting parameter mar to increase the margin at the bottom of the plot, to make some more room for the sub-title. However, I didn't manage to increase the margin that way. Instead I had to use oma, to increase the outer margins of the plot. I added the sub-titles using mtext, instead of using the sub argument in title. You set the distance from the plot with line. The default chart_Series title is turned off by setting name = NULL. Please also note the 'Note' in ?chart_Series: "Highly experimental (read: alpha) use with caution.". Anyway,
par(oma = c(5, 0, 0, 0))
chart_Series(SPY, name = NULL)
title("S&P Index", cex.main = 2, font.main = 4, col.main = "blue")
mtext(text = "text1\n\text2\ntext3",
side = 1, line = 9, cex = 0.75, font = 3, col = "red")