rvg icon indicating copy to clipboard operation
rvg copied to clipboard

Memory allocation failed : growing nodeset hit limit

Open DrRZ opened this issue 6 years ago • 2 comments

I'm trying to plot 6 scatter plots on one PowerPoint slide using officer with rvg's ph_with_vg_at() function. The 6 plots are achieved by using par(mfrow = c(2, 3)) within the code expression. Each plot has 122 lines in it so it is quite complex.

If I only plot 5 of the graphs, there's no problem, but if I do all 6 I always get this error:

Error in xpath_search(x$node, x$doc, xpath = xpath, nsMap = ns, num_results = 1) : 
  Memory allocation failed : growing nodeset hit limit
 [2]

DrRZ avatar Jun 25 '19 22:06 DrRZ

Hi,

Can you provide a reproducible example and the sessionInfo() result? I don't know how to reproduce.

Note that since latest version, it is encouraged to use ph_with instead of ph_with_vg_at or ph_with_vg.

davidgohel avatar Jun 26 '19 08:06 davidgohel

Here's a synthetic example that approximates what I was trying to achieve. It works with n.days = 7200 and fails at 7300.

n.days  <- 7200
n.plots <- 6

# use OfficeR package to output graphs to powerpoint
library(officer)
# also need rvg package to make editable vector graphics
library(rvg)

width  <- 10.61
height <- 5.60
xleft  <- 2.06
ytop   <- 0.78

plotted <- TRUE
while (plotted) {
    err <- try({
        days <- 0:n.days
        ppt  <- read_pptx()
        ppt  <- add_slide(ppt, layout = "Blank", master = "Office Theme")

        ph_with_vg_at(ppt, left = xleft, top = ytop, width = width, height = height, code = {
            par(mfrow = c(2, 3))
            for (i in 1:n.plots) {
                plot(
                    x = days,
                    y = 10 * exp(-log(2) / (1250 * (1 + 0.15 * rnorm(1))) * days),
                    type = "l",
                    col = "#FF00001A",
                    xlab = "Days",
                    ylab = "Value",
                    main = sprintf("Variable %i", i),
                    las = 1
                )
                for (j in 1:120) {
                    lines(
                        x = days,
                        y = 10 * exp(-log(2) / (1250 * (1 + 0.15 * rnorm(1))) * days),
                        col = "#FF00001A"
                    )
                }
            }
        })
    })
    if (class(err) == "try-error") {
        plotted <- FALSE
        print(err)
    } else {
        print(n.days)
        # to save powerpoint file:
        print(ppt, "error_producing_plots.pptx")
        n.days <- n.days + 100
    }
}

Here's the sessionInfo():

R version 3.6.0 (2019-04-26)
Platform: x86_64-w64-mingw32/x64 (64-bit)
Running under: Windows 10 x64 (build 17763)

Matrix products: default

locale:
[1] LC_COLLATE=English_Canada.1252  LC_CTYPE=English_Canada.1252    LC_MONETARY=English_Canada.1252 LC_NUMERIC=C                   
[5] LC_TIME=English_Canada.1252    

attached base packages:
[1] stats     graphics  grDevices utils     datasets  methods   base     

other attached packages:
[1] gdtools_0.1.9 rvg_0.2.1     officer_0.3.5

loaded via a namespace (and not attached):
 [1] compiler_3.6.0   R6_2.4.0         magrittr_1.5     htmltools_0.3.6  tools_3.6.0      base64enc_0.1-3  Rcpp_1.0.1      
 [8] uuid_0.1-2       xml2_1.2.0       digest_0.6.19    zip_2.0.2        rlang_0.4.0.9000

Admittedly, this is a big slide and would in practice be better to use bitmaps rather than vectors but I thought I'd report the issue and you can decide if it's worthwhile fixing.

Ideally, it would be nice to have the plot data as a bitmap but the decorations (axis lines, ticks, labels, etc) as editable so they could be tweaked in powerpoint but I couldn't find a trivially easy way of doing that. Could probably be achieved by first making a bitmap with invisible decorations then overlaying empty vector plots on top.

I'm also unclear how one would use ph_with in this example if you want an editable graphic in powerpoint.

DrRZ avatar Jun 26 '19 22:06 DrRZ