Raphus
Raphus

Reputation: 57

Writing multiple images in a loop

I would like to select certain images depending on the filename ending, combine them, and then save them. The list of filename endings is stored in h2h.nrp$comparison.

Hence, I wrote:

for (i in list(unique(h2h.nrp$comparison))) {
  pattern <- paste(i, ".png$", sep = "")
  Lfile <- list.files("plots - individual/", pattern = pattern)
  image1 <- image_border(image_read(paste("plots - individual/", Lfile[1], sep = "")), "white", "70x120")
  image2 <- image_border(image_read(paste("plots - individual/", Lfile[2], sep = "")), "white", "70x120")
  image3 <- image_border(image_read(paste("plots - individual/", Lfile[3], sep = "")), "white", "70x120")
  image4 <- image_border(image_read(paste("plots - individual/", Lfile[4], sep = "")), "white", "70x120")
  image5 <- image_border(image_read(paste("plots - individual/", Lfile[5], sep = "")), "white", "70x120")
  image6 <- image_border(image_read(paste("plots - individual/", Lfile[6], sep = "")), "white", "70x120")
  image7 <- image_border(image_read(paste("plots - individual/", Lfile[7], sep = "")), "white", "70x120")
  image8 <- image_border(image_read(paste("plots - individual/", Lfile[8], sep = "")), "white", "70x120")
  image9 <- image_border(image_read(paste("plots - individual/", Lfile[9], sep = "")), "white", "70x120")
  image10 <- image_border(image_read(paste("plots - individual/", Lfile[10], sep = "")), "white", "70x120")
  image11 <- image_border(image_read(paste("plots - individual/", Lfile[11], sep = "")), "white", "70x120")
  image12 <- image_border(image_read(paste("plots - individual/", Lfile[12], sep = "")), "white", "70x120")
  row1 <- c(image1, image2, image3, image4)
  row2 <- c(image5, image6, image7, image8)
  row3 <- c(image9, image10, image11, image12)
  row1.img <- image_append(row1)
  row2.img <- image_append(row2)
  row3.img <- image_append(row3)
  all.plots <- c(row1.img, row2.img, row3.img)
  all.plots.img <- image_append(all.plots, stack = TRUE)
  image_write(all.plots.img, path = paste0("vs", i, ".png"), format = "png")
}

which seems to run smoothly until the very last line, image_write.

An Error in file(con, "wb") : invalid 'description' argument error is returned.

I tried - just for the sake of evaluating where the issue was - changing path from paste0("vs", i, ".png") to paste0("vs", "i", ".png") and it worked brilliantly. Of course, this is not the desired output because the vs i.png image is re-written at every loop. Also, the all.plots.img element stored in global environment looks correct when I run print(all.plots.img).

So my - basic, probably naïve, understanding - is that there must be something wrong in the image_write line but I do not have a clue on what I did wrong.

I have checked Writing multiple images using Magick on R, whose solution seems actually identical to what I am doing. I have also checked other posts that pointed out that magick had some issues with memory and file size - I can confirm this should not be the issue of mine given that the single images are ~1MB in terms of size.

Can you please point out where the (100% stupid) issue is?

EDIT ---

I went with a function looped over a list with lapply instead and it worked brilliantly. Still curious about why it was not working with a for loop for future reference (as well as, hopefully, to help other people) - any idea?

Upvotes: 1

Views: 659

Answers (1)

St&#233;phane Laurent
St&#233;phane Laurent

Reputation: 84649

You have a vector v = unique(h2h.nrp$comparison) and you do for(i in list(v)). This loop iterates over the elements of the list list(v), which contains only one element: the vector v. So i = v in your loop, and paste0("vs", i, ".png") is then a character vector, not valid for the path argument because it must be a single character string. You have to do for(i in unique(h2h.nrp$comparison)) if you want to iterate over the elements of the vector unique(h2h.nrp$comparison).

Upvotes: 0

Related Questions