### Function to create lists of tables xtableList <- function(x, caption = NULL, label = NULL, align = NULL, digits = NULL, display = NULL, ...) { if (is.null(digits)){ digitsList <- vector("list", length(x)) } else { if (!is.list(digits)){ digitsList <- vector("list", length(x)) for (i in 1:length(x)) digitsList[[i]] <- digits } } if (is.null(display)){ displayList <- vector("list", length(x)) } else { if (!is.list(display)){ displayList <- vector("list", length(x)) for (i in 1:length(x)) displayList[[i]] <- display } } xList <- vector("list", length(x)) for (i in 1:length(x)){ xList[[i]] <- xtable(x[[i]], caption = caption, label = label, align = align, digits = digitsList[[i]], display = displayList[[i]], ...) attr(xList[[i]], 'subheading') <- attr(x, 'subheadings')[[i]] } attr(xList, "message") <- attr(x, "message") attr(xList, "caption") <- caption attr(xList, "label") <- label class(xList) <- c("xtableList") return(xList) } print.xtableList <- function(x, type = getOption("xtable.type", "latex"), file = getOption("xtable.file", ""), append = getOption("xtable.append", FALSE), floating = getOption("xtable.floating", TRUE), floating.environment = getOption("xtable.floating.environment", "table"), table.placement = getOption("xtable.table.placement", "ht"), caption.placement = getOption("xtable.caption.placement", "bottom"), caption.width = getOption("xtable.caption.width", NULL), latex.environments = getOption("xtable.latex.environments", c("center")), tabular.environment = getOption("xtable.tabular.environment", "tabular"), size = getOption("xtable.size", NULL), hline.after = NULL, NA.string = getOption("xtable.NA.string", ""), include.rownames = getOption("xtable.include.rownames", TRUE), include.colnames = getOption("xtable.include.colnames", TRUE), only.contents = getOption("xtable.only.contents", FALSE), add.to.row = NULL, sanitize.text.function = getOption("xtable.sanitize.text.function", NULL), sanitize.rownames.function = getOption("xtable.sanitize.rownames.function", sanitize.text.function), sanitize.colnames.function = getOption("xtable.sanitize.colnames.function", sanitize.text.function), math.style.negative = getOption("xtable.math.style.negative", FALSE), html.table.attributes = getOption("xtable.html.table.attributes", "border=1"), print.results = getOption("xtable.print.results", TRUE), format.args = getOption("xtable.format.args", NULL), rotate.rownames = getOption("xtable.rotate.rownames", FALSE), rotate.colnames = getOption("xtable.rotate.colnames", FALSE), booktabs = getOption("xtable.booktabs", FALSE), scalebox = getOption("xtable.scalebox", NULL), width = getOption("xtable.width", NULL), comment = getOption("xtable.comment", TRUE), timestamp = getOption("xtable.timestamp", date()), colnames.format = "single", ...) { ## Get number of rows for each table in list of tables nCols <- dim(x[[1]])[2] rowNums <- sapply(x, dim)[1,] combinedRowNums <- cumsum(rowNums) combined <- do.call(rbind, x) if (type == "latex"){ ## Special treatment if using booktabs if (booktabs){ tRule <- "\\toprule" mRule <- "\\midrule" bRule <- "\\bottomrule" } else { tRule <- "\\hline" mRule <- "\\hline" bRule <- "\\hline" } if (colnames.format == "single"){ add.to.row <- list(pos = NULL, command = NULL) add.to.row$pos <- as.list(c(0, combinedRowNums[-length(x)], dim(combined)[1])) command <- sapply(x, attr, "subheading") add.to.row$command[1:length(x)] <- paste0(mRule,"\n\\multicolumn{", nCols, "}{l}{", command, "}\\\\\n") if ( (booktabs) & length(attr(x, "message") > 0) ){ attr(x, "message")[1] <- paste0("\\rule{0em}{2.5ex}", attr(x, "message")[1]) } add.to.row$command[length(x) + 1] <- paste0("\n\\multicolumn{", nCols, "}{l}{", attr(x, "message"), "}\\\\\n", collapse = "") add.to.row$command[length(x) + 1] <- paste0(bRule, add.to.row$command[length(x) + 1]) class(combined) <- c("xtableList", "data.frame") hline.after <- c(-1) include.colnames <- TRUE } ## Create headings for columns if multiple headings are needed if (colnames.format == "multiple"){ if (is.null(sanitize.colnames.function)) { colHead <- names(x[[1]]) } else { colHead <- sanitize.colnames.function(names(x[[1]])) } if (rotate.colnames) { colHead <- paste("\\begin{sideways}", colHead, "\\end{sideways}") } colHead <- paste0(colHead, collapse = " & ") if (include.rownames) { colHead <- paste0(" & ", colHead) } colHead <- paste0(tRule, "\n", colHead, " \\\\", mRule, "\n") add.to.row <- list(pos = NULL, command = NULL) add.to.row$pos <- as.list(c(0, c(combinedRowNums[1:length(x)]))) command <- sapply(x, attr, "subheading") add.to.row$command[1] <- paste0("\n\\multicolumn{", nCols, "}{l}{", command[1], "}", " \\\\ \n", colHead) add.to.row$command[2:length(x)] <- paste0(bRule, "\\\\ \n\\multicolumn{", nCols, "}{l}{", command[2:length(x)], "}", "\\\\ \n", colHead) if ( (booktabs) & length(attr(x, "message") > 0) ){ attr(x, "message")[1] <- paste0("\\rule{0em}{2.5ex}", attr(x, "message")[1]) } add.to.row$command[length(x) + 1] <- paste0("\n\\multicolumn{", nCols, "}{l}{", attr(x, "message"), "}\\\\\n", collapse = "") add.to.row$command[length(x) + 1] <- paste0(bRule, add.to.row$command[length(x) + 1]) class(combined) <- c("xtableList", "data.frame") hline.after <- NULL include.colnames <- FALSE } print.xtable(combined, type = type, floating = floating, floating.environment = floating.environment, table.placement = table.placement, caption.placement = caption.placement, caption.width = caption.width, latex.environments = latex.environments, tabular.environment = tabular.environment, size = size, hline.after = hline.after, NA.string = NA.string, include.rownames = include.rownames, include.colnames = include.colnames, only.contents = only.contents, add.to.row = add.to.row, sanitize.text.function = sanitize.text.function, sanitize.rownames.function = sanitize.rownames.function, sanitize.colnames.function = sanitize.colnames.function, math.style.negative = math.style.negative, html.table.attributes = html.table.attributes, print.results = print.results, format.args = format.args, rotate.rownames = rotate.rownames, rotate.colnames = rotate.colnames, booktabs = booktabs, scalebox = scalebox, width = width, comment = comment, timestamp = timestamp, ...) } else { stop("print.xtableList not yet implemented for this type") } } ### Uses xtableList xtableLSMeans <- function(x, caption = NULL, label = NULL, align = NULL, digits = NULL, display = NULL, auto = FALSE, ...){ if (attr(x, "estName") == "lsmean"){ xList <- split(x, f = x[, 2]) for (i in 1:length(xList)){ xList[[i]] <- as.data.frame(xList[[i]][, -2]) } attr(xList, "subheadings") <- paste0(dimnames(x)[[2]][2], " = ", levels(x[[2]])) attr(xList, "message") <- c("", attr(x, "mesg")) xList <- xtableList(xList, caption = caption, label = label, align = align, digits = digits, display = display, auto = auto, ...) } else { xList <- x xList <- xtable.data.frame(xList, caption = caption, label = label, align = align, digits = digits, display = display, auto = auto, ...) } return(xList) }