Add Points to Image using Jpeg Device - r

I would like to add some points to an image I have created using image.plot. Here's my code with needed libraries. It places the .jpg in my working directory. Problem is my points are not showing up on the image. Any ideas not sure what I'm missing? Is it possible that the device is closing before points are added? Generic data is included below.
install.packages("RColorBrewer")
install.packages("fields")
library("RColorBrewer", lib.loc="...../R-2.15.2/library")
library("fields", lib.loc="...../R-2.15.2/library")
jpeg(paste("Steamflow", "timestep", ".jpg",sep = ''), width = 640,
height = 441,quality = 75)
image.plot(streamflux, zlim=c(-1,1), col=brewer.pal(11, "RdBu"),
yaxt="n", xaxt="n", main=paste("Stress Period ", "timestep", sep = ""))
points(WLX,WLY)
dev.off()
And here are datasets WLX, WLY and streamflux
WLY=c(9, 6, 9, 13, 17, 20, 22)
WLX=c(8, 19, 29, 20, 13, 20, 21)
streamflux=matrix(1:1452,44,33, byrow=FALSE)

The code I posted before is functional however I didn't configure my data correctly. The libraries needed to run the code have been added to the original question. I used image.plot but I believe you would run into the same problems using the base image. If you only specify a matrix of z values the image is plotted with axis c(0,1). If you specify x,y,z for each cell I don't think you will run into the problem I did where points were being plotted out of bounds. If you decide that you specifying a matrix of z values is easier than specify x,y,z, as I did, to keep your points from being plotted out of bounds you will need to scale your point data. In my case WLX=WLX/44 and WLY=WLY/33. As a side note you probably want to specify x,y,z if you're not using regularly spaced data.

Related

Fitting a long list of studies in Metafor Forestplot to make it readable

I'm trying to do a forest plot using metafor::forest. The problem is that because I have over 100 studies the output is unreadable because the rows blend together and overlap unless I choose a very small font (in which case you also can't read it).
Any ideas on how to plot this so that the font is large enough to be read without having all rows overlap?
Here's the code I'm using:
library(metafor)
res <- rma(yi, vi, data=dat)
par(mar = c(6, 6, 6, 6))
forest(res, addpred=T, header=TRUE, atransf=exp, at=log(c(.05, 0.5, 5, 15)), xlim=c(-5,5), ylim=c(-3,190), cex=.75)
This is the output
The only way it doesn't overlap is with cex = .05, but it is of course impossible to see anything:
I do not known the library nor the data, and cannot reproduce your example, but, for case, try using another output device:
png("file.png" , width = 480, height = 4000)
plot(runif(100))
dev.off()
Then see result file in current (getwd()) directory.

Lines don't align in rastertoPolygons

I am having trouble with aligning grids on a plot I made. Basically the plots show the result of a 34x34 matrix where each point has a value of 0,1,2,3 and is colored based on this. The lines which outline the cells do not match up perfectly with the coloring of the cells. My code and image are below.
library(raster)
r<-raster(xmn=1,xmx=34,ymn=1,ymx=34,nrows=34,ncols=34)
data1<-read.csv(file ="mat_aligned.csv",row.names = 1)
numbers<-data.matrix(data1)
r[]<-numbers
breakpoints<-c(-1,0.1,1.1,2.1,3.1)
colors<-c("white","blue","green","red")
plot(r,breaks=breakpoints,col=colors)
plot(rasterToPolygons(r),add=TRUE,border='black',lwd=3)
I would appreciate any help with this!
The problem is that the base R plot and the drawing of the grid use different plotting systems. The polygons will stay constant relative to the plotting window (they will appear narrower as the window shrinks), and won't preserve their relationship to the underlying plot axes, whereas the coloured squares will resize to preserve shape. You'll probably find that you can get your grid to match better by resizing your window, but of course, this isn't ideal.
The best way to get round this is to use the specific method designed for plotting SpatialPolygonDataFrame, which is the S4 class produced by rasterToPolygons. This is, after all, how you're "meant" to create such a plot.
Here's a reprex (obviously I've had to make some random data as yours wasn't shared in the question) :
library(raster)
r <- raster(xmn = 1, xmx = 34, ymn = 1, ymx = 34, nrows = 34, ncols = 34)
r[] <- data.matrix(as.data.frame(replicate(34, sample(0:3, 34, TRUE))))
colors <- c("white","blue","green","red")
spplot(rasterToPolygons(r), at = 0:4 - 0.5, col.regions = colors)
Created on 2020-05-04 by the reprex package (v0.3.0)
It is difficult to help if you not provide a minimal self-contained reporducible example. Something like this
library(raster)
r <- raster(xmn=1,xmx=34,ymn=1,ymx=34,nrows=34,ncols=34)
values(r) <- sample(4, ncell(r), replace=T)
p <- rasterToPolygons(r)
plot(r)
lines(p)
I see what you describe, even though it is minimal. A work-around could be to only plot the polygons
colors<-c("white","blue","green","red")
plot(p, col=colors[p$layer])

How to draw guide lines /w bokeh?

I draw following plot with bokeh.plotting.Figure.line.
How I can add vertical guideline to emphasize a point of Feb/14 ?
Here's another plot. This is bokeh.charts.Bar.
I'd like to add horizontal guideline to emphasize a point of 50. I searched bokeh doc but have no luck to find relevant API reference. It would be appreciate someone address me about this.
I added a vertical line to a simple line chart by creating a new set of data that corresponded to the vertical line I wanted to create.
from datetime import *
x = [date(2001,1,1), date(2002,1,1),date(2003,1,1), date(2004,1,1),
date(2005,1,1), date(2006,1,1),date(2007,1,1), date(2008,1,1),
date(2009,1,1), date(2010,1,1),date(2011,1,1)]
y = [0, 3, 2, 4, 6, 9, 15, 18, 19, 25, 28]
output_file("lines.html", title="line plot example")
p = figure(title="simple line example",x_axis_type = "datetime")
p.line(x, y)
a = [min(y),max(y)]
b = [date(2009,1,1),date(2009,1,1)]
p.line(b, a ,line_color="red")
show(p)
You can do this fairly easily with the ray glyph in bokeh. If you set the angle to be 1.57079633 (90 degrees in radians) you'll get a vertical ray. Just update the x value to be where you want the line and the length to be the height of your x axis.
p.ray(x=.5, y=0, length=1, angle=1.57079633, color='black')
You can probably use the new BoxAnnotation (new as of Bokeh 0.9.3) with zero width or height to do this, with slightly better effect:
https://docs.bokeh.org/en/latest/docs/user_guide/annotations.html#box-annotations
It's probably worth adding a LineAnnotation as well, I'll make an issue for it.

X axis relative to 1 not 0 in gap.barplot, how can I change this?

I have altered the sample code that from the help file for gap.barplot.
twogrp<-c(0, 4, 5, 7, 2,3, 1, 7, 18, 22, 25, 26, 28)
gap.barplot(twogrp,gap=c(8,16),xlab="Index",ytics=c(3,6,17,20),
ylab="Group values",main="Barplot with gap")
When I plot the above code, the resulting plot makes a 0 value appear to be a negative value, and a value of 1 look like zero. Is there any way to change this so that if my vector contains a zero value, nothing is plotted, and if there is a value of one then I see a raised bar. I have noticed that the sample files avoid ones and zeros, and that the plots resulting from the sample files have the x axis at y=1.
There is clearly a typo in gap.barplot (plotrix version 3.5-5). Right now it is setting the bottom of the bars to the minimum x value rather than the minimum y value. Here's some code that will copy that function and change that line (if found)
gap.barplot2<-gap.barplot
if (deparse(body(gap.barplot2)[[c(20,4,4)]])==
"botgap <- ifelse(gap[1] < 0, gap[1], xlim[1])") {
body(gap.barplot2)[[c(20,4,4)]] <-
quote(botgap <- ifelse(gap[1] < 0, gap[1], ylim[1]))
} else {
stop("line not found")
}
Then you can run
gap.barplot2(twogrp,gap=c(8,16),xlab="Index",ytics=c(3,6,17,20),
ylab="Group values",main="Barplot with gap")
to get
There appears to be no easy way to set the ylim[1]=0 without also setting ylim[2] (the max y-value). Lattice plotting functions would allow ylim=c(0,NA). Which would be nice to force a zero line but let the rest of the function figure out what the default max should be.
So you can use this alternative for now. I would contact the package authors to let them know about this error. You can send them a link to this question if you like.

R/quantmod: multiple charts all using the same y-axis

I'm trying to plot 6 days of intraday data as 6 charts. Quantmod's experimental chart_Series() function works with par() settings. I've pre-loaded the data into bars (a vector of XTS objects) so my code looks like this:
par(mfrow=c(3,2)) #3 rows, 2 columns
for(d in bars){
print(chart_Series(d, type = "candlesticks") )
}
This works, but each chart has its own different y-axis scale. I wanted to set a y-range that covers all 6 days, but cannot find a way to do this. I tried this:
ylim=c(18000,20000)
print(chart_Series(d, type = "candlesticks",ylim=ylim) )
but it fails with the "unused argument(s)" error. yrange=ylim also fails.
I can use chartSeries(d,yrange=ylim), and it works. But as far as I know I cannot put multiple charts in one display (?).
(It might strictly be off-subject, but suggestions for alternative R packages that can draw nice-looking candlestick charts, allow y-axis control and can draw multiple charts on one image would also be very welcome.)
With chartSeries, you can set the layout argument to NULL to prevent the layout() command from being called: this is what disables the mfrow setting.
library(quantmod)
getSymbols("AA")
op <- par(mfrow=c(3,2))
for(i in 1:6) {
chartSeries(
AA["2011-01"], "candlesticks",
TA=NULL, # No volume plot
layout=NULL,
yrange=c(15,18)
)
}
par(op)
If you want to keep the volume, you can call layout instead of setting mfrow: it does basically the same thing, but allows you to have plots of different sizes and choose the order in which they are plotted.
layout( matrix( c(
1, 3,
2, 4,
5, 7,
6, 8,
9, 11,
10, 12
), nc=2, byrow=TRUE),
heights = rep( c(2,1), 3 )
)
#layout.show(12) # To check that the order is as desired
for(i in 1:6) {
chartSeries(
AA[sprintf("2011-%02d",i)],
"candlesticks", layout=NULL, yrange=c(15,19)
)
}
Googling to understand Vincent's answer led me to the layout() command. It seems incompatible with par(mfrow), but some more experimentation found it can be used as an alternative.
ylim=c(18000,20000)
layout(matrix(1:12,nrow=6,ncol=2), height=c(4,2,4,2,4,2))
for(d in bars){
chartSeries(d,layout=NULL,TA=c(addVo(),addBBands()),yrange=ylim)
}
(You'll notice I added bollinger bands too, to be sure overlays still work too.)

Resources