R/moodle_m2s.R

Defines functions moodle_m2s

Documented in moodle_m2s

#' @title moodle_m2s
#' @description The \code{exams} package does not support multiple-choice questions with multiple correct answers but only one allowed answer;
#' but Moodle does. The function reads the XML file generated by \code{exams2moodle} and changes for **all** \code{mchoice} questions:
#'
#' * \code{<single>...</single>} to \code{<single>true</single>}, and
#' * modifies the attribute \code{fraction} in the tags \code{<answer fraction="...">...</answer>}.
#' If \code{fraction} is less than 0, it is set to zero, and if \code{fraction} is greater than 0, it is set to 100.
#'
#' If the \code{file} does not end with \code{.xml}, \code{.xml} is appended. At the end, the modified XML code is stored in \code{newfile}.
#'
#' @param file character: Moodle XML file with exercises to read from
#' @param newfile character:  Moodle XML file to write to (default: \code{file})
#' @param verbose integer: generate output (default: \code{1})
#'
#' @return invisibly the file name written to
#' @import xml2
#' @export
#' @md
#'
#' @examples
#' if (interactive()) {
#'   newfile <- tempfile(fileext=".xml")
#'   moodle_m2s(system.file("xml", "klausur-test.xml", package="exams.moodle"), newfile=newfile)
#'   file.edit(newfile)
#' }
moodle_m2s <- function(file, newfile=NULL, verbose=1) {
  if (!endsWith(file, ".xml")) file <- paste0(file, ".xml")
  if (is.null(newfile)) newfile <- file
  xml   <- read_xml(file)
  if(verbose>0) cat(file, "\n")
  # set all single in multichoice questions to "true"
  mc <- xml_find_all(xml, '//question[@type="multichoice"]/single')
  if(verbose>0) cat(" ", length(mc), "<single>...</single> entrie(s)\n")
  for (i in seq(mc)) xml_replace(mc[[i]], read_xml("<single>true</single>"))
  mc <- xml_find_all(xml, '//question[@type="multichoice"]/answer')
  if(verbose>0) cat(" ", length(mc), "<answer>...</answer> entrie(s)\n")
  for (i in seq(mc)) {
    mci <- mc[[i]]
    f <- as.numeric(xml_attr(mci, "fraction"))
    if (length(f)==1) {
      if (f<0) xml_attr(mci, "fraction") <- "0"
      if (f>0) xml_attr(mci, "fraction") <- "100"
      xml_replace(mc[[i]], mci)
    }
  }
  if (verbose>1) {
    mc <- xml_find_all(xml, '//question[@type="multichoice"]')
    for (i in seq(mc)) print(mc[[i]])
  }
  write_xml(xml, newfile)
  if(verbose>0) cat("  modified XML written to:", newfile, "\n")
  invisible(newfile)
}
sigbertklinke/exams2moodle documentation built on July 6, 2023, 3:26 p.m.