MALDIquantForeign/0000755000176200001440000000000014553557406013501 5ustar liggesusersMALDIquantForeign/NAMESPACE0000644000176200001440000000205714157631642014717 0ustar liggesusers# Generated by roxygen2: do not edit by hand export(import) export(importAnalyze) export(importBrukerFlex) export(importCdf) export(importCiphergenXml) export(importCsv) export(importImzMl) export(importMsd) export(importMzMl) export(importMzXml) export(importTab) export(importTxt) export(supportedFileFormats) exportMethods(export) exportMethods(exportCsv) exportMethods(exportImzMl) exportMethods(exportMsd) exportMethods(exportMzMl) exportMethods(exportTab) import(MALDIquant) import(methods) import(readMzXmlData) importFrom(XML,xmlEventParse) importFrom(XML,xmlParse) importFrom(XML,xmlValue) importFrom(XML,xpathApply) importFrom(XML,xpathSApply) importFrom(base64enc,base64encode) importFrom(digest,digest) importFrom(readBrukerFlexData,readBrukerFlexFile) importFrom(stats,na.omit) importFrom(stats,runif) importFrom(utils,download.file) importFrom(utils,modifyList) importFrom(utils,packageVersion) importFrom(utils,read.table) importFrom(utils,tail) importFrom(utils,type.convert) importFrom(utils,untar) importFrom(utils,unzip) importFrom(utils,write.table) MALDIquantForeign/man/0000755000176200001440000000000014404344473014245 5ustar liggesusersMALDIquantForeign/man/importMzXml-functions.Rd0000644000176200001440000000241014404344473021041 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importMzXml} \alias{importMzXml} \title{Import mzXML files} \usage{ importMzXml(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[readMzXmlData]{readMzXmlFile}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in mzXML file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import s <- importMzXml(exampleDirectory) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/}, \cr Definition of \code{mzXML} format: \url{http://tools.proteomecenter.org/wiki/index.php?title=Formats:mzXML} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}}, \code{\link[readMzXmlData]{readMzXmlFile}} } \author{ Sebastian Gibb } MALDIquantForeign/man/export-methods.Rd0000644000176200001440000000434614404344473017525 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/export-methods.R \docType{methods} \name{export,AbstractMassObject-method} \alias{export,AbstractMassObject-method} \alias{export} \alias{export,list-method} \title{Export files} \usage{ \S4method{export}{AbstractMassObject}(x, file, type="auto", force=FALSE, \ldots) \S4method{export}{list}(x, path, type, force=FALSE, \ldots) } \arguments{ \item{x}{a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects.} \item{file}{\code{character}, file name.} \item{type}{\code{character}, file format. If \code{type} is set to \dQuote{auto} the file extension is used.} \item{force}{\code{logical}, If \code{TRUE} the \code{file} would be overwritten or \code{path} would be created.} \item{path}{\code{character}, path to directory in which the \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} would be exported.} \item{\ldots}{arguments to be passed to specific export functions.} } \description{ This function provides a general interface to export \code{\link[MALDIquant]{AbstractMassObject-class}} objects (e.g. \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}}) into different file formats. } \details{ Specific export functions: \tabular{ll}{ tab \tab \code{\link[MALDIquantForeign]{exportTab}} \cr csv \tab \code{\link[MALDIquantForeign]{exportCsv}} \cr imzML \tab \code{\link[MALDIquantForeign]{exportImzMl}} \cr msd \tab \code{\link[MALDIquantForeign]{exportMsd}} \cr mzML \tab \code{\link[MALDIquantForeign]{exportMzMl}} \cr } } \examples{ \dontrun{ library("MALDIquant") library("MALDIquantForeign") s <- list(createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=1:5)) ## export a single spectrum export(s[[1]], file="spectrum.csv") ## identical to exportCsv(s[[1]], file="spectrum.csv") ## export a list of spectra export(s, path="spectra", type="csv") ## identical to exportCsv(s, path="spectra") } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassPeaks-class}}, \code{\link[MALDIquant]{MassSpectrum-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importCiphergenXml-functions.Rd0000644000176200001440000000222414404344473022362 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importCiphergenXml} \alias{importCiphergenXml} \title{Import Ciphergen XML files} \usage{ importCiphergenXml(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[MALDIquantForeign]{import}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in Ciphergen XML file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import s <- importCiphergenXml(exampleDirectory) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/exportMzMl-methods.Rd0000644000176200001440000000325514404344473020323 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/export-methods.R \docType{methods} \name{exportMzMl,MassSpectrum-method} \alias{exportMzMl,MassSpectrum-method} \alias{exportMzMl} \alias{exportMzMl,list-method} \title{Export to mzML files} \usage{ \S4method{exportMzMl}{MassSpectrum}(x, file, force=FALSE, \ldots) \S4method{exportMzMl}{list}(x, path, force=FALSE, \ldots) } \arguments{ \item{x}{a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects.} \item{file}{\code{character}, file name.} \item{force}{\code{logical}, If \code{TRUE} the \code{file} would be overwritten or \code{path} would be created.} \item{path}{\code{character}, path to directory in which the \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} would be exported. If \code{path} is a single filename all spectra will be exported to a single mzML file.} \item{\ldots}{arguments to be passed to internal functions.} } \description{ This function exports \code{\link[MALDIquant]{MassSpectrum-class}} objects into mzML files. } \examples{ \dontrun{ library("MALDIquant") library("MALDIquantForeign") s <- list(createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=1:5)) ## export a single spectrum exportMzMl(s[[1]], file="spectrum.mzML") ## export a list of spectra exportMzMl(s, path="spectra.mzML") } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/}, \cr HUPO Proteomics Standards Inititative mzML 1.1.0 Specification: \url{https://www.psidev.info/mzML} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importCdf-functions.Rd0000644000176200001440000000242614404344473020475 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importCdf} \alias{importCdf} \title{Import CDF files} \usage{ importCdf(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[MALDIquantForeign]{import}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in NetCDF file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects.\cr Please note that the \emph{RNetCDF} is needed. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import if (requireNamespace("RNetCDF", quietly=TRUE)) { s <- importCdf(exampleDirectory) } else { message("You have to install the RNetCDF package to use importCdf.") } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/exportImzMl-methods.Rd0000644000176200001440000000474114404344473020475 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/export-methods.R \docType{methods} \name{exportImzMl,MassSpectrum-method} \alias{exportImzMl,MassSpectrum-method} \alias{exportImzMl} \alias{exportImzMl,list-method} \title{Export to imzML files} \usage{ \S4method{exportImzMl}{MassSpectrum}(x, file, force=FALSE, processed=TRUE, coordinates=NULL, pixelSize=c(100, 100), \ldots) \S4method{exportImzMl}{list}(x, path, force=FALSE, processed=TRUE, coordinates=NULL, pixelSize=c(100, 100), \ldots) } \arguments{ \item{x}{a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects.} \item{file}{\code{character}, file name.} \item{force}{\code{logical}, If \code{TRUE} the \code{file} would be overwritten or \code{path} would be created.} \item{processed}{\code{logical}, If \code{TRUE} (default) the spectra will be saved in processed mode (means mass and intensity is stored for each spectra separately in contrast to continuous mode where the mass is stored only for one spectrum).} \item{coordinates}{\code{matrix}, 2 column matrix that contains the x- and y-coordinates for the spectra.} \item{pixelSize}{\code{numeric}, a vector of length 2 that contains the x and y pixel size in micrometers (default: \code{c(100, 100)}).} \item{path}{\code{character}, path to directory in which the \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} would be exported. If \code{path} is a single filename all spectra will be exported to a single imzML file.} \item{\ldots}{arguments to be passed to internal functions.} } \description{ This function exports \code{\link[MALDIquant]{MassSpectrum-class}} objects into imzML files. } \examples{ \dontrun{ library("MALDIquant") library("MALDIquantForeign") s <- list(createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=1:5)) ## export a list of spectra exportImzMl(s, path="processed.imzML", coordinates=cbind(x=1:2, y=c(1, 1))) } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} Schramm T, Hester A, Klinkert I, Both J-P, Heeren RMA, Brunelle A, Laprevote O, Desbenoit N, Robbe M-F, Stoeckli M, Spengler B, Roempp A (2012)\cr imzML - A common data format for the flexible exchange and processing of mass spectrometry imaging data.\cr Journal of Proteomics 75 (16):5106-5110. \cr \doi{10.1016/j.jprot.2012.07.026} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importMzMl-functions.Rd0000644000176200001440000000225414404344473020657 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importMzMl} \alias{importMzMl} \title{Import mzML files} \usage{ importMzMl(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[MALDIquantForeign]{import}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in mzML file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import s <- importMzMl(exampleDirectory) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/}, \cr Definition of \code{mzML} format: \url{https://www.psidev.info/mzML} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/MALDIquantForeign-parallel.Rd0000644000176200001440000000400414404344473021535 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/MALDIquantForeign-parallel.R \name{MALDIquantForeign-parallel} \alias{MALDIquantForeign-parallel} \title{Parallel Support in Package \pkg{MALDIquantForeign}} \description{ \code{\link[MALDIquantForeign]{MALDIquantForeign-package}} offers multi-core support using \code{\link[parallel]{mclapply}} and \code{\link[parallel]{mcmapply}}. This approach is limited to unix-based platforms. } \details{ Please note that not all import functions benfit from parallelisation. The current implementation is limited to run the parallelisation over different files. That's why only imports of multiple files could be run on multiple cores. E.g. a single mzML file containing 4 spectra would always be read on a single core. In contrast 4 mzML files each containing just one spectra could be read in using 4 cores. The improvement in the runtime depends on the amount of data to read, the proportion of parsing/decoding of the data, the amount of memory and the speed of the hard disk. Please note: It is possible that using parallelisation results in a worse runtime! } \examples{ ## load packages library("MALDIquant") library("MALDIquantForeign") exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## run single-core import print(system.time( s1 <- importMzMl(exampleDirectory, centroided=TRUE, verbose=FALSE) )) if(.Platform$OS.type == "unix") { ## run multi-core import ## (because the example spectra are very small (just 5 data points) the ## multi-core solution is slower on most systems) print(system.time( s2 <- importMzMl(exampleDirectory, centroided=TRUE, mc.cores=2, verbose=FALSE) )) stopifnot(all.equal(s1, s2)) } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MALDIquant-parallel}}, \code{\link[parallel]{mclapply}}, \code{\link[parallel]{mcmapply}} } \author{ Sebastian Gibb \email{mail@sebastiangibb.de} } \keyword{misc} MALDIquantForeign/man/MALDIquantForeign-package.Rd0000644000176200001440000000164414553551461021345 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/package.R \docType{package} \name{MALDIquantForeign-package} \alias{MALDIquantForeign} \alias{MALDIquantForeign-package} \title{Import/Export routines for \sQuote{MALDIquant}} \description{ This package reads and writes different file formats of mass spectrometry data into/from \sQuote{MALDIquant} objects. } \details{ \tabular{ll}{ Package: \tab MALDIquantForeign \cr License: \tab GPL (>= 3)\cr URL: \tab https://strimmerlab.github.io/software/maldiquant/\cr } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ Useful links: \itemize{ \item \url{https://strimmerlab.github.io/software/maldiquant/} \item \url{https://github.com/sgibb/MALDIquantForeign/} \item Report bugs at \url{https://github.com/sgibb/MALDIquantForeign/issues/} } } \author{ Sebastian Gibb \email{mail@sebastiangibb.de} } \keyword{package} MALDIquantForeign/man/importTab-functions.Rd0000644000176200001440000000261214404344473020504 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importTxt} \alias{importTxt} \alias{importTab} \alias{importCsv} \title{Import text files} \usage{ importTxt(path, ...) importTab(path, ...) importCsv(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[utils]{read.table}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports different text file formats into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \details{ \code{importTab}, \code{importTxt} and \code{importCsv} use \code{\link[utils]{read.table}} with different defaults. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import txt files s <- importTxt(exampleDirectory) ## import csv files s <- importCsv(exampleDirectory) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}}, \code{\link[utils]{read.table}} } \author{ Sebastian Gibb } MALDIquantForeign/man/supportedFileFormats-functions.Rd0000644000176200001440000000335714404344473022733 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/fileFormats.R \name{supportedFileFormats} \alias{supportedFileFormats} \title{Supported file formats} \usage{ supportedFileFormats() } \value{ a \code{list} with two named elements (\code{import} and \code{export}) containing a \code{character} vector of supported file types. } \description{ This function prints all file formats supported by \code{\link{MALDIquantForeign-package}}. } \details{ \subsection{Import}{ \tabular{ll}{ txt \tab \code{\link[MALDIquantForeign]{importTxt}} \cr tab \tab \code{\link[MALDIquantForeign]{importTab}} \cr csv \tab \code{\link[MALDIquantForeign]{importCsv}} \cr fid \tab \code{\link[MALDIquantForeign]{importBrukerFlex}} \cr ciphergen \tab \code{\link[MALDIquantForeign]{importCiphergenXml}} \cr mzXML \tab \code{\link[MALDIquantForeign]{importMzXml}} \cr mzML \tab \code{\link[MALDIquantForeign]{importMzMl}} \cr imzML \tab \code{\link[MALDIquantForeign]{importImzMl}} \cr analyze \tab \code{\link[MALDIquantForeign]{importAnalyze}} \cr cdf \tab \code{\link[MALDIquantForeign]{importCdf}} \cr msd \tab \code{\link[MALDIquantForeign]{importMsd}} \cr } } \subsection{Export}{ \tabular{ll}{ tab \tab \code{\link[MALDIquantForeign]{exportTab}} \cr csv \tab \code{\link[MALDIquantForeign]{exportCsv}} \cr imzML \tab \code{\link[MALDIquantForeign]{exportImzMl}} \cr msd \tab \code{\link[MALDIquantForeign]{exportMsd}} \cr mzML \tab \code{\link[MALDIquantForeign]{exportMzMl}} \cr } } } \examples{ library("MALDIquantForeign") supportedFileFormats() } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquantForeign]{export}}, \code{\link[MALDIquantForeign]{import}} } \author{ Sebastian Gibb } MALDIquantForeign/man/base64-encode.Rd0000644000176200001440000000200613731070764017052 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/base64encode-functions.R \name{.base64encode} \alias{.base64encode} \title{Converts double to base64 character.} \usage{ .base64encode( x, size, endian = .Platform$endian, compressionType = c("none", "gzip") ) } \arguments{ \item{x}{\code{double}, vector} \item{size}{\code{integer}, number of bytes per element in the byte stream (see \code{size} in \code{\link[base]{writeBin}}).} \item{endian}{\code{character}, the endian-ness (see \code{endian} in \code{\link[base]{writeBin}}).} \item{compressionType}{\code{character}, type of compression to use for compression of \code{x} (see \code{type} in \code{\link[base]{memCompress}}.} } \value{ Vector of type \code{character}. } \description{ This function converts a \code{double} vector to a base64 encoded \code{character} vector. } \seealso{ \code{\link[base64enc]{base64encode}} from \pkg{base64enc} package } \author{ Sebastian Gibb \email{mail@sebastiangibb.de} } \keyword{internal} MALDIquantForeign/man/exportTab-methods.Rd0000644000176200001440000000421714404344473020151 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/export-methods.R \docType{methods} \name{exportTab,AbstractMassObject-method} \alias{exportTab,AbstractMassObject-method} \alias{exportTab} \alias{exportTab,list-method} \alias{exportCsv} \alias{exportCsv,AbstractMassObject-method} \alias{exportCsv,list-method} \title{Export to text files} \usage{ \S4method{exportTab}{AbstractMassObject}(x, file, force=FALSE, \ldots) \S4method{exportTab}{list}(x, path, force=FALSE, \ldots) \S4method{exportCsv}{AbstractMassObject}(x, file, force=FALSE, \ldots) \S4method{exportCsv}{list}(x, path, force=FALSE, \ldots) } \arguments{ \item{x}{a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects.} \item{file}{\code{character}, file name.} \item{force}{\code{logical}, If \code{TRUE} the \code{file} would be overwritten or \code{path} would be created.} \item{path}{\code{character}, path to directory in which the \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} would be exported.} \item{\ldots}{arguments to be passed to \code{\link[utils]{write.table}}.} } \description{ This function exports \code{\link[MALDIquant]{AbstractMassObject-class}} objects (e.g. \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}}) into different text file formats. } \details{ \code{exportTab} and \code{exportCsv} use \code{\link[utils]{write.table}} with different defaults (\code{sep="\t"} in \code{exportTab} and \code{sep=","} in \code{exportCsv}). } \examples{ \dontrun{ library("MALDIquant") library("MALDIquantForeign") s <- list(createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=1:5)) ## export a single spectrum exportTab(s[[1]], file="spectrum.tab") ## export a list of spectra and use ; as separator exportCsv(s, path="spectra", sep=";", force=TRUE) } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassPeaks-class}}, \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[utils]{write.table}} } \author{ Sebastian Gibb } MALDIquantForeign/man/exportMsd-methods.Rd0000644000176200001440000000412214404344473020161 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/export-methods.R \docType{methods} \name{exportMsd,MassSpectrum-method} \alias{exportMsd,MassSpectrum-method} \alias{exportMsd} \alias{exportMsd,list-method} \title{Export to MSD files} \usage{ \S4method{exportMsd}{MassSpectrum}(x, file, force=FALSE, peaks, \ldots) \S4method{exportMsd}{list}(x, path, force=FALSE, peaks, \ldots) } \arguments{ \item{x}{a \code{\link[MALDIquant]{MassSpectrum-class}} object or a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} objects.} \item{file}{\code{character}, file name.} \item{force}{\code{logical}, If \code{TRUE} the \code{file} would be overwritten or \code{path} would be created.} \item{peaks}{a \code{\link[MALDIquant]{MassPeaks-class}} object or a \code{list} of \code{\link[MALDIquant]{MassPeaks-class}} objects.} \item{path}{\code{character}, path to directory in which the \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} would be exported.} \item{\ldots}{arguments to be passed to \code{\link[utils]{write.table}}.} } \description{ This function exports \code{\link[MALDIquant]{AbstractMassObject-class}} objects (e.g. \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}}) into mMass MSD files. } \examples{ \dontrun{ library("MALDIquant") library("MALDIquantForeign") s <- list(createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=1:5)) p <- list(createMassPeaks(mass=4:5, intensity=4:5, snr=1:2), createMassPeaks(mass=4:5, intensity=4:5, snr=1:2)) ## export a single spectrum exportMsd(s[[1]], file="spectrum.msd") ## export a single spectrum with corresponding peaks exportMsd(s[[1]], file="spectrum.msd", peaks=p[[1]]) ## export a list of spectra with corresponding peaks exportMsd(s, path="spectra", peaks=p, force=TRUE) } } \references{ \url{https://strimmerlab.github.io/software/maldiquant/}, \cr mMass homepage: \url{http://mmass.org/} } \seealso{ \code{\link[MALDIquant]{MassPeaks-class}}, \code{\link[MALDIquant]{MassSpectrum-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importMsd-functions.Rd0000644000176200001440000000221714404344473020522 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importMsd} \alias{importMsd} \title{Import MSD files} \usage{ importMsd(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[MALDIquantForeign]{import}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in mMass MSD file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import s <- importMsd(exampleDirectory) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/}, \cr mMass homepage: \url{http://mmass.org/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importAnalyze-functions.Rd0000644000176200001440000000203514464723603021402 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importAnalyze} \alias{importAnalyze} \title{Import Analyze 7.5 files} \usage{ importAnalyze(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[MALDIquantForeign]{import}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in Analyze 7.5 file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} \cr \url{http://www.grahamwideman.com/gw/brain/analyze/formatdoc.htm}, \url{https://eeg.sourceforge.net/ANALYZE75.pdf} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/import-functions.Rd0000644000176200001440000001100414404344473020050 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{import} \alias{import} \title{Import files} \usage{ import( path, type = "auto", pattern, excludePattern = NULL, removeEmptySpectra = TRUE, centroided = FALSE, massRange = c(0, Inf), minIntensity = 0, mc.cores = 1L, verbose = interactive(), ... ) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{type}{\code{character}, file format. If \code{type} is set to \dQuote{auto} MALDIquant tries to detect the correct file type automatically. It often depends on the file extension (if \code{path} is a directory the most represented file extension is used; \code{pattern} argument is ignored).} \item{pattern}{\code{character}, a regular expression to find files in a directory (see details).} \item{excludePattern}{\code{character}, a regular expression to exclude files in a directory (see details).} \item{removeEmptySpectra}{\code{logical}, should empty spectra excluded?} \item{centroided}{\code{logical}, if \code{centroided=FALSE} (default) the data are treated as not centroided and a list of \code{\link[MALDIquant]{MassSpectrum-class}} objects is returned. Use \code{centroided=TRUE} to assume centroided data and get a list of \code{\link[MALDIquant]{MassPeaks-class}} objects.} \item{massRange}{\code{double}, limits of mass import (left/minimal mass, right/maximal mass).} \item{minIntensity}{\code{double}, minimal intensity to import.} \item{mc.cores}{number of cores to use (default 1; only unix-based platforms are supported, see \code{\link[MALDIquantForeign]{MALDIquantForeign-parallel}} for details).} \item{verbose}{\code{logical}, verbose output?} \item{\ldots}{arguments to be passed to specific import functions.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function provides a general interface to import different file formats into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \details{ Specific import functions: \tabular{ll}{ txt \tab \code{\link[MALDIquantForeign]{importTxt}} \cr tab \tab \code{\link[MALDIquantForeign]{importTab}} \cr csv \tab \code{\link[MALDIquantForeign]{importCsv}} \cr fid \tab \code{\link[MALDIquantForeign]{importBrukerFlex}} \cr ciphergen \tab \code{\link[MALDIquantForeign]{importCiphergenXml}} \cr mzXML \tab \code{\link[MALDIquantForeign]{importMzXml}} \cr mzML \tab \code{\link[MALDIquantForeign]{importMzMl}} \cr imzML \tab \code{\link[MALDIquantForeign]{importImzMl}} \cr analyze \tab \code{\link[MALDIquantForeign]{importAnalyze}} \cr cdf \tab \code{\link[MALDIquantForeign]{importCdf}} \cr msd \tab \code{\link[MALDIquantForeign]{importMsd}} \cr } \code{path}: In addition to the above mentioned file types the following (compressed) archives are supported, too: zip, tar, tar.gz, tar.bz2, tar.xz. The archives are uncompressed in a temporary directory. Afterwards the \code{\link[MALDIquantForeign]{import}} function is called (with \code{type="auto"}). \code{pattern}: Sometimes unusual file extensions are used (e.g. \code{"*.xml"} for mzXML files). In this case a specific \code{pattern} could be defined to import files with an unusual file extension (e.g. \code{pattern="^.*\\.xml$"} to read all \code{*.xml} files in a directory; see \code{\link[base]{regexp}} for details). \code{excludePattern}: Sometimes some files should be excluded. E.g. to ignore additional aquired Bruker LIFT spectra (MALDI-TOF/TOF; which are not support, yet) you could use \code{excludePattern="([[:digit:]\\.]+)LIFT[\\\\/]1SRef"}. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import mzXML files s <- import(exampleDirectory, type="mzXML") ## import tab delimited file with different file extension (default: *.tab) s <- import(exampleDirectory, type="tab", pattern="^.*\\\\.txt") ## import single mzML file s <- import(file.path(exampleDirectory, "tiny1.mzML1.1.mzML")) ## import gzipped csv file s <- import(file.path(exampleDirectory, "compressed", "csv1.csv.gz")) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} \code{\link[MALDIquantForeign]{MALDIquantForeign-parallel}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importImzMl-functions.Rd0000644000176200001440000000306514404344473021031 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importImzMl} \alias{importImzMl} \title{Import imzML files} \usage{ importImzMl(path, coordinates = NULL, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{coordinates}{\code{matrix}, 2 column matrix that contains the x- and y-coordinates for spectra that should be imported. Other spectra would be ignored.} \item{\ldots}{arguments to be passed to \code{\link[MALDIquantForeign]{import}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in imzML file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") ## import s <- importImzMl(file.path(exampleDirectory, "tiny_continuous.imzML")) ## import only spectra for pixel 1,1 and 2,1 s <- importImzMl(file.path(exampleDirectory, "tiny_continuous.imzML"), coordinates = cbind(1:2, c(1, 1))) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/}, \cr Definition of \code{imzML} format: \url{https://ms-imaging.org/imzml/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}} } \author{ Sebastian Gibb } MALDIquantForeign/man/importBrukerFlex-functions.Rd0000644000176200001440000000233614404344473022052 0ustar liggesusers% Generated by roxygen2: do not edit by hand % Please edit documentation in R/import-functions.R \name{importBrukerFlex} \alias{importBrukerFlex} \title{Import Bruker Daltonics *flex files} \usage{ importBrukerFlex(path, ...) } \arguments{ \item{path}{\code{character}, path to directory or file which should be read in.} \item{\ldots}{arguments to be passed to \code{\link[readBrukerFlexData]{readBrukerFlexFile}}.} } \value{ a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the \code{centroided} argument). } \description{ This function imports files in Bruker Daltonics *flex-series file format into \code{\link[MALDIquant]{MassSpectrum-class}} or \code{\link[MALDIquant]{MassPeaks-class}} objects. } \examples{ library("MALDIquant") library("MALDIquantForeign") ## get example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") s <- importBrukerFlex(exampleDirectory) } \references{ \url{https://strimmerlab.github.io/software/maldiquant/} } \seealso{ \code{\link[MALDIquant]{MassSpectrum-class}}, \code{\link[MALDIquant]{MassPeaks-class}}, \code{\link[readBrukerFlexData]{readBrukerFlexFile}} } \author{ Sebastian Gibb } MALDIquantForeign/DESCRIPTION0000644000176200001440000000255114553557406015212 0ustar liggesusersPackage: MALDIquantForeign Version: 0.14.1 Date: 2024-01-22 Title: Import/Export Routines for 'MALDIquant' Authors@R: c(person("Sebastian", "Gibb", role=c("aut", "cre"), email="mail@sebastiangibb.de", comment=c(ORCID="0000-0001-7406-4443")), person("Pietro", "Franceschi", role=c("ctb"), email="pietro.franceschi@fmach.it")) Depends: R (>= 3.2.2), methods, MALDIquant (>= 1.16.4) Imports: base64enc, digest, readBrukerFlexData (>= 1.7), readMzXmlData (>= 2.7), XML Suggests: knitr, testthat (>= 0.8), RNetCDF (>= 1.6.1) Description: Functions for reading (tab, csv, Bruker fid, Ciphergen XML, mzXML, mzML, imzML, Analyze 7.5, CDF, mMass MSD) and writing (tab, csv, mMass MSD, mzML, imzML) different file formats of mass spectrometry data into/from 'MALDIquant' objects. License: GPL (>= 3) URL: https://strimmerlab.github.io/software/maldiquant/, https://github.com/sgibb/MALDIquantForeign/ BugReports: https://github.com/sgibb/MALDIquantForeign/issues/ LazyLoad: yes VignetteBuilder: knitr RoxygenNote: 7.3.0 Encoding: UTF-8 NeedsCompilation: no Packaged: 2024-01-22 20:59:12 UTC; sebastian Author: Sebastian Gibb [aut, cre] (), Pietro Franceschi [ctb] Maintainer: Sebastian Gibb Repository: CRAN Date/Publication: 2024-01-22 21:32:54 UTC MALDIquantForeign/build/0000755000176200001440000000000014553553440014572 5ustar liggesusersMALDIquantForeign/build/vignette.rds0000644000176200001440000000043014553553440017126 0ustar liggesusersRK0N8]AQ$oJ- 郯M%%Ϳyus#wwyIc9٘xLfHzJ1F/m)~ztnzS V9Q-# M *<(t;Tl٦?iЖul2C 6s6ΉZ( h", "", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", paste0(" "), " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", "") test_that(".exportImzMl", { m <- createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(name="TEST", file="TESTS/fid")) expect_error(MALDIquantForeign:::.exportImzMl(m, file=file.path(tmp, "m.imzML")), "The spectra contain no imaging information.") MALDIquantForeign:::.exportImzMl(m, file=file.path(tmp, "m.imzML"), coordinates=cbind(1, 1), uuid="12345678-90ab-4cde-af12-34567890abcd") expect_equal(readLines(file.path(tmp, "m.imzML")), sub(pattern="id=\"tmp\"", replacement="id=\"m\"", x=imzML)) }) test_that("exportImzMl,MassSpectrum", { m <- createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(name="TEST", file="TESTS/fid")) expect_error(MALDIquantForeign::exportImzMl(m, file=file.path(tmp, "ms.imzML")), "The spectra contain no imaging information.") MALDIquantForeign::exportImzMl(m, file=file.path(tmp, "ms.imzML"), coordinates=cbind(1, 1), uuid="12345678-90ab-4cde-af12-34567890abcd") expect_equal(readLines(file.path(tmp, "ms.imzML")), sub(pattern="id=\"tmp\"", replacement="id=\"ms\"", x=imzML)) }) test_that("exportImzMl,list", { expect_error(MALDIquantForeign:::.exportImzMl(list(1:3, 4:6), file="tmp.imzML"), "MassSpectrum.*supported") m <- createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(name="TEST", file="TESTS/fid", imaging=list(pos=c(1, 1), pixelSize=c(100, 100), size=c(1, 1), dim=c(100, 100)))) spectra <- list(m, m) MALDIquantForeign::exportImzMl(spectra, path=tmp, force=TRUE, uuid="12345678-90ab-4cde-af12-34567890abcd") expect_equal(readLines(file.path(tmp, "TESTS_1.imzML")), sub(pattern="id=\"tmp\"", replacement="id=\"TESTS_1\"", x=imzML)) expect_equal(readLines(file.path(tmp, "TESTS_2.imzML")), sub(pattern="id=\"tmp\"", replacement="id=\"TESTS_2\"", x=imzML)) }) MALDIquantForeign/tests/testthat/test_sanitize-functions.R0000644000176200001440000000030713211235236023501 0ustar liggesuserscontext("sanitize") test_that("sanitize-functions", { s <- c("ac", "a&o", "abc") r <- c("a<b", "b>c", "a&o", "abc") expect_identical(MALDIquantForeign:::.sanitize(s), r) }) MALDIquantForeign/tests/testthat/test_fileFormats.R0000644000176200001440000000075613211235236022130 0ustar liggesuserscontext("fileFormats") test_that("supportedFileFormats", { r <- list(import = c("txt", "tab", "csv", "fid", "ciphergen", "mzxml", "mzml", "imzml", "analyze", "cdf", "msd"), export = c("tab", "csv", "msd", "mzml", "imzml")) expect_identical(supportedFileFormats(), r) }) MALDIquantForeign/tests/testthat/test_msg-functions.R0000644000176200001440000000037213211235236022443 0ustar liggesuserscontext("msg") test_that("msg-functions", { expect_message(MALDIquantForeign:::.msg(TRUE, "foobar"), "foobar") expect_message(MALDIquantForeign:::.msg(TRUE, "foo", "bar"), "foobar") expect_silent(MALDIquantForeign:::.msg(FALSE, "foobar")) }) MALDIquantForeign/tests/testthat/test_testChecksum-functions.R0000644000176200001440000000145113211235236024316 0ustar liggesuserscontext("testChecksum") test_that("testChecksum-functions", { f <- normalizePath(system.file( file.path("exampledata", "ascii.txt"), package="MALDIquantForeign")) md5 <- "9274dd34d675950326a222a952309a17" sha1 <- "85572c8d56504d8bba2afb32d7d7df35fb127ab8" expect_true(MALDIquantForeign:::.testChecksum(f, md5, algo="md5")) expect_true(MALDIquantForeign:::.testChecksum(f, sha1, algo="sha1")) expect_false(suppressWarnings( MALDIquantForeign:::.testChecksum(f, "12345", algo="sha1"))) expect_warning(MALDIquantForeign:::.testChecksum(f, "12345", algo="sha1"), "Stored and calculated sha1 sums do not match") expect_warning(MALDIquantForeign:::.testChecksum(f, "12345", algo="md5"), "Stored and calculated md5 sums do not match") }) MALDIquantForeign/tests/testthat/test_compression-functions.R0000644000176200001440000000616713211235236024226 0ustar liggesuserscontext("compression") z <- c("bz2", "bzip2", "gz", "lzma", "xz") e <- c("zip", z, paste("tar", z, sep="."), "tar", "txt", "mzML") f <- paste(letters[1:13], e, sep=".") test_that(".isCompressed", { expect_identical(MALDIquantForeign:::.isCompressed(f), c(rep(TRUE, 11), rep(FALSE, 3))) }) test_that(".isTar", { expect_identical(MALDIquantForeign:::.isTar(f), c(rep(FALSE, 6), rep(TRUE, 6), rep(FALSE, 2))) }) test_that(".isZip", { expect_identical(MALDIquantForeign:::.isZip(f), c(TRUE, rep(FALSE, 13))) }) test_that(".isPackedOrCompressed", { expect_identical(MALDIquantForeign:::.isPackedOrCompressed(f), c(rep(TRUE, 12), rep(FALSE, 2))) }) test_that(".uncompress supports single file compression by gunzip", { u <- MALDIquantForeign:::.uncompress( system.file(file.path("exampledata", "compressed", "csv1.csv.gz"), package="MALDIquantForeign")) f <- system.file(file.path("exampledata", "csv1.csv"), package="MALDIquantForeign") expect_identical(readLines(u), readLines(f)) expect_identical(MALDIquantForeign:::.uncompress("foobar.txt"), "foobar.txt") expect_error(MALDIquantForeign:::.uncompress("foobar.gz"), ".*foobar.gz.* doesn't exist!") }) test_that(".uncompress supports tar compression by untar", { u <- list.files(MALDIquantForeign:::.uncompress( system.file( file.path("exampledata", "compressed", "csv.tar.gz"), package="MALDIquantForeign")), recursive=TRUE, pattern="^.*\\.csv$", full.names=TRUE)[1] f <- system.file(file.path("exampledata", "csv1.csv"), package="MALDIquantForeign") expect_identical(readLines(u), readLines(f)) }) test_that(".uncompress supports zip compression by unzip", { u <- list.files(MALDIquantForeign:::.uncompress( system.file( file.path("exampledata", "compressed", "csv.zip"), package="MALDIquantForeign")), recursive=TRUE, pattern="^.*\\.csv$", full.names=TRUE)[1] f <- system.file(file.path("exampledata", "csv1.csv"), package="MALDIquantForeign") expect_identical(readLines(u), readLines(f)) expect_error(suppressWarnings(MALDIquantForeign:::.uncompress("foobar.zip")), "unzip failed!") }) test_that(".cleanupUncompressedTmpFiles works", { n <- list.files(file.path(tempdir(), "MALDIquantForeign_uncompress"), recursive=TRUE) expect_true(length(n) > 0) MALDIquantForeign:::.cleanupUncompressedTmpFiles() expect_false(file.exists(file.path(tempdir(), "MALDIquantForeign_uncompress"))) }) test_that("typical auto import", { f <- normalizePath(system.file( file.path("exampledata", "compressed", "csv1.csv.gz"), package="MALDIquantForeign")) s <- createMassSpectrum(mass=1:5, intensity=6:10) i <- import(f)[[1]] metaData(i) <- list() expect_identical(i, s) expect_false(file.exists(file.path(tempdir(), "MALDIquantForeign_uncompress"))) }) MALDIquantForeign/tests/testthat/test_download-functions.R0000644000176200001440000000331013341767210023465 0ustar liggesuserscontext("download") url <- c("http://www.tld.com/", "https://www.tld.com/archive.zip", "ftp://ftp.tld.com", "/data/archive.zip", "/root", "/dev/data.csv") test_that(".isUrl", { expect_identical(MALDIquantForeign:::.isUrl(url), c(rep(TRUE, 3), rep(FALSE, 3))) }) test_that(".download", { skip_on_cran() urls <- c("https://raw.githubusercontent.com/sgibb/MALDIquantForeign/master/inst/exampledata/ascii.txt", "https://raw.githubusercontent.com/sgibb/MALDIquantForeign/master/inst/exampledata/csv1.csv") tmpdir <- tempdir() ascii <- data.frame(V1=1:5, V2=6:10) csv <- data.frame(mass=1:5, intensity=6:10) expect_identical(read.table( MALDIquantForeign:::.download(urls[1], file.path(tmpdir, "a.txt"))), ascii) expect_identical(read.table(MALDIquantForeign:::.download(urls[1])), ascii) expect_true(all(grepl(paste("^a\\.txt$", "^MALDIquantForeign_download/ascii_.*\\.txt$", "^MALDIquantForeign_download/csv1_.*\\.csv$", sep="|"), list.files(tmpdir, recursive=TRUE)))) files <- MALDIquantForeign:::.download(urls) expect_identical(list(read.table(files[1]), read.csv(files[2], comment.char="#")), list(ascii, csv)) expect_message(MALDIquantForeign:::.download(urls[1], file.path(tmpdir, "a.txt"), verbose=TRUE), paste0("Downloading ", urls[1], " to ", file.path(tmpdir, "a.txt"), "\\.")) }) MALDIquantForeign/tests/testthat/test_exportTab-methods.R0000644000176200001440000000235413211235236023262 0ustar liggesuserscontext("exportTab") m <- createMassSpectrum(mass=1:5, intensity=6:10) r <- data.frame(V1=1:5, V2=6:10) test_that(".exportTab", { temp <- tempfile() MALDIquantForeign:::.exportTab(m, file=temp) ## didn't work on win-builder.r-project.org ## (but on local linux and windows install (both R 2.15.2) #expect_equivalent(tools::md5sum(temp), tools::md5sum(file.path("data", # "ascii.txt"))) expect_equal(read.table(temp), r) }) test_that("exportTab,MassSpectrum", { temp <- tempfile() MALDIquantForeign::exportTab(m, file=temp) expect_equal(read.table(temp), r) }) test_that(".exportCsv", { temp <- tempfile() MALDIquantForeign:::.exportCsv(m, file=temp) ## didn't work on win-builder.r-project.org ## (but on local linux and windows install (both R 2.15.2) #expect_equivalent(tools::md5sum(temp), tools::md5sum(file.path("data", # "csv1.csv"))) colnames(r) <- c("mass", "intensity") expect_equal(read.csv(temp), r) }) test_that("exportCsv,MassSpectrum", { temp <- tempfile() MALDIquantForeign::exportCsv(m, file=temp) colnames(r) <- c("mass", "intensity") expect_equal(read.csv(temp), r) }) MALDIquantForeign/tests/testthat/test_importBrukerFlex-functions.R0000644000176200001440000000135313211235236025161 0ustar liggesuserscontext("importBrukerFlex") test_that("importBrukerFlex", { expect_error(MALDIquantForeign:::.importBrukerFlex("tmp.tmp")) path <- system.file( file.path("exampledata", "brukerflex", "0_A1", "1", "1SLin", "fid"), package="MALDIquantForeign") s <- MALDIquantForeign:::.importBrukerFlex(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importBrukerFlex(path, verbose=FALSE)) expect_equal(s, import(path, type="fid", verbose=FALSE)) expect_equal(trunc(mass(s[[1]])), 226:230) expect_equal(intensity(s[[1]]), 1:5) expect_equal(basename(metaData(s[[1]])$file), "fid") expect_equal(metaData(s[[1]])$laserShots, 100) expect_equal(metaData(s[[1]])$comments, paste0("TESTSAMPLE", 1:4)) }) MALDIquantForeign/tests/testthat/test_uuid-functions.R0000644000176200001440000000167413211235236022631 0ustar liggesuserscontext("uuid") test_that(".uuid", { expect_identical(MALDIquantForeign:::.uuid(init="foobar"), "3858f622-30ac-4c91-9f30-0c664312c63f") }) test_that(".isUuidV4", { ## invalid letters (not hexadecimal) expect_false(MALDIquantForeign:::.isUuidV4("z858f622-30ac-4c91-9f30-0c664312c63f")) ## not version 4 expect_false(MALDIquantForeign:::.isUuidV4("3858f622-30ac-3c91-9f30-0c664312c63f")) ## y (pos 17 is not 8, 9, A, or B expect_false(MALDIquantForeign:::.isUuidV4("3858f622-30ac-4c91-cf30-0c664312c63f")) expect_true(MALDIquantForeign:::.isUuidV4("3858f622-30ac-4c91-9f30-0c664312c63f")) expect_true(MALDIquantForeign:::.isUuidV4("3858f62230ac4c919f300c664312c63f")) expect_true(MALDIquantForeign:::.isUuidV4(MALDIquantForeign:::.uuid())) expect_equal(MALDIquantForeign:::.isUuidV4(c("foobar", "3858f62230ac4c919f300c664312c63f")), c(FALSE, TRUE)) }) MALDIquantForeign/tests/testthat/test_importCiphergenXml-functions.R0000644000176200001440000000135713211235236025501 0ustar liggesuserscontext("importCiphergenXml") test_that("importCiphergenXml", { expect_error(MALDIquantForeign:::.importCiphergenXml("tmp.tmp")) path <- system.file(file.path("exampledata", "ciphergen", "tiny.xml"), package="MALDIquantForeign") s <- MALDIquantForeign:::.importCiphergenXml(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importCiphergenXml(path, verbose=FALSE)) expect_equal(s, import(path, type="ciph", verbose=FALSE)) expect_equal(trunc(mass(s[[1]])), rep(26, 5)) expect_false(all(mass(s[[1]])[1] == mass(s[[1]]))) expect_equal(intensity(s[[1]]), 1:5) expect_equal(basename(metaData(s[[1]])$file), "tiny.xml") expect_equal(metaData(s[[1]])$name, "tiny example") }) MALDIquantForeign/tests/testthat/test_importMzXml-functions.R0000644000176200001440000000400513211235236024154 0ustar liggesuserscontext("importMzXml") test_that("importMzXml", { expect_error(MALDIquantForeign:::.importMzXml("tmp.tmp")) path <- system.file(file.path("exampledata", "tiny1.mzXML3.0.mzXML"), package="MALDIquantForeign") s <- MALDIquantForeign:::.importMzXml(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importMzXml(path, verbose=FALSE)) expect_equal(s, import(path, type="mzXML", verbose=FALSE)) expect_true(isMassSpectrum(s[[1]])) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny1.mzXML3.0.mzXML") }) test_that("importMzXml compressed", { expect_error(MALDIquantForeign:::.importMzXml("tmp.tmp")) path <- system.file(file.path("exampledata", "tiny1-compressed.mzXML3.0.mzXML"), package="MALDIquantForeign") s <- MALDIquantForeign:::.importMzXml(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importMzXml(path, verbose=FALSE)) expect_equal(s, import(path, type="mzXML", verbose=FALSE)) expect_true(isMassSpectrum(s[[1]])) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny1-compressed.mzXML3.0.mzXML") }) test_that("importMzXml centroided", { expect_error(MALDIquantForeign:::.importMzXml("tmp.tmp")) path <- system.file(file.path("exampledata", "tiny1-centroided.mzXML3.0.mzXML"), package="MALDIquantForeign") p <- MALDIquantForeign:::.importMzXml(path, centroided=TRUE, verbose=FALSE) expect_equal(p, import(path, centroided=TRUE, verbose=FALSE)) expect_equal(p, importMzXml(path, centroided=TRUE, verbose=FALSE)) expect_equal(p, import(path, type="mzXML", centroided=TRUE, verbose=FALSE)) expect_true(isMassPeaks(p[[1]])) expect_equal(mass(p[[1]]), 1:5) expect_equal(intensity(p[[1]]), 6:10) expect_equal(basename(metaData(p[[1]])$file), "tiny1-centroided.mzXML3.0.mzXML") }) MALDIquantForeign/tests/testthat/test_importMsd-functions.R0000644000176200001440000000114613211235236023633 0ustar liggesuserscontext("importMsd") test_that("importMsd", { expect_error(MALDIquantForeign:::.importMsd("tmp.tmp")) path <- normalizePath(system.file( file.path("exampledata", "tiny1.msd"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importMsd(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importMsd(path, verbose=FALSE)) expect_equal(s, import(path, type="msd", verbose=FALSE)) expect_true(isMassSpectrum(s[[1]])) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny1.msd") }) MALDIquantForeign/tests/testthat/test_ibd-functions.R0000644000176200001440000000313713211235236022415 0ustar liggesuserscontext("ibd") s <- list(createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=6:10)) processed <- matrix(c(cumsum(c(16L, rep.int(40L, 3L))), rep.int(5L, 4L), rep.int(40L, 4L)), nrow=4L) continuous<- matrix(c(16L, 56L, 16L, 96L, rep.int(5L, 4L), rep.int(40L, 4L)), nrow=4L) dimnames(processed) <- dimnames(continuous) <- list(rep(c("mass", "intensity"), 2), c("offset", "length", "encodedLength")) #test_that(".writeIbd", { #uuid <- "3858f622-30ac-4c91-9f30-0c664312c63f" #file <- tempfile() #MALDIquantForeign:::.writeIbd(filename=file, uuid=uuid) #}) test_that(".ibdOffsets", { expect_equal(MALDIquantForeign:::.ibdOffsets(s, processed=TRUE), processed) expect_equal(MALDIquantForeign:::.ibdOffsets(s, processed=FALSE), continuous) }) test_that(".addIbdOffsets", { rp <- list(createMassSpectrum(mass=1:5, intensity=1:5, metaData=list(imaging=list(offsets=processed[1:2,]))), createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(imaging=list(offsets=processed[3:4,])))) rc <- list(createMassSpectrum(mass=1:5, intensity=1:5, metaData=list(imaging=list(offsets=continuous[1:2,]))), createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(imaging=list(offsets=continuous[3:4,])))) expect_equal(MALDIquantForeign:::.addIbdOffsets(s, processed=TRUE), rp) expect_equal(MALDIquantForeign:::.addIbdOffsets(s, processed=FALSE), rc) }) MALDIquantForeign/tests/testthat/test_importCdf-functions.R0000644000176200001440000000416713211235236023612 0ustar liggesuserscontext("importCdf") ## create NetCDF test file # #library("RNetCDF") #nc <- create.nc("tiny.cdf") # #dim.def.nc(nc, "scan_number", 2) #dim.def.nc(nc, "point_number", 10, unlim=TRUE) # #var.def.nc(nc, "scan_index", "NC_INT", "scan_number") #var.def.nc(nc, "point_count", "NC_INT", "scan_number") #var.def.nc(nc, "scan_acquisition_time", "NC_DOUBLE", "scan_number") # #var.def.nc(nc, "mass_values", "NC_DOUBLE", "point_number") #var.def.nc(nc, "intensity_values", "NC_INT", "point_number") # #var.put.nc(nc, "scan_index", c(0,5)) #var.put.nc(nc, "point_count", c(5, 5)) #var.put.nc(nc, "scan_acquisition_time", c(1, 2)) # #var.put.nc(nc, "mass_values", 1:5, start=1, count=5) #var.put.nc(nc, "mass_values", 6:10, start=6, count=5) #var.put.nc(nc, "intensity_values", 11:15, start=1, count=5) #var.put.nc(nc, "intensity_values", 16:20, start=6, count=5) # #close.nc(nc) # test_that("importCdf", { path <- normalizePath(system.file(file.path("exampledata", "tiny.cdf"), package="MALDIquantForeign")) if (suppressWarnings(require("RNetCDF", quietly=TRUE))) { ## suppress warnings to avoid creation of Rplots.pdf expect_error(suppressWarnings(MALDIquantForeign:::.importCdf("tmp.tmp"))) r <- list(createMassSpectrum(mass=1:5, intensity=11:15, metaData=list(file=path, number=1, retentionTime=1, scanIndex=0)), createMassSpectrum(mass=6:10, intensity=16:20, metaData=list(file=path, number=2, retentionTime=2, scanIndex=5))) s <- MALDIquantForeign:::.importCdf(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importCdf(path, verbose=FALSE)) expect_equal(s, import(path, type="cdf", verbose=FALSE)) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 11:15) expect_equal(basename(metaData(s[[1]])$file), "tiny.cdf") expect_equal(s, r) } else { expect_error(suppressWarnings(MALDIquantForeign:::.importCdf(path)), "install.packages") } }) MALDIquantForeign/tests/testthat/test_exportMzMl-methods.R0000644000176200001440000001150214464725452023445 0ustar liggesuserscontext("exportMzMl") m <- createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(name="TEST", file="TESTS/fid")) bm <- .base64encode(1:5, size=8, endian="little", compressionType="gzip") bi <- .base64encode(6:10, size=8, endian="little", compressionType="gzip") tmp <- tempdir() mzML <- c( "", "", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", paste0(" "), " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", " ", paste0(" "), " ", " ", " ", paste0(" ", bm, ""), " ", paste0(" "), " ", " ", " ", paste0(" ", bi, ""), " ", " ", " ", " ", " ", "") test_that(".exportMzMl", { MALDIquantForeign:::.exportMzMl(m, file=file.path(tmp, "m.mzML")) expect_equal(readLines(file.path(tmp, "m.mzML")), sub(pattern="id=\"tmp\"", replacement="id=\"m\"", x=mzML)) }) test_that("exportMzMl,MassSpectrum", { MALDIquantForeign:::exportMzMl(m, file=file.path(tmp, "ms.mzML")) expect_equal(readLines(file.path(tmp, "ms.mzML")), sub(pattern="id=\"tmp\"", replacement="id=\"ms\"", x=mzML)) }) test_that("exportMzMl,list", { spectra <- list(m, m) MALDIquantForeign::exportMzMl(spectra, path=tmp, force=TRUE) expect_equal(readLines(file.path(tmp, "TESTS_1.mzML")), sub(pattern="id=\"tmp\"", replacement="id=\"TESTS_1\"", x=mzML)) expect_equal(readLines(file.path(tmp, "TESTS_2.mzML")), sub(pattern="id=\"tmp\"", replacement="id=\"TESTS_2\"", x=mzML)) }) MALDIquantForeign/tests/testthat/test_mzMl-functions.R0000644000176200001440000000113414404344473022602 0ustar liggesuserscontext("mzMl") test_that(".writeImzMlScanList", { m <- createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(imaging=list(pos=c(x=1e8, y=1e8)))) f <- file.path(tempdir(), "imzlscanlist") r <- c( " ", " ", " ", " ", " ", " " ) MALDIquantForeign:::.writeImzMlScanList(m, file=f) expect_equal(readLines(f), r) }) MALDIquantForeign/tests/testthat/test_importMzMl-functions.R0000644000176200001440000000543713211235236023776 0ustar liggesuserscontext("importMzMl") test_that("importMzMl", { expect_error(MALDIquantForeign:::.importMzMl("tmp.tmp")) path <- normalizePath(system.file( file.path("exampledata", "tiny1.mzML1.1.mzML"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importMzMl(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importMzMl(path, verbose=FALSE)) expect_equal(s, import(path, type="mzML", verbose=FALSE)) expect_true(isMassSpectrum(s[[1]])) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny1.mzML1.1.mzML") expect_true(isMassSpectrum(s[[2]])) expect_equal(mass(s[[2]]), 1:5) expect_equal(intensity(s[[2]]), 10:6) expect_equal(basename(metaData(s[[2]])$file), "tiny1.mzML1.1.mzML") }) test_that("importMzMl compressed", { expect_error(MALDIquantForeign:::.importMzMl("tmp.tmp")) path <- normalizePath(system.file( file.path("exampledata", "tiny1-compressed.mzML1.1.mzML"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importMzMl(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importMzMl(path, verbose=FALSE)) expect_equal(s, import(path, type="mzML", verbose=FALSE)) expect_true(isMassSpectrum(s[[1]])) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny1-compressed.mzML1.1.mzML") expect_true(isMassSpectrum(s[[2]])) expect_equal(mass(s[[2]]), 1:5) expect_equal(intensity(s[[2]]), 10:6) expect_equal(basename(metaData(s[[2]])$file), "tiny1-compressed.mzML1.1.mzML") }) test_that("importMzMl centroided", { expect_error(MALDIquantForeign:::.importMzMl("tmp.tmp")) path <- normalizePath(system.file( file.path("exampledata", "tiny1-centroided.mzML1.1.mzML"), package="MALDIquantForeign")) p <- MALDIquantForeign:::.importMzMl(path, centroided=TRUE, verbose=FALSE) expect_equal(p, import(path, centroided=TRUE, verbose=FALSE)) expect_equal(p, importMzMl(path, centroided=TRUE, verbose=FALSE)) expect_equal(p, import(path, type="mzML", centroided=TRUE, verbose=FALSE)) expect_true(isMassPeaks(p[[1]])) expect_equal(mass(p[[1]]), 1:5) expect_equal(intensity(p[[1]]), 6:10) expect_equal(basename(metaData(p[[1]])$file), "tiny1-centroided.mzML1.1.mzML") expect_true(isMassPeaks(p[[2]])) expect_equal(mass(p[[2]]), 1:5) expect_equal(intensity(p[[2]]), 10:6) expect_equal(basename(metaData(p[[2]])$file), "tiny1-centroided.mzML1.1.mzML") ## overwrite default arguments path <- normalizePath(system.file( file.path("exampledata", "tiny1.mzML1.1.mzML"), package="MALDIquantForeign")) expect_true(all(sapply(MALDIquantForeign:::.importMzMl(path, centroided=TRUE), isMassPeaks))) }) MALDIquantForeign/tests/testthat/test_list.files-functions.R0000644000176200001440000000167113211235236023734 0ustar liggesuserscontext("list.files") test_that("list.files-functions", { path <- normalizePath(system.file("exampledata", package="MALDIquantForeign")) expect_identical(MALDIquantForeign:::.list.files(path, pattern="tiny1-c"), normalizePath(file.path(path, c("tiny1-centroided.mzML1.1.mzML", "tiny1-centroided.mzXML3.0.mzXML", "tiny1-compressed.mzML1.1.mzML", "tiny1-compressed.mzXML3.0.mzXML")))) expect_identical(MALDIquantForeign:::.list.files(path, pattern="tiny1-c", excludePattern="\\.mzXML$"), normalizePath(file.path(path, c("tiny1-centroided.mzML1.1.mzML", "tiny1-compressed.mzML1.1.mzML")))) }) MALDIquantForeign/tests/testthat/test_importImzMl-functions.R0000644000176200001440000000444314464465745024170 0ustar liggesuserscontext("importImzMl") test_that("importImzMl continuous", { expect_error(MALDIquantForeign:::.importImzMl("tmp.tmp")) path <- normalizePath(system.file( file.path("exampledata", "tiny_continuous.imzML"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importImzMl(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importImzMl(path, verbose=FALSE)) expect_equal(s, import(path, type="imzML", verbose=FALSE)) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny_continuous.imzML") expect_equal(mass(s[[2]]), 1:5) expect_equal(intensity(s[[2]]), 10:6) expect_equal(basename(metaData(s[[2]])$file), "tiny_continuous.imzML") }) test_that("importImzMl processed", { path <- normalizePath(system.file( file.path("exampledata", "tiny_processed.imzML"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importImzMl(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importImzMl(path, verbose=FALSE)) expect_equal(s, import(path, type="imzML", verbose=FALSE)) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "tiny_processed.imzML") expect_equal(mass(s[[2]]), 6:10) expect_equal(intensity(s[[2]]), 10:6) expect_equal(basename(metaData(s[[2]])$file), "tiny_processed.imzML") }) test_that("importImzMl coordinates", { path <- normalizePath(system.file( file.path("exampledata", "tiny_continuous.imzML"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importImzMl(path, verbose=FALSE) expect_equal(s, importImzMl(path, coordinates=cbind(1:2, c(1, 1)), verbose=FALSE)) expect_equal(s[1], importImzMl(path, coordinates=cbind(1, 1), verbose=FALSE)) expect_equal(s[[2]], importImzMl(path, coordinates=cbind(2, 1), verbose=FALSE)[[1]]) expect_error(importImzMl(path, coordinates=3, verbose=FALSE), "The .*coordinates.* argument has to be a matrix with two columns") expect_warning(importImzMl(path, coordinates=cbind(1:3, 2:0), verbose=FALSE), "The following rows contain invalid coordinates: 1, 3") }) MALDIquantForeign/tests/testthat/test_exportMsd-methods.R0000644000176200001440000000462214464725774023325 0ustar liggesuserscontext("exportMsd") m <- createMassSpectrum(mass=1:5, intensity=6:10, metaData=list(owner="OWNER", institution="INSTITUTION", instrument="INSTRUMENT")) p <- createMassPeaks(mass=4:5, intensity=9:10, snr=1:2) bm <- .base64encode(1:5, size=8, compressionType="gzip") bi <- .base64encode(6:10, size=8, compressionType="gzip") tmp <- tempdir() msd <- c( "", "", " ", " tmp.msd", " ", " ", " ", " ", " ", " ", " ", " ", paste0(" ", bm ,""), paste0(" ", bi, ""), " ", " ", " ", " ", " ", "") test_that(".exportMsd", { MALDIquantForeign:::.exportMsd(m, file=file.path(tmp, "m.msd"), peaks=p) expect_equal(readLines(file.path(tmp, "m.msd"))[-c(4:5)], msd[-c(4:5)]) }) test_that("exportMsd,MassSpectrum", { MALDIquantForeign::exportMsd(m, file=file.path(tmp, "msp.msd"), peaks=p) expect_equal(readLines(file.path(tmp, "msp.msd"))[-c(4:5)], msd[-c(4:5)]) MALDIquantForeign::exportMsd(m, file=file.path(tmp, "ms.msd")) expect_equal(readLines(file.path(tmp, "ms.msd"))[-c(4:5)], msd[-c(4:5, 16:19)]) }) test_that("exportMsd,list", { spectra <- list(m, m) peaks <- list(p, p) MALDIquantForeign::exportMsd(spectra, path=tmp, force=TRUE, peaks=peaks) expect_equal(readLines(file.path(tmp, "1.msd"))[-c(4:5)], msd[-c(4:5)]) expect_equal(readLines(file.path(tmp, "2.msd"))[-c(4:5)], msd[-c(4:5)]) MALDIquantForeign::exportMsd(spectra, path=tmp, force=TRUE) expect_equal(readLines(file.path(tmp, "1.msd"))[-c(4:5)], msd[-c(4:5, 16:19)]) expect_equal(readLines(file.path(tmp, "2.msd"))[-c(4:5)], msd[-c(4:5, 16:19)]) }) test_that(".createMsdTitle", { f <- file(file.path(tempdir(), "test.msd")) expect_true(MALDIquantForeign:::.createMsdTitle(f) == "test") close(f) }) MALDIquantForeign/tests/testthat/test_filename-functions.R0000644000176200001440000000536313211235236023442 0ustar liggesuserscontext("filename") test_that(".cleanFilename", { expect_identical(MALDIquantForeign:::.cleanFilename( "/home/a:/\"foo&bar\"/g.\\23!/ foo-bar?.txt"), "_home_a_foo_bar_g_23_foo_bar_txt") }) test_that("file extension is returned", { expect_identical(MALDIquantForeign:::.fileExtension("~/foo.txt"), "txt") expect_identical(MALDIquantForeign:::.fileExtension( c("/etc/a.conf", "b.pdf")), c("conf", "pdf")) }) test_that("file name is returned", { expect_identical(MALDIquantForeign:::.fileExtension("~/foo"), "foo") }) test_that("path without extension is returned", { expect_identical(MALDIquantForeign:::.withoutFileExtension( c("~/foo", "/home/user/xyz.tar.gz", "/tmp/bar.txt")), c("~", "/home/user/xyz", "/tmp/bar")) }) test_that("file extension is changed", { expect_identical(MALDIquantForeign:::.changeFileExtension( c("/home/user/xyz.tar.gz", "/tmp/bar.txt"), c("txt", "csv")), c("/home/user/xyz.txt", "/tmp/bar.csv")) }) test_that(".cutFilenames", { expect_identical(MALDIquantForeign:::.cutFilenames( c("/home/user/foo.bar", "/home/user/xyz.tar.gz")), c("foo.bar", "xyz.tar.gz")) expect_identical(MALDIquantForeign:::.cutFilenames( c("/home/user/foo.bar", "/home/user/foo.bar")), c("foo.bar", "foo.bar")) }) test_that(".composeFilenames", { s <- createMassSpectrum(mass=1:5, intensity=1:5, metaData=list(file="/foo/bar.txt")) expect_identical(MALDIquantForeign:::.composeFilename(s), "/foo/bar.csv") expect_identical(MALDIquantForeign:::.composeFilename(s, fileExtension="xml"), "/foo/bar.xml") metaData(s) <- list(fullName="foo") expect_identical(MALDIquantForeign:::.composeFilename(s), "foo.csv") metaData(s) <- list(fullName=c("foo", "bar")) expect_identical(MALDIquantForeign:::.composeFilename(s), "foo_bar.csv") }) test_that(".uniqueBaseFilenames", { expect_identical(MALDIquantForeign:::.uniqueBaseFilenames( c("/home/user/foo.bar", "/home/user/foo.bar"), fileExtension="txt"), c("foo_1.txt", "foo_2.txt")) expect_identical(MALDIquantForeign:::.uniqueBaseFilenames( c("", "")), c("1.csv", "2.csv")) }) test_that(".make.unique", { expect_equal(MALDIquantForeign:::.make.unique(LETTERS[1:5]), LETTERS[1:5]) expect_equal(MALDIquantForeign:::.make.unique(rep(LETTERS[1:5], each=2)), paste(rep(LETTERS[1:5], each=2), 1:2, sep="_")) expect_equal(MALDIquantForeign:::.make.unique(rep(LETTERS[1:2], each=10)), sprintf("%s_%02d", rep(LETTERS[1:2], each=10), 1:10)) }) MALDIquantForeign/tests/testthat/test_importTab-functions.R0000644000176200001440000000573314404344473023635 0ustar liggesuserscontext("importTab") test_that("importTab", { ## suppress warnings to avoid creation of Rplots.pdf expect_error(suppressWarnings(MALDIquantForeign:::.importTab("tmp.tmp"))) path <- normalizePath(system.file(file.path("exampledata", "ascii.txt"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importTab(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importTxt(path, verbose=FALSE)) expect_equal(s, import(path, type="txt", verbose=FALSE)) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "ascii.txt") ## issue 29, double skip expect_equal( as.matrix(MALDIquantForeign:::.importTab(path, skip=2L, verbose=FALSE)[[1L]]), matrix(c(3:5, 8:10), ncol=2L, dimnames=list(c(), c("mass", "intensity"))) ) }) test_that("importCsv", { ## suppress warnings to avoid creation of Rplots.pdf expect_error(suppressWarnings(MALDIquantForeign:::.importCsv("tmp.tmp"))) path <- normalizePath(system.file(file.path("exampledata", "csv1.csv"), package="MALDIquantForeign")) s <- MALDIquantForeign:::.importCsv(path, sep=",", header=TRUE, verbose=FALSE) expect_equal(s, import(path, sep=",", header=TRUE, verbose=FALSE)) expect_equal(s, importCsv(path, sep=",", header=TRUE, verbose=FALSE)) expect_equal(s, import(path, type="csv", sep=",", header=TRUE, verbose=FALSE)) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "csv1.csv") ## auto header s <- MALDIquantForeign:::.importCsv(path, verbose=FALSE) expect_equal(s, import(path, verbose=FALSE)) expect_equal(s, importCsv(path, verbose=FALSE)) expect_equal(s, import(path, type="csv", verbose=FALSE)) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "csv1.csv") s <- MALDIquantForeign:::.importCsv(system.file( file.path("exampledata", "csv2.csv"), package="MALDIquantForeign"), sep=";", header=FALSE) expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "csv2.csv") ## auto header s <- MALDIquantForeign:::.importCsv(file.path(dirname(path), "csv2.csv"), sep=";") expect_equal(mass(s[[1]]), 1:5) expect_equal(intensity(s[[1]]), 6:10) expect_equal(basename(metaData(s[[1]])$file), "csv2.csv") }) x <- c("10, 30", "\"foo\", \"bar\"", "foo; bar", "foo\tbar", "1\t 2") sep <- c(",", ",", ";", "\t", "\t") test_that("autoHeader", { result <- c(FALSE, TRUE, TRUE, TRUE, FALSE) for (i in seq(along=x)) { expect_identical(MALDIquantForeign:::.autoHeader(x[i], sep=sep[i]), result[i]) } }) test_that("autoSep", { for (i in seq(along=x)) { expect_identical(MALDIquantForeign:::.autoSep(x[i]), sep[i]) } }) MALDIquantForeign/tests/testthat.R0000644000176200001440000000006413211235236016606 0ustar liggesuserslibrary("testthat") test_check("MALDIquantForeign") MALDIquantForeign/vignettes/0000755000176200001440000000000014553553440015503 5ustar liggesusersMALDIquantForeign/vignettes/MALDIquantForeign-intro.Rnw0000644000176200001440000001371314553545654022552 0ustar liggesusers%\VignetteEngine{knitr::knitr} %\VignetteIndexEntry{MALDIquantForeign: Import/Export routines for MALDIquant} %\VignetteKeywords{Bioinformatics, Proteomics, Mass Spectrometry} %\VignettePackage{MALDIquantForeign} \documentclass[12pt]{article} \usepackage{natbib} \usepackage{hyperref} \usepackage{tikz} \usepackage{bibentry} % inline bibentries \nobibliography* % no special bibliography for bibentry \newcommand{\R}{\texttt{R}} \newcommand{\CRAN}{\texttt{CRAN}} \newcommand{\Rfunction}[1]{{\texttt{#1}}} \newcommand{\Robject}[1]{{\texttt{#1}}} \newcommand{\Rpackage}[1]{{\texttt{#1}}} \newcommand{\Mq}{\Rpackage{MALDIquant}} \newcommand{\MqF}{\Rpackage{MALDIquantForeign}} \newcommand{\email}[1]{\href{mailto:#1}{\normalfont\texttt{#1}}} \title{\MqF{}: Import/Export routines for \Mq{}} \author{ Sebastian Gibb% \thanks{\email{mail@sebastiangibb.de}} } \date{\today} \begin{document} <>= library("knitr") opts_chunk$set(tidy.opts=list(width.cutoff=45), tidy=FALSE, fig.align="center", fig.height=4.25, comment=NA, prompt=TRUE) @ <>= suppressPackageStartupMessages(library("MALDIquant")) suppressPackageStartupMessages(library("MALDIquantForeign")) @ \maketitle \begin{abstract} \MqF{} provides routines for importing/exporting different file formats into/from \Mq{}.\\ This vignette describes the usage of the \MqF{} package. \end{abstract} \clearpage \tableofcontents \section*{Foreword} \MqF{} is free and open source software for the \R{} \citep{RPROJECT} environment and under active development. If you use it, please support the project by citing it in publications: \begin{quote} \bibentry{MALDIquant} \end{quote} If you have any questions, bugs, or suggestions do not hesitate to contact me (\email{mail@sebastiangibb.de}). \\ Please visit \url{http://strimmerlab.org/software/maldiquant/}. \section{Introduction} \Mq{} should be device and platform independent. That's why it has not any import/export functions. \\ \MqF{} fills this gap and provides import/export routines for various file formats: <>= supportedFileFormats() @ \section{Setup} After starting \R{} we could install \Mq{} and \MqF{} directly from \CRAN{} using \Rfunction{install.packages}: <>= install.packages(c("MALDIquant", "MALDIquantForeign")) @ Before we can use \Mq{} and \MqF{} we have to load the packages. <>= library("MALDIquant") library("MALDIquantForeign") @ \section{Import} \MqF{} provides an \Rfunction{import} function that tries to auto-detect the correct file type. Because this would never be perfect \MqF{} offers also many \Rfunction{import*} functions like \Rfunction{importBrukerFlex}, \Rfunction{importMzMl}, etc. Please see the manual page of \Rfunction{import} for a complete list (\Rfunction{?import}).\\ First we try to import some example data in Bruker Daltonics *flex-series file format using the \Rfunction{import} function. <>= ## get the example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") spectra <- import(file.path(exampleDirectory, "brukerflex"), verbose=FALSE) spectra[[1]] @ Next we use the \Rfunction{importBrukerFlex} function (the result is the same as above). <>= spectra <- importBrukerFlex(file.path(exampleDirectory, "brukerflex"), verbose=FALSE) spectra[[1]] @ \MqF{} supports compressed files, too (\emph{zip}, \emph{tar.\{bz2, gz,xz\}}). <>= spectra <- importCsv(file.path(exampleDirectory, "compressed", "csv.tar.gz"), verbose=FALSE) spectra[[1]] spectra <- importCsv(file.path(exampleDirectory, "compressed", "csv.zip"), verbose=FALSE) spectra[[1]] @ Remote files are supported as well. Data are taken from \citet{Tan2006}. <>= spectra <- import(paste0("http://www.meb.ki.se/", "~yudpaw/papers/spikein_xml.zip"), centroided=FALSE, verbose=TRUE) @ If you want to read peak lists (centroided data) instead of spectra data you have to set \Rfunction{centroided=TRUE}. <>= peaks <- import(file.path(exampleDirectory, "ascii.txt"), centroided=TRUE, verbose=FALSE) peaks @ \section{Export} The export routines in \MqF{} are very similar to the import routines. Please see manual page of \Rfunction{export} for a complete list of supported export routines (\Rfunction{?export}). First we create a simple list of \Robject{MassSpectrum} objects using \Rfunction{createMassSpectrum}. <>= spectra <- list( createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=6:10)) @ Now we want to export the first spectrum into a CSV file. <>= export(spectra[[1]], file="spectrum1.csv") import("spectrum1.csv") @ Exporting every file by hand is cumbersome. We want to export the whole list of spectra. Instead of \Robject{file} we use \Robject{path} now to specify a directory. Please note that we have to add the file type/format information now (we can use the \Robject{type} argument or the corresponding \Rfunction{export*} function). If the path doesn't exists we will get an error. To force \Rfunction{export} to create/overwrite the given path, we set the argument \Robject{force=TRUE}. <>= export(spectra, type="csv", path="spectra", force=TRUE) list.files("spectra") @ \section{Analyse Mass Spectrometry Data} Please have a look at the corresponding vignette shipped with \Mq{} and the \Mq{} website: \url{http://strimmerlab.org/software/maldiquant/}. <>= vignette(topic="MALDIquant", package="MALDIquant") @ \section{Session Information} <>= toLatex(sessionInfo(), locale=FALSE) @ \bibliographystyle{apalike} \bibliography{bibliography} \end{document} MALDIquantForeign/vignettes/bibliography.bib0000644000176200001440000000250213211235236020621 0ustar liggesusers@MANUAL{RPROJECT, title = {R: A Language and Environment for Statistical Computing}, author = {{R Core Team}}, organization = {R Foundation for Statistical Computing}, address = {Vienna, Austria}, year = {2014}, url = {http://www.R-project.org/}, } @ARTICLE{MALDIquant, title = {{MALDI}quant: a versatile {R} package for the analysis of mass spectrometry data}, author = {Sebastian Gibb and Korbinian Strimmer}, volume = {28}, number = {17}, pages = {2270-2271}, year = {2012}, doi = {10.1093/bioinformatics/bts447}, url = {http://bioinformatics.oxfordjournals.org/content/28/17/2270.abstract}, eprint = {http://bioinformatics.oxfordjournals.org/content/28/17/2270.full.pdf+html}, journal = {Bioinformatics}, publisher = {Oxford Univ Press}, } @ARTICLE{Tan2006, title={Finding regions of significance in {SELDI} measurements for identifying protein biomarkers}, author={Tan, Chuen Seng and Ploner, Alexander and Quandt, Andreas and Lehti{\"o}, Janne and Pawitan, Yudi}, volume={22}, number={12}, pages={1515--1523}, year={2006}, doi = {10.1093/bioinformatics/btl106}, url = {http://bioinformatics.oxfordjournals.org/content/22/12/1515.abstract}, eprint = {http://bioinformatics.oxfordjournals.org/content/22/12/1515.full.pdf+html}, journal={Bioinformatics}, publisher={Oxford Univ Press} } MALDIquantForeign/NEWS0000644000176200001440000002766414553546760014220 0ustar liggesusersRELEASE HISTORY OF THE "MALDIquantForeign" PACKAGE ================================================== CHANGES in MALDIquantForeign VERSION 0.14.1 [2024-01-22] -------------------------------------------------------- INTERNAL CHANGES * Fix VignetteEngine NOTE. CHANGES in MALDIquantForeign VERSION 0.14 [2023-08-11] ------------------------------------------------------ INTERNAL CHANGES * Adapt unit tests for `writeMzMlDocument`/`writeMsdDocument` to `libdeflate` (new default compression for `memCompress`/`memDecompress` in R > 3.4.1). CHANGES in MALDIquantForeign VERSION 0.13 [2021-12-23] ------------------------------------------------------ DOCUMENTATION * `exportMzMl` and `exportImzMl` also support the export of `MALDIquant::MassPeaks` objects. (Before just `MassSpectrum` was mentioned.) MODIFICATIONS * Change URLs from http to https where possible. INTERNAL CHANGES * Test for `MassSpectrum` and `MassPeaks` list in `.write{Imz,Mz}MlDocument`. * Remove `is.null(getGeneric(...))` tests before setting generics for S4 methods to avoid errors in package loading (especially with `pkgload::load_all()`). * `.writeImzMlDocument` uses `MALDIquant::coordinates` explicitly to avoid method dispatch conflict in combination with the `sp` package. Reported by Denis Abu Sammour (#33). CHANGES in MALDIquantForeign VERSION 0.12.2 [2020-09-18]: --------------------------------------------------------- * Fix `.autoSep` and `.autoHeader` to look just in the first line of an ascii document for separator/header information. Before the whole file was search but just the first line reported anyway. This results in an unnecessary long reading time. Affected functions (if arguments "sep" and "header" where not given by the user: .csv, .tab, .txt import: `import`, `importCsv`, `importTab`, `importTxt`. CHANGES in MALDIquantForeign VERSION 0.12.1 [2020-03-09]: --------------------------------------------------------- * Fix reading of txt, csv, tab files if "skip" argument is used ("skip" was applied twice). Affected functions: .csv, .tab, .txt import: `import`, `importCsv`, `importTab`, `importTxt`. Bug reported by Samuel Granjeaud (#29). CHANGES in MALDIquantForeign VERSION 0.12 [2019-01-30]: ------------------------------------------------------- * Fix reading of mzML with "non-standard data" arrays. Bug reported by Paul Turner. CHANGES in MALDIquantForeign VERSION 0.11.6 [2018-08-30]: --------------------------------------------------------- * Ignore comments in `.autoSep` and `.autoHeader`. Affected functions: .tab and .csv import, `import`, `importCsv`, `importTab`, `importTxt`. Bug reported by Fernando Pineda. CHANGES in MALDIquantForeign VERSION 0.11.5 [2018-08-14]: --------------------------------------------------------- * Fix psidev URLs. CHANGES in MALDIquantForeign VERSION 0.11.4 [2018-08-01]: --------------------------------------------------------- BUGFIX * Don't access `totalIonCurrent` for `MassPeaks` objects in `exportMzMl` and `exportImzMl`. CHANGES in MALDIquantForeign VERSION 0.11.3 [2018-05-27]: --------------------------------------------------------- BUGFIX * Don't use scientific format for numeric values in (i)mzML export. Patch by F. Orlando Galashan (see #25). CHANGES in MALDIquantForeign VERSION 0.11.2 [2018-03-18]: --------------------------------------------------------- BUGFIX * Fix missing unitName in intensity array in mzMl export. Reported by Jan Kobarg patch proposed by F. Orlando Galashan (see #22/#24). CHANGES IN MALDIquantForeign VERSION 0.11.1 [2017-12-04]: --------------------------------------------------------- BUGFIX * Fix handling of "processed" argument in `.writeImzMlDocument`; see #21. * Fix `export` method if there was no filename given. CHANGES IN MALDIquantForeign VERSION 0.11 [2017-09-01]: ------------------------------------------------------- BUGFIX * Fix integer overflow in `.ibdOffsets`; see issue #20. * Fix `exportImzMl` for missing coordinates, pixelSize and dimension; closes * #20. INTERNAL CHANGES * Put MALDIquant into single quotes in the DESCRIPTION file. * Rezip inst/compressed/csv.tar.gz using `gzip -n` to avoid lintian's package-contains-timestamped-gzip warning; see https://wiki.debian.org/ReproducibleBuilds for details. CHANGES IN MALDIquantForeign VERSION 0.10 [2015-10-31]: ------------------------------------------------------- IMPROVEMENTS * Add parallel support on unix-based platforms using the parallel package. All `import*` functions support the "mc.cores" argument (default is 1, means no parallel import). Please read also `?"MALDIquantForeign-parallel"`. * Add importer for .msd (mMass) files: `importMsd`. * Add basic export support for imzML files: `exportImzMl`. * `.importImzMl`: add "coordinates" argument to access specific spectra by their x, y coordinates within an imzML file; closes #14; affected functions: `import`, `importImzMl`. Thanks to Heath Patterson for this idea. MODIFICATIONS * Remove dependency "downloader". Since R 3.2.2 https is supported on all platforms by `base::download.file`. * Use "verbose = interactive()" in `import`. * Replace old imzML example files in inst/exampledata. * `exportMzMl`: improve documentation of the "path" argument. * `.importImzMl`: if the imzML file doesn't contain any UUID a warning is thrown instead of an error; affected functions: `import`, `importImzMl`. * `.importImzMl`: if the imzML file doesn't contain any checksum for its corresponding idb file a warning is thrown (before it was an error); affected functions: `import`, `importImzMl`. INTERNAL CHANGES * Import non-base functions/methods via NAMESPACE. * Use MALDIquant's new `coordinates` method. * Replace `require` by `requireNamespace` as suggested by "Writing R Extensions". * Rezip gzip'ed files using `gzip -n` to avoid lintian's package-contains-timestamped-gzip warning; see https://wiki.debian.org/ReproducibleBuilds for details. CHANGES IN MALDIquantForeign VERSION 0.9 [2014-08-11]: ------------------------------------------------------ IMPROVEMENTS * `.readAnalyzeIntensity`: allow to specify a mass range of interest to reduce memory usage while importing Analyze files; affected functions: `import`, `importAnalyze` * `importAnalyze`: use `as.double` after reading the image dimensions to avoid integer overflows in vector allocations (the Analyze 7.5 format specification limits the dimensions to integer). Thanks to Ken Frankel for reporting this problem. * `importImzMl`: add MD5 checksum support for imzML files. Thanks to Ken Frankel for reporting this problem. CHANGES IN MALDIquantForeign VERSION 0.8 [2014-06-16]: ------------------------------------------------------ MODIFICATIONS * `import`: set argument `centroided=FALSE` as default (was `NA` before). The automatically determination of profile/centroided data was too error prone. Now we read everything as profile data (use `centroided=TRUE` to read centroided data); affected functions: all `import` functions (e.g. `importBrukerFlex`, `importMzMl` ...). IMPROVEMENTS * `importAnalyze`: circumvent the limit of 32747 intensity values that is specified in the official Analyze 7.5 format. Thanks to Ken Frankel for reporting this problem. INTERNAL CHANGES * Fix VignetteIndexEntry. * Rename vignette output file from MALDIquantForeign.pdf to MALDIquantForeign-intro.pdf. * Check availability of the "RNetCDF" package in the `importCdf` man page to avoid build failures on CRAN. * Don't evaluate the remote import example in the vignette to avoid build failures on CRAN. CHANGES IN MALDIquantForeign VERSION 0.7 [2014-04-11]: ------------------------------------------------------ IMPROVEMENTS * Add vignette. INTERNAL CHANGES * Move tests into tests/testthat to adapt to testthat 0.8 and new CRAN policy; close #10. * Fix path of exampledata (needed because the test scripts moved to tests). CHANGES IN MALDIquantForeign VERSION 0.6 [2014-01-28]: ------------------------------------------------------ NEW FEATURES * Add basic import support for CDF files [contributed by Pietro Franceschi]; new function: `importCdf`. * `import`: add arguments "massRange" and "minIntensity" to limit import range; affected functions: all `import*` functions. * `import`: add argument "centroided" to allow import of centroided spectra as MassPeaks objects; affected functions: all `import*` functions. IMPROVEMENTS * Add "skip" argument to `.importCsv`, `.importTab`, `.autoSep` and `.autoHeader` to allow skipping first lines; affected functions: `import`, `importTxt`, `importTab`, `importCsv` BUG FIXES * `importAnalyze`: add support for ABSiex Analyze 7.5 files. Thanks to Pietro Franceschi for reporting this bug/odd behaviour. * `.importTab`: use `.autoSep` and `.autoHeader` (before they were used only by `.importCsv`); affected functions: `import`, `importTxt`, `importTab` * `.parseMzML`: fix assignment operation. Before all metaData of spectra were overwritten by the metaData of the last spectrum (affected only mzML files with more than one spectrum). affected functions: `importMzML` * `export`: fix one file export; additional affected functions: `exportMzMl`. INTERNAL CHANGES * Regenerate man pages with new 'roxygen2' (3.0.0). CHANGES IN MALDIquantForeign VERSION 0.5.1 [2013-09-18]: -------------------------------------------------------- BUG FIXES * Replace MALDIquant:::isMassSpectrum by MALDIquant::isMassSpectrum. * Replace deprecated function isMassObjectList. CHANGES IN MALDIquantForeign VERSION 0.5 [2013-09-08]: ------------------------------------------------------ IMPROVEMENTS * `import*`: add "excludePattern" argument to avoid import of specific files; closes #8. BUGFIXES * Fix "totalIonCurrent" test case. * Add import("methods") to NAMESPACE (fixes #9). INTERNAL CHANGES * Update dependencies; now MALDIquantForeign depends on R 3.0.0. * Replace all paste(..., sep="") by paste0. CHANGES IN MALDIquantForeign VERSION 0.4 [2013-04-28]: ------------------------------------------------------ NEW FEATURES * Add basic import support for imzML files and Analyze 7.5 files. IMPROVEMENTS * `import`: add "removeEmptySpectra" argument; closes #7. MODIFICATIONS * `import`: change default argument "verbose" to TRUE. BUGFIXES * `.download`: respects "verbose" argument now (fixes #6). INTERNAL CHANGES * Remove LICENSE file. CHANGES IN MALDIquantForeign VERSION 0.3 [2013-03-01]: ------------------------------------------------------ NEW FEATURES * Add basic support for mzML export. * Add basic import support for Ciphergen XML files. * `import`: add http(s):// and ftp:// support. * `import`: add uncompression support to allow import of zip/tar.{gz,bz2,xz}-archives. BUGFIXES * Add missing "usage" section in `export` methods manual pages. * `.files`: returns only unique file names; affected functions: all import functions. INTERNAL CHANGES * `.make.unique`: generates c("a1", "a2") instead of c("a", "a1") and c("a001", ..., "a099", "a100") instead of c("a", ..., "a98", "a99"); affected method: `export,list`. * DESCRIPTION: move base64enc, digest, readBrukerFlexData, readMzXmlData and XML to "Imports". * DESCRIPTION: remove MALDIquant from the "Imports" field. CHANGES IN MALDIquantForeign VERSION 0.2 [2013-01-14]: ------------------------------------------------------ IMPROVEMENTS * `exportMsd`: complete rewrite, write xml files manually instead of using the XML package (increasing speed). BUGFIXES * `export`: fix empty filenames. * `export,list`: stop if directory doesn't exist. * `exportMsd`: fix peaks argument. * `exportMsd` tests: respect endianness. * `import`: respect verbose argument in `import(type="auto")`. CHANGES IN MALDIquantForeign VERSION 0.1 [2012-12-10]: ------------------------------------------------------ * First public release. * Supported file formats: * Import: tab, txt, csv, Bruker Daltonics *flex files, mzXML, mzML * Export: tab, csv, msd MALDIquantForeign/R/0000755000176200001440000000000014553551252013673 5ustar liggesusersMALDIquantForeign/R/compression-functions.R0000644000176200001440000000635114404344473020372 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .isCompressed <- function(x) { z <- c("bz2", "bzip2", "gz", "lzma", "xz") .fileExtension(x) %in% c("zip", z, paste("tar", z, sep=".")) } .isTar <- function(x)grepl(pattern="^tar", x=.fileExtension(x)) .isZip <- function(x)grepl(pattern="^zip$", x=.fileExtension(x)) .isPackedOrCompressed <- function(x) { .isCompressed(x) | .isTar(x) } # unpack/uncompress files and return temporary filenames .uncompress <- function(x, verbose=TRUE) { f <- lapply(x, function(path) { if (!.isPackedOrCompressed(path)) { return(x) } else { if (.isTar(path)) { return(.unpacking(x, fun=untar, verbose=verbose)) } else if (.isZip(path)) { return(.unpacking(x, fun=unzip, verbose=verbose)) } else { return(.gunzip(x, verbose=verbose)) } } }) unlist(f) } # unpack and return tmp filename .unpacking <- function(filename, destdir, fun, verbose=FALSE, ...) { if (missing(destdir)) { pattern <- paste0(.withoutFileExtension(basename(filename)), "_") destdir <- file.path(tempdir(), "MALDIquantForeign_uncompress", tempfile(pattern=pattern, tmpdir="")) } funName <- deparse(substitute(fun)) fun <- as.function(fun) .msg(verbose, funName, " ", filename, " to ", destdir, ".") unpacked <- fun(filename, exdir=destdir, ...) if (!length(unpacked)) { stop(funName, " failed!") } destdir } # gunzip and return tmp filename .gunzip <- function(filename, destfile, verbose=FALSE) { if (!file.exists(filename)) { stop(sQuote(filename), " doesn't exist!") } if (missing(destfile)) { tmpdir <- file.path(tempdir(), "MALDIquantForeign_uncompress") if (!file.exists(tmpdir)) { dir.create(tmpdir, showWarnings=FALSE, recursive=TRUE) } pattern <- paste0(.withoutFileExtension(basename(filename)), "_") fileext <- paste0(".", .fileExtension(.withoutCompressionExtension(filename))) destfile <- tempfile(pattern=pattern, tmpdir=tmpdir, fileext=fileext) } .msg(verbose, "gunzip ", filename, " to ", destfile, ".") fi <- gzfile(filename, open="rb") on.exit(close(fi)) fo <- file(destfile, open="wb") on.exit(close(fo), add=TRUE) repeat { b <- readBin(fi, what=raw(), n=1e6) ## n==1e6 => nearly 50Mb if (length(b)) { writeBin(b, con=fo) } else { break } } destfile } .cleanupUncompressedTmpFiles <- function() { unlink(file.path(tempdir(), "MALDIquantForeign_uncompress"), recursive=TRUE) } MALDIquantForeign/R/AllGenerics.R0000644000176200001440000000323114404344473016205 0ustar liggesusers## Copyright 2012-2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see setGeneric(".composeFilename", function(x, ...) standardGeneric(".composeFilename")) setGeneric(".exportTab", function(x, ...) standardGeneric(".exportTab")) setGeneric(".exportCsv", function(x, ...) standardGeneric(".exportCsv")) setGeneric(".exportImzMl", function(x, ...) standardGeneric(".exportImzMl")) setGeneric(".exportMsd", function(x, ...) standardGeneric(".exportMsd")) setGeneric(".exportMzMl", function(x, ...) standardGeneric(".exportMzMl")) setGeneric("export", function(x, ...) standardGeneric("export")) setGeneric("exportTab", function(x, ...) standardGeneric("exportTab")) setGeneric("exportCsv", function(x, ...) standardGeneric("exportCsv")) setGeneric("exportImzMl", function(x, ...) standardGeneric("exportImzMl")) setGeneric("exportMsd", function(x, ...) standardGeneric("exportMsd")) setGeneric("exportMzMl", function(x, ...) standardGeneric("exportMzMl")) MALDIquantForeign/R/importCiphergenXml-functions.R0000644000176200001440000000260714404344473021651 0ustar liggesusers## Copyright 2013-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importCiphergenXml <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE) { .msg(verbose, "Reading spectrum from ", sQuote(file), " ...") if (!file.exists(file)) { stop("File ", sQuote(file), " doesn't exists!") } ## read file s <- .parseCiphergenXml(file=file) list(.createMassObject(mass=s$spectrum$mass, intensity=s$spectrum$intensity, metaData=s$metaData, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose)) } MALDIquantForeign/R/base64encode-functions.R0000644000176200001440000000372214404344473020272 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Converts double to base64 character. #' #' This function converts a \code{double} vector to a base64 encoded #' \code{character} vector. #' #' @param x \code{double}, vector #' @param size \code{integer}, number of bytes per element in the byte stream #' (see \code{size} in \code{\link[base]{writeBin}}). #' @param endian \code{character}, the endian-ness #' (see \code{endian} in \code{\link[base]{writeBin}}). #' @param compressionType \code{character}, type of compression to use for #' compression of \code{x} (see \code{type} in #' \code{\link[base]{memCompress}}. #' @return Vector of type \code{character}. #' @rdname base64-encode #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @seealso \code{\link[base64enc]{base64encode}} from \pkg{base64enc} package #' @keywords internal #' .base64encode <- function(x, size, endian=.Platform$endian, compressionType=c("none", "gzip")) { x <- writeBin(as.double(x), con=raw(), size=size, endian=endian) compressionType <- match.arg(compressionType, choices=c("none", "gzip"), several.ok=FALSE) x <- memCompress(from=x, type=compressionType) base64enc::base64encode(x) } MALDIquantForeign/R/msd-functions.R0000644000176200001440000000732214404344473016613 0ustar liggesusers## Copyright 2012-2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .writeMsdDocument <- function(x, file, peaks, encoding="utf-8") { ## stop if file isn't writeable if (file.exists(file) && file.access(file, 2) != 0) { stop("No permissions to write into ", sQuote(file), "!") } ## file handle f <- file(file, open="wt", encoding=encoding) ## header .writeXmlHeader(file=f, encoding=encoding) .writeXmlTag("mSD", attrs=c(version=2.2), close=FALSE, file=f) .writeMsdDescription(x, file=f) .writeMsdSpectrum(x, file=f) if (!missing(peaks)) { .writeMsdPeakList(peaks, file=f) } .writeCloseXmlTag("mSD", file=f) invisible(close(f)) } .writeMsdDescription <- function(x, file) { .writeXmlTag("description", intend=1, close=FALSE, file=file) .writeXmlTag("title", text=.createMsdTitle(file), intend=2, file=file) .writeXmlTag("date", attrs=c(value=.sanitize(metaData(x)$acquisitionDate)), intend=2, file=file) .writeXmlTag("operator", attrs=c(value=.sanitize(metaData(x)$owner)), intend=2, file=file) .writeXmlTag("contact", attrs=c(value=.sanitize(metaData(x)$owner)), intend=2, file=file) .writeXmlTag("institution", attrs=c(value=.sanitize(metaData(x)$institution)), intend=2, file=file) .writeXmlTag("instrument", attrs=c(value=.sanitize(metaData(x)$instrument)), intend=2, file=file) .writeXmlTag("notes", .sanitize(paste(metaData(x)$comments, collapse="\n")), intend=2, file=file) .writeCloseXmlTag("description", intend=1, file=file) } .writeMsdSpectrum <- function(x, file) { polarity <- paste(metaData(x)$ionizationMode, metaData(x)$polarity) if (length(polarity)) { polarity <- ifelse(grepl(pattern="+|positive", x=polarity), "1", "-1") } else { polarity <- "" } .writeXmlTag("spectrum", attrs=c(points=length(x), msLevel=ifelse(is.null(metaData(x)$msLevel), 1, metaData(x)$msLevel), polarity=polarity), close=FALSE, intend=1, file=file) .writeMsdArray(mass(x), name="mzArray", file=file) .writeMsdArray(intensity(x), name="intArray", file=file) .writeCloseXmlTag("spectrum", intend=1, file=file) } .writeMsdArray <- function(x, name, file) { .writeXmlTag(name, text=.base64encode(x, size=8, compressionType="gzip"), attrs=c(precision="64", compression="zlib", endian=.Platform$endian), intend=2, file=file) } .writeMsdPeakList <- function(x, file) { .writeXmlTag("peaklist", close=FALSE, intend=1, file=file) cat(paste0(" \n"), file=file, sep="", append=TRUE) .writeCloseXmlTag("peaklist", intend=1, file=file) } .createMsdTitle <- function(file) { .sanitize(.withoutFileExtension(basename(summary(file)$description))) } MALDIquantForeign/R/importImzMl-functions.R0000644000176200001440000001035614464465745020330 0ustar liggesusers## Copyright 2013-2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importImzMl <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, coordinates=NULL, verbose=FALSE) { .msg(verbose, "Reading spectrum from ", sQuote(file), " ...") if (!file.exists(file)) { stop("File ", sQuote(file), " doesn't exists!") } ibdFilename <- .changeFileExtension(file, "ibd") if (!file.exists(ibdFilename)) { stop("File ", sQuote(ibdFilename), " doesn't exists!") } s <- .parseMzMl(file=file, verbose=verbose) ibd <- file(ibdFilename, open="rb") on.exit(close(ibd)) ## test UUID uuid <- paste0(readBin(ibd, raw(), n=16, size=1, signed=TRUE, endian= "little"), collapse="") if (is.null(s$ims$uuid)) { warning("There is not any UUID in ", sQuote(file), "!") } else if (tolower(uuid) != tolower(s$ims$uuid)) { warning("The UUID in ", sQuote(file) , " and ", sQuote(ibdFilename), "do not match!") } else if (!.isUuidV4(uuid)) { warning("The UUID: ", uuid, " is not valid!") } ## test checksums if (!is.null(s$ims$md5)) { .testChecksum(ibdFilename, s$ims$md5, algo="md5", verbose=verbose) } else if (!is.null(s$ims$sha1)) { .testChecksum(ibdFilename, s$ims$sha1, algo="sha1", verbose=verbose) } else { warning("At least one checksum (SHA-1 or MD5) for the idb file ", "should be provided in the imzML file.") } sel <- seq_along(s$ims$ibd) isCoordinatesMatrix <- is.matrix(coordinates) && ncol(coordinates) == 2L if (!is.null(coordinates) && !isCoordinatesMatrix) { stop("The ", sQuote("coordinates"), " argument has to be a matrix with two columns (x and y position)!") } if (isCoordinatesMatrix) { pos <- do.call(rbind, lapply(s$spectra, function(x)x$metaData$imaging$pos)) sel <- match(paste(coordinates[, 1L], coordinates[, 2L], sep=":"), paste(pos[, 1L], pos[, 2L], sep=":")) if (anyNA(sel)) { warning("The following rows contain invalid coordinates: ", paste(which(is.na(sel)), collapse=", ")) sel <- sort(sel[!is.na(sel)]) } } .readValues <- function(file, x, column, isSeekNeeded) { if (isSeekNeeded) { ## WARNING: we know that `seek` is discouraged on some platforms, ## namely Windows. See `?seek` for details. seek(file, where=x[column, "offset"]) } n <- x[column, "length"] e <- x[column, "encodedLength"] readBin(file, double(), n=n, size=e/n, signed=TRUE, endian="little") } n <- length(sel) spectra <- vector(mode="list", length=n) isProcessed <- s$ims$type == "processed" isSeekNeeded <- length(s$ims$ibd) > length(sel) if (!isProcessed) { mass <- .readValues(ibd, s$ims$ibd[[sel[1L]]], "mass", isSeekNeeded) } ## read mass and intensity values for (i in seq(along=sel)) { .msg(verbose, "Reading binary data for spectrum ", i, "/", n, " ...") m <- modifyList(s$metaData, s$spectra[[sel[i]]]$metaData) m$file <- file if (isProcessed) { mass <- .readValues(ibd, s$ims$ibd[[sel[i]]], "mass", isSeekNeeded) } intensity <- .readValues(ibd, s$ims$ibd[[sel[i]]], "intensity", isSeekNeeded) spectra[[i]] <- .createMassObject(mass=mass, intensity=intensity, metaData=m, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose) } spectra } MALDIquantForeign/R/analyze-functions.R0000644000176200001440000001122614404344473017471 0ustar liggesusers## Copyright 2013-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see ## Analyze 7.5 header file .readAnalyzeHdr <- function(filename, verbose=FALSE) { if (!file.exists(filename)) { stop(sQuote(filename), " isn't readable.") } size <- file.info(filename)$size ## Analyze 7.5 header must be of size 348; ABSciex files are a little bit ## larger (384) if (size != 348 && size != 384) { stop(sQuote(filename), " is no ANALYZE header file.") } .msg(verbose, "Extracting header information from ", sQuote(filename), " ...") f <- file(filename, open="rb") on.exit(close(f)) ## first 4 bytes have to be 348 in little endian mode ## (384 for ABSciex) endian <- ifelse(readBin(f, "integer", n=1, size=4, endian="little") %in% c(348, 384), "little", "big") ## skip unused entries seek(f, where=38) regular <- readChar(f, nchars=1, useBytes=TRUE) if (regular != "r") { stop("Wrong file format. Images have to be of equal size (", sQuote("regular"), " must be ", sQuote("r"), ")") } ## skip unused entries seek(f, where=40) ## 2 == number of intensity, 3 == ncol (x), 4 == nrow (y) ## use as.double() here to avoid integer overflows in calculations like nx*ny ## later ## Thanks to Ken Frankel for reporting this problem. dimensions <- as.double(readBin(f, "integer", n=8, size=2, endian=endian)) ## We use the size of the t2m file. See .readAnalyzeIntensity for details. #ni <- dimensions[2] nx <- dimensions[3] ny <- dimensions[4] ## skip unused entries seek(f, where=70) datatype <- readBin(f, "integer", n=1, size=2, endian=endian) bitpix <- readBin(f, "integer", n=1, size=2, endian=endian) if (datatype %in% c(2, 4, 8)) { what <- "integer" } else if (datatype %in% c(16, 32, 64)) { what <- "double" } else { what <- "raw" } signed <- datatype == 2 size <- bitpix/8 ## skip unused entries seek(f, where=76) pixdim <- readBin(f, "double", n=8, size=4, endian=endian) ## pixelwidth in mm xd <- pixdim[2] yd <- pixdim[3] list(nx=nx, ny=ny, xd=xd, yd=yd, endian=endian, what=what, signed=signed, size=size) } ## Analyze 7.5 img file .readAnalyzeIntensity <- function(filename, header, ni, skip=c(0, 0), verbose=FALSE) { if (!file.exists(filename)) { stop(sQuote(filename), " isn't readable.") } .msg(verbose, "Reading intensity values from ", sQuote(filename), " ...") stopifnot(length(skip) == 2) skip <- skip*header$size f <- file(filename, open="rb") on.exit(close(f)) ## header$ni should contain the number of intensity values ## because the format specification uses int16 for header$ni it is limited to ## 32767 intensity values. ## We use the size of the t2m file divided by 4 to find the correct number to ## circumvent this size limit. ## Thanks to Ken Frankel for reporting this problem. i <- vector(mode=header$what, length=ni*header$nx*header$ny) dim(i) <- c(ni, header$nx, header$ny) for (y in 1:header$ny) { for (x in 1:header$nx) { ## CAUTION: seek on Windows is possibly buggy; see ?seek for details. ## If there are any bug reports on Windows we maybe have to ignore "skip" ## on Windows (which would disable the mass range/memory saving feature ## completely). seek(f, where=seek(f)+skip[1]) i[, x, y] <- readBin(f, what=header$what, n=ni, size=header$size, signed=header$signed, endian=header$endian) seek(f, where=seek(f)+skip[2]) } } i } ## Analyze 7.5 t2m file .readAnalyzeMass <- function(filename, header, verbose=FALSE) { if (!file.exists(filename)) { stop(sQuote(filename), " isn't readable.") } .msg(verbose, "Reading mass values from ", sQuote(filename), " ...") n <- file.info(filename)$size/4 f <- file(filename, open="rb") on.exit(close(f)) readBin(f, what="double", n=n, size=4, signed=TRUE, endian=header$endian) } MALDIquantForeign/R/exportTab-methods.R0000644000176200001440000000246014404344473017431 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see setMethod(f=".exportTab", signature=signature(x="AbstractMassObject"), definition=function(x, file="", row.names=FALSE, col.names=FALSE, ...) { write.table(as.matrix(x), file=file, row.names=row.names, col.names=col.names, ... ) }) setMethod(f=".exportCsv", signature=signature(x="AbstractMassObject"), definition=function(x, file="", sep=",", row.names=FALSE, col.names=TRUE, ...) { .exportTab(x, file=file, sep=sep, row.names=row.names, col.names=col.names, ...) }) MALDIquantForeign/R/xml-functions.R0000644000176200001440000000307314404344473016627 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .writeXmlHeader <- function(file, encoding) { cat("\n", file=file, sep="") } .writeCloseXmlTag <- function(tag, intend=0, file) { cat(paste0(rep(" ", times=intend)), "\n", file=file, sep="", append=TRUE) } .writeXmlTag <- function(tag, text=NULL, attrs=NULL, intend=0, close=TRUE, file) { intend <- paste0(rep(" ", times=intend)) if (length(attrs)) { attrs <- paste0(" ", names(attrs), "=\"", attrs, "\"") } if (length(text)) { text <- paste0(">", text) if (close) { text <- paste0(text, "") } } else { text <- ">" if (close) { text <- "/>" } } cat(intend, "<", tag, attrs, text, "\n", file=file, sep="", append=TRUE) } MALDIquantForeign/R/exportMsd-methods.R0000644000176200001440000000170714404344473017451 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see setMethod(f=".exportMsd", signature=signature(x="MassSpectrum"), definition=function(x, file, peaks, ...) { .writeMsdDocument(x=x, file=file, peaks=peaks, ...) }) MALDIquantForeign/R/ibd-functions.R0000644000176200001440000000436714404344473016574 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .writeIbd <- function(x, filename, uuid, processed=TRUE) { ibd <- file(filename, open="wb") on.exit(close(ibd)) uuid <- gsub("-", "", tolower(uuid)) uuid <- substring(uuid, seq(1L, 32L, by=2L), seq(2L, 32L, by=2L)) uuid <- strtoi(uuid, base=16L) writeBin(uuid, con=ibd, size=1L, endian="little") for (i in seq(along=x)) { if (processed || i == 1L) { writeBin(as.double(x[[i]]@mass), con=ibd, size=8L, endian="little") } writeBin(as.double(x[[i]]@intensity), con=ibd, size=8L, endian="little") } } .ibdOffsets <- function(x, processed=TRUE, encodedLengthSize=8L) { ## start at 16 (16 bytes for UUID) n <- rep(lengths(x), each=2L) encodedLength <- as.double(n * encodedLengthSize) if (processed) { offsets <- cumsum(as.double(c(16L, encodedLength[-length(n)]))) } else { sel <- seq(from=2L, to=length(n), by=2L) offsets <- rep.int(16L, length(n)) offsets[sel] <- 16L + cumsum(as.double(encodedLength[sel])) } matrix(c(offsets, n, encodedLength), nrow=length(n), dimnames=list(rep(c("mass", "intensity"), times=length(x)), c("offset", "length", "encodedLength"))) } .addIbdOffsets <- function(x, processed=TRUE, encodedLengthSize=8L) { offsets <- .ibdOffsets(x, processed=processed, encodedLengthSize=encodedLengthSize) i <- split(1:nrow(offsets), rep(1:length(x), each=2L)) for (j in seq(along=x)) { x[[j]]@metaData$imaging$offsets <- offsets[i[[j]],] } x } MALDIquantForeign/R/exportImzMl-methods.R0000644000176200001440000000304414404344473017752 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see setMethod(f=".exportImzMl", signature=signature(x="MassPeaks"), definition=function(x, file, id=.withoutFileExtension(basename(file)), processed=TRUE, ...) { .writeImzMlDocument(x=x, file=file, id=id, processed=processed, ...) }) setMethod(f=".exportImzMl", signature=signature(x="MassSpectrum"), definition=function(x, file, id=.withoutFileExtension(basename(file)), processed=TRUE, ...) { .writeImzMlDocument(x=x, file=file, id=id, processed=processed, ...) }) setMethod(f=".exportImzMl", signature=signature(x="list"), definition=function(x, file, id=.withoutFileExtension(basename(file)), processed=TRUE, ...) { .writeImzMlDocument(x=x, file=file, id=id, processed=processed, ...) }) MALDIquantForeign/R/imzMl-functions.R0000644000176200001440000000501214404344473017112 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .writeImzMlDocument <- function(x, file, id=.withoutFileExtension(basename(file)), processed=TRUE, uuid=.uuid(), coordinates=MALDIquant::coordinates(x), pixelSize=c(metaData(x[[1L]])$imaging$pixelSize, 100, 100)[1L:2L], ...) { if(isMassSpectrum(x) || isMassPeaks(x)) { x <- list(x) } if (!MALDIquant:::.isMassObjectList(x)) { stop("Only MALDIquant::MassSpectrum or MALDIquant::MassPeaks objects ", "are supported!") } if (is.null(metaData(x[[1L]])$imaging$pos) && is.null(coordinates)) { stop("The spectra contain no imaging information.") } isCoordinatesMatrix <- !is.null(coordinates) && is.matrix(coordinates) && ncol(coordinates) == 2L && nrow(coordinates) == length(x) if (!isCoordinatesMatrix) { stop("The ", sQuote("coordinates"), " argument has to be a matrix with two columns (x and y position)!") } else { size <- apply(coordinates, 2, max) dimension <- size * pixelSize x[[1L]]@metaData$imaging <- list(size=size, dim=dimension, pixelSize=pixelSize) MALDIquant::coordinates(x) <- coordinates } ibdFile <- .changeFileExtension(file, "ibd") .writeIbd(x, ibdFile, uuid=uuid, processed=processed) sha1 <- digest::digest(ibdFile, algo="sha1", file=TRUE) .writeMzMlDocument(x=.addIbdOffsets(x, processed=processed), file=file, id=id, imsArgs=list(uuid=uuid, sha1=sha1, processed=processed), ...) } MALDIquantForeign/R/createMassObject-functions.R0000644000176200001440000000644314464465745021265 0ustar liggesusers## Copyright 2014-2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Create a MassSpectrum or a MassPeaks object. #' #' This function creates a MassSpectrum or MassPeaks object (depending on the #' centroided argument). #' #' @param mass mass data #' @param intensity intensity data #' @param snr snr data #' @param metaData \code{list}, metaData #' @param centroided \code{logical}, centroided #' (if TRUE => MassPeaks, if FALSE => MassSpectrum) #' @param massRange \code{double}, length == 2, trim spectrum to #' \code{massRange}. #' @param minIntensity \code{double}, minimal intensity #' @param verbose \code{logical}, verbose output? #' #' @return Returns a MassSpectrum or a MassPeaks object. #' #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @rdname createMassObject #' @keywords internal #' @noRd .createMassObject <- function(mass, intensity, snr=NULL, metaData=list(), centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE) { if (!is.null(metaData$centroided) || !is.null(metaData$dataProcessing$centroided)) { isCentroided <- isTRUE(as.logical(as.numeric(metaData$centroided))) | isTRUE(as.logical(as.numeric(metaData$dataProcessing$centroided))) if (isCentroided != centroided) { warning("According to the metadata information the imported data are ", ifelse(isCentroided, "", "not "), "centroided, ", "but they are treated as ", ifelse(centroided, "centroided (MassPeaks)", "profile (MassSpectrum)"), " data. Maybe you want to use ", sQuote(paste0("centroided=", as.character(isCentroided))), ". See ", sQuote("?import"), " for details.", immediate.=TRUE) } } .msg(centroided & verbose, "Assume centroided data and creating a MassPeaks object.") ## trim AbstractMass object massRange <- MALDIquant:::.reorderRange(massRange) ## we don't use MALDIquant::trim here because we want to filter on the ## intensity as well i <- which(massRange[1L] <= mass & mass <= massRange[2L] & intensity >= minIntensity) if (is.null(snr)) { snr <- rep.int(NA_real_, length(i)) } ## create a MassPeaks object for centroided data if (centroided) { m <- createMassPeaks(mass=mass[i], intensity=intensity[i], snr=snr[i], metaData=metaData) } else { m <- createMassSpectrum(mass=mass[i], intensity=intensity[i], metaData=metaData) } m } MALDIquantForeign/R/filename-functions.R0000644000176200001440000000616514404344473017614 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .cleanFilename <- function(x) { gsub(pattern="([[:punct:]]|[[:space:]])+", replacement="_", x=x) } #' Determine file extension #' #' @param x \code{character}, filename. #' #' @return \code{character}, file extension. #' #' @seealso \code{\link[MALDIquant]{MassSpectrum-class}} #' @keywords internal #' @noRd #' @examples #' library("MALDIquantForeign") #' files <- c("/home/foo/bar.txt", "foobar.pdf") #' MALDIquantForeign:::.fileExtension(files) #' .fileExtension <- function(x) { pos <- regexpr(pattern="(\\.tar)?\\.([[:alnum:]]+)$|(/|\\\\)+[^.\\\\/]+$", text=x) ifelse(pos > -1L, substring(x, pos+1L), x) } .withoutFileExtension <- function(x) { sub(pattern="\\.[[:alnum:]]+?$|(/|\\\\)+[^.\\\\/]+$", replacement="", x=.withoutCompressionExtension(x)) } .withoutCompressionExtension <- function(x) { sub(pattern="\\.(zip|gz|bz2|bzip2|xz|lzma)+$", replacement="", x=x) } .changeFileExtension <- function(x, newExtension) { paste(.withoutFileExtension(x), newExtension, sep=".") } .cutFilenames <- function(x) { l <- strsplit(x, split=.Platform$file.sep, fixed=TRUE) if (any(lengths(l) == 0)) { return(sprintf(paste0("%0", trunc(log10(length(x))) + 1L, "d"), seq_along(x))) } nCol <- unlist(lapply(l, length)) mCol <- max(nCol) m <- matrix(NA, nrow=length(x), ncol=mCol) for (i in seq(along=l)) { cols <- 1:nCol[i] m[i, cols] <- l[[i]] } isIdentical <- apply(m, 2, function(co)all(co[1] == co)) isIdentical[is.na(isIdentical)] <- FALSE m <- as.matrix(m[, !isIdentical]) if (length(m)) { filenames <- apply(m, 1, function(r) { do.call(file.path, as.list(na.omit(r))) }) } else { filenames <- basename(x) } filenames } .uniqueBaseFilenames <- function(x, fileExtension="csv", sep="_") { filenames <- .cutFilenames(.withoutFileExtension(x)) filenames <- .cleanFilename(filenames) empty <- nchar(filenames) <= 0 filenames[empty] <- seq_along(empty) filenames <- .make.unique(filenames, sep=sep) paste(filenames, fileExtension, sep=".") } ## let make unique start by 1 .make.unique <- function(x, sep="_") { tmp <- lapply(split(x, x), function(y) { n <- length(y) if (n > 1) { fmt <- paste0("%s%s%0", floor(log10(n))+1, "d") y <- sprintf(fmt=fmt, y, sep, 1:n) } y }) unsplit(tmp, x) } MALDIquantForeign/R/importAuto-functions.R0000644000176200001440000000410614404344473020170 0ustar liggesusers## Copyright 2012-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importAuto <- function(path, excludePattern=NULL, removeEmptySpectra=TRUE, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE, ...) { files <- lapply(importFormats$pattern, .files, path=path, excludePattern=excludePattern) names(files) <- importFormats$type ## test xml files for ciphergen format files$ciphergen <- .testCiphergenXml(files$ciphergen) n <- vapply(files, length, integer(1)) if (all(n)) { stop("Could not detect any supported file type.") } m <- which.max(n) .msg(verbose, n[m], " files of type=", sQuote(importFormats$type[m]), " found.") import(path=files[[m]], type=importFormats$type[m], pattern=importFormats$pattern[m], removeEmptySpectra=removeEmptySpectra, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose, ...) } # test xml for ciphergen format # returns files in ciphergen xml format .testCiphergenXml <- function(files) { ## read first 4 lines of each file l <- lapply(files, readLines, n=4) p <- lapply(l, grepl, pattern="||") s <- vapply(p, sum, integer(1)) isCiphergen <- s >= 2 files[isCiphergen] } MALDIquantForeign/R/filename-methods.R0000644000176200001440000000367514404344473017252 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' This method creates a filename for a \code{\linkS4class{AbstractMassObject}} #' object. #' #' @param x a \code{\linkS4class{AbstractMassObject}} object #' @param fileExtension file type (e.g. "txt", "pdf", ...) #' @return filename #' #' @seealso \code{\linkS4class{AbstractMassObject}} #' @aliases .composeFilename,AbstractMassObject-method #' @aliases .composeFilename,list-method #' @docType methods #' @keywords internal #' @noRd setMethod(f=".composeFilename", signature=signature(x="AbstractMassObject"), definition=function(x, fileExtension="csv") { if (!is.null(metaData(x)$fullName)) { if (length(metaData(x)$fullName) > 1) { filename <- paste0(metaData(x)$fullName, collapse="_") } else { filename <- metaData(x)$fullName } } else { filename <- .withoutFileExtension(metaData(x)$file[1]) } paste(filename, fileExtension, sep=".") }) setMethod(f=".composeFilename", signature=signature(x="list"), definition=function(x, fileExtension="csv") { stopifnot(MALDIquant:::.isMassObjectList(x)) filenames <- unlist(lapply(x, .composeFilename, fileExtension=fileExtension)) .uniqueBaseFilenames(filenames, fileExtension) }) MALDIquantForeign/R/testChecksum-functions.R0000644000176200001440000000246614404344473020476 0ustar liggesusers## Copyright 2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .testChecksum <- function(file, target, algo="sha1", ..., verbose=FALSE) { .msg(verbose, "Calculating ", algo, "-sum for ", sQuote(file), ": ", appendLF=FALSE) fileChecksum <- tolower(digest::digest(file, algo=algo, file=TRUE, ...)) target <- tolower(target) .msg(verbose, fileChecksum) if (fileChecksum != target) { warning("Stored and calculated ", algo, " sums do not match ", "(stored: ", sQuote(target), ", calculated: ", sQuote(fileChecksum), ")!") return(FALSE) } TRUE } MALDIquantForeign/R/download-function.R0000644000176200001440000000343214404344473017452 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .isUrl <- function(x)grepl(pattern="^https?://|^ftp://", x=x) .download <- function(url, destfile, verbose=FALSE, ...) { if (missing(destfile)) { pattern <- paste0(.withoutFileExtension(basename(url)), "_") fileext <- paste0(".", .fileExtension(url)) tmpdir <- file.path(tempdir(), "MALDIquantForeign_download") if (!file.exists(tmpdir)) { dir.create(tmpdir, showWarnings=FALSE, recursive=TRUE) } destfile <- file.path(tmpdir, tempfile(pattern=pattern, tmpdir="", fileext=fileext)) } .msg(verbose, "Downloading ", paste0(url, collapse=", ") , " to ", paste0(destfile, collapse=", "), ".") for (i in seq(along=url)) { if (download.file(url=url[i], destfile=destfile[i], quiet=!verbose, mode="wb", ...)) { warning("Download of ", url[i], " failed!") } } destfile } .cleanupDownloadedTmpFiles <- function() { unlink(file.path(tempdir(), "MALDIquantForeign_download"), recursive=TRUE) } MALDIquantForeign/R/import-functions.R0000644000176200001440000004551214464723561017352 0ustar liggesusers## Copyright 2012-2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Import files #' #' This function provides a general interface to import different file formats #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @details #' Specific import functions: #' \tabular{ll}{ #' txt \tab \code{\link[MALDIquantForeign]{importTxt}} \cr #' tab \tab \code{\link[MALDIquantForeign]{importTab}} \cr #' csv \tab \code{\link[MALDIquantForeign]{importCsv}} \cr #' fid \tab \code{\link[MALDIquantForeign]{importBrukerFlex}} \cr #' ciphergen \tab \code{\link[MALDIquantForeign]{importCiphergenXml}} \cr #' mzXML \tab \code{\link[MALDIquantForeign]{importMzXml}} \cr #' mzML \tab \code{\link[MALDIquantForeign]{importMzMl}} \cr #' imzML \tab \code{\link[MALDIquantForeign]{importImzMl}} \cr #' analyze \tab \code{\link[MALDIquantForeign]{importAnalyze}} \cr #' cdf \tab \code{\link[MALDIquantForeign]{importCdf}} \cr #' msd \tab \code{\link[MALDIquantForeign]{importMsd}} \cr #' } #' #' \code{path}: In addition to the above mentioned file types the #' following (compressed) archives are supported, too: #' zip, tar, tar.gz, tar.bz2, tar.xz. The archives are uncompressed in a #' temporary directory. Afterwards the \code{\link[MALDIquantForeign]{import}} #' function is called (with \code{type="auto"}). #' #' \code{pattern}: Sometimes unusual file extensions are used (e.g. #' \code{"*.xml"} for mzXML files). In this case a specific #' \code{pattern} could be defined to import files with an unusual file #' extension (e.g. \code{pattern="^.*\\.xml$"} to read all \code{*.xml} #' files in a directory; see \code{\link[base]{regexp}} for details). #' #' \code{excludePattern}: Sometimes some files should be excluded. E.g. #' to ignore additional aquired Bruker LIFT spectra #' (MALDI-TOF/TOF; which are not support, yet) you could use #' \code{excludePattern="([[:digit:]\\.]+)LIFT[\\\\/]1SRef"}. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param type \code{character}, file format. If \code{type} is set to #' \dQuote{auto} MALDIquant tries to detect the correct file type #' automatically. It often depends on the file extension #' (if \code{path} is a directory the most represented file extension is used; #' \code{pattern} argument is ignored). #' @param pattern \code{character}, a regular expression to find files in a #' directory (see details). #' @param excludePattern \code{character}, a regular expression to exclude #' files in a directory (see details). #' @param removeEmptySpectra \code{logical}, should empty spectra excluded? #' @param centroided \code{logical}, if \code{centroided=FALSE} (default) #' the data are treated as not centroided and a list of #' \code{\link[MALDIquant]{MassSpectrum-class}} objects is returned. Use #' \code{centroided=TRUE} to assume centroided data and get a list of #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' @param massRange \code{double}, limits of mass import (left/minimal mass, #' right/maximal mass). #' @param minIntensity \code{double}, minimal intensity to import. #' @param mc.cores number of cores to use (default 1; only unix-based platforms #' are supported, see #' \code{\link[MALDIquantForeign]{MALDIquantForeign-parallel}} for details). #' @param verbose \code{logical}, verbose output? #' @param \ldots arguments to be passed to specific import functions. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' \code{\link[MALDIquantForeign]{MALDIquantForeign-parallel}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import mzXML files #' s <- import(exampleDirectory, type="mzXML") #' #' ## import tab delimited file with different file extension (default: *.tab) #' s <- import(exampleDirectory, type="tab", pattern="^.*\\.txt") #' #' ## import single mzML file #' s <- import(file.path(exampleDirectory, "tiny1.mzML1.1.mzML")) #' #' ## import gzipped csv file #' s <- import(file.path(exampleDirectory, "compressed", "csv1.csv.gz")) #' #' @rdname import-functions #' @export import <- function(path, type="auto", pattern, excludePattern=NULL, removeEmptySpectra=TRUE, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, mc.cores=1L, verbose=interactive(), ...) { ## download file if needed isUrl <- .isUrl(path) if (any(isUrl)) { path[isUrl] <- .download(path[isUrl], verbose=verbose) on.exit(.cleanupDownloadedTmpFiles()) } ## file exists? isReadable <- file.exists(path) & file.access(path, mode=4) == 0 if (any(!isReadable)) { stop(sQuote(path[!isReadable]), " doesn't exist or isn't readable!") } ## uncompress/unpack file if needed isCompressed <- .isPackedOrCompressed(path) if (any(isCompressed)) { path[isCompressed] <- .uncompress(path[isCompressed], verbose=verbose) on.exit(.cleanupUncompressedTmpFiles(), add=TRUE) } ## handle given file type i <- pmatch(tolower(type), c("auto", importFormats$type), nomatch=0, duplicates.ok=FALSE)-1 if (i == -1) { stop("File type ", sQuote(type), " is not supported!") } else if (i == 0) { ## auto detect file type if (!missing(pattern)) { warning("User defined ", sQuote("pattern"), " is ignored in auto-mode.") } return(.importAuto(path=path, excludePattern=excludePattern, removeEmptySpectra=removeEmptySpectra, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose, ...)) } else { ## user-defined file type if (missing(pattern)) { pattern <- importFormats$pattern[i] } handler <- get(importFormats$handler[i], mode="function") s <- unlist(MALDIquant:::.lapply(.files(path=path, pattern=pattern, excludePattern=excludePattern), handler, centroided=centroided, massRange=massRange, minIntensity=minIntensity, mc.cores=mc.cores, verbose=verbose, ...)) if (is.null(s)) { stop("Import failed! Unsupported file type?") } if (removeEmptySpectra) { emptyIdx <- MALDIquant::findEmptyMassObjects(s) if (length(emptyIdx)) { .msg(verbose, "Remove ", length(emptyIdx), " empty spectra.") return(s[-emptyIdx]) } } return(s) } } #' Import text files #' #' This function imports different text file formats #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' \code{importTab}, \code{importTxt} and \code{importCsv} use #' \code{\link[utils]{read.table}} with different defaults. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to \code{\link[utils]{read.table}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}}, #' \code{\link[utils]{read.table}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import txt files #' s <- importTxt(exampleDirectory) #' #' ## import csv files #' s <- importCsv(exampleDirectory) #' #' @rdname importTab-functions #' @export importTxt <- function(path, ...) { import(path=path, type="txt", ...) } #' @rdname importTab-functions #' @export importTab <- function(path, ...) { import(path=path, type="tab", ...) } #' @rdname importTab-functions #' @export importCsv <- function(path, ...) { import(path=path, type="csv", ...) } #' Import Bruker Daltonics *flex files #' #' This function imports files in Bruker Daltonics *flex-series file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[readBrukerFlexData]{readBrukerFlexFile}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}}, #' \code{\link[readBrukerFlexData]{readBrukerFlexFile}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' s <- importBrukerFlex(exampleDirectory) #' #' @rdname importBrukerFlex-functions #' @export importBrukerFlex <- function(path, ...) { import(path=path, type="fid", ...) } #' Import mzXML files #' #' This function imports files in mzXML file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[readMzXmlData]{readMzXmlFile}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}}, #' \code{\link[readMzXmlData]{readMzXmlFile}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/}, \cr #' Definition of \code{mzXML} format: #' \url{http://tools.proteomecenter.org/wiki/index.php?title=Formats:mzXML} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import #' s <- importMzXml(exampleDirectory) #' #' @rdname importMzXml-functions #' @export importMzXml <- function(path, ...) { import(path=path, type="mzxml", ...) } #' Import mzML files #' #' This function imports files in mzML file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[MALDIquantForeign]{import}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/}, \cr #' Definition of \code{mzML} format: #' \url{https://www.psidev.info/mzML} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import #' s <- importMzMl(exampleDirectory) #' #' @rdname importMzMl-functions #' @export importMzMl <- function(path, ...) { import(path=path, type="mzml", ...) } #' Import imzML files #' #' This function imports files in imzML file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param coordinates \code{matrix}, 2 column matrix that contains the x- and #' y-coordinates for spectra that should be imported. Other spectra would be #' ignored. #' @param \ldots arguments to be passed to #' \code{\link[MALDIquantForeign]{import}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/}, \cr #' Definition of \code{imzML} format: #' \url{https://ms-imaging.org/imzml/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import #' s <- importImzMl(file.path(exampleDirectory, "tiny_continuous.imzML")) #' #' ## import only spectra for pixel 1,1 and 2,1 #' s <- importImzMl(file.path(exampleDirectory, "tiny_continuous.imzML"), #' coordinates = cbind(1:2, c(1, 1))) #' #' @rdname importImzMl-functions #' @export importImzMl <- function(path, coordinates=NULL, ...) { import(path=path, type="imzml", coordinates=coordinates, ...) } #' Import Ciphergen XML files #' #' This function imports files in Ciphergen XML file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[MALDIquantForeign]{import}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import #' s <- importCiphergenXml(exampleDirectory) #' #' @rdname importCiphergenXml-functions #' @export importCiphergenXml <- function(path, ...) { import(path=path, type="ciphergen", ...) } #' Import Analyze 7.5 files #' #' This function imports files in Analyze 7.5 file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[MALDIquantForeign]{import}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} \cr #' \url{http://www.grahamwideman.com/gw/brain/analyze/formatdoc.htm}, #' \url{https://eeg.sourceforge.net/ANALYZE75.pdf} #' @rdname importAnalyze-functions #' @export importAnalyze <- function(path, ...) { import(path=path, type="analyze", ...) } #' Import CDF files #' #' This function imports files in NetCDF file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects.\cr #' Please note that the \emph{RNetCDF} is needed. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[MALDIquantForeign]{import}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import #' if (requireNamespace("RNetCDF", quietly=TRUE)) { #' s <- importCdf(exampleDirectory) #' } else { #' message("You have to install the RNetCDF package to use importCdf.") #' } #' #' @rdname importCdf-functions #' @export importCdf <- function(path, ...) { import(path=path, type="cdf", ...) } #' Import MSD files #' #' This function imports files in mMass MSD file format #' into \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects. #' #' @param path \code{character}, path to directory or file which should be read #' in. #' @param \ldots arguments to be passed to #' \code{\link[MALDIquantForeign]{import}}. #' #' @return a \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} or #' \code{\link[MALDIquant]{MassPeaks-class}} objects (depending on the #' \code{centroided} argument). #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/}, \cr #' mMass homepage: \url{http://mmass.org/} #' @examples #' #' library("MALDIquant") #' library("MALDIquantForeign") #' #' ## get example directory #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## import #' s <- importMsd(exampleDirectory) #' #' @rdname importMsd-functions #' @export importMsd <- function(path, ...) { import(path=path, type="msd", ...) } MALDIquantForeign/R/importMzMl-functions.R0000644000176200001440000000270014404344473020135 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importMzMl <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE) { .msg(verbose, "Reading spectrum from ", sQuote(file), " ...") if (!file.exists(file)) { stop("File ", sQuote(file), " doesn't exists!") } s <- .parseMzMl(file=file, verbose=verbose) lapply(s$spectra, function(x, globalS=s) { m <- modifyList(s$metaData, x$metaData) m$file <- file .createMassObject(mass=x$mass, intensity=x$intensity, snr=x$snr, metaData=m, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose) }) } MALDIquantForeign/R/mzMl-functions.R0000644000176200001440000004253314404344473016752 0ustar liggesusers## Copyright 2013-2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .writeMzMlDocument <- function(x, file, id, encoding="utf-8", imsArgs=list()) { ## stop if file isn't writeable if (file.exists(file) && file.access(file, 2) != 0) { stop("No permissions to write into ", sQuote(file), "!") } if (!MALDIquant:::.isMassObjectList(x)) { stop("Only MALDIquant::MassSpectrum or MALDIquant::MassPeaks objects ", "are supported!") } isIms <- length(imsArgs) ## file handle f <- file(file, open="wt", encoding=encoding) .writeXmlHeader(file=f, encoding=encoding) .writeXmlTag("mzML", attrs=c(xmlns="http://psi.hupo.org/ms/mzml", "xmlns:xsi"="http://www.w3.org/2001/XMLSchema-instance", "xsi:schemaLocation"=paste("http://psi.hupo.org/ms/mzml", "http://psidev.info/files/ms/mzML/xsd/mzML1.1.0.xsd"), id=.sanitize(ifelse(missing(id) || is.null(id), deparse(substitute(x)), id)), version="1.1.0"), close=FALSE, file=f) .writeMzMlCvList(file=f, isIms=isIms) .writeMzMlFileDescription(x, file=f, isIms=isIms, imsArgs=imsArgs) .writeMzMlSoftwareList(x, file=f) if (isIms) { .writeImzMlReferenceableParamGroups(x, file=f) .writeImzMlScanSettings(x, file=f) } .writeMzMlInstrumentConfigurationList(x, file=f) .writeMzMlDataProcessingList(x, file=f) .writeMzMlRun(x, file=f, isIms=isIms) .writeCloseXmlTag("mzML", file=f) invisible(close(f)) } .writeMzMlCvList <- function(file, isIms=FALSE) { items <- list( ms=list(id="MS", fullName="Proteomics Standards Initiative Mass Spectrometry Ontology", version="3.44.0", URI="http://psidev.cvs.sourceforge.net/*checkout*/psidev/psi/psi-ms/mzML/controlledVocabulary/psi-ms.obo"), uo=list(id="UO", fullName="Unit Ontology", version="12:10:2012", URI="http://obo.cvs.sourceforge.net/*checkout*/obo/obo/ontology/phenotype/unit.obo")) if (isIms) { items$imzml <- list(id="IMS", fullName="Imaging MS Ontology", version="0.9.1", URI="http://www.maldi-msi.org/download/imzml/imagingMS.obo") } .writeXmlTag("cvList", attrs=c(count=2), intend=1, close=FALSE, file=file) for (i in seq(along=items)) { .writeXmlTag("cv", attrs=items[[i]], intend=2, file=file) } .writeCloseXmlTag("cvList", intend=1, file=file) } .writeMzMlFileDescription <- function(x, file, isIms=FALSE, imsArgs) { .writeXmlTag("fileDescription", intend=1, close=FALSE, file=file) .writeXmlTag("fileContent", intend=2, close=FALSE, file=file) .writeXmlTag("cvParam", intend=3, attrs=c(cvRef="MS", accession="MS:1000579", name="MS1 spectrum"), file=file) if (isIms) { .writeXmlTag("cvParam", intend=3, attrs=c(cvRef="IMS", accession="IMS:1000080", name="universally unique identifier", value=paste0("{", imsArgs$uuid, "}")), file=file) .writeXmlTag("cvParam", intend=3, attrs=c(cvRef="IMS", accession="IMS:1000091", name="ibd SHA-1", value=imsArgs$sha1), file=file) if (imsArgs$processed) { .writeXmlTag("cvParam", intend=3, attrs=c(cvRef="IMS", accession="IMS:1000031", name="processed"), file=file) } else { .writeXmlTag("cvParam", intend=3, attrs=c(cvRef="IMS", accession="IMS:1000030", name="continuous"), file=file) } } .writeXmlTag("userParam", intend=3, attrs=c(name="MALDIquantForeign", value="MALDIquant object(s) exported to mzML"), file=file) .writeCloseXmlTag("fileContent", intend=2, file=file) .writeMzMlSourceFileList(x, file=file) .writeCloseXmlTag("fileDescription", intend=1, file=file) } .writeMzMlSourceFileList <- function(x, file) { files <- unique(unlist(lapply(x, function(s)metaData(s)$file))) if (length(files)) { dname <- dirname(files) bname <- basename(files) ext <- tolower(.fileExtension(bname)) .writeXmlTag("sourceFileList", attrs=c(count=length(files)), intend=2, close=FALSE, file=file) for (i in seq(along=files)) { .writeXmlTag("sourceFile", intend=3, attrs=c(id=paste0("SF", i), location=dname[i], name=bname[i]), close=FALSE, file=file) if (ext[i] == "fid") { .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000825", name="Bruker FID file"), file=file) .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000773", name="Bruker FID nativeID format"), file=file) } else if (ext[i] == "mzxml") { .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000566", name="ISB mzXML file"), file=file) } else if (ext[i] == "mzml") { .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000584", name="mzML file"), file=file) } if (file.exists(files[i])) { .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000569", name="SHA-1", value=digest::digest(files[i], algo="sha1", file=TRUE)), file=file) } .writeCloseXmlTag("sourceFile", intend=3, file=file) } .writeCloseXmlTag("sourceFileList", intend=2, file=file) } } .writeMzMlSoftwareList <- function(x, file) { .writeXmlTag("softwareList", attrs=c(count=1), intend=1, close=FALSE, file=file) .writeXmlTag("software", intend=2, attrs=c(id="MALDIquantForeign", version=as.character(packageVersion("MALDIquantForeign"))), file=file) .writeCloseXmlTag("softwareList", intend=1, file=file) } .writeMzMlInstrumentConfigurationList <- function(x, file) { .writeXmlTag("instrumentConfigurationList", attrs=c(count=1), intend=1, close=FALSE, file=file) .writeXmlTag("instrumentConfiguration", attrs=c(id="IC0"), intend=2, file=file) .writeCloseXmlTag("instrumentConfigurationList", intend=1, file=file) } .writeMzMlDataProcessingList <- function(x, file) { .writeXmlTag("dataProcessingList", attrs=c(count=1), intend=1, close=FALSE, file=file) .writeXmlTag("dataProcessing", attrs=c(id="export"), intend=2, close=FALSE, file=file) .writeXmlTag("processingMethod", intend=3, attrs=c(order=1, softwareRef="MALDIquantForeign"), close=FALSE, file=file) .writeXmlTag("userParam", intend=4, attrs=c(name="MALDIquant object(s) exported to mzML", value=""), file=file) .writeCloseXmlTag("processingMethod", intend=3, file=file) .writeCloseXmlTag("dataProcessing", intend=2, file=file) .writeCloseXmlTag("dataProcessingList", intend=1, file=file) } .writeMzMlRun <- function(x, file, isIms=FALSE) { .writeXmlTag("run", attrs=c(id="run0", defaultInstrumentConfigurationRef="IC0"), intend=1, close=FALSE, file=file) .writeMzMlSpectrumList(x, file=file, isIms=isIms) .writeCloseXmlTag("run", intend=1, file=file) } .writeMzMlSpectrumList <- function(x, file, isIms=FALSE) { .writeXmlTag("spectrumList", attrs=c(count=length(x), defaultDataProcessingRef="export"), intend=2, close=FALSE, file=file) for (i in seq(along=x)) { id <- ifelse(is.null(metaData(x[[i]])$id), paste0("scan=", i-1L), metaData(x[[i]])$id) .writeXmlTag("spectrum", intend=3, attrs=c(index=i-1, id=id, defaultArrayLength=length(x[[i]]), spotID=metaData(x[[i]])$fullName), close=FALSE, file=file) msLevel <- ifelse(is.null(metaData(x[[i]])$msLevel), 1, metaData(x[[i]])$msLevel) .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000511", name="ms level", value=msLevel), file=file) .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000294", name="mass spectrum"), file=file) .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000528", name="lowest observed m/z", value=min(mass(x[[i]])), unitCvRef="MS", unitAccession="MS:1000040", unitName="m/z"), file=file) .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000527", name="highest observed m/z", value=max(mass(x[[i]])), unitCvRef="MS", unitAccession="MS:1000040", unitName="m/z"), file=file) if (MALDIquant::isMassSpectrum(x[[i]])) { .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000128", name="profile spectrum"), file=file) .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000285", name="total ion current", value=totalIonCurrent(x[[i]])), file=file) } else { .writeXmlTag("cvParam", intend=4, attrs=c(cvRef="MS", accession="MS:1000127", name="centroid spectrum"), file=file) } if (isIms) { .writeImzMlScanList(x[[i]], file=file) .writeImzMlBinaryDataArrayList(x[[i]], file=file) } else { .writeMzMlBinaryDataArrayList(x[[i]], file=file) } .writeCloseXmlTag("spectrum", intend=3, file=file) } .writeCloseXmlTag("spectrumList", intend=2, file=file) } .writeMzMlBinaryDataArrayList <- function(x, file) { count <- ifelse(MALDIquant::isMassSpectrum(x), 2, 3) .writeXmlTag("binaryDataArrayList", attrs=c(count=count), intend=4, close=FALSE, file=file) .writeMzMlBinaryData(mass(x), file=file, c(cvRef="MS", accession="MS:1000514", name="m/z array", unitCvRef="MS", unitAccession="MS:1000040", unitName="m/z")) .writeMzMlBinaryData(intensity(x), file=file, c(cvRef="MS", accession="MS:1000515", name="intensity array", unitCvRef="MS", unitAccession="MS:1000131", unitName="number of counts")) if (MALDIquant::isMassPeaks(x)) { .writeMzMlBinaryData(snr(x), file=file, c(cvRef="MS", accession="MS:1000517", name="signal to noise array")) } .writeCloseXmlTag("binaryDataArrayList", intend=4, file=file) } .writeMzMlBinaryData <- function(x, file, additionalAttrs) { binaryData <- .base64encode(x, size=8, endian="little", compressionType="gzip") .writeXmlTag("binaryDataArray", attrs=c(encodedLength=nchar(binaryData)), intend=5, close=FALSE, file=file) .writeXmlTag("cvParam", intend=6, file=file, attrs=c(cvRef="MS", accession="MS:1000574", name="zlib compression")) .writeXmlTag("cvParam", intend=6, file=file, attrs=c(cvRef="MS", accession="MS:1000523", name="64-bit float")) if (!missing(additionalAttrs)) { .writeXmlTag("cvParam", attrs=additionalAttrs, intend=6, file=file) } .writeXmlTag("binary", text=binaryData, intend=6, file=file) .writeCloseXmlTag("binaryDataArray", intend=5, file=file) } .writeImzMlReferenceableParamGroups <- function(x, file) { .writeXmlTag("referenceableParamGroupList", attrs=c(count=2), intend=1, close=FALSE, file=file) .writeXmlTag("referenceableParamGroup", attrs=c(id="mzArray"), intend=2, close=FALSE, file=file) .writeXmlTag("cvParam", intend=3, file=file, attrs=c(cvRef="MS", accession="MS:1000514", name="m/z array", unitCvRef="MS", unitAccession="MS:1000040", unitName="m/z")) ref <- c("MS", "MS", "IMS") accession <- paste(ref, c(1000576, 1000523, 1000101), sep=":") name <- c("no compression", "64-bit float", "external data") value <- c("", "", "true") for (i in seq(along=accession)) { .writeXmlTag("cvParam", intend=3, file=file, attrs=c(cvRef=ref[i], accession=accession[i], name=name[i], value=value[i])) } .writeCloseXmlTag("referenceableParamGroup", intend=2, file=file) .writeXmlTag("referenceableParamGroup", attrs=c(id="intensityArray"), intend=2, close=FALSE, file=file) .writeXmlTag("cvParam", intend=3, file=file, attrs=c(cvRef="MS", accession="MS:1000515", name="intensity array", unitCvRef="MS", unitAccession="MS:1000131", unitName="number of counts")) for (i in seq(along=accession)) { .writeXmlTag("cvParam", intend=3, file=file, attrs=c(cvRef=ref[i], accession=accession[i], name=name[i], value=value[i])) } .writeCloseXmlTag("referenceableParamGroup", intend=2, file=file) .writeCloseXmlTag("referenceableParamGroupList", intend=1, file=file) } .writeImzMlScanSettings <- function(x, file) { .writeXmlTag("scanSettingsList", attrs=c(count=1), intend=1, close=FALSE, file=file) .writeXmlTag("scanSettings", attrs=c(id="scansetting1"), intend=2, close=FALSE, file=file) accession <- paste("IMS", 1000042:1000043, sep=":") name <- paste("max count of pixel", c("x", "y")) value <- unname(metaData(x[[1L]])$imaging$size) for (i in seq(along=accession)) { .writeXmlTag("cvParam", intend=3, file=file, attrs=c(cvRef="IMS", accession=accession[i], name=name[i], value=value[i])) } accession <- paste("IMS", 1000044:1000047, sep=":") name <- c(paste("max dimension", c("x", "y")), paste("pixel size", c("x", "y"))) value <- unname(c(metaData(x[[1L]])$imaging$dim, metaData(x[[1L]])$imaging$pixelSize)) for (i in seq(along=accession)) { .writeXmlTag("cvParam", intend=3, file=file, attrs=c(cvRef="IMS", accession=accession[i], name=name[i], value=value[i], unitCvRef="UO", unitAccession="UO:0000017", unitName="micrometer")) } .writeCloseXmlTag("scanSettings", intend=2, file=file) .writeCloseXmlTag("scanSettingsList", intend=1, file=file) } .writeImzMlScanList <- function(x, file) { .writeXmlTag("scanList", attrs=c(count=1), intend=4, close=FALSE, file=file) .writeXmlTag("scan", intend=5, close=FALSE, file=file) accession <- paste("IMS", 1000050:1000051, sep=":") name <- paste("position", c("x", "y")) value <- unname(metaData(x)$imaging$pos) for (i in seq(along=accession)) { .writeXmlTag("cvParam", intend=6, file=file, attrs=c(cvRef="IMS", accession=accession[i], name=name[i], value=format(value[i], scientific=FALSE))) } .writeCloseXmlTag("scan", intend=5, file=file) .writeCloseXmlTag("scanList", intend=4, file=file) } .writeImzMlBinaryDataArrayList <- function(x, file) { .writeXmlTag("binaryDataArrayList", attrs=c(count=2), intend=4, close=FALSE, file=file) .writeImzMlBinaryData(metaData(x)$imaging$offsets["mass",], file=file, ref="mzArray") .writeImzMlBinaryData(metaData(x)$imaging$offsets["intensity",], file=file, ref="intensityArray") .writeCloseXmlTag("binaryDataArrayList", intend=4, file=file) } .writeImzMlBinaryData <- function(x, file, ref) { .writeXmlTag("binaryDataArray", attrs=c(encodedLength=0), intend=5, close=FALSE, file=file) .writeXmlTag("referenceableParamGroupRef", attrs=c(ref=ref), intend=6, file=file) accession <- paste("IMS", 1000102:1000104, sep=":") name <- paste("external", c("offset", "array length", "encoded length")) value <- unname(x) for (i in seq(along=accession)) { .writeXmlTag("cvParam", intend=6, file=file, attrs=c(cvRef="IMS", accession=accession[i], name=name[i], value=format(value[i], scientific=FALSE))) } .writeXmlTag("binary", intend=6, file=file) .writeCloseXmlTag("binaryDataArray", intend=5, file=file) } MALDIquantForeign/R/list.files-functions.R0000644000176200001440000000337114404344473020104 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .list.files <- function(path, pattern, excludePattern=NULL, recursive=TRUE, ignore.case=TRUE) { files <- list.files(path=path, pattern=pattern, recursive=recursive, ignore.case=ignore.case, full.names=TRUE) if (!is.null(excludePattern)) { isExcluded <- grepl(pattern=excludePattern, x=files, ignore.case=ignore.case) files <- files[!isExcluded] } normalizePath(files) } .files <- function(path, pattern, excludePattern=NULL, ignore.case=TRUE, ...) { isDir <- file.info(path)$isdir files <- normalizePath(path[!isDir]) isMatching <- unlist(regexpr(pattern=pattern, text=basename(files), ignore.case=ignore.case)) != -1 files <- files[isMatching] files <- c(files, .list.files(path=path[isDir], pattern=pattern, excludePattern=excludePattern, ignore.case=ignore.case, ...)) unique(files) } MALDIquantForeign/R/exportMzMl-methods.R0000644000176200001440000000257414404344473017610 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see setMethod(f=".exportMzMl", signature=signature(x="MassPeaks"), definition=function(x, file, id=.withoutFileExtension(basename(file)), ...) { .writeMzMlDocument(x=list(x), file=file, id=id, ...) }) setMethod(f=".exportMzMl", signature=signature(x="MassSpectrum"), definition=function(x, file, id=.withoutFileExtension(basename(file)), ...) { .writeMzMlDocument(x=list(x), file=file, id=id, ...) }) setMethod(f=".exportMzMl", signature=signature(x="list"), definition=function(x, file, id=.withoutFileExtension(basename(file)), ...) { .writeMzMlDocument(x=x, file=file, id=id, ...) }) MALDIquantForeign/R/importTab-functions.R0000644000176200001440000000533414404344473017772 0ustar liggesusers## Copyright 2012-2020 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importTab <- function(file, centroided=FALSE, massRange=c(0L, Inf), minIntensity=0L, skip=0L, sep=NULL, header=NULL, comment.char="#", encoding="unknown", verbose=FALSE, ...) { text <- readLines(file, encoding=encoding) text <- tail(text, length(text) - skip) text <- text[!startsWith(trimws(text), comment.char)] if (is.null(sep)) { sep <- .autoSep(text) } if (is.null(header)) { header <- .autoHeader(text, sep=sep) } ## load ms file s <- read.table(text=text, header=header, sep=sep, skip=0L, comment.char=comment.char, stringsAsFactors=FALSE, ...) list(.createMassObject(mass=s[, 1L], intensity=s[, 2L], metaData=list(file=file), centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose)) } .importCsv <- function(file, centroided=FALSE, massRange=c(0L, Inf), minIntensity=0L, skip=0L, sep=NULL, header=NULL, comment.char="#", encoding="unknown", verbose=FALSE, ...) { .importTab(file=file, centroided=centroided, massRange=massRange, minIntensity=minIntensity, skip=skip, sep=sep, header=header, comment.char=comment.char, encoding=encoding, verbose=verbose, ...) } .autoHeader <- function(text, sep="\t") { l <- gsub(pattern='[\\\\"]*', replacement="", x=text[1L]) l <- strsplit(l, split=sep)[[1L]][1L] !is.numeric(type.convert(l, as.is=TRUE)) } .autoSep <- function(text, sep=c(",", ";", "\t", " ")) { pattern <- paste0(".+", sep, ".+") i <- vapply(pattern, function(x) { g <- gregexpr(pattern=x, text=text[1L])[[1L]] all(g > 0L) & length(g) == 1L }, logical(1L)) if (any(i)) { sep[which(i)[1L]] ## return only first match } else { sep[1L] } } MALDIquantForeign/R/importMsd-functions.R0000644000176200001440000000262214404344473020004 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importMsd <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE) { .msg(verbose, "Reading spectrum from ", sQuote(file), " ...") if (!file.exists(file)) { stop("File ", sQuote(file), " doesn't exists!") } ## read file s <- .parseMsd(file=file, verbose=verbose) s$metaData$file <- file list(.createMassObject(mass=s$spectrum$mass, intensity=s$spectrum$intensity, metaData=s$metaData, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose)) } MALDIquantForeign/R/importBrukerFlex-functions.R0000644000176200001440000000247514404344473021340 0ustar liggesusers## Copyright 2012-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importBrukerFlex <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE, ...) { s <- readBrukerFlexData::readBrukerFlexFile(fidFile=file, verbose=verbose, ...) list(.createMassObject(mass=s$spectrum$mass, intensity=s$spectrum$intensity, metaData=s$metaData, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose)) } MALDIquantForeign/R/parseMsd.R0000644000176200001440000001057014404344473015577 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Parse msd files. #' #' This function parses msd files. #' #' @param file \code{character}, path to msd file. #' @param verbose \code{logical}, verbose output? #' #' @return Returns a list with metadata and spectra. #' #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @keywords internal #' @noRd .parseMsd <- function(file, verbose=FALSE, ...) { XML::xmlEventParse(file=file, handlers=.msdHandlers(fileName=file, verbose=verbose), addContext=FALSE, useTagName=TRUE, useDotNames=TRUE, ...)$getData() } #' Parse msd files. #' #' This function is defines handlers for XML SAX parser. Internal use only. #' #' @param fileName \code{character}, path to msd file #' @param verbose \code{logical}, verbose output? #' #' @return function closure #' #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @references mMass homepage: \url{http://mmass.org/} #' @keywords internal #' @noRd .msdHandlers <- function(fileName, verbose=FALSE) { ## define local variables ## handle different mzXML versions msdVersion <- 0 ## save last opened tag (needed for .text()-processing) text <- character() endian <- "little" precision <- 32 ## build final list xml <- list() xml$metaData <- list() xml$spectrum <- list() ## handlers for specific tags ## mSD mSD <- function(name, attrs) { ## fetch version information msdVersion <<- readMzXmlData:::.grepDouble(attrs["version"]) .msg(verbose, "Found mSD document (version: ", msdVersion, ").") } ## mSD/description/date date <- function(name, attrs) { xml$metaData[["acquisitionDate"]] <<- readMzXmlData:::.attributeToString(attrs, "value") } operator <- function(name, attrs) { xml$metaData[["owner"]] <<- readMzXmlData:::.attributeToString(attrs, "value") } institution <- function(name, attrs) { xml$metaData[[name]] <<- readMzXmlData:::.attributeToString(attrs, "value") } ## mSD/spectrum spectrum <- function(name, attrs) { attributeNames <- c("scanNumber", "msLevel", "retentionTime", "precursorMZ", "precursorCharge", "polarity") attributeNames <- intersect(attributeNames, names(attrs)) for (i in attributeNames) { xml$metaData[[i]] <<- readMzXmlData:::.attributeToDouble(attrs, i) } } ## mSD/spectrum/mzArray mzArray <- function(name, attrs) { precision <<- readMzXmlData:::.attributeToDouble(attrs, "precision") endian <<- readMzXmlData:::.attributeToString(attrs, "endian") } ## default functions to catch tags without a handler .endElement <- function(name, attrs) { if (name == "title") { xml$metaData[c("name", "fullName", "sampleName")] <<- text } else if (name == "notes") { xml$metaData[["comment"]] <<- text } else if (name == "mzArray") { xml$spectrum[["mass"]] <<- .decodeArray() } else if (name == "intArray") { xml$spectrum[["intensity"]] <<- .decodeArray() } text <<- character() } .text <- function(x) { text <<- paste0(text, x) } .decodeArray <- function() { readMzXmlData:::.base64decode(x=text, endian=endian, size=round(precision/8L), compressionType="gzip") } ## return statement (please call getData()) list(getData=function() {return(xml)}, mSD=mSD, date=date, institution=institution, instrument=institution, spectrum=spectrum, mzArray=mzArray, intArray=mzArray, .endElement=.endElement, .text=.text) } MALDIquantForeign/R/parseCiphergenXml.R0000644000176200001440000000545314404344473017445 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Parse Ciphergen XML files. #' #' This function parses Ciphergen XML files. #' #' @param file \code{character}, path to Ciphergen XML file #' @param verbose \code{logical}, verbose output? #' #' @return Returns a list with metadata and spectra. #' #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @keywords internal #' @noRd .parseCiphergenXml <- function(file, ...) { ## metaData listNames <- c("name", "ionSourceVoltage", "digitizerRate", "massCalibrationA", "massCalibrationB", "massCalibrationT0", "massCalibrationInfo", "spotCorrectionFactor") xpath <- paste0("//spectrum/", c("spectrumName", paste0("acquisitionInfo/setting/", listNames[2:3]), paste0("processingParameters/massCalibration/", listNames[-c(1:3)])), "/text()") doc <- xmlParse(file, ...) metaData <- XML::xpathApply(doc=doc, path=xpath, fun=XML::xmlValue) names(metaData) <- listNames metaData[listNames[-c(1, 7)]] <- lapply(metaData[-c(1, 7)], as.double) metaData$file <- normalizePath(file) intensity <- XML::xpathSApply(doc=doc, path="//spectrum/tofData/tofDataSamples/text()", fun=XML::xmlValue) intensity <- as.double(strsplit(intensity, "[[:space:]]+")[[1]]) intensity <- intensity[!is.na(intensity)] ## tof2mass ## mass = U*(A*(tof-t0)^2 + B) ## Calibration formula was taken from: ## https://bioinformatics.mdanderson.org/Supplements/Datasets/KuererQC/scripts.zip ## file: ciphergenXMLreader.pl n <- 0:(length(intensity)-1) time <- metaData$spotCorrectionFactor*n/metaData$digitizerRate tof <- time-metaData$massCalibrationT0 mass <- metaData$ionSourceVoltage * (sign(tof) * metaData$massCalibrationA * tof*tof + metaData$massCalibrationB) list(spectrum=list(mass=mass, intensity=intensity), metaData=metaData) } MALDIquantForeign/R/msg-functions.R0000644000176200001440000000154714404344473016621 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .msg <- function(verbose, ...) { if (verbose) { message(...) } } MALDIquantForeign/R/export-methods.R0000644000176200001440000003610514404344473017005 0ustar liggesusers## Copyright 2012-2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Export files #' #' This function provides a general interface to export #' \code{\link[MALDIquant]{AbstractMassObject-class}} objects (e.g. #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}}) #' into different file formats. #' #' @details #' Specific export functions: #' \tabular{ll}{ #' tab \tab \code{\link[MALDIquantForeign]{exportTab}} \cr #' csv \tab \code{\link[MALDIquantForeign]{exportCsv}} \cr #' imzML \tab \code{\link[MALDIquantForeign]{exportImzMl}} \cr #' msd \tab \code{\link[MALDIquantForeign]{exportMsd}} \cr #' mzML \tab \code{\link[MALDIquantForeign]{exportMzMl}} \cr #' } #' #' @usage #' \S4method{export}{AbstractMassObject}(x, file, type="auto", force=FALSE, \ldots) #' #' @param x a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a #' \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects. #' @param file \code{character}, file name. #' @param path \code{character}, path to directory in which the \code{list} of #' \code{\link[MALDIquant]{AbstractMassObject-class}} would be exported. #' @param type \code{character}, file format. If \code{type} is set to #' \dQuote{auto} the file extension is used. #' @param force \code{logical}, If \code{TRUE} the \code{file} would be #' overwritten or \code{path} would be created. #' @param \ldots arguments to be passed to specific export functions. #' #' @seealso #' \code{\link[MALDIquant]{MassPeaks-class}}, #' \code{\link[MALDIquant]{MassSpectrum-class}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' \dontrun{ #' library("MALDIquant") #' library("MALDIquantForeign") #' #' s <- list(createMassSpectrum(mass=1:5, intensity=1:5), #' createMassSpectrum(mass=1:5, intensity=1:5)) #' #' ## export a single spectrum #' export(s[[1]], file="spectrum.csv") #' ## identical to exportCsv(s[[1]], file="spectrum.csv") #' #' ## export a list of spectra #' export(s, path="spectra", type="csv") #' ## identical to exportCsv(s, path="spectra") #' } #' #' @aliases export export,AbstractMassObject-method export,list-method #' @rdname export-methods #' @docType methods #' @export setMethod(f="export", signature=signature(x="AbstractMassObject"), definition=function(x, file, type="auto", force=FALSE, ...) { .exportToFile(x=x, file=file, type=type, force=force, ...) }) #' @usage #' \S4method{export}{list}(x, path, type, force=FALSE, \ldots) #' @rdname export-methods #' @export setMethod(f="export", signature=signature(x="list"), definition=function(x, path, type, force=FALSE, ...) { stopifnot(MALDIquant:::.isMassObjectList(x)) onefileSupport <- exportFormats$type[exportFormats$onefile] dots <- list(...) if (missing(path) && !is.null(dots$file)) { path <- dots$file dots$file <- NULL } isFile <- !isTRUE(file.info(path)$isdir) && tolower(.fileExtension(path)) %in% onefileSupport if (isFile) { do.call(.exportToFile, modifyList(list(x=x, file=path, type=type, force=force), dots)) } else { do.call(.exportToDir, modifyList(list(x=x, path=path, type=type, force=force), dots)) } }) #' Export to text files #' #' This function exports #' \code{\link[MALDIquant]{AbstractMassObject-class}} objects (e.g. #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}}) #' into different text file formats. #' #' @details #' \code{exportTab} and \code{exportCsv} use \code{\link[utils]{write.table}} #' with different defaults (\code{sep="\t"} in \code{exportTab} and #' \code{sep=","} in \code{exportCsv}). #' #' @usage #' \S4method{exportTab}{AbstractMassObject}(x, file, force=FALSE, \ldots) #' #' @param x a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a #' \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects. #' @param file \code{character}, file name. #' @param path \code{character}, path to directory in which the \code{list} of #' \code{\link[MALDIquant]{AbstractMassObject-class}} would be exported. #' @param force \code{logical}, If \code{TRUE} the \code{file} would be #' overwritten or \code{path} would be created. #' @param \ldots arguments to be passed to \code{\link[utils]{write.table}}. #' #' @seealso #' \code{\link[MALDIquant]{MassPeaks-class}}, #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[utils]{write.table}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' #' \dontrun{ #' library("MALDIquant") #' library("MALDIquantForeign") #' #' s <- list(createMassSpectrum(mass=1:5, intensity=1:5), #' createMassSpectrum(mass=1:5, intensity=1:5)) #' #' ## export a single spectrum #' exportTab(s[[1]], file="spectrum.tab") #' #' ## export a list of spectra and use ; as separator #' exportCsv(s, path="spectra", sep=";", force=TRUE) #' } #' #' @aliases exportTab exportTab,AbstractMassObject-method exportTab,list-method #' exportCsv exportCsv,AbstractMassObject-method exportCsv,list-method #' @rdname exportTab-methods #' @docType methods #' @export setMethod(f="exportTab", signature=signature(x="AbstractMassObject"), definition=function(x, file, force=FALSE, ...) { export(x, file=file, type="tab", force=force, ...) }) #' @usage #' \S4method{exportTab}{list}(x, path, force=FALSE, \ldots) #' @rdname exportTab-methods #' @export setMethod(f="exportTab", signature=signature(x="list"), definition=function(x, path, force=FALSE, ...) { export(x, path=path, type="tab", force=force, ...) }) #' @usage #' \S4method{exportCsv}{AbstractMassObject}(x, file, force=FALSE, \ldots) #' @rdname exportTab-methods #' @export setMethod(f="exportCsv", signature=signature(x="AbstractMassObject"), definition=function(x, file, force=FALSE, ...) { export(x, file=file, type="csv", force=force, ...) }) #' @usage #' \S4method{exportCsv}{list}(x, path, force=FALSE, \ldots) #' @rdname exportTab-methods #' @export setMethod(f="exportCsv", signature=signature(x="list"), definition=function(x, path, force=FALSE, ...) { export(x, path=path, type="csv", force=force, ...) }) #' Export to MSD files #' #' This function exports #' \code{\link[MALDIquant]{AbstractMassObject-class}} objects (e.g. #' \code{\link[MALDIquant]{MassSpectrum-class}}, #' \code{\link[MALDIquant]{MassPeaks-class}}) #' into mMass MSD files. #' #' @usage #' \S4method{exportMsd}{MassSpectrum}(x, file, force=FALSE, peaks, \ldots) #' #' @param x a \code{\link[MALDIquant]{MassSpectrum-class}} object or a #' \code{list} of \code{\link[MALDIquant]{MassSpectrum-class}} objects. #' @param file \code{character}, file name. #' @param path \code{character}, path to directory in which the \code{list} of #' \code{\link[MALDIquant]{AbstractMassObject-class}} would be exported. #' @param peaks a \code{\link[MALDIquant]{MassPeaks-class}} object or a #' \code{list} of \code{\link[MALDIquant]{MassPeaks-class}} objects. #' @param force \code{logical}, If \code{TRUE} the \code{file} would be #' overwritten or \code{path} would be created. #' @param \ldots arguments to be passed to \code{\link[utils]{write.table}}. #' #' @seealso #' \code{\link[MALDIquant]{MassPeaks-class}}, #' \code{\link[MALDIquant]{MassSpectrum-class}} #' #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/}, \cr #' mMass homepage: \url{http://mmass.org/} #' @examples #' #' \dontrun{ #' library("MALDIquant") #' library("MALDIquantForeign") #' #' s <- list(createMassSpectrum(mass=1:5, intensity=1:5), #' createMassSpectrum(mass=1:5, intensity=1:5)) #' p <- list(createMassPeaks(mass=4:5, intensity=4:5, snr=1:2), #' createMassPeaks(mass=4:5, intensity=4:5, snr=1:2)) #' #' ## export a single spectrum #' exportMsd(s[[1]], file="spectrum.msd") #' #' ## export a single spectrum with corresponding peaks #' exportMsd(s[[1]], file="spectrum.msd", peaks=p[[1]]) #' #' ## export a list of spectra with corresponding peaks #' exportMsd(s, path="spectra", peaks=p, force=TRUE) #' } #' #' @aliases exportMsd exportMsd,MassSpectrum-method exportMsd,list-method #' @rdname exportMsd-methods #' @docType methods #' @export setMethod(f="exportMsd", signature=signature(x="MassSpectrum"), definition=function(x, file, force=FALSE, peaks, ...) { if (!missing(peaks)) { stopifnot(isMassPeaks(peaks)) export(x, file=file, type="msd", force=force, peaks=peaks, ...) } else { export(x, file=file, type="msd", force=force, ...) } }) #' @usage #' \S4method{exportMsd}{list}(x, path, force=FALSE, peaks, \ldots) #' @rdname exportMsd-methods #' @export setMethod(f="exportMsd", signature=signature(x="list"), definition=function(x, path, force=FALSE, peaks, ...) { stopifnot(isMassSpectrumList(x)) if (!missing(peaks)) { stopifnot(isMassPeaksList(peaks)) export(x, path=path, type="msd", force=force, peaks=peaks, ...) } else { export(x, path=path, type="msd", force=force, ...) } }) #' Export to mzML files #' #' This function exports #' \code{\link[MALDIquant]{MassSpectrum-class}} objects into mzML files. #' #' @usage #' \S4method{exportMzMl}{MassSpectrum}(x, file, force=FALSE, \ldots) #' #' @param x a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a #' \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects. #' @param file \code{character}, file name. #' @param path \code{character}, path to directory in which the \code{list} of #' \code{\link[MALDIquant]{MassSpectrum-class}} would be exported. If #' \code{path} is a single filename all spectra will be exported to a single #' mzML file. #' @param force \code{logical}, If \code{TRUE} the \code{file} would be #' overwritten or \code{path} would be created. #' @param \ldots arguments to be passed to internal functions. #' #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}} #' #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/}, \cr #' HUPO Proteomics Standards Inititative mzML 1.1.0 Specification: #' \url{https://www.psidev.info/mzML} #' @examples #' #' \dontrun{ #' library("MALDIquant") #' library("MALDIquantForeign") #' #' s <- list(createMassSpectrum(mass=1:5, intensity=1:5), #' createMassSpectrum(mass=1:5, intensity=1:5)) #' #' ## export a single spectrum #' exportMzMl(s[[1]], file="spectrum.mzML") #' #' ## export a list of spectra #' exportMzMl(s, path="spectra.mzML") #' } #' #' @aliases exportMzMl exportMzMl,MassSpectrum-method exportMzMl,list-method #' @rdname exportMzMl-methods #' @docType methods #' @export setMethod(f="exportMzMl", signature=signature(x="MassSpectrum"), definition=function(x, file, force=FALSE, ...) { export(x, file=file, type="mzml", force=force, ...) }) #' @usage #' \S4method{exportMzMl}{list}(x, path, force=FALSE, \ldots) #' @rdname exportMzMl-methods #' @export setMethod(f="exportMzMl", signature=signature(x="list"), definition=function(x, path, force=FALSE, ...) { export(x, path=path, type="mzml", force=force, ...) }) #' Export to imzML files #' #' This function exports #' \code{\link[MALDIquant]{MassSpectrum-class}} objects into imzML files. #' #' @usage #' \S4method{exportImzMl}{MassSpectrum}(x, file, force=FALSE, processed=TRUE, #' coordinates=NULL, pixelSize=c(100, 100), \ldots) #' #' @param x a \code{\link[MALDIquant]{AbstractMassObject-class}} object or a #' \code{list} of \code{\link[MALDIquant]{AbstractMassObject-class}} objects. #' @param file \code{character}, file name. #' @param path \code{character}, path to directory in which the \code{list} of #' \code{\link[MALDIquant]{MassSpectrum-class}} would be exported. If #' \code{path} is a single filename all spectra will be exported to a single #' imzML file. #' @param force \code{logical}, If \code{TRUE} the \code{file} would be #' overwritten or \code{path} would be created. #' @param processed \code{logical}, If \code{TRUE} (default) the spectra will #' be saved in processed mode (means mass and intensity is stored for each #' spectra separately in contrast to continuous mode where the mass is stored #' only for one spectrum). #' @param coordinates \code{matrix}, 2 column matrix that contains the x- and #' y-coordinates for the spectra. #' @param pixelSize \code{numeric}, a vector of length 2 that contains the x and #' y pixel size in micrometers (default: \code{c(100, 100)}). #' @param \ldots arguments to be passed to internal functions. #' #' @seealso #' \code{\link[MALDIquant]{MassSpectrum-class}} #' #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' #' Schramm T, Hester A, Klinkert I, Both J-P, Heeren RMA, Brunelle A, #' Laprevote O, Desbenoit N, Robbe M-F, Stoeckli M, Spengler B, Roempp A #' (2012)\cr #' imzML - A common data format for the flexible exchange and processing of mass #' spectrometry imaging data.\cr #' Journal of Proteomics 75 (16):5106-5110. \cr #' \doi{10.1016/j.jprot.2012.07.026} #' @examples #' #' \dontrun{ #' library("MALDIquant") #' library("MALDIquantForeign") #' #' s <- list(createMassSpectrum(mass=1:5, intensity=1:5), #' createMassSpectrum(mass=1:5, intensity=1:5)) #' #' ## export a list of spectra #' exportImzMl(s, path="processed.imzML", coordinates=cbind(x=1:2, y=c(1, 1))) #' } #' #' @aliases exportImzMl exportImzMl,MassSpectrum-method exportImzMl,list-method #' @rdname exportImzMl-methods #' @docType methods #' @export setMethod(f="exportImzMl", signature=signature(x="MassSpectrum"), definition=function(x, file, force=FALSE, processed=TRUE, coordinates=NULL, pixelSize=c(100, 100), ...) { export(x, file=file, type="imzml", force=force, processed=processed, coordinates=coordinates, pixelSize=pixelSize, ...) }) #' @usage #' \S4method{exportImzMl}{list}(x, path, force=FALSE, processed=TRUE, #' coordinates=NULL, pixelSize=c(100, 100), \ldots) #' @rdname exportImzMl-methods #' @export setMethod(f="exportImzMl", signature=signature(x="list"), definition=function(x, path, force=FALSE, processed=TRUE, coordinates=NULL, pixelSize=c(100, 100), ...) { export(x, path=path, type="imzml", force=force, processed=processed, coordinates=coordinates, pixelSize=pixelSize, ...) }) MALDIquantForeign/R/parseMzMl.R0000644000176200001440000003054314404344473015735 0ustar liggesusers## Copyright 2012-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Parse mzML files. #' #' This function parses mzML files. #' #' @param file \code{character}, path to mzML file #' @param verbose \code{logical}, verbose output? #' #' @return Returns a list with metadata and spectra. #' #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @keywords internal #' @noRd .parseMzMl <- function(file, verbose=FALSE, ...) { XML::xmlEventParse(file=file, handlers=.mzMlHandlers(fileName=file, verbose=verbose), addContext=FALSE, useTagName=TRUE, useDotNames=TRUE, ...)$getData() } #' Parse mzML files. #' #' This function is defines handlers for XML SAX parser. Internal use only. #' #' TODO: fetch obo map file and use it #' #' @param fileName \code{character}, path to mzML file #' @param verbose \code{logical}, verbose output? #' #' @return function closure #' #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @references #' Definition of \code{mzML} format: #' \url{https://www.psidev.info/mzML} #' @keywords internal #' @noRd .mzMlHandlers <- function(fileName, verbose=FALSE) { ## define local variables ## handle different mzXML versions mzMlVersion <- 0 ## save last opened tag (needed for .text()-processing) openTag <- "" ## store current scan values nSpectra <- 0L curSpecIdx <- 0L curRefId <- character() currentArrayContent <- character() fileCheckSum <- character() ## supported? supported <- TRUE ## build final list xml <- list() xml$metaData <- list() xml$spectra <- list() ## imzML information xml$ims <- list() ## reference values references <- new.env(parent=emptyenv()) ## handlers for specific tags ## mzML mzML <- function(name, attrs) { ## fetch version information mzMlVersion <<- readMzXmlData:::.grepDouble(attrs["xsi:schemaLocation"]) .msg(verbose, "Found mzML document (version: ", mzMlVersion, ").") } ## mzML/referenceableParamGroupList/referenceableParamGroup referenceableParamGroup <- function(name, attrs) { openTag <<- name curRefId <<- readMzXmlData:::.attributeToString(attrs, "id", required=TRUE) } referenceableParamGroupRef <- function(name, attrs) { if (!is.null(references[[attrs["ref"]]])) { xml$spectra[[curSpecIdx]]$metaData <<- modifyList(xml$spectra[[curSpecIdx]]$metaData, references[[attrs["ref"]]]) } } ## mzML/run/spectrumList spectrumList <- function(name, attrs) { ## fetch number of spectra nSpectra <<- readMzXmlData:::.attributeToDouble(attrs, "count", required=TRUE) .msg(verbose, "Found ", nSpectra, " ", ifelse(nSpectra == 1, "spectrum", "spectra"), ".") } ## mzML/run/spectrumList/spectrum spectrum <- function(name, attrs) { openTag <<- name curSpecIdx <<- curSpecIdx + 1 supported <<- TRUE xml$spectra[[curSpecIdx]] <<- list() xml$spectra[[curSpecIdx]]$metaData <<- list() xml$spectra[[curSpecIdx]]$metaData[["id"]] <<- readMzXmlData:::.attributeToString(attrs, "id", required=TRUE) xml$spectra[[curSpecIdx]]$metaData[["numberInFile"]] <<- curSpecIdx ## IMS extension if (length(xml$ims)) { xml$ims$ibd[[curSpecIdx]] <<- matrix(NA, nrow=2, ncol=3, dimnames=list(c("mass", "intensity"), c("offset", "length", "encodedLength"))) xml$spectra[[curSpecIdx]]$metaData$imaging <<- list() } .msg(verbose, "Processing spectrum ", curSpecIdx, "/", nSpectra, " (id: ", attrs["id"], ") ...") } chromatogram <- function(name, attrs) { warning(" tag is not supported!") supported <<- FALSE } ## *cvParam cvParam <- function(name, attrs) { ## polarity if (.isAttrSet(attrs, "MS:1000129", "negative scan")) { .setCvValue("negative", "polarity") return() } else if (.isAttrSet(attrs, "MS:1000130", "positive scan")) { .setCvValue("positive", "polarity") return() } ## ms level if (.isAttrSet(attrs, "MS:1000511", "ms level")) { .setCvValue( readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE), "msLevel") return() } ## centroid data if (.isAttrSet(attrs, "MS:1000127", "centroid spectrum")) { .setCvValue(1, "centroided") return() } ## precision if (.isAttrSet(attrs, "MS:1000521", "32-bit float")) { .setCvValue(32, "precision") return() } else if (.isAttrSet(attrs, "MS:1000523", "64-bit float")) { .setCvValue(64, "precision") return() } ## compression if (.isAttrSet(attrs, "MS:1000576", "no compression")) { .setCvValue("none", "compressionType") return() } else if (.isAttrSet(attrs, "MS:1000574", "zlib compression")) { .setCvValue("gzip", "compressionType") return() } ## data arrays if (.isAttrSet(attrs, "MS:1000514", "m/z array")) { .setCvValue("mass", "currentArray") return() } else if (.isAttrSet(attrs, "MS:1000515", "intensity array")) { .setCvValue("intensity", "currentArray") return() } else if (.isAttrSet(attrs, "MS:1000517", "signal to noise array")) { .setCvValue("snr", "currentArray") return() } else if (.isAttrSet(attrs, "MS:1000786", "non-standard data array")) { .setCvValue("nonstandard", "currentArray") return() } ## IMS extensions if (.isAttrSet(attrs, "IMS:1000080", "universally unique identifier")) { xml$ims$uuid <<- gsub(pattern="[[:punct:]]", replacement="", x=readMzXmlData:::.attributeToString(attrs, "value", required=TRUE)) return() } if (.isAttrSet(attrs, "IMS:1000090", "ibd MD5")) { xml$ims$md5 <<- readMzXmlData:::.attributeToString(attrs, "value") return() } if (.isAttrSet(attrs, "IMS:1000091", "ibd SHA-1")) { xml$ims$sha1 <<- readMzXmlData:::.attributeToString(attrs, "value") return() } if (.isAttrSet(attrs, "IMS:1000030", "continuous")) { xml$ims$type <<- "continuous" return() } if (.isAttrSet(attrs, "IMS:1000031", "processed")) { xml$ims$type <<- "processed" return() } if (.isAttrSet(attrs, "IMS:1000042", "max count of pixel x")) { xml$metaData$imaging$size["x"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000043", "max count of pixel y")) { xml$metaData$imaging$size["y"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000044", "max dimension x")) { xml$metaData$imaging$dim["x"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000045", "max dimension y")) { xml$metaData$imaging$dim["y"]<<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000046", "pixel size x")) { xml$metaData$imaging$pixelSize["x"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000047", "pixel size y")) { xml$metaData$imaging$pixelSize["y"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000050", "position x")) { xml$spectra[[curSpecIdx]]$metaData$imaging$pos["x"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000051", "position y")) { xml$spectra[[curSpecIdx]]$metaData$imaging$pos["y"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000102", "external offset")) { xml$ims$ibd[[curSpecIdx]][xml$spectra[[curSpecIdx]]$metaData$currentArray, "offset"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000103", "external array length")) { xml$ims$ibd[[curSpecIdx]][xml$spectra[[curSpecIdx]]$metaData$currentArray, "length"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } if (.isAttrSet(attrs, "IMS:1000104", "external encoded length")) { xml$ims$ibd[[curSpecIdx]][xml$spectra[[curSpecIdx]]$metaData$currentArray, "encodedLength"] <<- readMzXmlData:::.attributeToDouble(attrs, "value", required=TRUE) return() } } ## default functions to catch tags without a handler .startElement <- function(name, attrs) { openTag <<- name } .endElement <- function(name, attrs) { if (name == "binary" && supported) { .decodeArray() } else if (name == "fileChecksum") { .calculateFileChecksum() } if (openTag == name) { openTag <<- "" } } .text <- function(x) { if (openTag == "binary" && supported) { currentArrayContent <<- paste0(currentArrayContent, x) } else if (openTag == "fileChecksum") { fileCheckSum <<- paste0(fileCheckSum, x) } } ## helper functions .isAttrSet <- function(attrs, id, name) { return(attrs["accession"] == id || attrs["name"] == name) } .setCvValue <- function(x, name) { if (openTag == "referenceableParamGroup") { if (is.null(references[[curRefId]])) { references[[curRefId]] <<- list() } references[[curRefId]][[name]] <<- x } else if (openTag == "spectrum" || openTag == "binaryDataArray") { xml$spectra[[curSpecIdx]]$metaData[[name]] <<- x } else { xml$metaData[[name]] <<- x } } .decodeArray <- function() { if (length(currentArrayContent)) { ## read base64 encoded array content (endian must be "little") content <- readMzXmlData:::.base64decode(x=currentArrayContent, endian="little", size=round(xml$spectra[[curSpecIdx]]$metaData$precision/8), compressionType=xml$spectra[[curSpecIdx]]$metaData$compressionType) xml$spectra[[curSpecIdx]][[xml$spectra[[curSpecIdx]]$metaData$currentArray]] <<- content ## clear array content currentArrayContent <<- character() } ## clear metaData xml$spectra[[curSpecIdx]]$metaData[c("precision", "compressionType", "currentArray")] <<- NULL } .calculateFileChecksum <- function() { n <- nchar(fileCheckSum) if (n <= 0) { return() } ## sha1 sum for this file (from the beginning of the file up to (and ## including) the opening tag .msg(verbose, "Look for '' position ...") ## 14 == nchar("") checkSumPos <- readMzXmlData:::.revfregexpr("", fileName) + 14 .testChecksum(fileName, fileCheckSum, algo="sha1", length=checkSumPos-1, verbose=verbose) } ## return statement (please call getData()) list(getData=function() {return(xml)}, mzML=mzML, referenceableParamGroup=referenceableParamGroup, referenceableParamGroupRef=referenceableParamGroupRef, spectrumList=spectrumList, spectrum=spectrum, chromatogram=chromatogram, cvParam=cvParam, .startElement=.startElement, .endElement=.endElement, .text=.text) } MALDIquantForeign/R/fileFormats.R0000644000176200001440000001000314404344473016263 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Supported file formats #' #' This function prints all file formats supported by #' \code{\link{MALDIquantForeign-package}}. #' #' \subsection{Import}{ #' #' \tabular{ll}{ #' txt \tab \code{\link[MALDIquantForeign]{importTxt}} \cr #' tab \tab \code{\link[MALDIquantForeign]{importTab}} \cr #' csv \tab \code{\link[MALDIquantForeign]{importCsv}} \cr #' fid \tab \code{\link[MALDIquantForeign]{importBrukerFlex}} \cr #' ciphergen \tab \code{\link[MALDIquantForeign]{importCiphergenXml}} \cr #' mzXML \tab \code{\link[MALDIquantForeign]{importMzXml}} \cr #' mzML \tab \code{\link[MALDIquantForeign]{importMzMl}} \cr #' imzML \tab \code{\link[MALDIquantForeign]{importImzMl}} \cr #' analyze \tab \code{\link[MALDIquantForeign]{importAnalyze}} \cr #' cdf \tab \code{\link[MALDIquantForeign]{importCdf}} \cr #' msd \tab \code{\link[MALDIquantForeign]{importMsd}} \cr #' } #' } #' #' \subsection{Export}{ #' #' \tabular{ll}{ #' tab \tab \code{\link[MALDIquantForeign]{exportTab}} \cr #' csv \tab \code{\link[MALDIquantForeign]{exportCsv}} \cr #' imzML \tab \code{\link[MALDIquantForeign]{exportImzMl}} \cr #' msd \tab \code{\link[MALDIquantForeign]{exportMsd}} \cr #' mzML \tab \code{\link[MALDIquantForeign]{exportMzMl}} \cr #' } #' } #' #' @return a \code{list} with two named elements (\code{import} and #' \code{export}) containing a \code{character} vector of supported file types. #' #' @seealso #' \code{\link[MALDIquantForeign]{export}}, #' \code{\link[MALDIquantForeign]{import}} #' @author Sebastian Gibb #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @examples #' library("MALDIquantForeign") #' #' supportedFileFormats() #' #' @rdname supportedFileFormats-functions #' @export supportedFileFormats <- function() { list(import=importFormats$type, export=exportFormats$type) } importFormats <- data.frame(type=c("txt", "tab", "csv", "fid", "ciphergen", "mzxml", "mzml", "imzml", "analyze", "cdf", "msd"), pattern=c("^.*\\.txt$", "^.*\\.tab$", "^.*\\.csv$", "^fid$", "^.*\\.xml$", "^.*\\.mzXML$", "^.*\\.mzML$", "^.*\\.imzML$", "^.*\\.hdr$", "^.*\\.cdf$", "^.*\\.msd$"), handler=c(rep(".importTab", 2), ".importCsv", ".importBrukerFlex", ".importCiphergenXml", ".importMzXml", ".importMzMl", ".importImzMl", ".importAnalyze", ".importCdf", ".importMsd"), stringsAsFactors=FALSE) exportFormats <- data.frame(type=c("tab", "csv", "msd", "mzml", "imzml"), extension=c("tab", "csv", "msd", "mzML", "imzML"), onefile=c(FALSE, FALSE, FALSE, TRUE, TRUE), handler=c(".exportTab", ".exportCsv", ".exportMsd", ".exportMzMl", ".exportImzMl"), stringsAsFactors=FALSE) MALDIquantForeign/R/sanitize-functions.R0000644000176200001440000000171514404344473017656 0ustar liggesusers## Copyright 2012 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .sanitize <- function(x) { x <- gsub(pattern="&", replacement="&", x=x) x <- gsub(pattern="<", replacement="<", x=x) gsub(pattern=">", replacement=">", x=x) } MALDIquantForeign/R/package.R0000644000176200001440000000333714553551252015417 0ustar liggesusers## Copyright 2012-2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Import/Export routines for \sQuote{MALDIquant} #' #' This package reads and writes different file formats of mass #' spectrometry data into/from \sQuote{MALDIquant} objects. #' #' \tabular{ll}{ #' Package: \tab MALDIquantForeign \cr #' License: \tab GPL (>= 3)\cr #' URL: \tab https://strimmerlab.github.io/software/maldiquant/\cr #' } #' #' @name MALDIquantForeign-package #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @keywords package #' #' @import MALDIquant #' @import readMzXmlData #' @import methods #' @importFrom base64enc base64encode #' @importFrom digest digest #' @importFrom readBrukerFlexData readBrukerFlexFile #' @importFrom stats na.omit runif #' @importFrom utils download.file modifyList packageVersion read.table tail #' type.convert write.table untar unzip #' @importFrom XML xmlEventParse xmlParse xmlValue xpathApply xpathSApply #' "_PACKAGE" MALDIquantForeign/R/MALDIquantForeign-parallel.R0000644000176200001440000000544714404344473021033 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' Parallel Support in Package \pkg{MALDIquantForeign} #' #' \code{\link[MALDIquantForeign]{MALDIquantForeign-package}} offers multi-core #' support using \code{\link[parallel]{mclapply}} and #' \code{\link[parallel]{mcmapply}}. This approach is limited to unix-based #' platforms. #' #' Please note that not all import functions benfit from parallelisation. The #' current implementation is limited to run the parallelisation over different #' files. That's why only imports of multiple files could be run on multiple #' cores. E.g. a single mzML file containing 4 spectra would always be #' read on a single core. In contrast 4 mzML files each containing just one #' spectra could be read in using 4 cores. #' #' The improvement in the runtime depends on the amount of data to read, the #' proportion of parsing/decoding of the data, the amount of memory and the #' speed of the hard disk. #' #' Please note: It is possible that using parallelisation results in a worse #' runtime! #' #' @name MALDIquantForeign-parallel #' @author Sebastian Gibb \email{mail@@sebastiangibb.de} #' @references \url{https://strimmerlab.github.io/software/maldiquant/} #' @keywords misc #' @seealso #' \code{\link[MALDIquant]{MALDIquant-parallel}}, #' \code{\link[parallel]{mclapply}}, #' \code{\link[parallel]{mcmapply}} #' #' @examples #' ## load packages #' library("MALDIquant") #' library("MALDIquantForeign") #' #' exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") #' #' ## run single-core import #' print(system.time( #' s1 <- importMzMl(exampleDirectory, centroided=TRUE, verbose=FALSE) #' )) #' #' if(.Platform$OS.type == "unix") { #' ## run multi-core import #' ## (because the example spectra are very small (just 5 data points) the #' ## multi-core solution is slower on most systems) #' print(system.time( #' s2 <- importMzMl(exampleDirectory, centroided=TRUE, mc.cores=2, #' verbose=FALSE) #' )) #' stopifnot(all.equal(s1, s2)) #' } #' @rdname MALDIquantForeign-parallel NULL MALDIquantForeign/R/importAnalyze-functions.R0000644000176200001440000000433614404344473020670 0ustar liggesusers## Copyright 2013-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importAnalyze <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE) { header <- .readAnalyzeHdr(file, verbose=verbose) mass <- .readAnalyzeMass(.changeFileExtension(file, "t2m"), header=header, verbose=verbose) massRange <- MALDIquant:::.reorderRange(massRange) massIdx <- which(massRange[1] <= mass & mass <= massRange[2]) skip <- c(massIdx[1]-1, length(mass)-massIdx[length(massIdx)]) mass <- mass[massIdx] intensity <- .readAnalyzeIntensity(.changeFileExtension(file, "img"), header=header, ni=length(mass), skip=skip, verbose=verbose) l <- vector(mode="list", length=header$nx*header$ny) for (x in 1:header$nx) { for (y in 1:header$ny) { l[[(x-1)*header$ny+y]] <- .createMassObject(mass=mass, intensity=intensity[, x, y], metaData=list(file=file, imaging=list(pos=c(x=x, y=y), pixelSize=c(x=header$xd, y=header$yd))), centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose) } } l } MALDIquantForeign/R/export-functions.R0000644000176200001440000000504014404344473017344 0ustar liggesusers## Copyright 2013 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .exportToFile <- function(x, file, type="auto", force=FALSE, ...) { if (file.exists(file) && !force) { stop("File already exists! Use ", sQuote("force=TRUE"), " to overwrite it.") } if (missing(type) || pmatch(tolower(type), "auto", nomatch=0, duplicates.ok=FALSE)) { type <- .fileExtension(file) } i <- pmatch(tolower(type), exportFormats$type, nomatch=0, duplicates.ok=FALSE) if (i) { handler <- exportFormats$handler[i] return(do.call(handler, list(x=x, file=file, ...))) } else { stop("File type ", sQuote(type), " is not supported!") } } .exportToDir <- function(x, path, type, force=FALSE, ...) { if (!file.exists(path) && force) { dir.create(path, showWarnings=FALSE, recursive=TRUE) } if (!file.exists(path)) { stop("Directory ", sQuote(path), " doesn't exist!") } if (!file.info(path)$isdir) { stop(sQuote(path), " is no directory!") } ## stop if directory isn't writeable if (file.access(path, 2) != 0) { stop("No permissions to write into ", sQuote(path), "!") } i <- pmatch(tolower(type), exportFormats$type, nomatch=0, duplicates.ok=FALSE) if (i) { filenames <- .composeFilename(x, fileExtension=exportFormats$extension[i]) filenames <- file.path(path, filenames) optArgs <- list(...) peaks <- list() if (hasArg(peaks)) { peaks <- optArgs$peaks optArgs$peaks <- NULL } for (i in seq(along=x)) { arguments <- list(x=x[[i]], file=filenames[i], type=type, force=force) arguments <- modifyList(arguments, optArgs) if (length(peaks)) { arguments$peaks <- peaks[[i]] } do.call(export, arguments) } } else { stop("File type ", sQuote(type), " is not supported!") } invisible() } MALDIquantForeign/R/importCdf-functions.R0000644000176200001440000000535114404344473017757 0ustar liggesusers## Copyright 2013-2014 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see #' @author Pietro Franceschi \email{pietro.franceschi@@fmach.it}, Sebastian Gibb #' \email{mail@@sebastiangibb.de} #' @keywords internal #' @noRd ## original code written by Pietro Franceschi ## modified for MALDIquantForeign by Sebastian Gibb .importCdf <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE) { if (!requireNamespace("RNetCDF", quietly=TRUE)) { stop("For netCDF support the ", sQuote("RNetCDF"), " package is needed. \n", "Please install ", sQuote("RNetCDF"), ": install.packages(\"RNetCDF}\")") } nc <- RNetCDF::open.nc(file) on.exit(RNetCDF::close.nc(nc)) scanIndex <- as.integer(RNetCDF::var.get.nc(nc, variable="scan_index")) scanLength <- as.integer(RNetCDF::var.get.nc(nc, variable="point_count")) retentionTime <- as.double(RNetCDF::var.get.nc(nc, variable="scan_acquisition_time")) ## read and process the spectra/peaks l <- vector(mode="list", length=length(scanIndex)) for (i in seq(along=l)) { mass <- as.double(RNetCDF::var.get.nc(nc, variable="mass_values", start=scanIndex[i]+1L, count=scanLength[i])) intensity <- as.double(RNetCDF::var.get.nc(nc, variable="intensity_values", start=scanIndex[i]+1L, count=scanLength[i])) l[[i]] <- .createMassObject(mass=mass, intensity=intensity, metaData=list(file=file, number=i, retentionTime=retentionTime[i], scanIndex=scanIndex[i]), centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose) } l } MALDIquantForeign/R/uuid-functions.R0000644000176200001440000000407514404344473017000 0ustar liggesusers## Copyright 2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see ## generate uuid needed for imzML idb files ## based on dplR::uuid.gen by Mikko Korpela ## should be compatible to: ## https://en.wikipedia.org/wiki/Universally_unique_identifier#Version_4_.28random.29 ## @param init used to create the md5 string, just for testing; don't change the ## default in other use cases. ## @return uuid string ## @noRd .uuid <- function(init=paste(c(Sys.info(), Sys.getpid(), unlist(R.version), Sys.getpid(), format(Sys.time(), "%Y%m%d%H%M%OS6 %Z"), runif(5L)), collapse = "")) { md5 <- digest::digest(init, algo="md5", serialize=FALSE) md5 <- strsplit(md5, "", fixed=TRUE)[[1L]] md5[13] <- "4" md5[17] <- c("8", "9", "a", "b")[strtoi(md5[17L], base=16L)%%4L + 1L] .paste0 <- function(...)paste0(..., collapse="") paste(.paste0(md5[1L:8L]), .paste0(md5[9L:12L]), .paste0(md5[13L:16L]), .paste0(md5[17L:20L]), .paste0(md5[21L:32L]), sep="-") } ## test uuid version 4 ## @param x character vector to test ## @return logical ## @noRd .isUuidV4 <- function(x) { grepl(paste0("^[0-9a-f]{8}-?", "[0-9a-f]{4}-?", "4[0-9a-f]{3}-?", "[89ab][0-9a-f]{3}-?", "[0-9a-f]{12}"), tolower(x)) } MALDIquantForeign/R/importMzXml-functions.R0000644000176200001440000000303514404344473020327 0ustar liggesusers## Copyright 2012-2015 Sebastian Gibb ## ## ## This file is part of MALDIquantForeign for R and related languages. ## ## MALDIquantForeign is free software: you can redistribute it and/or modify ## it under the terms of the GNU General Public License as published by ## the Free Software Foundation, either version 3 of the License, or ## (at your option) any later version. ## ## MALDIquantForeign is distributed in the hope that it will be useful, ## but WITHOUT ANY WARRANTY; without even the implied warranty of ## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ## GNU General Public License for more details. ## ## You should have received a copy of the GNU General Public License ## along with MALDIquantForeign. If not, see .importMzXml <- function(file, centroided=FALSE, massRange=c(0, Inf), minIntensity=0, verbose=FALSE, ...) { l <- readMzXmlData:::.readMzXmlFile(mzXmlFile=file, verbose=verbose, ...) lapply(l, function(x).createMassObject(mass=x$spectrum$mass, intensity=x$spectrum$intensity, snr=x$spectrum$snr, metaData=x$metaData, centroided=centroided, massRange=massRange, minIntensity=minIntensity, verbose=verbose)) } MALDIquantForeign/MD50000644000176200001440000001643714553557406014024 0ustar liggesusers18473109df1530cf7baa283b24fe4a80 *DESCRIPTION 239f2ca23dfb8e6e1c412d77e5fef820 *NAMESPACE 187592679f1af1d865f377bd03fcbbd5 *NEWS 468e3370a3294e48758e68bf44eb407f *R/AllGenerics.R cb42459b9b046fee4667dec625d0cfa6 *R/MALDIquantForeign-parallel.R f9b1350a757c7834f31ca532d25d1de5 *R/analyze-functions.R 1b58692832033443e81536a702fd1851 *R/base64encode-functions.R 5eded2dfa5ab6f30adab3b5f91bc46aa *R/compression-functions.R edbb6f3bcba17838f335546d6c697bf1 *R/createMassObject-functions.R 7142580c95b7bb81548ec28a1f57a757 *R/download-function.R 3732160f3b60f23d42531b5613c0282a *R/export-functions.R 8788d9f89ed9587f28956575ca68f38e *R/export-methods.R 8e81b2f07b5ebca91079b77b11da0c65 *R/exportImzMl-methods.R d3fd02920e121a29e811d24dce0783b3 *R/exportMsd-methods.R 48a24d1dbab2f9d192a5e031d61e86af *R/exportMzMl-methods.R 6e1fd732f6c0ec57aa1f09f089068a8e *R/exportTab-methods.R 781eb5c45c622bfa78d81c7f28170b42 *R/fileFormats.R 9b2c039ff63220f1d8f2406aec505578 *R/filename-functions.R 577b0fabac835a12bbe5e57a219380f1 *R/filename-methods.R 4fef02cb2ff00e5602946fcd2b37454b *R/ibd-functions.R 14e7c658a07e8045accc9fff15b0fc63 *R/import-functions.R 3371975060c82b5119a62c8c7579bc8c *R/importAnalyze-functions.R ed4770aec8f1ea4c60650efe0ff348f0 *R/importAuto-functions.R c06d3b011a012c10d4bb3b3f32b873a2 *R/importBrukerFlex-functions.R 991cd23737589302cfbf572bd310db16 *R/importCdf-functions.R d3dd95ff9db890c5c1d83b60502126d2 *R/importCiphergenXml-functions.R 5586b113fbb7f48486109fa3873804be *R/importImzMl-functions.R 34ecdc5f98b4a2c63917e28fa9667f69 *R/importMsd-functions.R 4e240d8c0feda7e3e4ccf8c33b65a638 *R/importMzMl-functions.R 291368ca35bc6754d0df2b33b72927fc *R/importMzXml-functions.R d92ab30da765f0d80987a3477b92fa74 *R/importTab-functions.R 3954121f5eee0b570cb941c93f5f5282 *R/imzMl-functions.R 70de7be37f0efc823649222aa7e700e8 *R/list.files-functions.R e5d102e802ed4fd8f4ee4cc1979a4c3e *R/msd-functions.R f19d21cfff588c1025ce88d1cd237426 *R/msg-functions.R d851edfeaf58521dc72cd3913e64bd30 *R/mzMl-functions.R a7cde2607138da51b60b56948ddb0087 *R/package.R cdc0028d88e43ac7fef5d9b0ee0a2dcb *R/parseCiphergenXml.R 76f9f0f45f43a0fee5527580d08afcb6 *R/parseMsd.R 230f437d9b1bb85466689fe8b11b9d7a *R/parseMzMl.R d4f6dc7b3fcac7a645b9ededbe1f7725 *R/sanitize-functions.R 44d338127260829b963160af58e3bdf7 *R/testChecksum-functions.R 0c89faab57ee2bd013c2d19cbbbcb453 *R/uuid-functions.R 9bd11f78213543c6d61423efa00cdb23 *R/xml-functions.R f61db891eb928123aba4412ca322f508 *build/partial.rdb 7ca8bfc075f62a5a8f86a841775aafb1 *build/vignette.rds 52c2cb8ccc8897b4ce122bb81377b9b0 *inst/doc/MALDIquantForeign-intro.R 9600ed294b05bd28e4b08efc2bd0ba84 *inst/doc/MALDIquantForeign-intro.Rnw dc72a3ad4799d8af4bcbe71e9726451b *inst/doc/MALDIquantForeign-intro.pdf 9274dd34d675950326a222a952309a17 *inst/exampledata/ascii.txt 85077ca13692b5a2469af51d18cffd64 *inst/exampledata/brukerflex/0_A1/1/1SLin/acqu fe054ad2e7b98bee673f9ff22d50f00c *inst/exampledata/brukerflex/0_A1/1/1SLin/fid 10e9d68aa23b1d7b85688a969be41897 *inst/exampledata/ciphergen/tiny.xml 4b725014b8cacf380e44475b95905d7d *inst/exampledata/compressed/csv.tar.gz c449fa2a93410566dba5e145ed09b0ae *inst/exampledata/compressed/csv.zip 448976240c5d1caccd3d2fe3a8c04e7e *inst/exampledata/compressed/csv1.csv.gz 4ca88a472371bd1e63d57987c06c4c43 *inst/exampledata/csv1.csv 4b2a03f6bbe5747bd50273be357533c1 *inst/exampledata/csv2.csv 90838531af29160ed4d7917edd7dbc4c *inst/exampledata/tiny.cdf 064e9a9a06250b5a29593ca23c592891 *inst/exampledata/tiny1-centroided.mzML1.1.mzML b2bc5ad00c449401ae4495677673af0a *inst/exampledata/tiny1-centroided.mzXML3.0.mzXML 4cabaefc8fe6d8f1bd0f55a9ba06e763 *inst/exampledata/tiny1-compressed.mzML1.1.mzML 09be2b7fff0d1834938d4aebaab4761c *inst/exampledata/tiny1-compressed.mzXML3.0.mzXML e06173e88f17386b359e124f8a33e758 *inst/exampledata/tiny1.msd 489b1be67d30d175969dbb66f8bcb9b7 *inst/exampledata/tiny1.mzML1.1.mzML 3b8bd26f7fc636e57388d52b3f9f3eb7 *inst/exampledata/tiny1.mzXML3.0.mzXML dcd657ee36f05b2b7be19f4db23184a4 *inst/exampledata/tiny_continuous.ibd 2decd26e6ba4ee132ab91fbe21125390 *inst/exampledata/tiny_continuous.imzML 1bcd45de54f0180c38afceb468371971 *inst/exampledata/tiny_processed.ibd ff2f70b3f12cb3cdafdcbe81b856a3ed *inst/exampledata/tiny_processed.imzML 87f5c724abd0bb9ff676efa05ed2c40d *man/MALDIquantForeign-package.Rd 88ad938fdbfb2b78ae7952182b3b156f *man/MALDIquantForeign-parallel.Rd 6de4e4e3f192010756eabc50c291753e *man/base64-encode.Rd 0fb40e9f5596930a603e9586d4b86a5f *man/export-methods.Rd a3ebe853172535c0b79a498e51bc87b8 *man/exportImzMl-methods.Rd f31b03d8e523f36d9aa3d5b0a989f486 *man/exportMsd-methods.Rd ff72c29bf9eb1cb7420ceb7560541251 *man/exportMzMl-methods.Rd 8e9ba98d9189ee13a0314fc03db5120c *man/exportTab-methods.Rd 0a2ef3fda9ad3e4845f8ce264ee960f6 *man/import-functions.Rd 5913b1aba8e892bb9dfd8ab3544315a6 *man/importAnalyze-functions.Rd 438a331c57aecdcb4edc692ed912833f *man/importBrukerFlex-functions.Rd ad4373d5a94c132402c9d1e8036ee327 *man/importCdf-functions.Rd 349b2edbae5b3fe5cc7d0487c9f9c624 *man/importCiphergenXml-functions.Rd 9bf9c2d1e269fa2813979a634ccdd2ad *man/importImzMl-functions.Rd 56fb8de96fd5fe42cb00a58e8629dd8b *man/importMsd-functions.Rd 2cfa83d2b5706d0921683c2b9ae46a3f *man/importMzMl-functions.Rd 9fce880a92858b413e869f9fbc04d4e6 *man/importMzXml-functions.Rd 2dd21b28cb0ca9530fe8d3e01d3d0b91 *man/importTab-functions.Rd abd990e4b75d7356cb1b9442e35f9325 *man/supportedFileFormats-functions.Rd f743796f136a436364c76e6b0f83d474 *tests/testthat.R b798ecbef464ea1807946fa217445894 *tests/testthat/test_compression-functions.R 0857bc348532e96bcfd91f7ae4d0475d *tests/testthat/test_createMassObject-functions.R debeabc712adc81b15966652fc9be840 *tests/testthat/test_download-functions.R e74111e7717d26f7790b4f8a1709213d *tests/testthat/test_exportImzMl-methods.R 8f3ae0b444a353e6a37ec3bfacfb0e74 *tests/testthat/test_exportMsd-methods.R 42593c8dd7bb81d9e2fa62354b68bc2d *tests/testthat/test_exportMzMl-methods.R bc154ef954d4012596f14aeeb9f9d90a *tests/testthat/test_exportTab-methods.R c0c445cb3dc0146a53ed5c7cb4326467 *tests/testthat/test_fileFormats.R 4c794d2aa272d40186b93e7d19ab3d25 *tests/testthat/test_filename-functions.R 2c30aa4314b05352630a6a9a74578475 *tests/testthat/test_ibd-functions.R 84ac426570d99e3a3e4639013b4ca6b7 *tests/testthat/test_importBrukerFlex-functions.R 071c254f1a0870eb09163742840ee3eb *tests/testthat/test_importCdf-functions.R 8432026fd0ec2a342cfe9c6f23dc21ca *tests/testthat/test_importCiphergenXml-functions.R 17ea5917b8dbc97de2d1214e0391acb8 *tests/testthat/test_importImzMl-functions.R 688f77adbcefb49f0910338a8fbff29e *tests/testthat/test_importMsd-functions.R de7de747a128ba1c30656b7b3d663edd *tests/testthat/test_importMzMl-functions.R 107cb57fff1e06e1619d810443734b90 *tests/testthat/test_importMzXml-functions.R 79de24105faaba91da6564d64f8d89ee *tests/testthat/test_importTab-functions.R 683c710df52b1d3218ba8e708943b15b *tests/testthat/test_list.files-functions.R 33be42ee6c030ad06a3b25898995fa63 *tests/testthat/test_msg-functions.R c0ef452eab581e6b3f15b30f0101481f *tests/testthat/test_mzMl-functions.R 62f4062ce2e6a8e8bb3aacefded07bf0 *tests/testthat/test_sanitize-functions.R c107102debc5d24e6096c38dde9199fc *tests/testthat/test_testChecksum-functions.R 09171eb807444e4b40e76a31edec4eec *tests/testthat/test_uuid-functions.R 9600ed294b05bd28e4b08efc2bd0ba84 *vignettes/MALDIquantForeign-intro.Rnw dcdcd775ae2bcfb2aea05af8e6921bef *vignettes/bibliography.bib MALDIquantForeign/inst/0000755000176200001440000000000014553553440014450 5ustar liggesusersMALDIquantForeign/inst/doc/0000755000176200001440000000000014553553440015215 5ustar liggesusersMALDIquantForeign/inst/doc/MALDIquantForeign-intro.Rnw0000644000176200001440000001371314553545654022264 0ustar liggesusers%\VignetteEngine{knitr::knitr} %\VignetteIndexEntry{MALDIquantForeign: Import/Export routines for MALDIquant} %\VignetteKeywords{Bioinformatics, Proteomics, Mass Spectrometry} %\VignettePackage{MALDIquantForeign} \documentclass[12pt]{article} \usepackage{natbib} \usepackage{hyperref} \usepackage{tikz} \usepackage{bibentry} % inline bibentries \nobibliography* % no special bibliography for bibentry \newcommand{\R}{\texttt{R}} \newcommand{\CRAN}{\texttt{CRAN}} \newcommand{\Rfunction}[1]{{\texttt{#1}}} \newcommand{\Robject}[1]{{\texttt{#1}}} \newcommand{\Rpackage}[1]{{\texttt{#1}}} \newcommand{\Mq}{\Rpackage{MALDIquant}} \newcommand{\MqF}{\Rpackage{MALDIquantForeign}} \newcommand{\email}[1]{\href{mailto:#1}{\normalfont\texttt{#1}}} \title{\MqF{}: Import/Export routines for \Mq{}} \author{ Sebastian Gibb% \thanks{\email{mail@sebastiangibb.de}} } \date{\today} \begin{document} <>= library("knitr") opts_chunk$set(tidy.opts=list(width.cutoff=45), tidy=FALSE, fig.align="center", fig.height=4.25, comment=NA, prompt=TRUE) @ <>= suppressPackageStartupMessages(library("MALDIquant")) suppressPackageStartupMessages(library("MALDIquantForeign")) @ \maketitle \begin{abstract} \MqF{} provides routines for importing/exporting different file formats into/from \Mq{}.\\ This vignette describes the usage of the \MqF{} package. \end{abstract} \clearpage \tableofcontents \section*{Foreword} \MqF{} is free and open source software for the \R{} \citep{RPROJECT} environment and under active development. If you use it, please support the project by citing it in publications: \begin{quote} \bibentry{MALDIquant} \end{quote} If you have any questions, bugs, or suggestions do not hesitate to contact me (\email{mail@sebastiangibb.de}). \\ Please visit \url{http://strimmerlab.org/software/maldiquant/}. \section{Introduction} \Mq{} should be device and platform independent. That's why it has not any import/export functions. \\ \MqF{} fills this gap and provides import/export routines for various file formats: <>= supportedFileFormats() @ \section{Setup} After starting \R{} we could install \Mq{} and \MqF{} directly from \CRAN{} using \Rfunction{install.packages}: <>= install.packages(c("MALDIquant", "MALDIquantForeign")) @ Before we can use \Mq{} and \MqF{} we have to load the packages. <>= library("MALDIquant") library("MALDIquantForeign") @ \section{Import} \MqF{} provides an \Rfunction{import} function that tries to auto-detect the correct file type. Because this would never be perfect \MqF{} offers also many \Rfunction{import*} functions like \Rfunction{importBrukerFlex}, \Rfunction{importMzMl}, etc. Please see the manual page of \Rfunction{import} for a complete list (\Rfunction{?import}).\\ First we try to import some example data in Bruker Daltonics *flex-series file format using the \Rfunction{import} function. <>= ## get the example directory exampleDirectory <- system.file("exampledata", package="MALDIquantForeign") spectra <- import(file.path(exampleDirectory, "brukerflex"), verbose=FALSE) spectra[[1]] @ Next we use the \Rfunction{importBrukerFlex} function (the result is the same as above). <>= spectra <- importBrukerFlex(file.path(exampleDirectory, "brukerflex"), verbose=FALSE) spectra[[1]] @ \MqF{} supports compressed files, too (\emph{zip}, \emph{tar.\{bz2, gz,xz\}}). <>= spectra <- importCsv(file.path(exampleDirectory, "compressed", "csv.tar.gz"), verbose=FALSE) spectra[[1]] spectra <- importCsv(file.path(exampleDirectory, "compressed", "csv.zip"), verbose=FALSE) spectra[[1]] @ Remote files are supported as well. Data are taken from \citet{Tan2006}. <>= spectra <- import(paste0("http://www.meb.ki.se/", "~yudpaw/papers/spikein_xml.zip"), centroided=FALSE, verbose=TRUE) @ If you want to read peak lists (centroided data) instead of spectra data you have to set \Rfunction{centroided=TRUE}. <>= peaks <- import(file.path(exampleDirectory, "ascii.txt"), centroided=TRUE, verbose=FALSE) peaks @ \section{Export} The export routines in \MqF{} are very similar to the import routines. Please see manual page of \Rfunction{export} for a complete list of supported export routines (\Rfunction{?export}). First we create a simple list of \Robject{MassSpectrum} objects using \Rfunction{createMassSpectrum}. <>= spectra <- list( createMassSpectrum(mass=1:5, intensity=1:5), createMassSpectrum(mass=1:5, intensity=6:10)) @ Now we want to export the first spectrum into a CSV file. <>= export(spectra[[1]], file="spectrum1.csv") import("spectrum1.csv") @ Exporting every file by hand is cumbersome. We want to export the whole list of spectra. Instead of \Robject{file} we use \Robject{path} now to specify a directory. Please note that we have to add the file type/format information now (we can use the \Robject{type} argument or the corresponding \Rfunction{export*} function). If the path doesn't exists we will get an error. To force \Rfunction{export} to create/overwrite the given path, we set the argument \Robject{force=TRUE}. <>= export(spectra, type="csv", path="spectra", force=TRUE) list.files("spectra") @ \section{Analyse Mass Spectrometry Data} Please have a look at the corresponding vignette shipped with \Mq{} and the \Mq{} website: \url{http://strimmerlab.org/software/maldiquant/}. <>= vignette(topic="MALDIquant", package="MALDIquant") @ \section{Session Information} <>= toLatex(sessionInfo(), locale=FALSE) @ \bibliographystyle{apalike} \bibliography{bibliography} \end{document} MALDIquantForeign/inst/doc/MALDIquantForeign-intro.pdf0000644000176200001440000050242514553553440022262 0ustar liggesusers%PDF-1.5 % 33 0 obj << /Length 608 /Filter /FlateDecode >> stream xڅTKs0W֮H=5ƙdC&9`6$<6ݜF=k!D4Lg`-1/jhҀ''+}uUnr]O;FIHf!N%NFu'_{HDh-z޷eDI c٪?M-DYH)Y z?$@OS387.FYr7)H_-vm-K+Lţ7za'PN)u/M~":>s= }.4k^E2Z@|P< W+&^S:&Q&<۬ XESoDF5@@*4+㬹Ҕ!ހjq\ܝ梬mZ6K9"D]vε`iJ a"=˖4cc"\'@/ dT*+~wghxy#&DKau.xz*Fpl΀e.jfy'a_ޘn1Ul+9㰫w> endstream endobj 57 0 obj << /Length 1259 /Filter /FlateDecode >> stream xWKs6 WVi&E#Nݙ6mmѶZYrD)L|rlv'9tzHAG:6A|b~-ӀgLp%:6s3rV(%0f"e"Wd£Y Ytm4o9 |̈́Y 9zACAw2 );m׃zZٴ$_P]x,qsRW5`𓶖FwĬd;wO$~{xyMnuOL%ٞW\%+IB)c_ISOo~}s?覿jx:8cg`l*R3GiDOhvVl#X{D[9iߚpy$ַS,x?bߒw"ʡ2zw HT]hӂ;*4PA!4IPўE3fMFO(lzӪāѣrJ!Sla ﱽ <$ j6$zxaYWhgp;@L )r c\by1J-]ۙ0c 4VDB+,(jCۓr 5 8h kfhk\Wz@u5Kj;8ƢHZ h|[elT8)d}%I4aʮ?ýsŤ&o8jolELD!8yXWKrF*vl ʖM=z~yRUg(f33tV<+I.tUdRC8 Yi& ? |J4NNmlA䡂Lrс}ϭG{6sG9zr;Q$)LjOsq~&7TXbr9ats:5| }0и Yo۲`2u `L#"=\PxF9׻v77ra? !@w?-Û(j${MVOGN\* DZpZ.p!)I,Kl_j{ȿŹH<*"%s!hg+|^/޽&zۗjw{w|O T’LU^0_VF endstream endobj 67 0 obj << /Length 1488 /Filter /FlateDecode >> stream xXKs6Wp4DctZ7'Zd)Q!))bɍ\ge,o1.|緘n#2+{|wD@ `P)ّb%VH`Rew>ʗgGOA48#-x F1c88Igo~ $"2"q.sv "AuS I8FLbdEKJ [rT:^S3x~ۛY6b/Sxmf;3kR &$[Vx$RYE516f^{ g/0v\3oƷV`[aBߝ'1Qַ``Hk̠"T˅UbAލXO%Iea) *)t>6"HI$)>0$5KRx/0, vzLU,)Y} )$/L:ڀc$hȅSXnFLaFU2O׭?O,ښe0T?IHFWԔ}|c8kc̽_8Q_"!Y-~DEL9lR0K; +:Hv#b3 |@ѣS,xWuS`ف pԦ]B݁($E 0mK3 KFT8JnrY>»@ $E=QR#&uҗ%T+˓SC]QU!) j(xhSzńo.j1_$j1V^Iif5e=.Wi \5qGlA,-+7jrXL\t~\lڄXWdmjUOg.zgZIXs=d8"6H;Ƕ)ʪ|J7]JS'Z_ׯMy1K*w=Fdnȣ- xz5|7qu:L*HHh[Hp7ӻm'H~OMuֱs/%Ʃ8\= ZuF 7N}ܙ[ >:lrUVf&if> r#{koaVv&ۉ5 !/z>cR/CTOa! endstream endobj 72 0 obj << /Length 1083 /Filter /FlateDecode >> stream xKo6BN26HϢ-t}loiPjZ=Ŀ~>HS!CRrH1 (sWe:5myk;@+범lv$G`!I*B:g>"gAaI3y\_߾磞7 CRh U$ pFέsnG+3pn07K$O T(`)@sk!e//p 4kW8Q LO3+-C* r.{U~Ne'#8=iA`1ltZ)!x6]Frhbfb fU><1޶--kMa[ n ,3U揉8~4߈{SBe4Uujŗ ;[* L:Kb+=S;oXHA`_ɞEY?VfA3*DJVYٳCyBBcs74e[]j,1ߌ>h׈!<ō^'5-W?urTDP]]s.2lU}֪>#\D oW繅ĴJ!䵜S W֜`ɪJ?p$$uզEmg|%٫U{lu\\[DmL$ k$)Ri;Y1ei,U#ʽX!cŪ\ ac|&Uc̑ш wh,4:n:LL1a?&Y8㤎 q)Nb'u:ΑɊ$ԑRNqD{h "&sg͗LRU„}u윋%Jt"0EVoI@m7ܝOֻTRac05{iQH0$5Ɂo ҁڳ@W&;'&t.w~ YBB5x?9Zv?(R IQBH>iQ endstream endobj 79 0 obj << /Length 1209 /Filter /FlateDecode >> stream xZ[S6~Wxxrٲ%Yv-Kӆt:ӔagZN<Ȳ0bCyQst>. +eqrj[ ޿LXWJ-u -3jBS+Jt/<`HZ_;rޏ=c$( >])H5Z{'r0L;q.`R a345:8 1A;Mi)S+۵Qf~F׬Rcu_&YQ_@A?!"39ϡv˚~N]tΧݏ_aZeOңEeI^HH-x`||M _pwdMSB/h瑪S_Ŗl5η?9@[!N({k1{[ayw6vxRÌL-e9[Xo)em4[/eq)粿~qU;6v[h|:[d>pA`C */r p@H۰}P" H}^$Dza k.ek@1RF']#p0VcLT)30Zy_ KNFe 9 ݰ MC;K0pk,kڒq2}S'-'*f#IW_}6 6y P]Ӳ:J1#%N\Xaouᙓ,ӣd7y(y@Dv$Ӳ)x }%/G{}K8 {eyɄPEq| h>Me6`r yǰ-Lpo.)_6[;<L'-I Ie:i1Ҽ A8 sn1׼Y=}-dvWC󀱉w.@yO endstream endobj 85 0 obj << /Length 1731 /Filter /FlateDecode >> stream x]s4=“|P,YePH@;]̜4zVZ^L&Vj?;3w~8g) ;CO4Ms` JB`|vS`ԓ5ɚ^+1Wm">lZq:Qxo>y/{I%ŶkڟwVCƒ- V=!|Ŧ;jtc@E8wVG~%56p͒,J}YpGƝf|Qܫσ /V2kr˴,9v$`Měl`wtr;5!"er0N~?LR"htek"$#e M)l6}=C]hYh^>Gaaq@upCwaCЭ`6Nw}詞z"dgW endstream endobj 89 0 obj << /Length 1378 /Filter /FlateDecode >> stream xko6O2Q$%RR Ht]ae"KDv" ް/x<ދ{{s{oG؍W4I%,f!YhxWS!G(;9e#ez)U{o'BW (cj (G4eR C!4o4Dءk=žP-VvEE57żJ9nQ4GN-P '#{,cDi ϏN}E)i xPc06.1F%/ccDpo&]V QJ5aةX.e[ y3u+@VKQN <Ɲ{ "3c=s{8x=MN?_AG<r1G^(j j74/4yxX=w>$JEq LKs \JɝYޝ_Ĺ-WuST4 & A(f Ɠ_\&=tf91bbwĥ캢lR( 0il8_) ~rS5M%,f)+U!:%&4F6J!Zpbv-aep?x4yPU̫YD@N_y_U*zֺ!eכNpJ>}?| ϴBccI]_)>SdP*钽Js̝Uime8s8p3VڻYώ.2J-\@avr": FaYLܷyŤ祎3~gG)]ku۰:PzN@! o~9h?Vzb҆uŘB;Iչ=7E.fYeY?v*D[rTlrG`+O+HjvAae/\-h%E1_khD+t(e=Vq_ְ=-݁eO(wyY> SU~]vvݬ_9 # Pr XR*W)x.x[L&?%1f?u:wI['lqF6$2 DAQRJ cYPÃ4O ~<):;gv\Wg^/+nJf"r2#QศU-w!Noԧ6I448Hdj`{C endstream endobj 96 0 obj << /Length 505 /Filter /FlateDecode >> stream xuRMo0 W(o˽Y2ȡ[ú(Z.lgð( #HN+]uuVJc$r&h&uA=L?d%]vOUuGnB_KueSŊR'{F6ᴎͱn<"uc?B]l}c}aC=YL2%%Ó-@:NNZG,EI`s#9D7['%8;O!֩gܟ&b:8\Cܣ`k_8lϕ 8z@pM D:> stream xڍPJ-h/b =x,xpk${?jvt9= 4lRV < ) Q6prsrrc00a z +$ ({aOD5@psr C@@w@ qb0@`[>,L.!!?)Gl ta ǧ-m%L00;ѕgfxa-+nt;@Cb BA'dvh+^9"E`}8.v;w"ӟ`%vX@W0O+dtp<݁`O@&ZB0WvW9~y:f9'+# >Y0dt^_d v݆3 $7Ʉo \ OK[x98~zq8AO?>@wu l XlNdY q>ɏ ɓ¬ N^bMC-Y/4`pq~GUr*)o 0= ̀ΥyR.osqZ>}q?Og +wspg^3{5,8/UJCק>͂ÿ*Yia/As;4 O |Oei|>i 4<%q?0 za<]p=NS9?5FRMo$7pX qq8p }?zzj*tJ6]_ {Ne<7Ak^Ϻj~)X 93(06*4gg_/.VN|wp;f{B۵̐ $[e91kbs"CzfTh5H!lbY]YP=qu :4P*JpvOϻOt;Y|Ib_lvߠp'TSV_Oji gpfhh*܋)H1vgQ|}gQC QYP'Q{74ηA5BGWJ] [+c> 釜oeK'ώyc1M3&F)%O Ct݊d 3L9 ˻ih 缃I3;0UQFj U3 n ̱<.;IS׏.Zt .ԛdC ųD|蕜rA]$Qit KI4M kwO c7 3M8Q$%P!`; Cy&!:7QCfv9J_Np;XT9oh&J:f%iyLD8avbcKorj?yC(fi8@:jN#(lA9D\ȣ|spϼl4cJ$!q3>DWizQ4ޛE`"[Z{k\TTTtoρZL$vt_h=Vڜ@7}M7,7'&1 X5q?U0(q$365ь \iw s s4i?zıX5=? ](WL՛e,Ϲf~iz 6ts棱bk/IDhw ]L4s8~B.>[yaϪ\ǒB2Я5>;{X+P߂fvd KU+n棭{QIux(Z3*SڦeJpǧ/GC9=WtknF~ CVJr,]>wng Q)i\k~Vl e̽ TԀbԥ*[ vNJ^X˲׌/9= xp51G-n=&?& X3NZ\sRw,ڰOcZ:7>֖QlB[vEml2a7`q}kY$Vuܼ6s8PƩ\jY2{iѺHr2m<~ śr47A2F#UN=2.t t:VvswKл^_~6"cɒEbg+nNKF2n¯vJ+aڃ `xmzeݐ0f ѦF M8{qN1Pn1f[ NɵoqthN g3e21cdH$%=FZb BrMXxU^4[z_•0ul:+8*,}+W]kS <5iD+keZ8 ^MVLxk[>7Q*A=k3S1k@o4e tUAC̸1t; I ҚO171ӣXy+\?31{3QEEXMXjt9Uٷk 4?cFD4~L;Csԧ (%jlWIˇw2|uԥn'P;A<7xTx=?; cBӭuExckߑiصL KBi I[.c0PvF/m[fo˭\P ب_h""iX"NEt0C%vWq*7겔0K.:υ==Iy?A5,=uf!ht3,sqYH 95휔m `m5wMTg=+773g.:,ij"}M:BRvPFUmu'O !k)U $82oOu}A%B6ɗ*F6/,D~^{AaM:HsO,9|TN42k6{76#.?ݛ垤>dOt[O2h!3-˫]dlDTdb 6WqP8`G LKzpU.s>S?ɼ6`},&IdRpݗ{:'ոyau +wu$켇,ӮKqgzMc(zTuCe(ժ2mc/K RxE{L-2-I[0V!R (P`tm.JP~w=52XT*d^%Nٻ(LQ͈#PE^;p]{'MD@a^qKKZf_.׳h?J+q&wkG߶ܾӝWu(~X8;lҩ0g&ˉES!b#نSuQqOU!blK|K<錘iŏk?4*Rś=4wS4`XF+͗Lk>/xE.j'zrs3$bLJ!uE1k\,f ::Q,O bJiMu5Zn鏒PS K_ky"̏ `/70_8#+b  5)ס 7xeܼxs]V'F76<+ p= T "]l4aRCC›?L"|8i[v4[qEo.f2z,]ow:B2N,sׅD?^^,PAzJm+z , [:|r/q|MSlnp)Ag|Sw14t ""ЩZ1Pe^wAV2#zCCt"Sb;aoJ@͆vVYM+LJN.; qU[e.:Hkۖ&"%jy&.@Ǜm}DCT)vT>,@lSCi^ZZ@9CAfDңd/%qoqyv?-M3E$y Zvs0 {'tG!;~VU<& ;FQƩue%Fgfsy.N& ZZFo(=:%S]~l;Vwa^y{uUv [8նOkQrzcFBE" 8PXHIzpHAEC$iԔạVi=u6ѶRdVX D5 ~ =ΰBѳ NuWUDUnQlq6frJ*4<<>=ÄSռys՝S\ZKJwQ"]Z:t%"0TJbH9-Y8` S,{Uޣ .Uz!(AB1.g60K-7^j? nCa;אh]MӪ6M~ѮW=:^5{5(z12h*&ɲA^ZU)d%Ji+bө1bU[a!ͲjC\/%0iʸ;ǃϹH Ml[DUt݂T棁O}+%>e܄}#ΣkL6[Xf"se䑩 g5>GJ>mǙXUWmŅJ&FxQk`9"u'EܖTԭ zM\zKa/\ soQ>Kg+%Z-*ãG? -]:n=Lh"ECYIJE~p!<7Пe{\8˪}fcffҐUuȦ0l0s]R7 -, j"tYʎI(vD1iPs*T#[QjQp=gyU)%!TeTɦ=Ӽ֐;fc"7yg[J2MSɊiw)+G%Dv\LY&ibp|`Jp.o0rس?[F1&YyL(>s\4 `sx2T˨ڦo8!Q$I 9YM :}1xopzn]oeE3B"N7z~z^j{^|F҉lK]%K %;&:3dJBA/nf^vq8_QiʉP68_8]'^ѓ*Uݻr5+ c220d^PZ٤:Ի56 `;ėuaM`^5Q:pEru7`$5ʈ~t\A@-Ě)Ҽ7|~Ϣ"d>%8x@ή%3$!PlQdPNwLhokZƜC4TJ yzY!nfJMym2zWېo%8eEY˳Ij4aoY.v&aElC 9R Vnkyy=w޺Mߕ[#Z0a"`jJʷIlEjh5>3Ja'c"jl!valjY2FUaU7l>†Kf.F5;v1e߮ "_dVJAH#P{LP%g]$wNQT;7?F,­w_؍4핎a^# VB4hLۍ?}!othFkئݿrPWsUS5~RϘ{ϝlGMcyIyߣ9^INQOq_rto|ݓ\Y$:`Euga 7ygLBPsu1^MHmã!z-Uiř^q~ nfWd|tTiMM,ytѫWsQ8؊-Pijh"[|iKBGD5Ds)+kd8('}F"m$)U8&HrϬ=h1Ofec80'mܫ@b|$a6͍2cIX6*7tH8%.1sŽr^BkZ$VŇ圣{.:Ck&fhdzt!I"?ٿ1cr ߵ !<*wg5+rr8pAq zB+OxӹQ0L{*5g$&T˽ϵj8;aSOB/}~m>qa tɾHO |yc ѠjtBnS6rTbEu^~OؚO2B0ѹc֟.Zg,z F:<*{'& LLE1-PiVo(>fF?Uu~ Ag.zeE'&)xFkH@$=F\nHRrLĀؒ=Iwt=xu]PYB}&TH.lUͷU_UV ;VxnE,DOsKMu5*>3VNG 7r? FUhw86y#n/X!Ѳ;(LvF[kd?AWIܣ)gLM=fA"mv;:vښcP~\oTCln!O [5rH@5_Vq\\w# kDjz#H~b:1<_h=>]FN=j k',D,%~?Eo4>dI ]~2)lHZv8 ~{d}ɮEu7:*fmi36.:+Ԑ㖕,Ա[#=Ё<>^H ;bjh- 7ZPĪN,396ӢSW#~=X<@ʶR#-<=`rt h'x|=>n,c>& hGKSoo we_H qE )w-1LjQb endstream endobj 114 0 obj << /Length1 1867 /Length2 11847 /Length3 0 /Length 13010 /Filter /FlateDecode >> stream xڍP- Awww 4иkpIpA kpwxdf{Uݽ^YP*1ٛ\YX bڬlv&6JJu ?vJM3ގ_ q'&ty%*d]mV.>Vn> N|  9#P;x:-,]^/ƔG8@6. ׊@)_)h,]\ݙLNB w%@ rr~ Pڂ n vӡfot^ 6`Sk Z&#PrIpL+w"@SS{['`\<\@;Dk< hU_'k>gS'33̿Ӽ-w`'{2uvvA`;3c:0k؁]A2q^M,@.Nn.^0d]@u_o{ _98|o 0L@`;Aw{X^ `l_5 <]RqrNN@OW)qrY_ Lv.!|No,'0x ^߈,b0^(x̪W߈ V0> fAV3_5U`N x/:Ϳkm kmCW/k1A v';+u 0~bl͹+]_s5d*<@!V5!m_E Pnk2z;ޣ%Ve:]& -mJ\,<%Nn"M%bTyr j씥vtAQżu+] V٩C|,bш,1$̱u{=:pߞKѻT9R "~g$5>5_b-IX3FjzU `C;7k?շ]CJ@V|vrlj_>}3)W *#r -.n&K> U})8}oAlD.!q]+1+idS g4@:!YP ~bd` F]kܡzTgM:oZL4S';;D=M(0Ӣ6Fh% aʍ7j볝&kߌy]b7*: ZM Jt+OG56tuM#l1yiЍ.c/|_쵭ffev}$GK)N^J)Mz@$\:tz-zGtH.'HUXC8b%923O0Z/0Ķ>!CA2aa~vi~m!]g?#e8AB'*/,fTtBBC|^! L6F~d.0J Hx/ ~OZ2 ;?ՙHpH:AFt[ =-\7?i}Kk[AٵQE1ISB*2mZkA.١ 8!OtV頖;.A͑ 4 B?\)kuǺ֦{W>~]x5{JòAH *?t?Zh^d,F,p۶xtgVꤒ>!ݲQ e]H۽xXr[dz„Own]F4ap4Ef+0qH_%^ǖu4Mh`$xk!!g"rNjoy2 W;`suwUjƚ?x e@h_AQ?et$HW7l sC򓼁t_);CK=}vc41KF|^A胋3Y/NUB2[|=CY󓻥I;voHPjM*-G(=lo^/Uf}Ʒ@#D[R9u[ScFcfm /"Xb[g-j* R1 !^ ?E,3\4"(Q.oӏ<.̀K>Nvq8V W 0oIv{r6BSք y(RuL&]rWj4;~4Z}$$#,yV\Tw*o0PAE"nV2 <>'͘]D{NE>V۴6MzԲk?T_" zԑFL)=%xϝĴ|v2.2| O"ߜw őR+0$kNP ~`"Q<,'!0kayww_s4y BjI ~-f8'CA"_L|ʯ`ȸ:bPIWLP tLn|_h)q̕P+74uUuv'sW$ղfhuk굚G?Vx'?u>V#tcԙ]mq7y;'ܪ"'|^D ~$|xBJr-2mbN\]"W/76Yߜvg.$Ȱ@u0]ɔY'ְ*H-ibnR{Z;Z' &F3tYbږToIZD SOf/ozO(eC"nĞ, mZ'1C7fؔ9wx;[4#[/er: Fd c /p`}(}n~6XRg=UxBHJ YqV9WnWL|\S8]h#o#Dr7[ aJ΄!,\^$Hr2b!m8Rn{(|Z#Hq΄ i4pF:qrƙc,?ߨ9KZ =bK'lr鹙\ `%*Wwnx=Kz8F?Lh,Jhq`/e4fj}1uKbg{{-=i12ݤ cFeەơ1bg1E4Q_84Ǐ65'-KD$v Z3RJX hiCXӻ~G% $`@,a :>dKp$ nF&ĴvDʫ6Z s39%Yl=L8Qn,Oxr9]zurP%G oq޺itZ8,7 ѳ,418'ꤪo.~sNUPOYWyG ? RQ-FN#&X֪N=Ɇ{!N:E4lEZ-^ʐvՇPRT_$2i#q=d|?;) 9](Q{e XYe?!? o+n/d0ڜPSA@EVY7X% 7Z 8OVJX&/1.9R;WgT'*zsEO6mV$elU4+tPxzoCq^>ˡE拑* bGRePIަ`6ݤ4U [k# Cȝ9M+xl|'ڸVr~rZ0mt'![`{9}VQeУQ>*ҘD$E}O>g\ -MoڡJ.%b)bQGv%`.ufd kPWƒ2'ɣȯY T:v/צت n!Q`쩱'Ov#y& k1.]wfXWڒՙG; -V,L'X}qHG)xG] EJXC1oT|ւԈ}³t"F$,*sG ث۶ ~A5qө}sB£nvy)sni%O{R0z^(}آ`d=pN.ԣ鹮f=)L"Onml$(H}3 -jVY+YD ?qXҺ lhZDF]ln{_J)(hFeK58tH5_qP[qXK`Hߴsy'%ALKƓΤ NFN{r}  -yL4Yb6i2NBnrx>Hp?'1G6{g?aZ 8{)!嗾:55yBܠ{6 FKxL*Z&nN-^q-J[ͶhmY4Jlŗ!i?/i2 "8S!QiMl lF?~nt@2,j l2ET |jPssI:3-nSVT532(b͞4#k:X|3Ϧz*;z׀4vmHk-]F$4'@1~*˭N5P֋c597wi*-4lf(Fv|m Gį>1/,CM< Mp&Ipr['S߹]B:h%0?~>PQJb4w%'j5j ,ȍ]GhFݸ֫AJR `bv~_rApu4jYCR*qZ4Ĩeyc; EiB~otx#|J$50t0X13q)ezzCn,I͖Kp*iSz$ݨP猯0.@;z7Xw^`g9=% [ V"DS]7/(KeOY,Ҋ5T%Q,bߔbոq4>Bnz*JQBA &LV^gA͢B@P1rxdBC/*Lr|7m>Ќ"XTg"p>F )KgWa^~5>T@ <0N`}Hek!X}o#- ~p[ E$lB"qш} |x/|zUG ^DQy 3 !t+5p{ۢo;oǾ=Eto9mb0tnԶF#C> ǚU#,DB6KaM*{M/‘x= >GsQ %2nE5-~D\Wd^dQ9Q$B*Rι@9 2QCr\D-.jUA猺wN ֓ne0Ú^2Rhg %U,?9K qin Mxbjb]h6:ZE .Dޗ #/b2H$xp`ҳtu>R3|CI^s|MoFإDZ)I>?Wh=2u DL TTi&_yH6; #۾ldGHp( 7CXp{zDwSsn]}ݝ ]\*$q8ũҁ:Lh9QOke? f[0<ǯ &DdL2S:FrC~, 5; f\Ci{8"pU#K$8fYD:ZQ0 lZ CVwOR9HE-B` vMEq*}h|7!PDg*7۞T'fHAӫK(A0&%I*+ zz1)|R>aMWK h=?zP}XPYTK"֊ G#S~l:$`LTRED'yf]N*;B`C\:ysC=_,/\Ƌ1H$JBJdMA Rw O BZ]l24HvXW\}hnc8!3O=J'>)^\ kEBlX"{7+=B &U7xk>T'M|s2\!VƂ3f6{ye2F\٠|#4E &-qjL}:izF֮Q2S[d=|+֘K szDiנnSUa酨n-Ǘ=42!w!:wlBr[%n0 k>(nЬ[ M822 fF_NAO@n-i . ,7Ņj=''Ν˃.b*qC1d)-'  C J ;C?>^^|ȃ.Ӽ[QNPh#ÂFr2pJrSfǐ*wKGBGO` /o1JqR *ګhnv2wU Dhe qshKhad+%[YZZLDzR쐆Ht"y,ѷLotf1-0r] &P¶7rODc ˩j*?Nqqy0$$ZU[Y:9|r㖥zKd}(v!Eiʞy mSzxdႬ#e[{SwSX (~xhbb,д}C:(KumҖJߤc+ +hJM0%5jKӊn(EAm;eun)0$pXlmוIX}5_wfޞx+^nllE.ەo{[PGDefL{^3}S&;Frx!zcM=Ob@>6ZU,QB?X̵@pC rcdA~֜]aUvQ7μ.N!$ ԞhX3+S8}Cq4e 9IYe})%MQvyM=^ *VJB4)K\wGT=ٛ~G d;jD:<EQ8W0Aj#^Ռ[)_䠘Bo f2Pd(05D9+Mzu>fIUR"77Pb\1CY^D=ɋ[" NhۍOό5o+mFԖv-b·aڿ{YrQZ|ܙdٔZ\Ulj&]z<P42G2ttǼ5<&VtV .t?bf] ,o5LB F &|.t eKl}T5a>oM*Z@5ocdQE3V+[Ws|; 6~z^YA!]Sa ܘ Of+ӻ7Lo9py6_t}:*fK0 s~bpN)o1%//{tMAbx(we>y}]oCz?:X7xo.#)ų*~'&z2D R⯻H4>"B)3cViIEXkJ,BS,kq vD~=TJHԜr}45gDϽ%0rg8ϒ`piǾM28NJ 64uÃ2N߻m4N[Yl%NTj~4dAc[';lQ_zn#%N,)x`*K:Yw=_SSmi2grip@ďLjw,iυmZ{1bbƅ`.^&A4YV&I2*ޑnWe&Z\ {S™\ r$#*4%ٸu|m ё9ޚm[ƠtɣMkEU7o~כQsk/AP;'k"2|7 wMG_뉒yPt פrկ!;Y jjX@N&㶈&j]RVKƞn',QU%L^T kI0&tk Qe9jyV> qv[)8cE_1~4.ra]p˨*%BBT%=v{eq"TlIY`C Jf6I݁iShku8(kǥh$zXI50HCHN= }-Wi K6g4Py~ۋ~8}WSrΧk{㧭ހnM_WS#k\R7N*({1l5Ǥx( F6ϒc ]Y7i]"9s7ɻvuOi$#}g.sV?6Z(' T8T = u> stream xڍtXkؾ(%R b0KJJ)e.` "ݩ!Q: 08H@@@DuLg) )0LM P/"#ph HZ@Ĺ~d=q($0G1(`C@08z̝Lр@Ho@t;.5!aЀk60HuǑ~xlX?/ 'c(x46&fl<N3z7=B} 0L%+H+/7?,t!? pB*{B$_B/`hdҌY\G_Mr n}"Jb36[x䬩f[ud}Y I[h'~pB>@[$ Z h3^/[w>cM87k"|,,V;KcS,iPt6ӆʾMSGʥ ;u;wbw ޱ6.ON%x/ZZSᲒVtUa;>a 8!`p͉"0 O8"=OxJiXh)1u`2ܮgvʫrTWuuHVHᤚO_^m$wzFQc!Ul0 G6ǭ5\%UZ$3ް߬J1_sV|j=\Z>j3rC ݠD:~kϗpi]%bțVH'dE{#wjG aq“P*xk=Βmd /0y~Ȳ:n L _jlGq?[?no8X)q`T-UГ6GugoVҲ`^>KPmx ګ@GOK-6bHݴi[ hY$LjJ~{pݟ;WsO]3g spH\|J~_ }^,<Pb4S靳t(u}eWbKvۇJ|^ٞ*fդXhң55Ĝ_.@ksa  Xp K',򵎗|F}%WWauw3LLC٘Ft=u?[}4j)en)9ŝEIj~ctlR?r*?cg%ug5-J]wtΖEs/:}2ACgvR#d)jĂ۞Z_>0v?F̧s{?_#Tr^%=suwe}MMJH5|XۻpjjdtQ ^$φ?)'YFFʳ̏ER8=,Gn#1[Îw« 5\jyt/~~},3Z\n騩#z*Į{ڼ9! GYTKüoXx}e q emS21ɲ$ AHj\AE~-'ZLQիmr0ӯMOWNl'͖[jKp̕<4lLйR3Sc+wl+ifթ%ɐig@d$F 4X'47rkc+o9=}q7Ms5&gvgq|Iz{L-ThkiL3v+ϪfgH\ukQ-wC7BOvb%_QQsC篝-;X[%" v>蝩XGWwC_ W֒JWH3gwx~*KrVTXFRijvHJ>St6hrx !3)y-qiT4xsHKrDQmkfJmGKbiB_\=!]^UuhQ"¾fn]kM4v]B{5Kc]^ 9) \I$)FK{h?ΙR_W1NK\W-t`e~"snuy F$^"7P3 'VG 4F ᫍ[-?u=\E<Զe|˹n[:z40gyC~!;yQ!Q-8A'nNy{fֈ_rFp׽GD r޳LQKDDQXq |:%i43MgF&Hx OW ̥j|Ȕ@ۜ Ϸ6Om^>9pKJO,pɡIicqZuS.Kf1U3F3 o&\Е*=4䮬.yWrq Dn'\|K,~6#,/RKpہLm ɤoe/h %vG(cSZC; q~0Enng9xM ?.I~Q&yT4J*<= Zw:ydkcRĕӣmR~?S$R_jm`^M~ y,>ZO>B"<ƦIm9w\8d'Gtʎl2Y3VRorMmlin)sd峛57xx]H=O+61|3>s,L:ak^\2qCZU{"vQ\VK\oH{zrR)As \m\q"-_:3h`{8)Dk }[uF.im{xbt`Hu4\v녭SхJQęk,#.j֤$L5 @2oX0X1c%S&Xak m'm7S:on%`Ӛt19T͒n([AFI\<ʳxrXzoǑ'$raDp&X+)㠈}ڧcwa24\'44̜hu[ 5L.J_59)8&h$٪G;)72YTsQq>̩:ӏ{%f F9Mok]`.sp}Nc^T{2S1JC\R1M3Z'#7L'#PbX\:wC_iD:bM qgb:,Vgi_)EvEE7BQ7rbHA0./#O+!~<VW},1?baW9UKj$[o\/'Ŀaf۵Qk] jl}: FOHNiWg>;#JzL~Ţ.ҟ1#4lo}r0 fsJ*,!{8>on̸zޥ62# U<שUHWVVZϦ9ʂjùKF¶9Fьo4@OlXjVӄ{sEJCf杯dhԽsN i+%6z h\MbU$(4= aNpSj?]G0bS{Y҈BYipJ,Ha|G" 7] Y?Ԩ5ʗ8!|d <*] ORkaS+Toӷ^\R'tΈ=fc#Y|Tߟ]=Qj>GG; YULlѢ6VZ=_+`rQ8`@Sc(M%XLL*)̦=s5᳒\c!7&"7Cw3.Em>| endstream endobj 118 0 obj << /Length1 1746 /Length2 12826 /Length3 0 /Length 13935 /Filter /FlateDecode >> stream xڍP[- wwwww,8$Kp%\|9UUóW^{Sj0Y:l, %u6V++ ++;"5-Zf/+ f467??++NI3[K @H-jkm~;>t6>>?b W[ 3Gv=@t6`3?bj-LAn W%f*cAhغep{o{[ [%v8@CN r X?:lfalmh TY^`&D3{7x33[{37Ÿbj.fkG?Ҽݲ>I[W۵{{G'OG߿EX;m]ArSLجA`+++yYH _g'g[ [+?D_73" 0Y:" 5 `6{l?e6^N/P\SBB^w2sٹXl ۇQ5[ƿb|}QΥ6 ?Cnj<MYoCIq9{MxZw(9ZZ%ʁA?h&mT[5-ٵ2{[G 5Zߞzۜ>Rcy#5 q|v,N[y+'W?: jaf ^Zh/@_^_M 'vy{va&N7]+ߤ9s6zJU_M?oJlEx|c iżWW-]]?|EA /✓@]]X]'4N=k*\2}uVȺX`ʶo%gߣzDG'xVą ܾ#o$̚{~.~!S纸cyx}-_ U۫V@z*b0d:<{Lπy6f3gL>3G{WMv*}|ߘ#4)xE+} ^͂Ed9(L+,նюݵ#?vraD}X;e&*8խ&XZ Vm7ڝVvK|S^3(z6GAM.C}̷-wC۝:%""֞l R6Q+$0w: 9lt%d'!l[0ݐ#ħ\~1 ?6f0=1B_C_pHfeJu~[U5̄7*qY$˼.8dw C XN+Z wGC?XlTT:iߟWzFlj}ᦒ.#v{DS܃ܡ1MGSa{ɓ\NhQWP0ohA&H v;:,ꬽe(JFBq" ͻ|J mm*_JΞ&קt(xu!OQ/VQMkZbKĵ3}hqJvVlcY@am֚b#\-l&*7ú5߂* ; %E"~!L=q'Ly9WeDVS%}!DTd5q]HOnF4<Ķ,-@]lʅ:*Ty3--˄Uᬾ~!km|-7l0&SdT'd$  ',ɕxNb E;U1CK6^\Y79O:`AJmrdҲǩAnir+ג_s o"uRI^)GH/:~Ҝ]7k`-TR攞ˊAN&#LNJ_{}s#f2ZQzP*&_~($Zn[+iDʶc{a5<ڨr- %2 ǖTnEtؽx]-vشąDkNY:|N'n{*Nxnm9wLElNaPR,oC:$(a\4eG5_d|J~ &Ѝ<=(?`Pؠ=,fp`l;h(96̆WV:S.0ߛqՌ*\JF nO,c2Q};* `"E嗇z(KVᣒS}I[&tGViT@=R-TO \ϧo۝]Y g Vdml̿vI p@"z\z5o+˳Y 8 4=-Se! H*R/E:9iN#aޖ *TA"&qJsLa}#) ;˕;"Õ9S`$5Skzk[A:!s%l #JgNlRWqT8Mzl=rKQR^3 5f탥`>)_EC llY|zC8&]޳5HUN1v7wٍ/tuI_9xmwR#(U(r1vNO2{=v3:}*|*9XC: ҘFbSOjIj]D +7&JԚߔ[xb \2~b蹀jo"TǤ!^>O+v̢~kWC[S켦duxʵsF%8ԣY6}A8t4qLWEKE@lP&UnX_>7~i+T~٬P+)cLq}e/3-*A-Q!UvS&o<Y/[Ҭ`1e9sgWAO[(Cλ{{'ïd)QI!ȫeRf!Vw^Arq~< ,ːaaQp_s-^=mRLWޱXp); ȷ?_5N[]y1 xGezԩi"m<ntJ{ōIy}3ɝR*^;]>ÊiDk ,}~]#_3M:=!(ߙSm]/GV!̲,_.8T\;wPy)0+8D|XNh+ٔfTA.E0΅qa=l(%LEtq* ىa` .Pe  `E⨐OQZ Kn'm x uAQ~ kfQ)՜w_bk&ɇSAܓ@N(PXIU7>f /i([0lPG mwC4\_͸Jz2e|П& p?r%O"e #ew6JEox t /MUW獿OZI_ʨ[MHd67oY@jҤ´%B<!xC k9z*Ƚ۶/Xxä+}Zsd oSȔ`TZ)M͐h=?4464|6F 'q" ?8Cfr=Z n20~K#.hjmVF$+]0LdB4?!k}3vXETde,+Dc ݲ);*Z9ZӪ]CǾIRigBcfH 6G*LO3+yݽW\/SV-\:ȟWf:Q*!sle/s|Y2Hkxq~,yC!u։B)ʄ϶1ưgo eͭBUG"m wa$+qVY2?{;`ҎjlwI,{?$#Vp`ZƝD&a 4ydqc-[cɣ3,U5 Ci/ҽTWlgQ+􎜫˙X)XȺנ՝ɳ)L=WC7,IԋVb` #8&lq>Wx}|>0M23]O*[B\C R^йK:,lH;}$ƻ<[>3?;/by` 4u}G gn%>x{<x%ʠz, tLjԗ.ONc3R"<=KE0WCM'd̊4Pg R.Ӕ՟n"-í}ƆOpՆ6Kͭ>0.X DyD gNL{td`7jS׉w mo^9Etٍ8Ke3F3/3;'\ANuYiZ'WȷE <}W鲎q_޵VPJ JnAt ʲ&^ǟuKRX~mwLtS0/kv,V-L-#3VEln\KQArJ1st_$b>PR[Fqq K1̥zS/{}ү>ae`Qd[fFf΁҂R[|k&hD[R~/ED5jOs@l ]ZABLt4Xfn#>L" !@:B/uaO ZDmǀeS 92uX>(cBOZrJ? K^~1hg}؀f4>1S*d#c1n|ݓD2@Ϣ2 f0pJJGe|#69fUFc BMa;aBy/.>,/'Mgs?4oi+nZ=#^dЃCJV؎A:}׮nB/y*梻\yZC7oNԔ&Ұ/9"SIOq= kO 2T*b-cG*TIL0jYds]"ѣ+̒pR)IpXȣGAj0RUE8IYUrtWIYb+UO|ij2E?83dLE:feQ)(fEvkKLK+h7Ÿi2/PDAx-_^td11NzyyF\wi`,%m j!mPL`Bn~XnRѸ9p ]TkLpsV&r 9<elo_"+(#듈N*rf|YMV& n4UU2Ԝ`i됲|Yrɭ>G^3lT ( kM2|SQžvD .Q25'j kKE!pN|rx+%yʇ#E،0X:Yes\Ci,|E>YȊt)}#5-6Z~c!o6UlmoVxםڜ۰bbszMh05MA,}GLGȇCMSW X6o-e\g  D6!vv-HS Ư~kQgBwC,;mjqhDp&aߐn 0[ӸSϫ2w%:DmA'!] vT[y YQ)9J52eU#BbΘ^B"ɗ oac\NhZ[CZ0Xr^] E}ihAK:+-3:+ߢ$5cnFBǵnGok;XQoA6̖bP`UoSd>@ \*Ճ;l~I{ŗ֜-yIEG|J@& PHpfY7"1ɚ3(ZJ-[ׄ_й1I ^qz~sz+U0j%rd.c E֊W1;F1#`\">$PTn 9d* 腒&SIޭQ!$HŠИ'I"r;{QPbayQUyCC[>uB1ݶQe@%a\֦J)3RcsC׻o^.60Ykۜ0h)Ջ. C$+v k/9?ڿkoՖF+mutohw$!}G~pc 3r b87xo"[-$ŨDw6&4!CI%2/cD$_ >GwW@_qK{;mt 5O@0xjhL@/ل`c3(ױy˳3qMtcsrn ڒ 2u}8wƚ!2b'-Ө+};PDs#.$cx6'Q[,q {D,/=zFy}5pf1vqf,?SYWpqR$W[̹1X)ieU3,'^i !nwȇs_̦,>w4xi,ʐ!xv`ؤOTB<2+j ڎU elݒ pϓ*YfP+xi2qZDQb0z+3*=}"^~`(j8}40ꇡΫA\GWt(@IiI"ͦW ٌaZq#PO)OJ;=HE9ϡ Zw|rFh&#yEd-1'`ۺSȷI-6t0 iMa۔ [eءT(-u,2#P>=CDڎ!A͈NkokuBWo0FB o&'޻jS` rR sBf+K0`SSN rnM*?ź[ ;~b>hu>%H=RbݘDd?Fw$$N#Bd tŠWK1U(#tj\ IR<(Vӄ|(\b5 GY޴nw.FXtt"n G$X_hH`%|:ȆcYXxJPés0wE?9%m-#1N  p^BĮEGjHaL=hTjO#tG3 [߲{lQ+ <  cەZPF|!i#ȍ-ZOGG,E K]8!6A~aqǡ<6+t ]T"= ڕD!&BHJLw^ס#Bn5\E. DU)Ⱦ|SK[:,F{6 B$#h j?gc4`gXeb-rd:kAz_Brd-vܻp{T9 >[띞PʜVֵ_\D/~-y%EOCyIUAh WjƊđS/Z1Kɟ|g"#4 U>Op,COɳ\#~MF) {{: JQ6?YIgbbQJTYŠ\yGi= w4ES,O-ieB}p2Sm72vq\! R[?SH% 2I7z@|A`)s #O@?EBh4QHMo* UTsMC͙<)Ng* &Q΄> stream xڌTk 0twww 5ݍttt7 -)%!] <<-ւ}4Z,f@Y + @JEΉBC rGB tr9e 4uʤM]v*` +'dgC'A PtQh N +kh7gp1:MSk=4@t..A66wwwVS{gV'+Qf; t:-m r[`n@v s  :Z 5̀Oxljn`1{VK& 0[64svL͠Un BO{N 33wl@,r]Q~' rCڂKw60  agg@sk=!|!% /l8}oBX]f@+Oth7C 0d?ec)++2?:II7 7 awuS`t],tJSΟ?w߱TK <_ϛ߂]_j=?НuuwVhrZS=[3F,hr1{Ydv 0P``g_:2>9 8Rl`qLL=Qء^E _; `c;@]|N(O&[7$MؤMc!)!nfWC]A!hv]Ak!N֢h!h-:ZAkCZ!? n &C40ok\lm@ oKhy|9ݎdѡD)2 ϓn-\.EΝ|&WL`B=*6X猽^MHMh@@ w=6E-ͻxi,mu}2׶1-ͤ =!6D٧+k |fjg5;zW=^{Hxuzx)>pVC1o̿|ml@7!m a=p63EMF;K,qg {B)4A"{5m)ү߿&uh%F JըjQ+wۈM2g<XEHqwͰ㮯nJbo(F+xS{1Ĩ]JKU. G-^d&?XG6F(A!}y5œX|Nv4:_tz} Ba!BOa+עϵ +]2@-ݚqC%ݫe߼8ݏrSBxR YDM_2siMZt*+92!vs0Vv+l*ߠ08Yk&5[}%9CزpsO'*a*wߋXm6[YfrA }NJ?}@˵W/gߌ6X[cDL>b"ŀHU'߶"U\ՊfN{LgC@%#J=i|+b鴯a g~1Ekn,(!oI$c/<iɼc:n$;&6hԳDnx1Ju&>()8"G5`O䉾ж_}};{@ \HGXg=H®$Feb Gmo7T/}2ɟAXZ^.۬OWBh(Ɍh1r$%E>Y}d:EUk{åvI֙Ȝk_s t.3u0۟}+&0E٭x}p.13[3 !g$M2-F)?W0x$"/~Mr ӛL)nzaubǰ湰Iӂgri[ N?W o4}c%g\ é2%߆Dj~5D'xZ/jvxcB#FOz.eEKE1bˊ݈8Q+jŕk7t4DWtCD60*e`__qL0IjLnăwgrgb`[bQC$Qߏ}.7CHbLx!*#|̋4+%-1Q'ӻtKhxaW.QTejQR&Sz];^ Tï\+&ڨMUr0xy4X {e*$)+cʾ87NE7-;ce]E 9 NJ:Q}8NG*t|òĘab3s"v!,vY<[%͠pv$?A?ieUA&!)7KsW`RLܬͣ>z~}@_԰jo 'أ- ߞȖs4Ư ,10.cͲvp3C 771YQ5r/v'~m`PFf}GlܙxOFb$:{*A UdSM>G NW/#2v-plͨkuφʌ]R}y N jHtńXvaY(!ajKT0#j9/uY) >{!wRU{}[8f%.IZӢ~Uj62ݏA{V4I=]yO#mCsnb,L" $TBXE .FTővV3ҴJT3 )F5dxZm{vn]^QC2I1[Tb:t'AG\̥L~gTTK'Fp(fb@%I@bc7L V1^$쫤_h1/jlw]`Ѕ.!CP#c%y~1 y;{d`՟EԸ WG-nWexTUb=񤾧 פ83NuŏIFL M QR^W`,o}v#.hfڹ}bD+[_ 8%k'^4v_;k!pa&B )M S.-w8JIfm\rsaFy ф>9]n?x,D4W tm{)|/lrʩvB$"Sū^Ű( F߰U,UApLR_bn~J>e۝rF+#(dI>*6Wb2H _]ⶆt@zڧ>ֹ?zWߊ l1n䎵XMsu .(ف}S{{2lD-Z,YJB1Je!<tMzPGuWFL y@+~c>KEc&)l#.o)S:yr"t 5^GvPpBikUO"V<"o=<rdjz\1}Us/bGB#3ɻ( aW(|_4v t',hp~ #:qf: 8 .k??E5Q9|靎Nƣڈr)F ֭hH#cwhVm^<:?E2aSjxSpnSՔKiX w_ݪǧkϭ5Q y\yǹ24ktC{8j_X+-X!6]ò-9ꁜp$+HÇ36IP|</KJ&>6%slQNeMQ)5c{0 eIz/99EFZ1>{R] %qUCw5Ey|)0qb!_ xlufKC(˅lj$+'L46ãײN?I&n{SO0^Y %Xy/$>r"'k˃!ҵHW[E$dcY51s%_!l!O2R78M,GWvyLR 7fOxĈFN1D5>~3!W|HJ xͼ>+?.J?s'K{aSWAeڒq0i|jX8&ϸ{ B\E*GnA *(\l HQ240T %Om>EՀ_ goGY;? jRI^Ydr7E!5)3e_˷DŞ5;yҼ}"'@cEect}R6hqf4_𳷵t+>2& 13 4s6i(Aњ_[2h<[-ڇBĨ< ؙwϳW^*pUǠ;zQ? /Bw~|9yL+y޽弘яxs[TE^GbEVk,MBg^Jd7 8rՏ4uF4qj.qۛvH?EsC7}#M6m>#|xK[ʀ@u7-&3z)z8s.d 9^@Tt[Hc]cն 1{kGM_~!: /_^ط|b.6@,\7 9p]\Dp3}ml>*,&ըxwT}rnevψVDv2GI-=!LKz=;8i=Wr܂Wdf*JHFok e=V4v[M|<4 ^`bGmNMF>S^oTvEj./Ofey aދ韻%(^m`3{{Wfg\*E ك[kѦLЄ\ӘO5~64Ua-_E1Pإ(Nfdo5ޕ\ODezCI&"3:(f>V:*=*ư#ܔiLPx4&ʤܥ2QWK1rK7Q?1:Ƨˇ_8dzA{Q]i8"[PcܔWr*ciXMX\PLξG]7ā9`efz~ wUb{+--yTvƳnl@|# p$Y7˂`@LD/Q oެSCL~'Zu}ϠHǠ6@j.Hg40E `pei${M`/,Ԭx3۰*` f0GNˎ0pr'ti#tG(N :+@_K3w#SQQ_(i9ieOM_aZΑ }~ԍϓ0Z/7>תr;~e ]oLMD͆vĀӍh7TfPCHWY,IJ jSѝhg<"Ը|NSp:Y)Oăü2(J9M[. kk? +XPi.0_,IaGݗ;5g~ uLJtby,`= }' Ήgu[ f'0ccTvK=~D}'Mۨ~L"=`e+H:΅3%`e|T\q[bh O1ò"NVDRծ'^>I/>5ӊxlRo6Anqkx8^{R.-%L/1β{5)ܦpBG$ ]05 -s`o@.͘b`[Oşv2|w-,#3|yEgsbEkM*l1hy/>`[xσ`]Я:Ei ;#=2 [ <"DZa&D>BNXH]c4t49$L]wZlFF'JjDΔ5"󹥠`y 6[D7u"6=cp4/Կ?r(l|xF@^9YC4ª\D,tȝҏ!7L^EO*k 3Ρ`axWuTZuQϧ4:RmE` Jv{[±d yS&˯2(k1M[K~|RYݣoRC1\;!/YP$~}8ABob6t:P)eHH5˾R .}ˍ c,q4cx8O5Dd!ko[gP;G#P&%q$ħǫ-E)S{94YӅt~׍lĂ#H,U &0nٝ28A "T 9.~,= Go6[+ w#[.R# 2xQnIҶXV{*SUeSA\3x.o r=vJ2M&NFt]'Ω&wtUIFL;ST>?bp:1WG緈${b4:q Sy:\z7,W^=Ko-,{a׆.iq/ϳpT֍=|8D=얟.(ơjdŪ9aBNMI{xGAH(WxL]wȓhrN=@'Axl5l_!HG:5iټjH x]!f)Xf揅ha}c3)d6)n.A>XG|9"DC eFP^ܸ3=cCЗŦHn1j:o-Gz` ?ipW+dWYߍ1S"-Mp4H(&FqL얍U.BXzNrr65iDO% ^+r8QF+/r^z>^j'Jwkfy.7Éa,՚{7_x/$,D%g9zR4AVx7X?\u$u㫏佲"I*7$^IY6Sr$<,@!4@8onQfڀ V7ƯZ53m+W&r(bwW!{Zd4Rl*u/o"-N0o]uD jBd(.Ue{$ lqp>BvhP^X!Cu|2Twlhs7p_+ZLdbKmR-e#J ^/Ԓ,< 73PGiq] ?Pkh̞[htgU;?[},H H5m*w$y06 cp4t3<:W:%.n ^-S˒bʕTnj^UcA6k ȬSS_~N2#ɦrCz4<Rk/2'IW)!JiPԢX*M>fHrpg̃F;yNI M=Ug3; `y^?dACT!?"y'X(,78ٹ>ny^ ;RWM_~T$g-څPGK]I[_hmWvcu梾Hox&Pk+\"NOb6XCp+ +]c`N27<{YECaH6?hp ɗ9y#lzW2[ 'Ȍen u%MwzU;N%`-8@7%{ Be]^4v=\6؈%ABQo>铍W?yJaNn=ټ]4\3!X?TgˮrcW1#o..CCOOOH6Jz[л_kxQ*L^7U0xQ XCdRT!b]7勃r!9/ 4OM͎/qXūteBܧ0? S)y gcJ"v 5ʕ/;(vf/F!YX rguvm[Jz :Ӏ0^ޚ=DEwN xv5o\ZfnbSwbկ(N,v~Zw`lD8@|:3e !,f ɠDžD_RlSQًKI;d؛o qhюja' } A79."F·V:2$,Rb`'~=ji'vY:e2-eq*O)}`Dg}}V|X׍ڸX]M_&0NDL ?êȬI w[OLi:Z[싶PL2wYօL] BRBN'<660 Ep;Cm.m2R ?'&x/ʕg;i3%Z}@O"mHXi>:.-N3|{NFDY2@254J{9WNjrkYh*R(Y뫷(d9 Dj#)xK [^ s}<xb[b;`!JpڲP}! mxcx!'rPk^ޭ^Bb7l{?*/pkbJ~۹V#`\N )FcMߝKn^vmʽ`o17!'an%&Ugzg! wQ̗y =!oΒt>7ìb-"ZIpy\:YLU.d ζVKϚ<DෙBn}I:jvN),M?:mL7*ҜD|!ؼ!p7~k߈A{15lR3ׄڧa~iGG_oqj֗a^Kji,6:- *yK^mzy^_mgƙ&\޲eD*6^GVn8B+{*2gJ$TH{qq>{#B!~KMf&%<$x^G-DGދU!!|L:LļwjDʑ7 nwt \y9\!R4ZO gZV`Kx/bWg+c8ZN]O4'RӉ:){0,^ {\ SbAfK?➳9/~e|wE+K"7kh$Z5ZS j2c)ɺH7)\5$/wt,6P Eg6sV\"wI,sQeIݧp)V.ࣤpXH:,/qYd|o)k)rr/MgY2VSFX~MK/ӂ1|}4mWZlF\-4/CeBEMMR>R ڋ#ķ5d(X}=NO<΅.[&5`ݽa{| ċ e`_ 9*)@:\8SMB ,Oߍ$IfcPEe&&Pno,r&4)̴Z>pi!}{fB::UZF,ZcZ,A:a}D% /*Dy, 0Ç&|A]]X˚sO$ƌڨLJp3借~JthMؕ&;ݦDл+2ҩzj@;˳\#6hw` :KV3'67SȋfJXKy%/D,NUȘpC _{|1a$* 1 PW:2E!/[3̆]ȉV@޺fZ|Cx蘯#B i7tx3,S-+{QC OyS.@)g%Z'ז p:l| h''rypކj*voLiD߿r!ӬTXB~8GylW<ɔ@ĬFJV2╟<HqB `anX߱Y&B>oJ قSz#D.]dYx^kщ{tؘO,VFd,5utc!=?PvlC鴏V䵊 @{$]T{?A6JUNRpBds=M:OTpnM3rTǞΝTV5 |qߒZlV6k>nTyVϏ2Ҽ>Q/w_-b!^epzI7qiVAOhE&?8KǪ{00_iI؟K >s/r굽jG.KKeRd@aFB7u7HrOHy.]eVy& !hT&LdgMDe"b\&u5Mxl&Cx->D&+= &B񀉐">ワ=aø' xv:S CsJ5S6GQDRx閌QuȖKxAR)6dI&٩hh3(jsيW-{{I Y] ^@_ǒo165`5]%(beSO @7u(?VcO Dck99/3+ B_-*?xV$9`W]y{$ ,r E<9`g9k2MO5K)#SϞRد֝Y=]4-Q1Fnl0jJ &/]+-='5ĒM0f)VziLW}+_GrHnw/"Lg[\ $?&n`k9 yZi]K(!zb Yo>} G'ޞpfqRb`KGMA=efѯ}#Sҵd|fQjyl~l $־*E@7qʒW\bgXGVv**%vߏFeS }Μ9,͡D9FmC77[N/\0=ʷpn}iNr#ԣ<1"E={ A:q9&}*nyQZ'0pt4({]5NA9" Mv:\\ч||-,wLZgqBmdjl6x3uǚgg YtV/_e, ckĩؕjM[zf {|VnĹ[9&r%,w_F0VMz ܻhbmFŅ y2O ՄKV]|$ip{a}pZ${fXR8zԥ{>anB>wWMxejQd#QIwaz'Igwb:ؖ&o'`tsBR>iZjMIEij^F0"}oj679, 0=ldkn6QuuBZ\ zcbd\.iMܷkPz<9JM!=xsJ(HmEb^ M\>s_Gq`߬«]aJÕ-S~?᩹oJI?Xl-:h_ { nɪHkpK#I B~/7W!H} ~nٕ"$:h˺.Lޡ.:AFO-|yO>̰3M'I'iEAfnmK9xWyf;Q mN>k{R| ,ׅExD#E?鎋U^$=auэ+%MF=_ųhv,}"a"+5 At~ώ@7"˺<4u~蘉Ǯk{7ye>DRO"s*!B1r8BD73TYJ5y:~=eG#!|eF(g'f[t7wTslR@2ń_oS# #F6uHS#po#/i |s_ }ݮC;My-`gvIRpaFCLb𥆃Mb :I?P#C>Tt|U*gτBY֢w{}]*dF\\NdO' g&6W7jF+o:w~ a[CPS@Cڳ]Z5"zLFw^]qŜ`x8q}Y}}!Q)O/AlQ֙HZ~ªU&Zji(_wnSaOmZGHMsktui;Ҷ?]ejv+AK*7oؾ38qEޮyz5<'GtX{PtioۡU\X(zY;'i(RADLNA¦ )b{p[͇k]n:;uUBꈁ5r1S$@~0IJvpW:u+tq\ÍPRTQ/:F#:&=lsF +V ey6I&F¶ah4 $4n#״DXF9TJR]rU:~{(oYb)ĺƼƢ 0'C6vx/ ~P+pdF%XUǺU-fț=ꀸaBF'6ek>e:Ŏlt #.gg=FNlqW'"iNӠX cE_g-hhAbgy-iWrX3U iVRTV[Q.?\? UA6 On 뤔f<eIOs@*>iڴh˿uYF┠n9*8tbq3[ĬMN}y-}>l$i'yς.3s373κted9}wmkg:7ƒJ@&Й{u$EHꀖ_ȽG[R>ϸ*A)E) %uN;"ŅC=ҔxyXϲ(1bڃE9McoǸQ ]S_9H/9-i?_7oGV//ܵi. s`;] Xgؖ$K:It| is1nS ='~z&h|\'*q.h|Ql\Uqno$P|йDӕȰ5kMڲ@3x&$cHoh( ɄBY*uMnnRtePP(6km!Ў_M64QRBP_$4qa}` Շm|K!NHl/9,a 姷\:ڟJAY XWyHj N\XGn%²dr~LWvƋ L|.7:Ӵ ;UUN{'*><2oQ>nX^˰+cl]Oe.Cj|Hίaon=t1~ɜVe7 5Uqة AZHݞj҄OAiZD=8,B.&?.*ɐika(F"Nl J/G 31 r ,^ͮekU VFW dfë́MH҆`Op2B6Qb9xRx|[} @,3C_iYY 8޾Bq?f0z]?Бw._!#~yؕN5;A2F<l"alUG}XfUٽX F#?pf^T4'Rz7蜜a cE.!) Sx}خ6*]‰&mP(c˂"+}Sd $n^?+]O!%vS0:x>nySSNҬ^7L?WrsT?uJ#N Z5D]#u ҢSeiKwk x biohwYVWrǥv!H^'GطEyqBڢc06r#$:IJvɏZF{RP_B!5%t c&-vYX z^da>mgqGٝvG#sZ']rK.]RXŦ9"N|/⌨by9/f{pp!*RVѮzR ƫD098dG$v `}df@hPWh*kqpQϟ3HaHRPuU}qb v<Y YyL&&b]!2n4nĤQ-F)۵iPMӦd)l OEL6,}kt7NOitjw4h)3E8To(4TrlWV k0 X[at6>-ɿ4B i0xC2(̛4#4?cc#џ`2Cau2DėPlsÐH]&S8I1&Dбn&%I>`mD>hi,&RtS,"L=B+* pΏ,^TkJ(fNn>]42-*ͧN+: w'[1,VTGV-q0eW+D5*69 O_gR󊄠@>Do6 @ʴaHaUsEL J*'+?:=M I~T=m[!]&CYzOS,*J\@:Z@>!Aىf?޸T]JFXt@&y[K&Ρ᨜؉R#&O|!p*yjHZ { m)9͔J{RkU ^k0\=S@Xs*9d1Lnڝ&>-եMVՋu/qi$t,Xr\Fp8l_kEOH/72jv9½*)i/L1V jo`)Sy2Jև-}GA?q0g'`-ȋ̪Bb>=gPŶqV8hÿxگXBe[M%=Sy# /Ug*FE tlX"\- FX?kD#i 86d_iݜ)1b5Ó-OXssG:Z endstream endobj 122 0 obj << /Length1 1592 /Length2 8670 /Length3 0 /Length 9720 /Filter /FlateDecode >> stream xڍP\.LA&H3:';]K ;ᑜs={5U{u^i^+2Œ0#+3 & ٙ@6T55o3* f9>AO),PS=/rX$~ nv'fTڿ,O dX9,6@?R=  )? )ÿ!9X`q|b8=-8?]*0l:?3yhYz])ʅikD`fK3c޾9"R$akqCBxc9r˝aV AhHM/ R&5v~VM:dhx0rq]H| RQ%v_2W8Ec1MDDBs9uq95H!ˀCg-f}L͡X ghN GQAV# [L~kZ-.d7W^H(b(?4\mIa&ϱt.;<d S ƾ/MIx|:%\Uڏs%z{xD1vW&r+pc.uH40D9mm!Ɖza9#&~7H5q7xjZkIW^Vvq_^x?x^ ^%vМ޽۹w]h]#vI}-?SgX]p9ir{RzdO=fȀFi (F̐^qbӚޒJ ӕb $Tx[ːeYP9l#AC:VIRm(Z!!c0?=NƼ5pUB5&%+Yt#mT@hbNgUѴtPK{Ugf}z|Mi a44\X~i,VXpo7L/ypx 7"G`ː F @>sϒYxF05; u ʘ_Fep3HPnƋ߰!Ťu !᳊׶Ii!n(mWǪO= Rfd~ty.ףpyMP>qōܻ&HgV2 ]!jfྷ|D*ꅿSKdǃ' D3Zf([i8.Ba%P*7ZSRSoZz6VgEv_!7kH, R^#EZ 1_m8|MN[xkP(%g[Lp]ۘǮite_ݻ(K$_nj<[ctުMR7gt<򱋒_yMNMZ#*)B7$qY덹3ZnK#1QC`;w CltšyoK7h} ?[ b HЕ)% XϨ.|uiM׎#V֜r wirF'r2wzm0o1KY%6$΍>W a3a<{9'5R X yǖgx9~i-6V6-LGԬF- NxIP= ]~|ō p#ҸYee(;rKv\`k~y6#7_ l[ʅ3'4#G2UbS=K^r1a+;8h徐G$f1Qr,5FC'wߺ}zk$\j4oYe B oK ߨt&sH}*j]_\ղؤp&}).ЮaZp2d$|#C96exP.] ȃa*Dyu}"#=Yۤn϶Ytr3EYc SA6s']G=s7:,B4cGPíG&9I m% z<*3~ڤRe :y%#.Z*'d>?Q HGlպWr=ٱ՝as Tv#S}x[!^qvdYp$ Gbb"!Jp n~1ou=ǚ2#ț&Aj\e-DϝY#Ҍ ڢNS RF*ʀ>6ww)d(Z- BnvX-o/#vfX0`z א$$Te]*K1,'qNyjg}ZYMyɐxt (d.X%4n]E'㯥L<4*1f-fl[ :n^ܤj.b4FaMqbE\^Nϴ%=/pdm^=]d迩!N.6]$Vxe h:Mi|Vno O-:T}Ih⃂ׁ&Bd/oL\ [kC(vHdrZa? 8xf渃 ۖۺŲ)X=qٍFQr(L_|27&hUP?߱ CzU]&! 6.+d1U]\ƆeD%:Qp;;1'I!%f χcV&$X mWcě |.G:G2,"Y|(/ DJQҴƔg@tKOi PʾΗTԯÝtͼ\.EQs/E7/撃Ɯv?|mk(eb2 M+A .#!٠gʹhyցDˊwDje÷@_=9QHF9dZjC-W]u!hh{EN  eޜ r=nVbru>J(#5 =&iLkm3oUj>KIpx/zPBBz8P]Ӫ7YD$?|΅g+73c͢pS^ƒ/M]U,Ie!΋Vnbkܣ) bc=$9^by,w6h:+*SB\sO%V-G 8Cx'쌑|:\Ne02y(vͶ'-ueݵT5sh4E],[C5^qs*@DE՜_/½v\K FxgkS;K&KoDTI8\unJEev\ugiuw%J\/6‰W5p#SR:"C-c ʊHH;<67%W:)4517I|{)"H65?|9)#%BniI,NrҿuZah7󦴑Ʉy'r3$Y/xgVؽV?rWjt:AYrޭ0O3C@=%"a{S/2s<>)!v ߞ`Rn"Y49}:\OqbYO-Ͽ@dg'^֗)N[k2΋'h'LLUo)W>,BRD>8~~kal=Z~K0o9R*}nsng9Y$WXdr۳8yʃxU\;Sxta_:AJx"%(Y[}nF.G!f6U&ҕ,yp}0~2b_.;(8>})FbBz|nfB6QH\)Zp ``w>eܹܐ EZmlnE(K4^V? * ~1uQ%%-vT+)>hT@(֙|R'`/)8`䲅uYn/6XTR4AK)R7?%h{U1jiю;&:=7rCRMl:O,'#Û;Wv6$ ޿L3a0vU^K1c x,iN\auv%׽9Uŋ0DHeK#ɷ{5, υAtwzNnB~\Y]=}%[2ug%ZeIJ}خOB g^/>J\>E! Ě񓝔Tp(V_XC"Ǧ_̴@JN-T)8WZH{Ϙfu `+=Fh$HE/"˱6$[K'-6Y TP@݁$vi*_ݻ|;ㅩ6&p"XV:c"p_&b n0"A~j nlh슔]i5U24&YdwYۯw+}bx 6ZC4ܡ RT旉TzDI?3h>^ι) 'WN j9^|T=sLiu8$”]%Ze!EŪPRbW`mZ"1FoRh·{Ark1ceLT/ s&!3$NQ-\/l(v7.B 1p˾n!H(US?j*U[~鴬[}<BěӔhjЃqhFqSVi팒~HNк~=5j H5M8sr,oLe&Oull?Ұ#JOR 좄`&H#@T:$Xq J!i(ņs Qa$9S]ΗΦJE (qY%ւ"MZ8ɢ:fMMh~̆TY: 04nY`)LBM2cQꊔ o~EKugs:U0>}>VPx1<Z׼֋>'6~_BG1NjJd"w~=s@?'efԫLu[فdXN yv ^_A~5z gFGx+xc!.Ghmj!Ǥ&Oקt|n؂~-]/ D/h :k Gl<}tc_EIȤwơᆟp/{ie[D3>Ăb2I"7;UHcy6$: y7B0NS㾼xEbNԖ=&vPXSڲTN߂.Sᑎ=Ӿ&Q>e4<\h(":¸D;f|+N->`&x}^Sm"W~2dt㸖Z#dq X`$K܎XJ;EmC1ݔzAUmv3©/1*zH8>"04D[ <‘GԒHLCesdT\g+Y>Htkф\X%G 7P@^L.ڗDCy%l+F,lmmBN@^X )lD[˔YM̦uy,:W^5n [^E@g~#x2ʧcH+y}#ցIlG!\ji[x9J{ r5݌ :0ww;ytSzL_3IqФPe dאpvLE΍'BңgrnɗNgՈSX!?(Q"nl&bW7ߢt.}Yz)F}@"989IHĶo_XmLL)na^F'D$옏"_4"ȭWD |z\[[gjVfOhJ<^#g@8G}c佮;FD(|pF*o=vzr7ʨ l6_;u=:WÀJ=DJΎ gi3̀1_2|ڊD_n;RTyaQÝT םm=oA u30*{[q+$W_*w avDm7DآZWد~Ыz/ɺJ6,_}d s♪L0MBtOd(G™C7>VqY^5K<<:oxW3--/>z'? ,P=)| Xͅ/>,#r&J:\9l:dyumZW1/`Q[[+[wɈH% )RO(Vt R|ʤThcptr gjœ ~oU& PֱM1bׂ `X4y+ցd۷G5/MB$bQ,U0JkI8FGӃDq%_r2 j-z~o@{$u ¡vITkQGð^qBnTuxb⨿ƶY)wx#Su~y䒶+f=31$‹I nJrn[ζ]6?wPjbӜî*AYy{Ծ0rXGf('lDQ#xG9d\F~mq(<\.f`/R_o"#l^*m={'riaBp:7lU)xB_sOe#a>nZ"2>rfI|w\K0>H_-s}>LHFjyASaq&lH]KG%&:z 'uq֋c$u9z:rl0Hzߠ y LEVNq"5sy.H92G!ڎ\H<ǝKv&,QQAe'H;oM{ ?LDQfյ#Ju*[G u'9Z_ ]O--A i9wHmbل[[!a?[Rɜn.Qۮ)=h O2f}hB 5YGjmI*T Hhw-:1lO^4A>-?|" endstream endobj 124 0 obj << /Length1 1409 /Length2 6224 /Length3 0 /Length 7189 /Filter /FlateDecode >> stream xڍxTSۺ5E:[@zM@@{'@ $HBUz " HQtA@@}c72^7֜;LTviQXQ6@b@/9m'㵄ych@yXM (odn Po 6@싀 h Cƫ Faqu@ YYO7F X7'"!6)ݰX~~~b`OUQPLa/ 52 3/ ac0΀D@`( .ypf:#//_@J'W"w0A{zQ+@FbX4. F .8M70o#A (+ n5PP5' ŐO =@z~Wp 5KQmsaR@Yii)v󇸉*`mqcBp,>tsEsEgZ}ucBŵ u4/*$*! @ 4@FF <`ğ>#VGdjO"g.C40nBpC,%wD `O2\,NhP %]^,+ѢbM? jBb_v_zC"P0c4 ˇiu5P4$`oopq+)@J(7b(4~,(wC`H,1.'5a0lq ruޠ'axe'>f0N A>IUgh}`VO —x몇%#_8hI4i&TvvV2}?]`6mewSjlVlJQ.=.U쨍=u2]%=DjW"׀uw^ ޗ<*믗cU4>LVǧ*uV\÷L,}t3mXҧP-ݗ>Mhy#6|Lmn" yTyx9~BqSOYteՙ>DΝ@Y [J#9Vo.t,t:\>c7Dľ<DZsfN^ty>τZw=Ց:}Ec)!m{uL)J 5-."4ђU]N*1ymcxvJ,5%ǧjoI|Ѧu+ xwi^ u5D.އz=nΕ؛ԋ-UCbNtUwIߓl[4"3{gBםdJfy6͟eT0wT95EC}X뤍Ի%+9LFV;Z*hY:0> B8Pu/h)S-(1<7x+RI CϽoZ^l:u!gK}/nm$"@Vv8+1m46)s/K5/%֝$گյW@3Gv{|;߬ 9M42*sSfOe 952؇sh| ER;*ʗH|sHa$S>gSR "1GϘ W(d.kOf|dbJ ;k%sΰJk ׿|1 K~ЬBd'|JR6M׶R[kzcQnvdL1ñPߴ9!fn7J] /(_׌ K LȺUradV[KIEld`T3#^QZeM÷biޞo殩ḟ|{6X,58 ?}ḕшb^M#Hwh{ˌ=_ Qʐ!{Ew֬=35SG4Y)O1|QQS? )W}ZjZe6.Kʺq3'S:ʕVUY*E-嚯4NvqGOU9M(f cCP^'P#Kͳj( #x1_kxW "6><|11 s8R!?r 3rܨ~9UnlM58sx]}z-}\6{whwCփ<&E;=KE}: ÝyT0u4ѻ|@-5%nވ`ػr?q餱rS-Oo~%8ҝqcaC/h{+ "kzʼЦiо,3LG 5?S*=x~ob8εA2U) ~K%D/-m|歡rEOKWTtUeN;N;Xx֑wE6yrnG`N Q%]hlν{ž){IUsaP:Hu[VcQ먛_~ʦ{&?L, OҐq V@j+TCt,{+Qu[)z~& @tb q}wO^8OP8^pNvzlʲt0c/ fB63XGR}S(HԣeRRV0F1*)j+mY&' e,}X@C1v7#ohHҸ{m4 @ɠe#YoTʻ-4OM wc NQIwo _l\=~F*䵦9L%J݃mGuDե]m|6>ח-be *e Hعcrv131O(ظx '#9dCJHs`Z )/s-بCŶ5XYGǀXӂՎ|1n6? s/qƼ'XtrCZvOP5^U˓< d[A~DNTRg嚟\g{nnmTҮvy2y8FŹlyf IGlY'cc8ӫEOֻxUڥ{{Iob֨Ik/3V1̈́44E(0=s1^##7!x//֭oȧyCEkYϣHJ3j[煷^y0ΥP3Ivʫ*qH'm*:Tfd/ZX"sSه/ xTkL|OGW&pL7Y΄Pօʗ Zlzq9Wt_a|JH?X5ݡu,i[`x}EtF@{ֽqsZ9[@qzEZCYy7k*.AF:hy=E\1zM7lizzC[=uUw^H&s ]VŽ?`3ϸӣ9}ǜ Mz/jRO @9"pϣu;I݂.X_AaY=I%<&'Yk7yհRWrup0+'MZGs4Vo\ؒL|yp}$DA%rgmW D%wHN p5h۫tX7afk񟭩gwx  (p̣)lh_r)ΐ/_kICV}[LOPcܸ螰ha]uŽ_,΍;&bbkflz`2tJZSR5OYՃD9hj"OrsUHo7?~jhYj6uc!{Y*[[}ȒE$`~ue^MΈ!X-cvm:N;qaj 3Wg3/¯8*ku.W8^% yj_Ff(/}te$ Cw|WwzOB f%^$U9|m,wƗ35:zM(J3j|5]񪎜R1yY@S ti.ӥ%y`c]z:RtcYUKYWOGw#K3dX*S@9=כo8ro7}{k=vxEnRndx&XPqDl{tvZa73f{y?߅;{EaݱP)R˵&G4O=`IhD= 0:Ab^&ufA<@-'%~"_pCJKoݬwZ5 P~XpgVF(>O>;L8 ࿴b6ZHcK|\wxԮq*m(~#́.P3Nh{BȼXJit:mM8XM*:G9~)7^^G>1!|ad.+;7]X|U!¡J#Rq|Hvc)UJ}̅Tb3 ]Z#pocO>W0P[T>ymtK u_¼U$Ͻ9{o֐i<4 &ͅ& t8Jl/e6u2}9ŗ ~ MN?v.WƀqirݘJv;kjBa9UG ɯB$"}PP V|xdg CBaΝZ !aB=,[_MdAcnɏj#2^4m lE˂/qd̜=Kt&(P焰 +YExvHS@$6gG{MLE0weǓOd#v n6M h)7xCIDO`1Ez4 Dnm:f;S*qŗ,ocw]n_ L!-yI݇9 F+*X)m(~K P8bW rÐCUj$J!ru쫃,RQh RƎ=^8G3~O\K߁I]g2 =5Jio0&AmZLbk3dOu*m첳(u 24P1G'`^5x/*}0g$rX[^ˋj$Z|r4`R J#~_roę> stream xڍP\ `-H{$Xphw\Bp 4,Ƚޫڽ9טkPBARP# ;+P .9Y@u5?r {0"/ q{LP 9Y9<@ !^ a 6( 8ln?z;??/Q=P4rټd41AM G A/dh+jd 7 p;ZTA {g)JF6[cE[RA]A5qxqq/j e[/c p{ jckqCf`k@YJՑ`1ol62~1t#K`but`u[#a^, 1؀ ('ݍõ@] Af`m:ٲi@vN Ym^D(An @&l$PwdC҃-` lzCp0r@^V/BagM s0/b_] ?~}{a)bG&%!,*wUA],<nv;; xo#u񕅘A27^R0蟀@gD%HO=_?z#/ur|E.@&UlVeD!/fabr%;H]A*`GX\}C@*P7̋t/Kfbr8POe7$jDzqpP/xl)O2X!PK^3= `Cxl ~M `S/b^bqL/?̈_|)_jfkE|)_> K3_%?^dBs迊ei_%ÿ?x/st|b/Rbdoru/T\A&(SPʀrѷ.,C\gaȚDąn9sgD&oW9 kV˞)Mf̞#w N[:Ss:^ viBu?K-jX"Ñ8EӚUOR;:#ڽM^+bCH{C,o8$BwKo0&Tͪٴq{C 'Svi썮Pf C-6[\X"WbrW)ik̾y2suJc|E].@dC"C'527wWbQ^W=j{ҞٲD&ɴ:ӑ30)W:~ 7bKHYl"p |\2;p C_\BY>Fz<ִ,j׍FRx>ć193ըNje?#<5#k6E:XP*}=@#<&pğ>kQzm!Q6\c\\2}Ě+}d E<#yiۚH$aO*-6BDrT3LK6j"?zB\`zi }kȆ:=&Mx#Uo6gl^5WS>ȂlAOWF#4\dMGUIr.Y2o"p-7>N&D: jc[3}/ܦ$`IbpFj-_gm#XHWnؾ!&EezKj>,n0jMTW;( ^ьW KBCz npȯ7b*~R,#[URb Vͅ.pp=W'@4Z0CG7=&wqKkvBPv'B2]0Sfexr&Nφ_KPG}Ӟ ms H7Q^bBkcrO>q{O0c}4ƃlU|Nj|@PLf+hzB"e8{p=2:y](H `aQ՘3vAWD[,oE}eK2E i>w9ljIpJ.дJxb[<r=v!̉5y4#Liړ214U `Ua y|ͥ'7e7qU 6[,q!APJGJ.";' R]/hʈ/>"<^= j"+lEd:4kAŵr^з.Sse[sTf!G|U⑳i=sꉋw lضIJtᗏAE &MGyaT0zw+G4 F(ݪ=$+2 O?drR?OQVޣ|@{X OB>ޕ=?YuLqpoK0t;ݏ`6Q|Ogoa(R"N1`|©rlʘTlk϶&2-Oc|r*|}l1IOejypo֝S-^EB $#i0?Y-K!wg ћJRu[R9:u49I]K+ `cNX$ƭek7{yn1#;383 LfF`J)a4wje!٠T=_=,юk|E=;'*] [x34uvJs8 U[_>גn(iiG)up :KXjlӐȽיde.BTg[_阏f V 0^-U~0 >/K6=1#Wr4y]ϒȳ*J9x׽5;rՓ Fobcr*خ9 ̕ _?0*._Cr.QF>%3ޣHɤ!hCC!8Q#jgԵC m;$mXhu.]wUo[z7ABpJk͙# T@PiN^: @9c3rj V4 oA>*|9_{n#.1-ƽE XS&ݛ_NH$Yɠ{nO[. B Y̠OiW8vnQ#<eu~Xx:oͬ^}dwp,`KF}ӖU_-Հ~Yt3ߜRRJ;O 쌷 *Q,mdI9iCd3hvL3&5Е)c:|1,(߽ ;Ҡ=Sf.3p&93m||Ha.v˜OMcU4- QKbVY'F]g T°H2E\u R̞Q__#c.b͢V;u<.T1 Yr^!v 9WA`Fw7lԊ{l25o]Hm !=\9\ rj籣a3K glD!, \bJF;5E^[S;x#zQ?֦%X830C@ļ7G_.TX Uܵ3h>fHxđpI# =M&v}bU$;\-Y-E6+{F3Ull֬zn4ֹ{_G_ŷ(6džYqV@;'38ko^fq\.6C-Ci/VJ{jus5I&E\uD;VͷZA`72Ȼw,H`hνg7t뜡mF(S@m:hx|G0*/ /烵7Onk11bQ`UWx.g-ġXW$2('hg{KlT#ʉ[?7~4沀ZHljiхpyϜ! RWbA6`(|z3wX^yd*'t4Eb48vƒHIyᕘU ZǫyK1(RJ~RyҪud|:%r-<_OX3'L^C:E|%gDo,Θ2CW_ð%^1{Ŗ{M\NTBӤjÞp~O{߶Ǫ_J 0.1ȝuVyp>`Nib7j: 7p|HHY,QYǮLȅ&}Ф/:b?8u:qV2o)mffԓtmk.!FS?!͌UA[8=twPDj,t"u^ca,-X뉻#@ܩ]lT *h\/v{'X1 KRVǎO0(H>YonIwѹZvmf{tܙSMOZ696 JVo`e/0y1?]J`AVo'WB[1"0(B{SV AA)0+Iᆅ^ώșR Ƭ<G LD ph'3`YU Z][7kR# `ALjd$klS$/jŧك}F=,%mk;ݟ,Eb\ vQ3tRԮAc~j)bEܞӕz>!6ߡfem6|8Å\a WJ ;0~=؅Kia Y s鷯^Ns8Yr^˂Z~n^JArpOS2M n[C(&B%CnU'hGP]~{~HIO~q& +^t -ZrSRWdʘ_?]яtB+&7hs3lhߜSw=M-N_<ȩkCҸM)Qk\BT#sJB{7r0PYDD7i< ^{JkSH@bg!BIîeoh.iecEQYR#'iw]o$5jERLk;`M-M<cvف \_h@߽͡z9$CS-ٷed瀫֯5G;Ļ5[?-H >6U\/fKn gyF |ר54*x~t=r lƼ-Ն>=#]7>8u"sn3c5«R%YEvB5)F3S8uN%e5Vv>|ׄƑbA+|}YK 5D>[ B:]9e 'U_}X<N. ^HiįIx)*:-6꿩^%yav>Y1T|YPP؛Cvg19lII&$Ttx LKH"6ݪs lɽFhK7t6щdgjzjj bn7Ĭ鰅t`w1 ʀ^Ax\qC9J?,`ĸ-,v>S&:3fb)-%6V\vns*&-n ϥ ,+P1@o>eMEX $ͣm0'k/ coRւ4-%$ą?xrhU,b}옣m:[NX;24} T5HXAV>vx&gJǣ0`9~o{g[PgF+4t[\HƉs.m{+=g [ Tb,-?V1E sTxMVjÄE7L33:T'@~a/bݔgB^%dQ6')d:u.S R$L IDWoGi@κ/ۛH׺"5YEs;p*{pix[,ݓ5`Z?<[WRlHHxCzv4M4zg[XKD:TY{@۲*ךrЋ*u9QY8+G RMx2]Xb*Vi* ? h JR: ܶi"WA:lhHLv<2`]0V.0wBͪO*}6*q~؁` *!dxc^E x*)g2vFVr7r[?`Lf'Uzz6O9a2ҾbZ/osc9b=Vw۪ped6 _b~/gkmw%wf[.xC}JKn: 3c1V8oZfe ^i?sKH'(Cw. k/N3o t Hkq pSZ\UdR=5e>߰s6rSmID#w|Zr9qī`徰C!tlײ:]ضR#kkMlGX"d$$![12zc )4߹}c%޼at]ᢛ~c¾OB')>GTET}+hf~+Vڕ8fv R"qNrhtY* ]q. l"o8V_fxE~WLԸ` f37| TU.JVbUv6*M}+DʍIR2٧z7 *4S7r5@=sN-vUYUZQgl3ZWKw3sL _[+J͏svtјTt}#w;(jH#dscE1@Y%0/vĭ._Ĺδ+P$`rOݚ!.sNY,:a Bⵝ`(gC[?y$P1sb:{˼A*l=K,<"B|~[s?Wg,\};!Ba׸y&4x)l jÈЀk0#T<:# BH=&rJT;)ȷ&. 6rib<m+? ?Ɛ]>tݢcrjՖ0uéB<.-xWKmmȂ˴Ś;,zzDF.%oghv5PYQ }Uv?ϖečs%+(Cp7xI-nʮ⋇CLE4y(GyEv1Q54Fn#"|ݹ&#nb,?bQR#=H <^]Krzj'$ U `yNR;jZ!z&o#"sڞK[$A5XJO33<t|_Zn-4F5vݣJ +væ~];&u[;y.@X葺gsOlV#~)1lJ}KmMĴ5z;-5s,޲D5^SypQNf!Cb%7%?>Ұg;~>z] 08z^!_ \Fd,V,'Y7J HQl1] lN~uwq-TN`@+g =G)5MXC<~ODtt^R˶(tHAW5[H`&$cuA gYyqJ.8䖬j;ډF=R6N&βa``/]RpcСtaQ$|G/y@p1Â7bzŝs[ݓl46j*n7eI{Ͻ,Է<6oz ^ȼN$ij U ) dQ}0I1LMF|.`dL OЦohdϥ;R2ZMxGBɏqWף?/߄X0pF?{ ZJ԰@JKZщ%؋YOl398瞕OV6p;{P5):j'xzxWظ6%sYze-S\p7-\jjk^^ \'yܓp!l=~|NV(xa?ۊwp{c9/֘2Og0R`Z)c^1?ڍ "6d'BEo)pH2,Vu@t\|o#kucHCaDPN5J&ՈRs=k44\A")-ߐ V-n@渏*m ln8 |~N5-Iws6SŅ<-*zlo2HW*Pq&h m{vTcKեbLuuT8t^K㔎?@YݨHgSpF_5>W'A/>> 3JH~Á fOc&Gֺ<ɬI30n8up>Hs(v}eQj~׾^<ߪFRH Z(ؿu8ZI軭瑥wd=}o=q9Bf~+œ&]y1]s&wS'C '&8j`H~AyNSfVFU@Yl| ٗn EV[[j'}G;A4I2 3燭)Žt MyXX9ҥs< S˘j{m78.x^/.M˖i=IՓm0jC5v7fkwbbt%y.D) Ũa gΔtj goi.س [/&<4nEڻ4gJzo =sŵ LNٟw\CVoUiCpDb!ۣ(I%9ū0Yx)iN\zRq^  >:։T%B\/_|y0~ra;X3WE8@56B~ j(j:)g s&1doT:FOJP:REtxf^8ol"1.IC 6SQ?c/ }[Rr 9 /:W6  jz =iV7Ili +zE0J‰f̮ۃy1 \L Ozĭ Ņn~1e)2ebB$tӊ<*y@.$#Dg0FW(99z Mf7{SCʜCS~q|?v$qjÊLdHdx>59e쵱XoE+nЁ(vq3[ecDU@$OPޡMo'SGZsudE D5vEj 6e (G6E| R:֠ q1ЬP+D_C@%u.{{),Q`TIOV QT?&Q3hIT'T-H{Jc y%ō[_(4ћ&U%2R¢Q[[Ӝ٤3s.Kԣ~­Bl*1>>rVfc-Q1gXaWɖ$y-#VzLlҟN.]jN4)xdfy< (PYz||Ii#93]n0|?(ng)nbmj h9}+r0 bc@JEkےG{֯z U4lg\)F7#3(nTSvxͲ޶{k*9c`x,'5Mj~;T/c&*>.eeGLTew1m#e,_![rxdwWVj:K<Q˛ƼOL~3J~ril1}a˷+1c@4蕨ug5WoF  dmTkfq-$DzY$) vO'ثDyn## BlߟP)&WvR~G eIe9򌱖AI||'W<uwPl\=[@~\ $ v 'O''~ZWƹz>״MØ!,눭mǘgペgwEY 2q%Ȫ;HJbYx7Y[2p͢d5T$';O%{_ۼ\(Bz.9z N<5$G}^èkGdͽxmmm9J ;3s|mbr?oqAc[Z<oOlM/qL;G -Gh1$|Y?fKG񳖩wXQG endstream endobj 128 0 obj << /Length1 1695 /Length2 10821 /Length3 0 /Length 11904 /Filter /FlateDecode >> stream xڍP-@=ƥqww{.{;3_^uUw׶s>TMl6`Ff^* 3BǎDtp!4 Dy[ `efց f 23dlmHvn 3skPXxx[@Ɔ6yC9@W j~s0؎ŅڑL@g Ck_1"QTA:TlM.@ d q| q1:^Tv@?rtEN# dc0Yr`W0=75dehJuCGh;2:~;1ۘZ[mH9_ݍ˵u2٘ɎIdjBf8X@{؜wU7;Ny7$|l}|ԏSmEZ?{H̠*dg !Ccč֥Wҵde4x~^%,c4CZ'Y\9|280[Z W٫R8:$(ڛwskeoF(=Dd< "7>,d10Blzt;ՑcrX%jeAAU1;F[3uqSl* A u3wWpZ:=>q1FDYmY{ –#o^L^c1qb7_*~愆9M~ZPUO`7?x p3bԘAp.šŴï]ӟҗK$>Ugd2'J`5;\:icNyJnA3TZݰX~%JuF{t{jti/ VFքTiPBSb)yymtL^[0?G,H֯E 7кZ7iU$c 2:)3`*>=bl7d-TYΰ[XŋX i̻x%\;/}YA<:+!-KWKxUAQ -/z-6RjYUgѧy%TJ @JpcqǶ(vfcH9 'TLo:/uRÛ2iB"5'(a\D{MGݕb̚$w|(K͇!̂$fr*tD b>PmuR&%,>?ݸ':BFBOY0!s{@xwP,f.7L9MlB۟W ݏXi7S/~EkQ qJ|hgn7>uaAz=`5ʖ rkj:[z{tYPdjvBa$U$(As)}VSSq\LmײNwyHDĝу J>.ȆC>^z[1%c1p;DZd-<;H06%>4߀MO )[j,NFY9D(^%_§[t"4GB5T{!"}%( 񣪹p@0"E>dNKZSz$uԟgS"RnϠR dcfo*)xI* q~dՌ]9e7O遽"`oXR2Pf7VhP^k;M>ٴ˻do~êӉbFCt}@. /0Tzp(1ҥ6Ra@ ymc?ozr ֮wR|TE$vh`JXKr:ʊNaU( (O=exEO@c冴c&jȱ04`ibsPZf3ߖjJ@5>~M.^_Epg3fEn)br}mߢ=VO jM\<Q%e^ܙ3ڵÖ R7c1FC!6<*1{ni(`mX?x 4j8 Vy:uidJVl9ű, lط1oyn'Ũyf. vj^2: J?2h=w"}1E03{:,F;&?hHe:m.CRF(&qȴgU'8:etv.7It "?prm4[nD2cgbwFm_aҵM!/@פ]"#}qϐ/CZAgxaf"uV0oxԞ$d*ɰtta#r;.ՠ}'sk}yId#*s5^(F5`Cxxv$LDIe!9uTiOeDMiAP?QC##T˿)U~oJfJI#I~,Wn8F-b= A4a10 NJxZhdtoc $iz`msq?W!jr㹪Nly~|z[/^7RD2<2̘QͲNl4_.VPe32dǃ-d ~;F"ハ ܞ+YkZPlYC7*]I5sX nla6'bߓl R4O|6 W긧e 4b'( A'WNBF} :5,J}bT4#8f}L?T#_ZgA4WS g1uot'%+T-]/-̌LyK3#');J~ /{ŏ:osV47_TWE&&tȱݚEBmP}=>v6S$nh(h#аK&y颐 ic>MY@kYRb,]#GwA C ẒTv|:'2$?Bq qmLNxoo65nvkD7:OЪ৲{{l$1'pc%bRxiOSn]}Ef. &X=w71|WTSܶQ{,.Λ:lB"wc3ƖJF~H̹=cD;3QU"Kg迒0@lQqwզ<#d'/.gl B 6iZtQi3[:W[D'e鶌lX;es>x)3kc5{a곅՝+żͯ?BCC- IiЦ Bv3}~jfʮrǍ|U>%؍[$̙kQ]MأOPDrc!#$Yy8Wp cMK6̘R][sNgXa+~o% /J>s#r4J d PMȏE<6++Y\z~bVE#YQAeNL#x9}KԬF]^K4T0rƾ0'Dpg^ܕ\Ɂ] uԒ3Uk4zq,]ь~6;imᛶ'^^)wԫ!Y]Ux5Qxq;pwj.u0xS#P .| ADK #n W5W0e1>WL>/:CFTkzcoQrJ4}6SCՐ+50v!oRj2QgֳˡouR3I޺ZJWC8=_YM{ ۦDrlAF. /x͑lTtA@O+l[ygl'D9m|xq컌 gC6, (|xQيܳtslowцbvGchm~z_0t=Ơh`Xlt"XNUizCM58 !+*+/"y!1}\EbC0ʃì;*uyLLigܹD3X2iTn_Fy7cbCNl|?ݨ#@^ V6]zfJ-жe(8vT{*zWtAfQ:'_9+]C)y#‡fJ΋} \q&P jQnQ?ϋɌ7A6o{#_m p>(5d?VfSAo[")󲉊)b ; | 1i o۳q,ʾ3IǘdtTD.e9bl2z^ϟ|rڴ;>+y 2ipϨ:~Y?!u8pd>W=?=+em: ʇT)_$QPzb֑/1sa ^|g ܮJ`5/0~%tZ&iъ` qԒȄ6)X;bx@;FbO 75$T.rݨX5d!4kǍLӛ)炥+0IP&+u6QJc᧥ǀ>P$xȏatr+ܔ~-=D@1[ܧ\MCIȌC*aql"wK=qlXSFi~EݑJ)5m ^7@!D^'?|E\yeAhR򮞪_p,,&vM/ձe7[/YޣG<{j{jMd̿Vq-ޫo[wBAi]ʩitjmK1IqH-b:ȑlR1l 4<"pyTh @26Y,eiGjꈴ l<[ FMNms UI9BR4O ]sL>~2GU?h2]',3:YS]uRppzEq_Q_~$e+M,pyBTO{ҤZ0Z"V>dIC#KÒ瀡´VL&v3mÃeV̥_n8 nXL W(g4nBCQabRbYy̎ѯ4Vӵ0_b?-8]ڃP >P Zemf_e(vug~5w곊dk%!rat?~4Efoኢt]o쇹N}c!劙{ߎ7Z=+9AHj.|yFcqZ&X Xfqv#ad_لQ̎/W: W/騂;mDyH }ӑoU'VD^hgӎV/WcuqOOIBn94Ȕl^!KŴvr("ܿ?I/=:jB73p×$~N-tvKrŇ4\3m466zw[kć\%Qɟ8 `3K>!fؕƢ3"-m}.~_zqR4/FnD:ۑ U~X!^Ee%1D)1fAx8n3Z5W+<̢7p).SX{i;%wdot*kH,7Fe$ 9ڋ= fxI6UHr^f`} /7Esop f/n}u>\'7B i0Zke!4@H>(VR!2y-K(,="YuxeAxj@W3#_}Yvb$Ä,l4Ȝ}.I,\Q _̢TK4zm4F#~,(ΙфU.,%RuI~y>^VA`S9?;cA]Kcm]Huv*cwN|`}g'޵ӶጇX@{b3y:*Km& nAa&i\J*'lR;96LKff;|ϢK0⬯Hb&k%OhONs4n/ZhVl6ӔȥeMu+c;[wvQ@S\0]N*Lwz5~$4_Y{-;UwSH6ijT:edzON->;gI]Op(ߌP=}1<#lv!8*@V0P8gAma፾hLѓr+au> )BRۙ^7sӕ68JTܝeʥܑ E#uTq3&U)T$h;.c5D gI+dpz<ɽTYo@5`l_1:(τv,ONfiI.|Lhܓ˰ cB=ܡ9/zIoZRo>GC3-fsGC.¹AV{=4VFSH6Ue4S TF[vs0KDU<CʴZsP;vF'7!Ϲos*7PMfį6Zy?:2}eX91JGSs{k ="I¤ށ'l ½ aH;!i8"^g4tvd  oF+kn&}n2TLɓ%z^ 3z[|i7:;I(ٜ p'`ޘaI.Vĵ<A߅Y8:vαc7g[ni3aNIa*Ib$9L|F=\)⏀{l߉9-Ԏ2|@[w5Zhտ˓B#]/Al+DC긦dy5&a[ "I<l/ǂQ!Tqg ֽsKED߰=ԯgI5h{,ی\Êe$ ȥP$cϤR'zI}%y~%0:L'rO1X3d׎O"#rYO<7acp.>*Oa`:ދx8N"?iNa}8}_J{[SR#mèNd.?ϝͦ']WtgzY,1ݙHPj3*kف_M&U óB&I˚<"X/ Us1.~ зМ<\?Qͱ} 3[_?؝O I{{m ye.zQ⅏ jyrHl::-ߘ)4B)9;HİV+8QjO¯+p_yA&?_q?K]~Ojeat 9}OMLR$&ZzovZ[j֔ 'oF1+W!x6'tT`nNi?.xh3gFB‘jPG2}ͪiYckMzk'RFܞɟr_D]q);hDLy=ҽ'4\׵GIM}2McR2-&e/$v8/ ߤy;SZ5e>y=!fOU+CiW=/wM&fe%Az ?V"Z\q Wo@WRIf4]Ŕd*:/L6tPQ;zW) Ul ҡs~1KrHOU;CbbڼۍbVY"b{+16x0As\.gGa"VR.WzҼ8E1-lX-X KdFmG_?=]w͑D;9As]R|%p"հBH8I{_“X($f Ϊ8>U;3ECF ``D8; \GCNm JpT=ggiKa %GH(* VhWMO K|*pWkh2wO@RI4O3ľh ̴\ٸd._P2ze>'~GxGBI/D9g⑲'NQzkJC}m0[m>̰(KPU YF@hƣՒooo(b1 mbh d? %XuI U.tx%ȻfM|1FpfNs^ fGaV6sP2rvSw4%fM-`Ӫйp̚8T5ܼ)xGg,vK>^Fkq+i)Z<#2gA U^m'@"zSʟ_D(oѬHnדBRZO?n*55I 795'}q7!! XSw摉{, >RΊ+FyTE4tm}zqp1i endstream endobj 130 0 obj << /Length1 2578 /Length2 11665 /Length3 0 /Length 13136 /Filter /FlateDecode >> stream xڍT)!LDj Flt4JwHtIt"zw>H׀[n Vܹy$Z>>A>>ffC#tf#CB tGДA-8 HJ'w(=6-:vaV;Bm~brwBA@@ nvBxplRv^^^<@'7 ; n]=6)NRaAf!^@W0Ap07 @xit5S?m K0(::ʚ<\ z@k_z "sBxܠsmQ0E;>%+?u`~C(; g'0XM f v .7ȎCg_LdD~pg8 #~p܀`8O?? rXm0{27F xƇ?~Ͽf9܋b^}Jz9I_ Dą ߽ ,J `g= G-v?f|| aKߌ:7"eGǿl NPG$s-8b`WjmND8|I#xy`pw ]wRaoHpDH tE|^{UG^{$UG]!k#wŸ=BxпGHkx#8¦=B"~Dh@7)Gt!dİ@Kp t!jc 97)̿ DA"a11- G1 "B;:]@Dqbpxq*X{D{D6~@[Dm_?Egh"DT>DDڎw垏=GF؂!v>"k}8e؈cΈ6 CovFL -B8;z-1rovhBpwGP*?ff#EF!.#Af D#m^w;WF$Ca~f>zGV/? ^¨}K`׿#ρpE; qZ 3pd}mXE<樀^Q c*mEc˜YS[1+L,3b$ȿֵC׹LjizlittZ llN&)\7H4;;dmy2*RLLJX|v;ɩv5&#.3zzʹ4x'ٻ2;]"VcI据ǔl!'alnúBã: aMVOȞq>K!Tzײ*Ѐ*qXbYƧnryj~&t3_ ;O裠'? ѣ^]_;娫oX$8FGGW&ЭAL yM9JL&/å)GiXlRrfB\\8u_ZJEWwZQHIcj:^丆O⩔%08ur)¢bw!lX^ G'<kwOۣPi5\UgTD~vLu1/&5{Eg`=i DaV`-κ#m׸L5<.{qx$37 (`I|@5tLݮuU{Rjz5C+,# %ֵ1H3.Sv) 64A*z^:e_ߔmIr $]zN q8^{9U6]F^:m nKU \9EF7C,#;Td%imԗRBO#dk=Of2ϽOOj~, r {˪<\  <]2Pd1I: a5|1.i}`vcʣ/F%x"6aʔśV|nt8C#r5̇}4R /LҎ(Rðȟ^\Zi.m^tݬ 2XatZ9ۅM]s-+3~c??[ =.4:1} 9E*++&oan'[G tw`ҵyLU83γf'K>9uRZΝ-3} Nz&(ܦj%h[=JnY/14gϙC1؟OBGgf<`INkHl:\JQ az^_t#'@;R7D+seM/7ּ &Dzwʴ]NJi /Ҹ"1TڏRw AZ-yUo{:7قPxqf $07F^S]Lϡ1wG7t-%HM6gure4$L_H(js:E$)eDDqa M(:izڣyX[4sJS$*K#V*)h[9Qvg `3z_ tDx]o9 {~,ʂ{@ynۢeaJDJu":6<潐V5C?-orxu9O@JFOQD{E*&4՞%}ec}R}$.qOdx֡@(x4 q;͌Bz~a^֊1pm9't$$ʭCʞ?^"k}{85.)čt%f~PE}ŘE=b[XtrfYM(3R+׊MV>خ9J5Ow̲'bz8"_{0s]`l|9+Oe1fI{qN(>0An/#^9Ղy7f@&Q(֖>niffCl0jb|xe@xцGӬCEz:_'whK xʚR q4 C@+*\AOedeUE>@Rg4%mFܬDc&/c/;ފ= ij=PJNa&9^֜Mǩ9ٔ6N*t5 9 rxʾ#B6,9= z} Gy6FyW'H59 ZCl-ɩNcIuR3[PzALsBD!*7Z#ɆgcPeiٹdx'v!5RrQB0;CXr8ZGJ.zv黫+eNM69&9ZwS|[2_Yd3@vbR:([-c*ޯ3%0pQYۤ|Cc=f4FI[x(y%r' Fk ~.D߮G06;+l,a% Hcޑhv:Ïb+bvl )͏=˂=,8:H(ҥ?TY$#fCkT_QpAϵ4Lp9]ey+B9:ڊ+t6cb|\}S@PI+ޛ|kū/GH^׍5WiuUu{&Þ.`H ?=֠E(LF9weg2.G0UWJ--DW nظtVCp9y#쌁2=4H\ ? VhAp~*k e.~430w~/k#/3O&$F}VxكFhp&j0j&x2odl0VGSSs% PYZ?JYP 7MN uPP6_V< .3ib{fK;dwR*Z+fJoy0UuFi7d ι*SC/5)m[[D 'kI±xF& \MIFҡՂ:ž"noѮҶϡocܶWTgg0˾& nF k 's"[ӌ9Db;vaXhJ@m":Lp~%{} *] RsڹՂ[g5-{Lqs1@ʸ.n/uKN,wjw[NvpU},-˚fq-RY# fG_jXZY/0p8U*Ӑ♗.|*ach__IZ:POOrnčje3B^V*j(,wWgܢ59f4 2Hs&LM} *cDie 5%\Cf5_ pO=k7~?Br%C@tP`[Kn?r{_%~H^~ =}FsИM#jƃn  }WR#J)+\v$>⬛/Z9Nx*\i8֑/B)8>-c!֖$CW{Mul~b~J[ހ,x!XaɌ,Gּi/m.)J?y|9n](=Lՙv/\'6(yz!sBwc5͠+_:Nm2rq;﬑4jf =ei? K,_YP aPSb[SQnGW2vw;Amӷ )ĻaRk3ՔRsFgėJK(nBb%Bsm?*߈Y^u(a7ɓ b+83c׋i=|x,] KM wo"&8|Jzp1/*o׌y3YC{*n/R<Ț%Vg;gxp3DQǩWsN*gCh98Ew%8[&Җŋ5 ]*y\Ĭ^?^f Y8Vw{s0;ZiSuM~YzG?*Ӧ o#ÓP|>;GCɄkn#CZs+=%º..LqߍZPڅv<޳a)rsMJakS9ב5ujMַeknh7L'*{t? {qEsX|&m[ƥ[`]N oy~YodlҜe32uJhUV4q25xz[PBi_M%ίr=22t)9)Ը H02jE^ XnV`Tq˦*pZJ1!qONɻ)ۍDvоBEZ%Ί7?:fӿmbRlLEr4EZF)ֆp-|[T4Osdc:|Q&\P GkAE'eu (tR .g18UTk8q!i4MqR{Hk-zE1$/cR&1–(m? }-ٵrV9.c 9qʔ%Ř0fN-zn{y^6BYw,Em$y5]=ZB drͩ"eڣSa;'&i 7DF;eԴg/Hvq Gm4.>))QlG '2`=Q]k)L8n8IRtgqk؆%N#N BunZ1kpr/)Vˈ~ њ?\jRjx߽$ֱSytqv(ʷe[FtY*|F%cVGcv #2eɇş٧%;{yvXxM? -;#15)PjPUO?BUE4 |yV.ЕAbe&0is[HOnMmTZ֖ $&z98 7 og*8F8de~8ɨI6 ,^Lx|s}['M#.Y05O»,Mu$B:iqHW7ޝw}mg kn rLi`Tꟍ9#J{j0lm$×mix|֝$eJXi1lE!T3}"Δ7Ϟͫ2Ϣs_$hƟ &OPz߄~5iޢ=;E j% z-OɒjPˮR~]/?VZuk3lj,{֖q2~NT9*c!2+4BԣF6Ksi%C*t :s^Se;4?H<u5zLɌVr,enUt Pc)ф/hJ5xEj'jI-k8z34EJZCM3ᤨ1h\S"#'f &/?V_ ]{/>M3vD4]+臺eaLQ#)epF2 C!>fT_x9EIP7&*ޟs^` )&<%cO|&Ky>In]}.Lrw*q䫡]vn##A}1mIQ]?*60v|A)^t#;y>~/8η=SMW>)8!$Nw` 9w}UagsbS!dfS)F,iP.B4]_6ݱLY!]mlgx{C:q ;?EެPkq ?8l~#_B_B1* 4|櫄OX{LiR ӗf 9ӫ)c$n??4f$%4[2hubfHrCV9{H^wlfK}VTdG[񸌾pP*(>MvWTKIbݕ`:7ufl$eJ Y đfgd2G/ɺ_`MLJ3<'\˗ $z!VJ3bXVh*05JLS8Gl<M=2=or=4tb[k W"ƳD?aBEn%;9Œp@D"0 nG*{ƗU%1_գIv GڴʍxpEc\bȰݝZ)_F vܬ(2Dpn/G']bΟn;w l0=ОO{d"hOX뷫p^h8«E)-[mx[˸JVjHXlZq^]snFsR&Ŝ՛cuiyXQT\&N Y&5+j9EL#Ws#YR7y~N-l=lK)0dG^LZ\h ) =?%%Vc1BbYa?匴@¼$їٌ5ٗ΂CY&!վ 4*n`ʫ;}Yy C"k` &mLf#dAcyAvQDe@~׬^hTZ'ElQU/ӯ嫃-n:O)j,,:`@2"T/ 6e\7NzHǎ˘\jʴ}Ng/`N,aY;ZR 6(镥uX_J+YCVZ P _5J:(o~]`+@xpT7%n{]fC2ydf(x%/WX_}n E)g$*a_A+% ͦi(=iY)cqޤ'YRwDžAKG2WZQod|g5qq!K> stream xmxePX5'h`p܂Cp\w ݝ@pMp'ݷU}u{tqi(d `W-/';3; PSFC ‰JC# BRf . rs9Qi'/+ނ P ԁ8@m-lBb.n,P7?E u%UUd*@Y5s;Zl-@` :- `Kۿ8M!f8eTUҒZ@3%PIO9Edu@,,P,Tvv+dm FeK7yOB.hYA989G'7W A@ _?yW?:(OEdfGj+3?3e??z%?Wi YUuu[` -GK3jflϿd& fP[O_2_Ӈdsq|?t-ܠPo"@ ԥy`]ZsXtt6<;D o-|4ҩ@s Mf@hc1FDw%T~kuƧ:*gKAj\Y ΟecLg Ft2?~2UaMۄm- D;!4),t׿oߘkc>N }/ja,MĚk7we[.ع1v:biHzMSLh=_$q>WܸݥVy3fH |Ew Q2IX|֚W):*I p.IT1!uQK:WwZ([9${P!~#uIq$wAhvS FI$Y_n#A4H!۪^>i1F$NUAq-PKE*D"m2ZEVlќU|M׮KS͛AY "9:T<_򺍝ҚP\Xxח 5EM$dCG=g]ۭRSkg=z\l/б<0wO?SdB &F#E #pnS7ǔR2.ۥҗ Kd^,4DSSj'5σTkҶv!qy`$۸p)t,ӷ(_FZ};BHB_ t{%"9NDizLVJ'N(Gvkۘ/@J%`:K7aFʍUْ8Mgڣz}e,Ed/ic%?bsI3_B1 <&+-҇Lf#2۔JnIcr^)72GkXʇgVܤVE~&!TuB1˽( зəY8a^cQEh}d&ޱqR XK p /bYE}$`k[!jn:%eFrITGS Ravu Ac׈pKQ|/fj_3QR`GQ5R-NĖG3XeU|V,}XJrߢURaVų*@LR"Tx?Sg=a@^ ZE' O)(E81sJgn~4+xv+ͪ ~u~|tA Yr %dܧlVMp~<.0@A/"9zxL8炫bnFͰj$ʹg#KAʹ鼟ȢpD|{sI&K(ҐX`+Z[:qܠ͉7A"b}䙴 NۙsUs %qv7% Q57Jh5Ln6.Ѯة"og ܐj׫%w̓>26K`.8Ft'E 길?|MkQ- 0ʅ(m3ZNl?-݀p9\>"3-}!V_,il,;'z;Di}G](q`8%%."P!82w^{Y^ #}]7˻ly+@gp[E'fԼZ£[Y=[޵4|+ _M-q -pw4D]l/2 Y%Z¢q <0oRt #.V?Пg{E'ߵgy52`C])O)y:8.>) QZ1W}75tM4̥iUc*#1[ai-ْSnqr `Q*Ѐ.jyxp$P*tʕ.(M}$_]QwrwHš{Ey3—5֧b{aE-VxuI fqg(9xG`hAG:훂cD6˖ m6o>D=K,%m o-1閳0I#"pQF,g+X@O&A:XU;+&vDm9Hbb&봇un495Q\c,$_] #962/>jIiFO?kg>I*N3oWI"0yHlʱb%CaD\mw}.Y-F_ Y|b&ۻ uw~p:;z̥ԏ> Yj%4{W)L?5->J EPfL!,T9nBxhE mi]QÀy"V݈m|0c"+nr oSU{i_g`߿V|RނGyR.o -#EjA-M= &mIcVb X p h9q1!x}'hL31PK.L}I9pf헬s?k$u,۷)d @F/KB W&D,>nf83i>`;\`'q1zBV&dkc^>Ҧ^0=k:kV,;^QG:5m t\}l\6"^$~M꾖읕41\g4+֧Av^Φ[yXK ,t+jA#L趞^.5={a âR)VI"m6r7$F#GW$]}7A/ыJo[XB3Ӫ[.wTZ|ӉH]r!9{Pӯi^Ir>.ַ{/їuOSl+X0?$(TUe=I[-Q"MƜ)HO%OZJ p4]4EwZZ7pÖ,ΌzojO Yhν_`웇N#Wy43hQ6}\Dz"եF(?7>IKI1襸ᗑy!ѰĜ!k:|hͳU%b]\n✜>w#gMZՙl ԙUȄ"͚c7_zM|=xdNEcTNklF.cß(d|htPgU a!)k8l3UE!S,Gnza)VV$xWU%K~pJnTr2EH3N#{mcaq(5xNJh^A6^'#F)36_VDŒP "Ц\>oiO=BwxOkz8h7Z\\鱍֤^3=$`EDВp Xi5Eŷ6ӹ'cP~u,I۫ہ@uMv,l"t*yΎN[e!ẅ́M}K)~)FoÈR28G&9qZy>Fo'H DUY`޴#vQHJfݩwry}afԎv(٪[99,W!nDU @* [ƿM9l[)89;Or>Tmٷ6om"w`wKLީ Р4U-uQ)ě]6tAWMQAn&H2a9&/$w][=CAՓۙO.7 uQQ SɑөxԻo8/Lw`җbdp'G&8SzeNF7X ;'8ˏ*o,=ѐ˕M܊㷧~R_ (ü&w_Wr=UTI\z7x:<ؖBkHU=|eܾtҰSyE6f̳d*(ly]}32ovFugNrhIV 2i67J=){}CE3 we/D6MϢ&3wԾbau\8+ާ d/lJͩT@ra^Na&*r)JQZ3=Zď.orBH4a]mO=!>PօFUY'N9N+N"nEY}_2.\ѴcA*0f5qpյ$w [}MJ﬌&ڼ(R! Cv ptXK.+& 6"ݱX`Q@K2DSppU@{ˏc2;k<'jdrJX-{/Oz/t=bcAtXtub%TXzwlF.||cuf0|#P``ZB(RO +{ b} m9Jʤ UX9h67{K~ʁFhX#?wе(ܔBfЫr}d _\Kpkּgشx܌@a}*J-כ*ae-:oy^j]H`^.>UI3J/m+~a[3} kL(M Jr֗W>)Я yƌ+I9PǸ_t${ptyhyj,SF}+Rd}l]tsxa[œqK]۠n0 ݣ8/q)΢E PNW빬8[Deե_sUe+/nY92MPtDk*+}un 8zdfmvs첹T8mgZJe}fR`{ H }\A,>,f9tj Ml2U6/J)Tf{H8Сn[$<_*6ņ{XTcZS=h𜤧.ޗXY*Uygmj!t.;Cۮ?De5zb;Gkv[!}2Շz礅j1!;T(g\ga5+|kϤtqK,4QKwD-UƠhW]K{paXRhRְWyo@>{=JRm3hEݰ6AeTNlx>G^exr,{͂$-FBN3":dXˆ /IE٤ g@ŷuܜt ̧~Ibkڵ,u~8Z氃,-AvJlC*,G3j -5:feoU`XKI>UlۻHy0\!ikEf,GHt?M6+Cf6);ބpy58z 菆*8/~S*0J-!ͺJGa'ܩRq OBĿfS~"jt 2hl+]Sh/5vFɦ&~~luh̊64/^cmt:8\͒JR_H8^HY|S1hכfD)|)7?/ó8I螱T1 np%u5.?ۃp⫈-,@mk#\G)mb4-,M\,@qұ5ioş|Qː9/% ALv aka9s:Q$ }*R+9 ڱmXܚ?;?̙)Z&{)h2 fQ]-Hi)n"S,U˗%t3 2TL66 "Cl5|8cꃆ:P%-a(Ue GgFIk`gM4Dz| #ܚ%l*M?EywoQ5T#`ߖOcnz ]6okFߒ1gzQ/QKPE55 a(Rg8;A's$δuw=Gݲh?ЩȢokM4̤܏$"#Y(n?`n/C O,GF|oY%:Ot9c+f w`6>JO`j\E>"q (PÇ'G}avȣԆ"X}s JyKR0;5y~#W鍋0l.omo7> -9kL+NyڴcQ{[kx/U>{jQ1/DMH@XrPGUP_?o7sqf/YFhV//٧; Rmh}ũΔT1Ǝ[5'uԩ%ŠO+;/ ލEL=AjAiצ^T_@kXٜO2hLO^|>+m5LF^`/F |!yF!MY}9$7 3e] endstream endobj 134 0 obj << /Length1 721 /Length2 4791 /Length3 0 /Length 5386 /Filter /FlateDecode >> stream xmVg4Z&j% D f Q轷1 c :#ZD5Ee(Ѣ}}׷ַΟups(#(7H$+i@ ($Jͭآ- " 0!n@pn>H \m0(`pE`'~Bz4C uuLմT*ZuxڹB (H C!G An9 0@IA@` h޴Q7l kԿݿѿUߑ Q;#N"ojp@oҍ }- U@.*(d.!|tt7Z:2> A=z,1bs͊~"Sw , c6P1𑚵H,Cɘן a^MY@g~Gӡ& W/2#-_Xz5R¥7~R̐-uMejiNei ^Ga=tYL/؟؈e Ar.QT Y{ fu7`szXR&ҩ}R 3ȥ Gb [|/z>!Y&Fc ^mvKJƃ` 7"YAc!%j6a ʴ3ڸTZEE[0 nno1ԏؿ@*{X6XԘNb\̇} swM9ݿOZ>ŏޥ'iٵ~7;0:c7XVV,aҌB!x[YZJP]BQ̸bdjm@!ۯs\ꬋ⁞T2?kf`|ąćݓ@|vO)UD_ %ABt'c q}fJT]îˑanZws"k62!gi@]sO#_ q 5/%_Xd?RTLb]RM2*w~>-s(X$ c\5 I&1My/&5"roV6൛w}/ ̧3'lސN,Dò2o >ECxD_)̓MhW:WM)Q1m^t͕ .u5=pS rIA/ƃ,,}_'< agxOӊsyO]#Q$n2]BfnK=Š3B(K77;VI6U781 E^JCs@ Lsf Wp ~`y͸7"K'T$??_pJԨ:]У0QX z=x^VxծusIr_wKqAf;t~4f1 /ԃ,PFFÖIk -7.;V-p~qT+85ơyFֽ2M!4KX'jr,`53ln};>B<sil;7~=a}ozU@9sJ!O~k٪rf&psɿS|}]R|aAջGN{t~fMKTyP +{+gi䭀Gg>sD#)kceU!X3:SU1XXql& 6W^LT7@zT$C23s XM"A&[ʢs7%[61}:՞ #}"FȲPxCAF|4XI P %0ԭZfeH yekfFyf, eK6)MH*׉|tG%[gW1Gl\uOk=w 99w6'k6hV8Fkܘ1-a7=>K$|$2wmd|<|Ǫ2f9H_Ke^{䐹fxKZJBrjĀ&;Y5DäVy`Fga1}Qae3U $ _9m 7yw\C\8T|-%S3E i6I1 )C[wޥ&?xwJԡVѢ|=7N\e!yK53SMGy̏~%WoɴI1fҙlZ$ [(A^voZ~/0ъ9%/l%J}~xBT`Ei}3W]=~IO%ύ8u.WS= )iU9tz N5n^PfSyOpZl#KOR:e Aoر3Ս}#˶Ja ?p>8^ӈate0*>3NZJM|K> L-f'm}Ϲ?Zb}̕1{o̖ҕQ9.ި)ZSazkSeԾ9kc v~)BwRv1&܊k,,/fk2Hlv7U.`T{Z4"ߚ0d&2&ݪưпYP-j[js7jDP\LfPG\Fh+a:7U߰s|Uƴߘ.ˆ6o~ hSb,R߭'QWw,Ń.\kD ُORd,XV Jy4sӍ~)$Io=饹\RU8Tgmh&V#a:>$0_Cуy l:|" RzHzv+%#9]Qa\-;Kc{K;KES:D,Z t;j\^R|f!+'*hg Ja^xGҚ{.aA-HhFUZ 类H.чN+٭CmSi*:A ~&VjcаLk}A=j4BL]W%*YQ׏s)`lfsY1MmnyUx$uvk;?؁y&ʉPӊ/C\Ǿ; A&OEe&-WE|PIZ+N*'UZVGݼӏL4MUit*#8w\D:4YxHP ƞ}zp᜷j,x:|;̀emh#t}єP羭x3p}fyxF endstream endobj 136 0 obj << /Length1 721 /Length2 5243 /Length3 0 /Length 5832 /Filter /FlateDecode >> stream xmrPZ5P*P+ł-RBBHRJqw(NZ] ]9{vs^Da\<ym5^>?3# G!e0Q> Ёx^f neZNPB\ր...R.N\\M:0m X0UA]CMgnP[N0 @,PH(/MN\ @,Qv59: ' #Uv$I pk:?0ACUA\( H|SBZ9{@algB`A;a5h̑/Jh{V;`PM8jKsĽEa wvBQH>y?r@-e9 GZt^;BK]4=wn7<\__d,+ D?r-aH߆o"`n0 )XM|͇BoѢou٧x1 5!wZCTD#~Ej(`8}E.cwVeEo=J; uCt{MA䴝Re|q2m-D?A*MX'VKZfH^,Oce/3SYgٯbYytdWzg}.VbC}DJ/aUֲR+}ծP[yW6JQ G8[am0 ]VoIYk 6}|nz#M H} j]AtLKHd_,~Rɍ?&gf N,1 Gbtwk#kuCWKU*1Ohh.;/v~Fpl`JԤ0 rĀ8;.,W4 \vuŽ8}l0r|5U͗|>yΓ䫗Sj\]W(/hǁ@x* (bA,n ңJcoN:VWRش@$tl=m0e]󌭉Nt) o&ƴ|n!3i4m] |)xZBfF?aov1 PH?/B3<S^56яt.;.zl1 Y?6?NGYB4d&d"kXkH ]SFh6co)糈j&%[SPn2^h9>g&<

=7op܉(ʎT/( Qv l(y .Ewr9_gR.U2.#Ot7)sZC˩/A3S¯PԶL/!ư T/TƐ-r[!+ԇe6>o;VBM)ii]f2t;}"4ږզey)XΒ`l+ɷwNyů\6+7 q 5m}:鍷w\x(g͔u20F+ o} I3(XmDYbD&#CL=61`uN6?NA[mԺإD-W.]%#,n{@vݣfh:ҍI^ŝZ\E.Y;qAzCfDlK*_.T_|'YiW0<cdlTr- ;qP%Ó =dpfeK;J̩<|p7':BjUݶ^/I$G6L֤?XaH?O__rH1*1) Ny~Ў9Gr`nYʨ(~7og/q.0C1wIqW-:|cgdy X`}JE wfp``egtB@Jg'*DCԭTNGni7>y=}0tx3sL|tڝ7#ke0˽` .1`A8hAR$1o'=Z3dT)?0}rUc %sjõ>wV"-8<>jPY,V!}zj.>CbN /\c, I2&iO\-b @U:u+?>8W61YNECHC'VPrȖBgq_$cFeO14Q@TU0}0վO}~/sN5)zJ c-I6cx?ek+\Xy`<Ϥ>'q$Մ͙H֖ܡii(3?tOP!cƮBGUQ~?_DOAfkK+$YW7D6uwNr4qͽD4u2A]ijOvWm#@@{P/^ Ips74`!mdX0lөiqX[9m鋋=jVzC8:e(DO1k|1k sRh<4`4)7LhHdR/wR+uK6 Cc fk4äe֨$)R0arإs{m+A=Qrb{+V?%i5+p}ߟbF(2I /_kL,ڻ^L$L/'G`2&|ln=B=" 2?,M^qS4}߼gW8D Ty>t T{0J(@Sd̒4k}`d-?̉O3XPg{eh/ Sy-ǔT2!@SJ=1 WŬIx.ɾܩ'%77\Ej2i\->] o>haHL586uϋbo>4 SDH>%j-Y |uQ8'-HmwjlJIա\xpO:yұϓN|I/|yI>O:yҹϓ.|R T<띹_mKz}K=W7"V{/@̪X endstream endobj 139 0 obj << /Length 741 /Filter /FlateDecode >> stream xmUMo0WxvHB!qmU^!1H__myݷDULG^͹t߷.k4c*S'ҵ>]g,yݔKeF$mS3&qGRp`I_3[dE4ݹn'&9綐7UaL)l:M z!YU0rўo>ν9},lj'}4>2]ݼ[ivjs92V+Vh ~y8&X-MmM|ŖE LS7Њ~& U 2X(pm XX(W8X&LR4=zukTGEm7h8Kc`Iu(!a <#G >n-tJ!]O2`̏S#',<ؓL%qO8\π: 3ht ,+9ugCwËpD|ORɉ#ɇW m藒1NwH=8! 4DCp&q"pBCT/9!ɨ~B }Rq҉TFIܨύ|nTs|neEA;~<6OIystg>O:yұϓN|I/|yI>O:yҹϓ.|R T<띹_mKz}K=W7"V{/znb endstream endobj 140 0 obj << /Length 683 /Filter /FlateDecode >> stream xmOo0C@@8l[jWHL7$Q!LUzSnffonh/}f}emy9f|vrvx}[(mmMyTnrlnwwVqTrvԧnfx Wŷ?yQJ ySN2k1ꯑJ.g%мFw66XͿS>r}|oݥNrl6rGىǼ?;'4>+JV}}Ⴕ.Mۻ:ɚx\_h`:Pp/ *,}!$B -fu[ǘ6LQe }ĭAk2$mAGs AI:םJ "ʔ43:KaCg" s rJ_i:6dPtk69u̩3ȣ" P݀^R/z0cP_Y̰*z~ʟ''Mq_ uWG5do9JOpH+8QhfgBfg"fg$fg,e@yɟ1S3SS0S+UjfjCfj#fj&.]1SkԦf44U44 Kx׆_|0n:8pw{]Ap^N3^?'y endstream endobj 141 0 obj << /Length 739 /Filter /FlateDecode >> stream xmUMo0WxvHUdCmU^!1H#x?gx]OTm$|͜s_Iss :L;<Sz==׾f`*_`ɫڟk3'iѴ}=M;7rfnj-eSӵOLg~8 )ok A8 $`I\3`Af<Z]! xNky"7 _㓧q H`nḱRONH=CpB:# =%888QA~!*zƜАT?!~> tw8y*sύ }nFE>7*QύR>7G];~<6OIyktg>O:yұϓN|I/|yIg>O:y҅ϓ.}2 L> stream xmUMo0WxvHUdCmU^!1H#x?gx]OTm$|͜s_Iss :L;<Sz==׾f`*_`ɫڟk3'iѴ}=M;7rfnj-eSӵOLg~8 )ok A8 $`I\3`Af<Z]! xNky"7 _㓧q H`nḱRONH=CpB:# =%888QA~!*zƜАT?!~> tw8y*sύ }nFE>7*QύR>7G];~<6OIyktg>O:yұϓN|I/|yIg>O:y҅ϓ.}2 L> stream xmUMo0WxvH UdCmU^!1HDI8߯-@=ۙڽ١=?w]pwdV^ڑݧl#oxdGa0NiqF?Sր'YNR}{f{x2A! u xk={Exo"}Rɑ#x۠_J B C쩁b8!=%p&r"D9 Qg̑Tu+gGNN8O-(7ZRntH ʍ(7:hEњr1+w(O:͓.ndm'#Ʉ'> stream x[[s۶~ׯc;gBoLڹj6̓,36Oeɑ4?DI+N:@\,vc`i"B2Ըh&ǏɈgJS ȔaZǎ]`V3 6,ȴe1jОYV3c4Bv -h -!XkՅJr Bj,$ 2t, s1tUKP9H^HI6Ezz3t<hyPǼ,ofoa;ELN o֗noxzP?KQ&P,` U]v@l^tVi n]ڙ#xWV,l`Q/XP:+ ǥ7n9K:G)5?a*@{Z12Jl?NݑEP{,mlPg6 36c2zRAޝg1~}z|q姪_j,Y覥`3]^M6Ǽ6#MkIC'ӌU~65gYmQ*Z/cZ?mRGh K 9#@AHʴ %}*́I#=oMFCP5S]񱑺ͪfy$s6WffnOyƫTE6D!!%T̜2=> iۿm߷^Сu=/zWx'|)`л0)vӛGֱGt\ {7z;A׻..q\2쑤GuoPwi]^#<x\;{Ox}l)Uufg͋Z&qt|DE=!? ?}~K>2 K~P!TyqY"Bf~{sr 5iȭѵr Z;CiFhpsuV'B`ԫ*mTw:_7u!'F>qէN4r} sW+\r\γ7 zKq?ϋPmxvף7 5]O  a"wgr̟g%_pnI L&$h0ϫr\N PMrxNrA7}X!AxM/:Ɖic͈DhZr_x`>%1_'5ٓϞqc5泺m>6Lm@\v_Um͟>}qtuO]*Grv0w m%+#zٸ/O^~[ݗ;Я{6ݴZNo"QKj/dU3koO ĝ+>jDEU<)[-!pVy`AV}g" ]gW}|iH_ m8_Ţ@4ۛIr::dOxR)<57:/'W%aI5Y6πeLlKdK"*Q^3ײH~Y$m׊$WD2b{Deɖ@%]Hn/dI %W @qU @K{eVuI*OJF\+ endstream endobj 144 0 obj << /Length 900 /Filter /FlateDecode >> stream xmUMo:W5?$R. d9M eCkmCp;;w~>|3E_?O]5߶w]Occ]=~?}Oyh9%?۹׬B|Ɯ>);vw%g43>\ 6 EJ78 1{~`W(-;]%=xe_,b+-O;q\L}UI--=BKE1p[! Mߊyu>.N5K)Wb٬8i[_uʕMzQ)V(Txޢjy!Z2P="Zd0\ÃGR\).2*Шa!U,H`+j.5Nα@VK-x%3%AYӀzΚ>kP#5m0Woþj.ZT$X/)n)#Wo(oRZ $Kp4Z-b\1ܰJ P"GXQi/8k^Zq:Zs9dB )sL-7xJ`aɽ)f$1 dъcCZC<73JgznHȰYɚTa,_-O87}KԴܗLloK+gJ.GZyVc48Wt]:P~`rZq.n1] S/Pu7Ue:?&?!d&1yHn5)yғBx#1ޞ]Go׏M?X endstream endobj 146 0 obj << /Length 750 /Filter /FlateDecode >> stream xmUMo0Wx$*B!qض*jn$H$3Ch<~3~~~ngjv9{C{K;K.k6㳵ችm#O7٦4\ =؏8ݿ߳4B8͌>sIvdXC6OLx9im$l6Dl_7ڞhz*{pɲ2kAʶC+mk>lpfIQTT?LA>J e .1PbpqH I$\kL8Hb،Shąr =z51XQg_s2Ē+ sC:CQ}.'c-BbOEu+Xg~:?aj B.U $,ĨAA 2A%%" 19hM_)ELN 1sR3fg =傸aCYjV^w&L= 3nqFyDŽϠOL5'pZx?i^x?IGO:~I4ϼt~3][gF~Qgf}fB3y,h3cL}f23{,g>KYN0`^ay{7)q W7:*ሟS`R$m endstream endobj 147 0 obj << /Length 672 /Filter /FlateDecode >> stream xmTn0C6*drضj^pHA@Cfy'n`g#govh/}eg羋򶺜m=Ooٽ[׌uRۉ=Iۏw{VQҜ8ߛIߞ3d_ ~~hZ# W c *'qU;HHV7xwuɻa;zopO_`_ݥNd0m6G_?[6vLClw6ZsaD%!p%blcä  PP[ u_g_x4$O<X^\NB8 \;cBbMx y%P 3jok:E q:/d48Q4A2="\šY+ːs(5$Y r~+A\HȕWr{Nxo $TL~K//p1sQ*GG-G-GzA>|)3Q/G""&!uN>|%h8hh$hb,n~ᰏnˣ+p]h \2 M endstream endobj 148 0 obj << /Length 672 /Filter /FlateDecode >> stream xmTn0C6*drضj^pHA@Cfy'n`g#govh/}eg羋򶺜m=Ooٽ[׌uRۉ=Iۏw{VQҜ8ߛIߞ3d_ ~~hZ# W c *'qU;HHV7xwuɻa;zopO_`_ݥNd0m6G_?[6vLClw6ZsaD%!p%blcä  PP[ u_g_x4$O<X^\NB8 \;cBbMx y%P 3jok:E q:/d48Q4A2="\šY+ːs(5$Y r~+A\HȕWr{Nxo $TL~K//p1sQ*GG-G-GzA>|)3Q/G""&!uN>|%h8hh$hb,n~ᰏnˣ+p]h \2 ᫄ endstream endobj 149 0 obj << /Length 720 /Filter /FlateDecode >> stream x}TMo0+J6*ħöUSEj9߯ IVcf͏睟ݛ{)^؝}]u:vzyu|CW$nmmΑmq5)M{`qjS5JJ:㩷?ʗym&ܚrMP_v}^JE[gb'gŇYxdOiQ74ѻ::'{ܶ[-IPۡi cw 5BzvM.^1k:qB_zfzԌTzSS/;,& ˂#6| 8a>}: i Y?yD9%r55LL4 n!д2G=4ϣ_O endstream endobj 150 0 obj << /Length 719 /Filter /FlateDecode >> stream x}TMo0+J6*ħöUSEj9߯ IVcf͏睟ݛ{)^؝}]u:vzyu|CW$nmmΑmq5)M{`qjS5үxO%r^q &\TƦkw(:m>8+>4m="${Jљ8=tz-/nqOR|-M.nTSXlDmqb]goo*co߭r#el[⌷L @ baomBҽ$`$@B)@p@)p2 d Ί?a.e8s`Wg+`#)S%~8NTҌYE, (6*3FӪr44P#Yf͞hhӰCkE88+j"7G9~PpC+R2C#`p˜1q EE5=F]=7z&`qp&bð| _/cSMrΤ f/%m Ȱw \ԉCb֓x5cfw(:Kzgqf1iXg3Np y/hHS>W#/5ferTapC w=衡xz* endstream endobj 151 0 obj << /Length 720 /Filter /FlateDecode >> stream x}TMo0+J6*ħöUSEj9߯ IVcf͏睟ݛ{)^؝}]u:vzyu|CW$nmmΑmq5)M{`qjS5үxO%r^q &\TƦkR@YwDoYia) SZM5_$$>kxq4|;o4vhwqB؝Bf#j{p7P_?{+4}+VYu}e}n.ˍggfjj{k:lF #QhJq  HQ/e.!Pp #]gQtVTv)#l-g!7'uӾ:[sI r.39uf *gQNxEqV11V啣Yq:54kDCZ+)]Ws8:а/9R\Qrz\8Ç]按Sp/ d8D(B!4׳030 =;fzÞJmw&^0C~/nS0GKW皠NdzG5cC)!=E^K<3Iò8ȿ q3NOg{ACt~Qn~ɸ\ %1.: *4hH`<4̶E hS!| endstream endobj 161 0 obj << /Producer (pdfTeX-1.40.24) /Author()/Title()/Subject()/Creator(LaTeX with hyperref)/Keywords() /CreationDate (D:20240122215911+01'00') /ModDate (D:20240122215911+01'00') /Trapped /False /PTEX.Fullbanner (This is pdfTeX, Version 3.141592653-2.6-1.40.24 (TeX Live 2022/Debian) kpathsea version 6.3.4) >> endobj 145 0 obj << /Type /ObjStm /N 24 /First 191 /Length 844 /Filter /FlateDecode >> stream xڕn8soG( $>,r`Rbw(Z m)n H9q8H`4  4Ha(,%@J@f 7D\$*$nT&#w5y% Ԝi˜ "͔Δ IxE; \2hF89x)(^]Sg(v{pYTz[M|xrՌT}3*v>cz3^N8(7z$v!c慐HnmsV;KU4h0B':K= VL!i"|qM1y}]֠(vzʁ3v M/lq?\_Ce'BqHߖP5:hNPu#N`G7: UTWͫ9˾tUm/.E^ލyJzybXoÔ20YI@= |@{Q!4^_1k5@M`huf6|4+5.]Mۜ^5H Շ Dvh8x[.GRe7rcoߕrS9Qc&7T=?ìʞ6oVݭDAG~MZsys^^oL3 endstream endobj 162 0 obj << /Type /XRef /Index [0 163] /Size 163 /W [1 3 1] /Root 160 0 R /Info 161 0 R /ID [ ] /Length 433 /Filter /FlateDecode >> stream xJQ4GL-3L+[vL,M˯JIhDXl HAN&54iRL~<^{YffkpzD MALDIquantForeign/inst/exampledata/compressed/0000755000176200001440000000000013341755345021103 5ustar liggesusersMALDIquantForeign/inst/exampledata/compressed/csv1.csv.gz0000644000176200001440000000012113341751101023067 0ustar liggesusersA҇[csv1.csvSVHRVHJ,RM,.VQ+I+,T21212ֱ2ѱ214'4MALDIquantForeign/inst/exampledata/compressed/csv.tar.gz0000644000176200001440000000026013341755345023023 0ustar liggesusersڇ[csv.tarν 0̹AST` M{+"S}ӗ*6dW)G6|JA8z>Daw) er)5/J2t1OQy"9:Le7-IroZAs8+ O(MALDIquantForeign/inst/exampledata/compressed/csv.zip0000644000176200001440000000033213341755332022414 0ustar liggesusersPK nM'44csv1.csvUT ڇ[ڇ[ux # foo # bar "mass","intensity" 1,6 2,7 3,8 4,9 5,10 PK nM'44csv1.csvUTڇ[ux PKNvMALDIquantForeign/inst/exampledata/tiny1.mzML1.1.mzML0000644000176200001440000000673013211235236021674 0ustar liggesusers AAAAAAAA8D8AAAAAAAAAQAAAAAAAAAhAAAAAAAAAEEAAAAAAAAAUQA== AADAQAAA4EAAAABBAAAQQQAAIEE= AAAAAAAA8D8AAAAAAAAAQAAAAAAAAAhAAAAAAAAAEEAAAAAAAAAUQA== AAAAAAAAJEAAAAAAAAAiQAAAAAAAACBAAAAAAAAAHEAAAAAAAAAYQA== MALDIquantForeign/inst/exampledata/tiny1-centroided.mzML1.1.mzML0000644000176200001440000000753213211235236024013 0ustar liggesusers AAAAAAAA8D8AAAAAAAAAQAAAAAAAAAhAAAAAAAAAEEAAAAAAAAAUQA== AADAQAAA4EAAAABBAAAQQQAAIEE= AADAQAAA4EAAAABBAAAQQQAAIEE= AAAAAAAA8D8AAAAAAAAAQAAAAAAAAAhAAAAAAAAAEEAAAAAAAAAUQA== AAAAAAAAJEAAAAAAAAAiQAAAAAAAACBAAAAAAAAAHEAAAAAAAAAYQA== MALDIquantForeign/inst/exampledata/ascii.txt0000644000176200001440000000002513211235236020551 0ustar liggesusers1 6 2 7 3 8 4 9 5 10 MALDIquantForeign/inst/exampledata/tiny_processed.imzML0000644000176200001440000001235413211235236022734 0ustar liggesusers MALDIquantForeign/inst/exampledata/tiny1-compressed.mzXML3.0.mzXML0000644000176200001440000000304413211235236024312 0ustar liggesusers eJyz/8AABg4SUJoBSstAaQ4orQClBaC0EpQWgdIqEBoA0joENg== 0 0 7e7ef0ea030f6a56d34a4ebd446e22b22844d432 MALDIquantForeign/inst/exampledata/tiny1.msd0000644000176200001440000000106713211235236020500 0ustar liggesusers tiny eJxjYACBD/YMEOAAoTigtACUFnEAADZ/Alw= eJxjYDjgwMDwAIgZHBkYBIBYwREAJcMDFA== MALDIquantForeign/inst/exampledata/csv2.csv0000644000176200001440000000002513211235236020312 0ustar liggesusers1;6 2;7 3;8 4;9 5;10 MALDIquantForeign/inst/exampledata/tiny.cdf0000644000176200001440000000071413211235236020366 0ustar liggesusersCDF  scan_number point_number  scan_index4 point_count<scan_acquisition_timeD mass_valuesTintensity_values\?@? @ @ @@@@@ @"@$MALDIquantForeign/inst/exampledata/csv1.csv0000644000176200001440000000006413341754745020333 0ustar liggesusers# foo # bar "mass","intensity" 1,6 2,7 3,8 4,9 5,10 MALDIquantForeign/inst/exampledata/tiny1-compressed.mzML1.1.mzML0000644000176200001440000000665413211235236024043 0ustar liggesusers eJxjYACBD/YMEOAAoTigtACUFnEAADZ/Alw= eJxjYDjgwMDwAIgZHBkYBIBYwREAJcMDFA== eJxjYACBD/YMEOAAoTigtACUFnEAADZ/Alw= eJxjYAABFQcwxaAEpRWgtAyUlnAAACEsAds= MALDIquantForeign/inst/exampledata/tiny_continuous.ibd0000644000176200001440000000021013211235236022645 0ustar liggesusers4VxLޯ4Vx?@@@@@@ @"@$@$@"@ @@@MALDIquantForeign/inst/exampledata/brukerflex/0000755000176200001440000000000013211235236021074 5ustar liggesusersMALDIquantForeign/inst/exampledata/brukerflex/0_A1/0000755000176200001440000000000013211235236021554 5ustar liggesusersMALDIquantForeign/inst/exampledata/brukerflex/0_A1/1/0000755000176200001440000000000013211235236021714 5ustar liggesusersMALDIquantForeign/inst/exampledata/brukerflex/0_A1/1/1SLin/0000755000176200001440000000000013211235236022642 5ustar liggesusersMALDIquantForeign/inst/exampledata/brukerflex/0_A1/1/1SLin/acqu0000644000176200001440000000071113211235236023515 0ustar liggesusers##.SPECTROMETER TYPE= TOF ##.IONIZATION MODE= LD+ ##$AQOP_m= 0 ##$BYTORDA= 0 ##$CMT1= TESTSAMPLE1 ##$CMT2= TESTSAMPLE2 ##$CMT3= TESTSAMPLE3 ##$CMT4= TESTSAMPLE4 ##$DELAY= 10000 ##$DW= 20 ##$HPClBHi= 0 ##$HPClBLo= 0 ##$HPClOrd= 0 ##$HPClUse= no ##$Lift1= 0 ##$Lift2= 0 ##$ML1= 2400000 ##$ML1_raw= 2400000 ##$ML2= 280 ##$ML2_raw= 280 ##$ML3= -0.0013 ##$ML3_raw= -0.0013 ##$NoSHOTS= 100 ##$SPType= 0 ##$TD= 5 ##$TLift= 0 MALDIquantForeign/inst/exampledata/brukerflex/0_A1/1/1SLin/fid0000644000176200001440000000002413211235236023323 0ustar liggesusersMALDIquantForeign/inst/exampledata/tiny1-centroided.mzXML3.0.mzXML0000644000176200001440000000316613211235236024273 0ustar liggesusers P/AAAAAAAABAGAAAAAAAAEAAAAAAAAAAQBwAAAAAAABACAAAAAAAAEAgAAAAAAAAQBAAAAAAAABAIgAAAAAAAEAUAAAAAAAAQCQAAAAAAAA= 0 0 1cf2b3695447d2dd698b465e27f452a80192dd62 MALDIquantForeign/inst/exampledata/tiny1.mzXML3.0.mzXML0000644000176200001440000000313413211235236022150 0ustar liggesusers P/AAAAAAAABAGAAAAAAAAEAAAAAAAAAAQBwAAAAAAABACAAAAAAAAEAgAAAAAAAAQBAAAAAAAABAIgAAAAAAAEAUAAAAAAAAQCQAAAAAAAA= 0 0 b87b09a4f34561d5572f9a6d30056106f819bc69 MALDIquantForeign/inst/exampledata/ciphergen/0000755000176200001440000000000013211235236020667 5ustar liggesusersMALDIquantForeign/inst/exampledata/ciphergen/tiny.xml0000644000176200001440000000153513211235236022400 0ustar liggesusers tiny example 20000 2.5e+008 Quadratic 24000000 0.0013 0 20000 hand made 1 false 1 2 3 4 5