Combining Vector and Bitmap Graphics in a PDF

Combining vector and bitmap graphics in a pdf

Use ?rasterImage, or more conveniently in recent versions image with option useRaster = TRUE.

That will dramatically reduce the size of the file.

my.func <- function(x, y) x %*% t(y)
pdf(file="image.pdf")
image(my.func(seq(-10,10,,500), seq(-5,15,,500)), col=heat.colors(100))
dev.off()

pdf(file="rasterImage.pdf")
image(my.func(seq(-10,10,,500), seq(-5,15,,500)), col=heat.colors(100), useRaster = TRUE)
dev.off()

file.info("image.pdf")$size

file.info("rasterImage.pdf")$size

image.pdf: 813229 bytes

rasterImage.pdf 16511 bytes

See more details about the new features here:

http://developer.r-project.org/Raster/raster-RFC.html

http://journal.r-project.org/archive/2011-1/RJournal_2011-1_Murrell.pdf

R: Bitmap output in PDF

UPDATE: have now added method based on readPNG() as suggested in comments above. It's a bit slower (3s vs 9s) and seems to result in slightly larger file sizes than ImageMagick. rasterImage() interpolation makes no difference to filesize or timing, but alters the appearance slightly. If it's FALSE, then it looks the same as ImageMagick

I have just come up with the following solution using ImageMagick. It's not perfect, but it seems to work well so far.

png2pdf <- function(name=NULL,removepngs=TRUE,method="imagemagick",pnginterpolate=FALSE){
# Run the png() function with a filename of the form name%03d.png
# Then the actual plotting functions, e.g. plot(), lines() etc.
# Then dev.off()
# Then run png2pdf() and specify the name= argument if other pngs exist in the directory

# Need to incorporate a way of dealing with non-square plots

if(is.null(name)){
names <- list.files(pattern="[.]png")
name <- unique(sub("[0-9][0-9][0-9][.]png","",names))
if(length(name)!=1) stop("png2pdf() error: Check filenames")
}else{
names <- list.files(pattern=paste0(name,"[0-9][0-9][0-9][.]png"))
}

# Can change this to "convert" if it is correctly in the system path
if(method=="imagemagick"){
cmd <- c('C:\\Program Files\\ImageMagick-6.9.0-Q16\\convert.exe',names,paste0(name,".pdf"))
system2(cmd[1],cmd[-1])
}else if(method=="readPNG"){
library(png)
pdf(paste0(name,".pdf"))
par(mar=rep(0,4))
for(i in 1:length(names)){
plot(c(0,1),c(0,1),type="n")
rasterImage(readPNG(names[i]),0,0,1,1,interpolate=pnginterpolate)
}
dev.off()
}
if(removepngs) file.remove(names)
}

Plot as bitmap in PDF

Here's a solution that gets you close (50kb) to your desired file size (25kb), without requiring you to install LaTeX and/or learn Sweave. (Not that either of those are undesirable in the long-run!)

It uses the grid functions grid.cap() and grid.raster(). More details and ideas are in a recent R-Journal article by Paul Murrell (warning : PDF):

require(grid)
# Make the plots
dev.new() # Reducing width and height of this device will produce smaller raster files
plot(rnorm(2e4), rnorm(2e4), pch="+", cex=0.6)
cap1 <- grid.cap()
plot(rnorm(2e4), rnorm(2e4), pch="+", cex=0.6, col="red")
cap2 <- grid.cap()
dev.off()

# Write them to a pdf
pdf("test.pdf", onefile=TRUE)
grid.raster(cap1)
plot.new()
grid.raster(cap2)
dev.off()

The resulting pdf images appear to retain more detail than your files test1.png and test2.png, so you could get even closer to your goal by trimming down their resolution.

Combining vector and raster images in gnuplot

Use the multiplot feature in gnuplot to do this

e.g.

set terminal postscript eps enhanced color "Helvetica" 20
set output 'my_data.eps'

# beginning of multiplot
set multiplot

# the first plot
set size 1,1
set origin 0,0
set xlabel "Distance 1"
set ylabel "Distance 2"
set log x
set log y
set xrange[0.01:1]
plot "my_data.m" title "" with p pt 5

# smaller overlay plot
set size 0.45,0.45
set origin 0.15,0.5
set xrange [:0.2]
set lmargin 5
unset xlabel
unset ylabel
unset arrow
unset logscale
set xtics 0.05
set ytics 0.2
set grid
plot "my_data.m" title "" with p pt 5

# end of multiplot
unset multiplot

Reference

You may also find this link helpful : http://gnuplot.sourceforge.net/demo_4.2/image.html



Related Topics



Leave a reply



Submit