I'm trying to use vegan package in R to create NMDS plots for my research. I'm having problems placing the legend in the correct area, however. The legend always covers some of the points and gets cut off by the outline of the plot. Anyone have any ideas of how I could format the legend outside of the plot area, or move it so that it doesn't cover up any points?
Here is an exported image of what my graph looks like now, with part of the legend missing and covering up some points.
Here is the script I've been using:
op <- ordiplot(nmds, type = 'n')
cols = c('darkred', 'darkgreen', 'darkblue', 'yellow', 'pink', 'lightgreen', 'lightblue', 'black')
points(nmds, cex = 2, pch = 16, col = cols[coral_ENV$Year])
ordispider(nmds, groups = coral_ENV$Year, label = TRUE, label.size = 0.2)
ordihull(nmds, groups = coral_ENV$Year, lty = 'dotted')
legend("topleft", inset = 0.03, pch = 16, col = cols, text.width = 0.05, legend = levels(coral_ENV$Year))
I'm pretty new to R so I'd appreciate any help!
Related
having issues getting three ellipses colors to show up. I am seeing all three shapes, but missing a color.
Also, I have two labels that I hope to delete. They could remain as points, but they aren't needed for the visual.
Here's my code-
#ordinate, nmds with bray-curtis distances
camord <- metaMDS(freq, distance = "bray", autotransform = FALSE)
#plotting ordination
ordiplot(camord, display='species')
ordilabel(camord, display="species",font=3, col = "black", cex = 0.5)
with(env, ordiellipse(camord, Habitat, col = as.numeric(envhab), lwd = 1.75))
legend("topright", legend = c(levels(envhab)), fill= as.numeric(factor(levels(envhab))))
I've been struggling with this for a day or two, tried a few things...
tried rearranging my CSV and using points...
points(camord, display = "species", label = colnames(camord)[1:11], cex = 0.5)
to just label the first 11 species.
Tried using text function... no labels again.
ordiplot(camord, display='species')
points(camord, display = "species", cex = 0.5)
with(env, ordiellipse(camord, Habitat, col = as.numeric(envhab), lwd = 2))
legend("topright", legend = c(levels(envhab)), fill= as.numeric(factor(levels(envhab))))
text(camord$species[1:11,1], camord$species[1:11,2], labels = colnames(camord)[1:11], cex = 0.5)
Many apologies as I am just beginning to learn. Any help or guidance would be appreciated.
Normally I provide some sample code for an reproducible example, but in this case it is a bit tricky. But I believe this question can be solved also without a reproduced example.
I have an image plot generated with the following code:
col <- c("red", "white", "blue") # set the color palette
image.plot(lon.list[[1]], lat.list[[1]], MK.list3[[6]][[8]],
main = paste0("Drought Index Trend \n", names(Index.list[[1]])[1]),
col = col,
xlab = "Longitude [°]",
ylab = "Latitude [°]",
legend.lab = "",
legend.line = 2.5,
zlim = c(-1,1))
plot(sf_object, add = T, border = "Black")
The resulting plot is the following:
I have a problem with the legend labels. Since there are only three values, -1, 0, 1, it is sufficient that only these values are displayed at the legend in the middle of each color.
So it should like this (the different colors don't matter):
Anybody with a hint how to achieve this?
Thanks to the comment of user20650, I found the solution. Here is the updated code which does what I want:
col <- c("red", "white", "blue") # set the color palette
image.plot(lon.list[[1]], lat.list[[1]], MK.list3[[6]][[8]],
main = names(Index.list[[1]])[8],
col = col,
xlab = "",
ylab = "",
legend.lab = "",
legend.line = 2.5,
zlim = c(-1,1),
axis.args = list(c(-1:1))) ### this is the new part ###
plot(sf_object, add = T, border = "Black")
Just a minor question. I am trying to make a legend for the following plot.
# fitting the linear model
iris_lm = lm(Petal.Length ~ Sepal.Length, data = iris)
summary(iris_lm)
# calculating the confidence interval for the fitted line
preds = predict(iris_lm, newdata = data.frame(Sepal.Length = seq(4,8,0.1)),
interval = "confidence")
# making the initial plot
par(family = "serif")
plot(Petal.Length ~ Sepal.Length, data = iris, col = "darkgrey",
family = "serif", las = 1, xlab = "Sepal Length", ylab = "Pedal Length")
# shading in the confidence interval
polygon(
c(seq(8,4,-0.1), seq(4,8,0.1)), # all of the necessary x values
c(rev(preds[,3]), preds[,2]), # all of the necessary y values
col = rgb(0.2745098, 0.5098039, 0.7058824, 0.4), # the color of the interval
border = NA # turning off the border
)
# adding the regression line
abline(iris_lm, col = "SteelBlue")
# adding a legend
legend("bottomright", legend = c("Fitted Values", "Confidence Interval"),
lty = c(1,0))
Here's the output so far:
My goal is to put a box in the legend next to the "Confidence Interval" tab, and color it in the same shade that it is in the picture. Naturally, I thought to use the pch parameter. However, when I re-run my code with the additional legend option pch = c(NA, 25), I get the following:
It is not super noticeable, but if you look closely at the padding on the left margin of the legend, it actually has decreased, and the edge of the border is now closer to the line than I would like. Is there any way to work around this?
That's a curious behavior in legend(). I'm sure someone will suggest a ggplot2 alternative. However, legend() does offer a solution. This solution calls the function without plotting anything to capture the dimensions of the desired rectangle. The legend is then plotted with the elements you really want but no enclosing box (bty = "n"). The desired rectangle is added explicitly. I assume you mean pch = 22 to get the filled box symbol. I added pt.cex = 2 to make it a bit larger.
# Capture the confidence interval color, reusable variables
myCol <- rgb(0.2745098, 0.5098039, 0.7058824, 0.4)
legText <- c("Fitted Values", "Confidence Interval")
# Picking it up from 'adding a legend'
ans <- legend("bottomright", lty = c(1,0), legend = legText, plot = F)
r <- ans$rect
legend("bottomright", lty = c(1,0), legend = legText, pch = c(NA,22),
pt.bg = myCol, col = c(1, 0), pt.cex = 2, bty = "n")
# Draw the desired box
rect(r$left, r$top - r$h, r$left + r$w, r$top)
By the way, I don't think this will work without further tweaking if you place the legend on the left side.
Is it possible to obtain the appropriate value of inset automatically so that the left corner of legend will always be just outside of the top right corner of plot?
In the plot below I had to try several values for inset manually. It would be nice to not have to do it manually since I have to make multiple plots.
graphics.off()
windows(width = 5, height = 5)
set.seed(42)
par(mar = c(5,5,1,10))
plot(rnorm(50,15,5), rnorm(50,15,3),
xlim = c(0,30), ylim = c(5,25),
pch = 19, col = c("red","blue"))
par(xpd = TRUE)
legend("topright", inset = c(-.80, 0),
pch = 19, col = c("red","blue"),
legend = c("LEGEND 1","Second Legend"))
After the plot call, before adding the legend, use par("usr")* to extract the coordinates of the plotting region.
Then, instead of positioning the legend using a 'keyword' and inset, use x and y with the top-right coordinates of the plotting region obtained from par("usr"). Adjust x with a suitable coefficient.
coord <- par("usr")
legend(x = coord[2] * 1.05, y = coord[4],
pch = 19, col = c("red", "blue"),
legend = c("LEGEND 1", "Second Legend"))
And just for fun, a more convoluted alternative.
After plotting, call legend with position topright, but without plotting it to the device (plot = FALSE), and assign it to an object.
Extract the left x and the top y coordinate of the legend box, and its width (see Value section in ?legend), to be used in x and y in legend:
leg <- legend("topright", pch = 19, col = c("red", "blue"),
legend = c("LEGEND 1", "Second Legend"),
plot = FALSE)
legend(x = (leg$rect$left + leg$rect$w) * 1.05, y = leg$rect$top,
pch = 19, col = c("red", "blue"),
legend = c("LEGEND 1", "Second Legend"))
*From ?par
usr A vector of the form c(x1, x2, y1, y2) giving the extremes of the user coordinates of the plotting region.
The position calculations that are made when inset parameter(s) have been specified, are in fact based on par("usr") (see line 188-199 in the legend code).
I have done a PCA in R and have graphed the results with a scatter plot.
I have 7 data variables and the last set of points come out as stock yellow. How can I make it so each set of points is a specific colour?
This is the code I have been using:
plot(clam.pca$x[,1], clam.pca$x[,2], pch = clam$Form.code,
col = clam$Form.code, cex = .8, lty = "solid", lwd = 1,
xlab = "Axis1", ylab = "Axis2", xlim = c(-0.2, 0.30))
Rory
You can't set the colour to a variable using the generic plotting functions. You have to manually set what colour you want as a vector. So for example:
x<-seq(1:10)
y<-seq(1:10)
cols<-ifelse(group=="a","red","green")
plot(x,y,col=cols)