Trazar una leyenda fuera del área de trazado en gráficos base?
Como dice el título: ¿Cómo puedo trazar una leyenda fuera del área de trazado cuando uso gráficos base?
Pensé en juguetear con layout
y producir una parcela vacía para contener solo la leyenda, pero me interesaría una forma de usar solo las instalaciones del gráfico base y, por ejemplo, par(mar = )
para obtener algo de espacio a la derecha de la parcela para la leyenda.
Aquí un ejemplo:
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch = 2, lty = 2, type="o")
legend(1,-1,c("group A", "group B"), pch = c(1,2), lty = c(1,2))
Produce:
Pero como dije, me gustaría que la leyenda estar fuera del área de trazado (por ejemplo, a la derecha del gráfico/gráfico.
10 answers
Tal vez lo que necesita es par(xpd=TRUE)
para permitir que las cosas se dibujen fuera de la región de la trama. Así que si haces la trama principal con bty='L'
tendrás algo de espacio a la derecha para una leyenda. Normalmente esto se recortaría a la región de la trama, pero haga par(xpd=TRUE)
y con un poco de ajuste puede obtener una leyenda tan a la derecha como pueda ir:
set.seed(1) # just to get the same random numbers
par(xpd=FALSE) # this is usually the default
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2), bty='L')
# this legend gets clipped:
legend(2.8,0,c("group A", "group B"), pch = c(1,2), lty = c(1,2))
# so turn off clipping:
par(xpd=TRUE)
legend(2.8,-1,c("group A", "group B"), pch = c(1,2), lty = c(1,2))
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-09-12 15:04:18
Nadie ha mencionado el uso de valores negativos inset
para legend
. Aquí hay un ejemplo, donde la leyenda está a la derecha de la parcela, alineada a la parte superior (usando la palabra clave "topright"
).
# Random data to plot:
A <- data.frame(x=rnorm(100, 20, 2), y=rnorm(100, 20, 2))
B <- data.frame(x=rnorm(100, 21, 1), y=rnorm(100, 21, 1))
# Add extra space to right of plot area; change clipping to figure
par(mar=c(5.1, 4.1, 4.1, 8.1), xpd=TRUE)
# Plot both groups
plot(y ~ x, A, ylim=range(c(A$y, B$y)), xlim=range(c(A$x, B$x)), pch=1,
main="Scatter plot of two groups")
points(y ~ x, B, pch=3)
# Add legend to top right, outside plot region
legend("topright", inset=c(-0.2,0), legend=c("A","B"), pch=c(1,3), title="Group")
El primer valor de inset=c(-0.2,0)
podría necesitar un ajuste basado en el ancho de la leyenda.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2012-05-10 05:36:05
Otra solución, además de las ondes ya mencionadas (usando layout
o par(xpd=TRUE)
) es superponer su gráfico con un gráfico transparente sobre todo el dispositivo y luego agregar la leyenda a eso.
El truco es superponer un gráfico (vacío) sobre el área de trazado completa y agregar la leyenda a eso. Podemos usar la opción par(fig=...)
. Primero le indicamos a R que cree una nueva gráfica sobre todo el dispositivo de trazado:
par(fig=c(0, 1, 0, 1), oma=c(0, 0, 0, 0), mar=c(0, 0, 0, 0), new=TRUE)
Ajuste oma
y mar
es necesario ya que queremos tener el interior de la trama cubrir todo el dispositivo. new=TRUE
es necesario para evitar que R inicie un nuevo dispositivo. Luego podemos agregar el gráfico vacío:
plot(0, 0, type='n', bty='n', xaxt='n', yaxt='n')
Y estamos listos para agregar la leyenda:
legend("bottomright", ...)
Añadirá una leyenda en la parte inferior derecha del dispositivo. Asimismo, podemos añadir la leyenda al margen superior o derecho. Lo único que tenemos que asegurarnos es que el margen de la parcela original sea lo suficientemente grande como para acomodar la leyenda.
Poniendo todo esto en una función;
add_legend <- function(...) {
opar <- par(fig=c(0, 1, 0, 1), oma=c(0, 0, 0, 0),
mar=c(0, 0, 0, 0), new=TRUE)
on.exit(par(opar))
plot(0, 0, type='n', bty='n', xaxt='n', yaxt='n')
legend(...)
}
Y un ejemplo. Primero cree la trama asegurándose de que tenemos suficiente espacio en la parte inferior para agregar la leyenda:
par(mar = c(5, 4, 1.4, 0.2))
plot(rnorm(50), rnorm(50), col=c("steelblue", "indianred"), pch=20)
Luego agregue la leyenda
add_legend("topright", legend=c("Foo", "Bar"), pch=20,
col=c("steelblue", "indianred"),
horiz=TRUE, bty='n', cex=0.8)
Resultando en:
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-02-14 16:06:31
Lo siento por resucitar un viejo hilo, pero yo estaba con el mismo problema hoy. La forma más sencilla que he encontrado es la siguiente:
# Expand right side of clipping rect to make room for the legend
par(xpd=T, mar=par()$mar+c(0,0,0,6))
# Plot graph normally
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch = 2, lty = 2, type="o")
# Plot legend where you want
legend(3.2,1,c("group A", "group B"), pch = c(1,2), lty = c(1,2))
# Restore default clipping rect
par(mar=c(5, 4, 4, 2) + 0.1)
Se encuentra aquí: http://www.harding.edu/fmccown/R /
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2011-10-24 18:02:43
Me gusta hacerlo así:
par(oma=c(0, 0, 0, 5))
plot(1:3, rnorm(3), pch=1, lty=1, type="o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch=2, lty=2, type="o")
legend(par('usr')[2], par('usr')[4], bty='n', xpd=NA,
c("group A", "group B"), pch=c(1, 2), lty=c(1,2))
El único ajuste requerido es establecer el margen derecho para que sea lo suficientemente ancho como para acomodar la leyenda.
Sin embargo, esto también se puede automatizar:
dev.off() # to reset the graphics pars to defaults
par(mar=c(par('mar')[1:3], 0)) # optional, removes extraneous right inner margin space
plot.new()
l <- legend(0, 0, bty='n', c("group A", "group B"),
plot=FALSE, pch=c(1, 2), lty=c(1, 2))
# calculate right margin width in ndc
w <- grconvertX(l$rect$w, to='ndc') - grconvertX(0, to='ndc')
par(omd=c(0, 1-w, 0, 1))
plot(1:3, rnorm(3), pch=1, lty=1, type="o", ylim=c(-2, 2))
lines(1:3, rnorm(3), pch=2, lty=2, type="o")
legend(par('usr')[2], par('usr')[4], bty='n', xpd=NA,
c("group A", "group B"), pch=c(1, 2), lty=c(1, 2))
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-01-06 02:49:22
Solo puedo ofrecer un ejemplo de la solución de diseño ya señalada.
layout(matrix(c(1,2), nrow = 1), widths = c(0.7, 0.3))
par(mar = c(5, 4, 4, 2) + 0.1)
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch = 2, lty = 2, type="o")
par(mar = c(5, 0, 4, 2) + 0.1)
plot(1:3, rnorm(3), pch = 1, lty = 1, ylim=c(-2,2), type = "n", axes = FALSE, ann = FALSE)
legend(1, 1, c("group A", "group B"), pch = c(1,2), lty = c(1,2))
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-10-14 11:01:00
Recientemente encontré una función muy fácil e interesante para imprimir leyenda fuera del área de la parcela donde desea.
Hacer el margen exterior en el lado derecho de la parcela.
par(xpd=T, mar=par()$mar+c(0,0,0,5))
Crear un gráfico
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch = 2, lty = 2, type="o")
Agregue la leyenda y simplemente use la función locator(1) como se muestra a continuación. Entonces usted tiene que hacer clic en donde desee después de cargar el siguiente script.
legend(locator(1),c("group A", "group B"), pch = c(1,2), lty = c(1,2))
Pruébalo
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2017-12-11 02:40:24
Puede hacer esto con la API Plotly R, ya sea con código, o desde la GUI arrastrando la leyenda donde lo desee.
Aquí hay un ejemplo. El gráfico y el código también están aquí.
x = c(0,1,2,3,4,5,6,7,8)
y = c(0,3,6,4,5,2,3,5,4)
x2 = c(0,1,2,3,4,5,6,7,8)
y2 = c(0,4,7,8,3,6,3,3,4)
Puede colocar la leyenda fuera del gráfico asignando uno de los valores x e y a 100 o -100.
legendstyle = list("x"=100, "y"=1)
layoutstyle = list(legend=legendstyle)
Aquí están las otras opciones:
-
list("x" = 100, "y" = 0)
para el Exterior Inferior Derecho -
list("x" = 100, "y"= 1)
Fuera de la Parte superior Derecha -
list("x" = 100, "y" = .5)
Fuera del Centro Derecho -
list("x" = 0, "y" = -100)
Debajo de la izquierda -
list("x" = 0.5, "y" = -100)
En el centro -
list("x" = 1, "y" = -100)
A la derecha
Luego la respuesta.
response = p$plotly(x,y,x2,y2, kwargs=list(layout=layoutstyle));
Plotly devuelve una URL con su gráfico cuando realiza una llamada. Puede acceder a eso más rápidamente llamando a browseURL(response$url)
para que abra su gráfico en su navegador.
url = response$url
filename = response$filename
Eso nos da este gráfico. También puede mover la leyenda desde la interfaz gráfica de usuario y luego el gráfico se escalará consecuentemente. Estoy en el equipo de Complotly.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-01-20 21:20:14
Intente layout()
que he usado para esto en el pasado simplemente creando un gráfico vacío a continuación, correctamente escalado alrededor de 1/4 o así y colocando las partes de la leyenda manualmente en él.
Aquí hay algunas preguntas más antiguas sobre legend()
que deberían ayudarte a empezar.
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2010-10-14 10:17:27
Agregando otra alternativa simple que es bastante elegante en mi opinión.
Su parcela:
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch = 2, lty = 2, type="o")
Leyenda:
legend("bottomright", c("group A", "group B"), pch=c(1,2), lty=c(1,2),
inset=c(0,1), xpd=TRUE, horiz=TRUE, bty="n"
)
Resultado:
Aquí solo se agregó la segunda línea de la leyenda a su ejemplo. A su vez:
-
inset=c(0,1)
- mueve la leyenda por fracción de la región de la gráfica en las direcciones (x,y). En este caso la leyenda está en la posición"bottomright"
. Se mueve por 0 regiones de trazado en la dirección x (por lo que permanece en "derecha") y por 1 trazado región en dirección y (de abajo hacia arriba). Y sucede que aparece justo encima de la trama. -
xpd=TRUE
- vamos a la leyenda aparece fuera de la región de trazado. -
horiz=TRUE
- instruye para producir una leyenda horizontal. -
bty="n"
- un detalle de estilo para deshacerse del cuadro delimitador de leyenda.
Lo mismo se aplica al agregar leyenda al lado:
par(mar=c(5,4,2,6))
plot(1:3, rnorm(3), pch = 1, lty = 1, type = "o", ylim=c(-2,2))
lines(1:3, rnorm(3), pch = 2, lty = 2, type="o")
legend("topleft", c("group A", "group B"), pch=c(1,2), lty=c(1,2),
inset=c(1,0), xpd=TRUE, bty="n"
)
Aquí simplemente ajustamos las posiciones de la leyenda y agregamos espacio de margen adicional al lado derecho de la gráfica. Resultado:
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2018-03-26 22:00:05