diff --git a/docs/additional-resources/developer-guidelines-for-addding-new-dependent-libraries.md b/docs/additional-resources/developer-guidelines-for-addding-new-dependent-libraries.md new file mode 100644 index 00000000..436bf1f4 --- /dev/null +++ b/docs/additional-resources/developer-guidelines-for-addding-new-dependent-libraries.md @@ -0,0 +1,68 @@ +Developer Guidelines For Adding New Dependent Libraries +====================================================== + +# Our dependency library philosophy + +In short, requirements for adding a new library are: +- indispensable functionality +- license compatibility +- availability for all platforms + +## Indispensable functionality + +In general, adding a new dependency library (of which we currently have more than a handful, e.g. Xerces-C or ZLib) +imposes a significant integration and maintenance effort. Thus, the new library should add **indispensable functionality**. +If the added value does not compensate for the overhead, alternative solutions encompass: + +- write it yourself and add to the OpenMS library (i.e. its repository) directly +- write a TOPPAdapter which calls an external executable (placing the burden on the user to supply the executable) + +## License compatibility + +OpenMS has a BSD-3 clause license and we try hard to remove dependencies of GSL-like libraries. Therefore, a new library +with e.g. LGPL-2 would be prohibitive. + + +## C++ standard compatibility + +Needs to be compatible and therefore compilable with the same C++ standard as OpenMS. + +## Availability for all platforms + +OpenMS is meant to run and behave the same on the three main operating systems, i.e., Windows, macOS and Linux. Adding +a new dependent library is thus required to be available on these platforms + +- on **WindowsOS** this usually means, adding the new library to the Contrib in debug and release variants. In short all + recent versions of Visual Studio (VS2008 and onwards) must be supported (or support must be added). This encompasses + - a solution file (which can be either statically present or generated by a meta-system like CMake) is available + - the lib actually compiles and is linked to the **dynamic** VS-C++ runtime lib (since this is what the OpenMS lib will + link to as well - combining static and dynamic links will lead to linker errors or segfaults). + +- on **macOS** it should be ensured that the library can be build on recent macOS versions (> 10.10) compiled using the + mac specific _libc++_. Ideally the package should be available via **HomeBrew** or **MacPorts** so we can directly use + those libraries instead of shipping them via the contrib. Additionally, the MacPorts and HomeBrew formulas for building + the libraries can serve as blueprints on how to compile the library in a generic setting inside the contrib which should + also be present. + +- on **Linux** since we (among other distributions) feature an OpenMS Debian package which requires that all dependencies + of OpenMS are available as Debian package as well, the new library must be available (or made available) as Debian + package or linked statically during the OpenMS packaging build. + +## How to add it to the contrib build + +Add a CMake file to `OpenMS/contrib` into the `libraries.cmake` folder on how to build the library. Preferably of course +the library supports building with CMake (see Xerces) which makes the script really easy. It should support static and +dynamic builds on every platform. Add the compile flag for position independent code (e.g. `-fpic`) in the static version. +Add patches in the *patches* folder and call them with the macros in the `macros.cmake` file. Create patches with +`diff -Naur original_file my_file > patch.txt`. If there are problems during applying a patch, make sure to double check +filepaths in the head of the patch and the call of the patching macro in CMake. + +- All the libraries need to go into (e.g. copied/installed/moved) to `$buildfolder/lib` +- All the headers under `$buildfolder/include/$libraryname` (the only exception to leave out the library name subfolder + is when the `Find$libraryname.cmake` does not support this subfolder e.g. because system libraries are not structured + like this, see boost). +- All needed files into `$buildfolder/share/$libraryname` + +Then test the build on your platform including a subsequent build of OpenMS using that library. Submit a pull request to +`OpenMS/contrib`. Submit a pull request to `OpenMS/OpenMS` that updates the contrib submodule. Make sure the libraries +are correctly shipped in pyOpenMS and the packages (especially dynamic libraries and especially on Windows). diff --git a/docs/additional-resources/external-code-using-openms.md b/docs/additional-resources/external-code-using-openms.md new file mode 100644 index 00000000..770b6cb5 --- /dev/null +++ b/docs/additional-resources/external-code-using-openms.md @@ -0,0 +1,120 @@ +External Code using OpenMS +========================== + +If OpenMS' TOPP and UTILS tools are not enough in a certain scenario, you can either request a change to OpenMS, if you +feel this functionality is useful for others as well, or modify/extend OpenMS privately. For the latter, there are multiple +ways to do this: + +- Modify the developer version of OpenMS by changing existing tools or adding new ones. +- Use an **External Project** to write a new tool, while not touching OpenMS itself (see below on how to do that). + +Once you've finished your new tool, and it only needs to run on the development machine. To ship it to a new client machine, +see, read further in this document. + +# Compiling external code + +It is very easy to set up an environment to write your own programs using OpenMS. Make sure to downloaded and installed +the source package of OpenMS/TOPP properly. + +```{note} +You cannot use the `install` target when working with the development version of OpenMS, it must be built and used within +the build tree. +``` + +All important compiler settings and preprocessor definitions along with the OpenMS library are available. The most +important variables are: + +- `OpenMS_INCLUDE_DIRECTORIES`: all include directories containing OpenMS headers +- `OPENMS_ADDCXX_FLAGS`: preprocessor macros we require written as `(-DMACRO1 -DMACRO2)` + +and the OpenMS target itself (which you can link against). + +The example that follows will be explained in details: + +```cpp +### example CMakeLists.txt to develop C++ programs using OpenMS +project("Example_Project_using_OpenMS") +cmake_minimum_required(VERSION 3.0) + +## list all your executables here (a corresponding .cpp file should exist, e.g. Main.cpp) +set(my_executables + Main +) + +## list all classes here, which are required by your executables +## (all these classes will be linked into a library) +set(my_sources + ExampleLibraryFile.cpp +) + +## find OpenMS configuration and register target "OpenMS" (our library) +find_package(OpenMS) +## if the above fails you can try calling cmake with -D OpenMS_DIR=/path/to/OpenMS/ +## or modify the find_package() call accordingly +## find_package(OpenMS PATHS " +cmake -G "" . +``` + +For more information visit the website of cmake at cmake.org and consult the documentation. + +```{important} +Have fun coding with OpenMS! +``` + +# Shipping external code to a new machine + +If you've modified OpenMS itself and not used an external project use our installer scripts, to build your own OpenMS +installer for your platform (see our internal FAQ which is built using "make doc_internal") and ship that to a client +machine. + +If you've used an external project and have a new executable (+ an optional new library), use the installer approach as +well, and manually copy the new executable to the `TOPP/UTILS` binary directory (e.g. on Windows this could be +`c:/program files/OpenMS/bin`, on Linux it could be `/bin`. + +If you do NOT use the installer, copy all required files manually, plus a few extra steps, see below. What needs to be +done is a little platform dependent, thus very cumbersome to explain. Look at the cmake installer scripts, to see whats +required (for Mac and Linux see `OpenMS/cmake/package*.cmake`). + +In short: + +- copy the `OpenMS/share/OpenMS` directory to the client machine (e.g `/share`) and set the environment + variable `OPENMS_DATA_PATH` to this directory +- copy the OpenMS library (`OpenMS.dll` for Windows or `OpenMS.so/.dylib` for Linux/Mac) to `/bin`. +- copy all Qt4 libraries to the client `/bin` or on Linux/Mac make sure you have installed the Qt4 package +- [Windows only] copy Xerces dll (see `contrib/lib`) to `/bin` +- [Windows only] install the VS redistributable package (see Microsoft Homepage) on the client machine which corresponds + to the VS version that was used to compile your code (use the correct redistributable package!, i.e., architecture + 32|64bit, VS version, VS Service Pack version). If you choose the wrong redistributable package, you will get + "Application failed to initialize properly..." error messages. diff --git a/docs/advanced-resources/build-custom-openms-knime-package.md b/docs/advanced-resources/build-custom-openms-knime-package.md new file mode 100644 index 00000000..24d45584 --- /dev/null +++ b/docs/advanced-resources/build-custom-openms-knime-package.md @@ -0,0 +1,115 @@ +Build Custom OpenMS KNIME package +================================ + +The following guidelines should help in preparing your own KNIME package. If you still encounter any errors, please +[contact us](../contact-us.md). + +## Prerequisites + +- **KNIME SDK**: Download it from the [KNIME Download Site](https://www.knime.com/downloads) (at the end of the page). + We will use Version 2.9.2 (We assume that you have installed it to ~/Development/knime/eclipse_knime_2.9.2 but it could + be anywhere). +- **Apache Ant**: The Generic KNIME Plugins project uses Apache Ant as the build system. On Linux and Mac, install it + using your package manager. For Windows, see the [Apache Ant Downloads](https://ant.apache.org/bindownload.cgi). For + macOS, `brew install ant`. +- A clone of OpenMS and a compiled contrib should be available on your system. Please check the OpenMS documentation for + instructions how to compile OpenMS. For simplicity we will assume that the OpenMS build tree is located in + `~/Development/OpenMS/build`. + +## Prepare your build environment and create the plugin directory + +To generate the source code of the OpenMS KNIME plugin, prepare the build environment. For this, download a recent version +of the search engines distributed with OpenMS. Checkout the tested versions of the binaries matching your system from the +OpenMS subversion repository at sourceforge. Let's assume that the search engines are located in +`~/Development/knime/SEARCHENGINES/`. + +```bash +svn export --force https://github.com/OpenMS/THIRDPARTY/trunk/All ~/Development/knime/SEARCHENGINES_ALL +svn export --force https://github.com/OpenMS/THIRDPARTY/trunk/Linux/64bit ~/Development/knime/SEARCHENGINES +mv "~/Development/knime/SEARCHENGINES_ALL/LuciPHOr2" "~/Development/knime/SEARCHENGINES_ALL/MSGFPlus" "~/Development/knime/SEARCHENGINES/" +``` + +to get the search engines for 64 bit linux build. Supported builds can be found in the [thirdparty tool repository](https://github.com/OpenMS/THIRDPARTY). Ensure that in `~/Development/knime/SEARCHENGINES` ou now have multiple folders (one per searchengine) that +each immediately contain the respective binaries (and metafiles) for all searchengines. + +After downloading the search engines we can activate the knime preparation in the OpenMS build system by calling cmake +with some specific arguments in the build directory. + +``` +$ cd ~/Development/OpenMS/build +$ cmake -D SEARCH_ENGINES_DIRECTORY=$HOME/Development/knime/SEARCHENGINES/ -D ENABLE_PREPARE_KNIME_PACKAGE=On . +``` + +now, if you used the Makefile generator, execute the `prepare_knime_package` target, e.g., + +``` +$ make prepare_knime_package +``` + +This should recompile OpenMS and construct all the necessary input files for the KNIME plugin generation in the directory +`~/Development/OpenMS/build/ctds`. + +## Generate the plugin source code + +Based on the files generated in the previous step, now, generate the source code of the KNIME plugin using the +GenericKNIMENodes NodeGenerator tool. Start by cloning the latest version of the GenericKNIMENodes into the directory +`~/Development/knime/GenericKnimeNodes`: + +```bash +$ cd ~/Development/knime +$ git clone git://github.com/genericworkflownodes/GenericKnimeNodes.git +``` + +The node generator can easily be called using `ant`: + +```bash +$ cd ~/Development/knime/GenericKnimeNodes +$ ant -Dplugin.dir=$HOME/Development/OpenMS/build/ctds -Dcustom.plugin.generator.target=$HOME/Development/knime/openms_plugin/ +``` + +This will generate the source code of the OpenMS plugin in the directory `~/Development/knime/openms_plugin/`. + + +## Compiling and running the OpenMS plugin + +Before compiling and testing the OpenMS KNIME plugin we have to install some additional plugins necessary for building +the OpenMS nodes. For this we start the previously downloaded KNIME SDK and click on **Help** > **Install New Software...**. + + In the now open dialog we select the **KNIME Desktop Update Site**. + + ![](../images/advanced-resources/KNIME-Desktop-Update-Site.png) + + From the list below we select the `KNIME File Handling Nodes`, the `KNIME Build System`, and the `KNIME Testing Framework`. + + ```{tip} +KNIME Build System and KNIME Testing Framework (ships with KNIME SDK) are probably not necessary to install. + ``` + +![](../images/advanced-resources/KNIME-File-Handling-Nodes.png) + +![](../images/advanced-resources/KNIME-Build-System.png) + +Now follow the installation procedure by clicking on **Next**. + +Now that the KNIME SDK is properly setup import the GenericKNIMENodes plugin and the generated OpenMS plugin by clicking +on **File** > **Import...**. First select `Existing Projects into Workspace` and select the GenericKNIMENodes directory +(`~/Development/knime/GenericKnimeNodes`). Repeat those steps with the OpenMS plugin directory +(`~/Development/knime/openms_plugin/`). + +![](../images/advanced-resources/Existing-Projects-into-Workspace.png) + +![](../images/advanced-resources/select-root-directory.png) + +This should add the base plugin and the OpenMS plugin to your build environment. Note that it is necessary to copy both +`de.openms.*` and `com.genericworkflownodes.*` into the same subfolder. + +Now, start a KNIME instance from within the SDK by clicking on **Run** > **Run Configurations...**. Double click on +**Eclipse Application** to create a new run configuration. + +![](../images/advanced-resources/eclipse-application.png) + +Rename the run configuration (e.g., KNIME Testing) and select `org.knime.product.KNIME_PRODUCT` in `Run a product`. + +![](../images/advanced-resources/new-configuration.png) + +After clicking **Run** a new KNIME instance should start containing the OpenMS KNIME nodes. diff --git a/docs/advanced-resources/custom-compilation.md b/docs/advanced-resources/custom-compilation.md new file mode 100644 index 00000000..a8487430 --- /dev/null +++ b/docs/advanced-resources/custom-compilation.md @@ -0,0 +1,36 @@ +Custom Compilation of OpenMS +=========================== + +To compile with self built compilers and non default standard libraries, follow listed steps. + +To choose any specific compiler, instead of the system default, add the whole path to these options for the cmake call: + +- GCC: + ```bash + cmake -DCMAKE_C_COMPILER=/path/to/c-compiler/binary/gcc -DCMAKE_CXX_COMPILER=/path/to/c++-compiler/binary/g++ + ``` + +- Clang: + ```bash + cmake -DCMAKE_C_COMPILER=/path/to/c-compiler/binary/clang -DCMAKE_CXX_COMPILER=/path/to/c++-compiler/binary/clang++ + ``` + +To compile OpenMS with clang and a specific GCC stdlib, instead of the system default one: + +Use this cmake option to specify an additional compiling option for clang: + +```bash +cmake -DMY_CXX_FLAGS="--gcc-toolchain=/path/to/gcc" +``` + +with the path to the top gcc directory (containing the directory lib64) to the cmake call. + +```{warning} +This combination does not work for all versions of clang and gcc. +- Clang 9.0.0 and GCC 4.8.5 stdlib does not work! +- Clang 9.0.0 and GCC 9.2.0 stdlib does not work! +- Clang 9.0.0 and GCC 8.3.0 stdlib compiles, but some tests fail. +- Clang 6.0.0 and GCC 7.4.0 stdlib (Ubuntu 18.04 default versions) works +``` + + diff --git a/docs/images/advanced-resources/Existing-Projects-into-Workspace.png b/docs/images/advanced-resources/Existing-Projects-into-Workspace.png new file mode 100644 index 00000000..245226c5 Binary files /dev/null and b/docs/images/advanced-resources/Existing-Projects-into-Workspace.png differ diff --git a/docs/images/advanced-resources/KNIME-Build-System.png b/docs/images/advanced-resources/KNIME-Build-System.png new file mode 100644 index 00000000..230c84a8 Binary files /dev/null and b/docs/images/advanced-resources/KNIME-Build-System.png differ diff --git a/docs/images/advanced-resources/KNIME-Desktop-Update-Site.png b/docs/images/advanced-resources/KNIME-Desktop-Update-Site.png new file mode 100644 index 00000000..d1d3727e Binary files /dev/null and b/docs/images/advanced-resources/KNIME-Desktop-Update-Site.png differ diff --git a/docs/images/advanced-resources/KNIME-File-Handling-Nodes.png b/docs/images/advanced-resources/KNIME-File-Handling-Nodes.png new file mode 100644 index 00000000..17b4d82d Binary files /dev/null and b/docs/images/advanced-resources/KNIME-File-Handling-Nodes.png differ diff --git a/docs/images/advanced-resources/eclipse-application.png b/docs/images/advanced-resources/eclipse-application.png new file mode 100644 index 00000000..ba79e668 Binary files /dev/null and b/docs/images/advanced-resources/eclipse-application.png differ diff --git a/docs/images/advanced-resources/new-configuration.png b/docs/images/advanced-resources/new-configuration.png new file mode 100644 index 00000000..d8aff95c Binary files /dev/null and b/docs/images/advanced-resources/new-configuration.png differ diff --git a/docs/images/advanced-resources/select-root-directory.png b/docs/images/advanced-resources/select-root-directory.png new file mode 100644 index 00000000..245226c5 Binary files /dev/null and b/docs/images/advanced-resources/select-root-directory.png differ diff --git a/docs/images/research/whitepapers/design-summary.png b/docs/images/research/whitepapers/design-summary.png new file mode 100644 index 00000000..841be1c8 Binary files /dev/null and b/docs/images/research/whitepapers/design-summary.png differ diff --git a/docs/images/research/whitepapers/summary.png b/docs/images/research/whitepapers/summary.png new file mode 100644 index 00000000..097f5c90 Binary files /dev/null and b/docs/images/research/whitepapers/summary.png differ diff --git a/docs/index.rst b/docs/index.rst index aab0b3ef..8276502f 100644 --- a/docs/index.rst +++ b/docs/index.rst @@ -62,6 +62,7 @@ Contents :caption: OpenMS TOPP Tools topp/topp.md + topp/adding-new-tool-to-topp.md .. toctree:: :maxdepth: 2 @@ -70,10 +71,19 @@ Contents developer-faq.md contributor-faq.md +.. toctree:: + :maxdepth: 2 + :caption: Advanced Resources + + advanced-resources/custom-compilation.md + advanced-resources/build-custom-openms-knime-package.md + .. toctree:: :maxdepth: 2 :caption: Additional Resources + additional-resources/developer-guidelines-for-addding-new-dependent-libraries.md + additional-resources/external-code-using-openms.md additional-resources/openms-git-workflow.md additional-resources/reporting-bugs-and-issues.md additional-resources/write-and-label-github-issues.md diff --git a/docs/research/whitepapers/OpenMS-2.0-kernel-whitepaper.md b/docs/research/whitepapers/OpenMS-2.0-kernel-whitepaper.md new file mode 100644 index 00000000..719e571c --- /dev/null +++ b/docs/research/whitepapers/OpenMS-2.0-kernel-whitepaper.md @@ -0,0 +1,122 @@ +OpenMS 2.0 Kernel Whitepaper +=========================== + +## Introduction + +With the constantly increasing amount of data that needs to be handled in computational mass spectrometry we start to +reach the boundary of what is possible given the current design and implementation of the OpenMS kernel. Already in 2012 +the OpenMS core team discussed and identified the need for a redesign of the OpenMS kernel with respect to it's scalability +and ease of use. So far, only partial solutions have been proposed that lack the approval of the OpenMS core team as +well as the OpenMS community. + +This document summarises the discussion of the OpenMS core team, held at the OpenMS developer retreat in Izmir, +Turkey 2014. + +## Detailed problem description + +With modern mass spectrometry instruments and measurement techniques the amounts of data that need to be analysed in +computational mass spectrometry reach magnitudes that do not fit into the main memory of neither desktop nor clusters +machines. Therefore the OpenMS kernel has to be redesigned to decouple the algorithms from the actual implementation of +the data structures. + +Here we describe the interfaces and concepts we plan to implement for OpenMS 2.0. The OpenMS team has acknowledged the +fact, that this will only be possible in an incremental way, i.e., implementing those interfaces on top of the existing +data structures and then switch the individual classes to the new design, instead of a large redesign in a separate +development line. + +## Benchmarking the changes + +Before we start to implement individual changes we intend to create a benchmark suite. This benchmark suite should +enable us to assess the changes in memory consumption and runtime due to the new data structures. + +## Spectrum/Chromatogram interface + +The first decision reached during the discussion was to abandon the `Peak` data structure. It will be replaced by a pair +of `double`s such that a spectrum/chromatogram is a combination of two `std::vector`. + +```cpp +class RawDataArray +{ + std::vector intensities_; + std::vector positions_; +}; +``` + +with invariant `intensities.size() == positions.size()`. This data structure will be augmented with a container to hold +position-wise meta data (see for instance `FloatDataArray`). + +```cpp +class RawDataArray +{ + typedef std::vector MetaDataArray; + typedef std::string MetaDataID; + + std::vector intensities_; + std::vector positions_; + std::map meta_; +}; +``` + +Given this base class `Spectrum` and `Chromatogram` can be derived from this class, redefining `position_` to either +`m/z` or `rt`. Additionally the `Spectrum` and `Chromatogram` will add relevant members (e.g., MS-level for `Spectrum`) +that should not be stored as meta data. + +``` +class Spectrum : public RawDataArray +{ + int ms_level_; + Precursor precursor_; + double rt_; + int scan_id_; +}; +``` + +The overall design is summarised in the following figure. + +![](../../images/research/whitepapers/summary.png) + +## MSRun (was MSExperiment) + +`MSExperiment` will be renamed to `MSRun`. On top of MSRun we will define an interface that hides the actual implementation +of `MSRun` from the user allowing the use of cached, on-disc, or full in-memory implementations. Direct access to +chromatograms will be hidden behind the `ISpectrumAccess` and `IChromatogramAccess` interfaces. + +```cpp +class ISpectrumAccess +{ +public: + int getNrSpectra() const; + getMetaSpectrum(int i) const; + const ISpectrum& getSpectrum(int i) const; + const ExpMeta& getExperimentMeta() const; + // iterators for spectra + SpectrumIterator spectrumBegin(); + SpectrumIterator spectrumEnd(); +}; + +class IChromatogramAccess +{ +public: + int getNrChromatograms() const; + getMetaSpectrum(int i) const; + const IChromatogram& getChromatogram(int i) const; + const ExpMeta& getExperimentMeta() const; + // iterators for chromatograms + ChromatogramIterator chromatogramBegin(); + ChromatogramIterator chromatogramEnd(); +}; +``` + +The overall design is summarised in the following figure. + +![](../../images/research/whitepapers/design-summary.png) + +## Modularisation + +We decided that the OpenMS library has to be modularised. Starting with SuperHirn as a proof of concept we will identify +other parts of the library that should be an independent module and move them into a separate library. Additionally we +will add a new library `libOpenMSChemistry` that should implement light-weight alternatives to the existing chemistry +data structures. + +To avoid the direct integration of classes associated to UTILS into OpenMS, we will additionally support multi-file UTILS +compared to the existing TOPP like utils, that should consist of only one file. diff --git a/docs/topp/adding-new-tool-to-topp.md b/docs/topp/adding-new-tool-to-topp.md new file mode 100644 index 00000000..dbd431c5 --- /dev/null +++ b/docs/topp/adding-new-tool-to-topp.md @@ -0,0 +1,102 @@ +Adding your own tool to the TOPP suite +===================================== + +# What is TOPP/UTILS? + +## The OpenMS pipeline (TOPP) + +Any tool that is written with the OpenMS library can easily be made into a TOPP tool by simply using the OpenMS command +line parser which is able to parse ParamXML, a powerful XML based description of the tool. Hence most analysis algorithms +in OpenMS are available as a stand-alone tool which can be called on the command line or integrated into workflow engines +via the CTD mechanism. A current list of TOPP tools can be found in [the documentation](https://abibuilder.informatik.uni-tuebingen.de/archive/openms/Documentation/release/latest/html/TOPP_documentation.html). + +## What do I have to do to add a new TOPP tool? + +The recommended way is to inherit from the class TOPPBase as in existing TOPP tools (sources available in /src/topp/). This will add command line parsing functionality to your tool as described in the TOPP section of this page. + +- Add the code to `src/topp/` and register it in `src/topp/executables.cmake` +- Add your tool (with the correct category) to `getTOPPToolList()` in `src/openms/source/APPLICATIONS/ToolHandler.cpp`. + This creates a doxygen page with the `–help` output of the tool (using `TOPPDocumenter`). This page must be included + at the end of the doxygen documentation of your tool (see other tools for an example). +- Add it to the TOPP docu page (in `doc/doxygen/public/TOPP.doxygen`) +- Add the name to `src/topp/executables.cmake` +- Write a TOPP test (add it to `src/tests/topp/CMakeLists.txt`) + +```{warning} +Handle any kind of input files to your TOPP tool via command line flags and use the `${DATA_DIR_TOPP}` prefix. Use +ini-files to specify output-files, but not input-files. Doing otherwise will break out-of-source builds. +``` + +```{hint} +add `-test` to the call of your TOPP tool and also create the expected output that you put in `src/tests/topp` with that +flag active. The flag ensures that UniqueId's, dates etc are equal no matter where and when the tool is run. +``` + +## What do I have to do to add a new UTILS tool? + +- Add the code to `src/utils/` and register it in `src/utils/executables.cmake`. +- Add your tool to `getUtilList()` in `src/openms/source/APPLICATIONS/ToolHandler.cpp`. This creates a doxygen page with + the `–help` output of the tool (using `TOPPDocumenter`). This page must be included at the end of the doxygen + documentation of your tool (see other tools for an example). +- Add it to the UTILS docu page (in `doc/doxygen/public/UTILS.doxygen`) +- Write a test (this is optional for UTILS). See TOPP tools above and add the test to the bottom of `src/tests/topp/CMakeLists.txt`. + +## I want to implement a new file adapter. What is to be done? + +First, add a file adapter class to the `include/OpenMS/FORMAT/` and `source/FORMAT/` folders. The file adapter should +implement a default constructor, a load method and a store method. Make sure your code conforms to the OpenMS Coding +conventions. For automatic file type recognition, you need to + +- register your new file type at the Type enum in `/include/OpenMS/FORMAT/FileTypes.h`, +- flag the file type as supported in the isSupported method of `/source/FORMAT/FileHandler.C` +- register the file extension in the getTypeByFileName method of `/source/FORMAT/FileHandler.C` + +If the new file is a peak or feature file format you should also add it to loadExperiment or loadFeatures, respectively, +of the FileHandler class. To add the file format to the TOPPView open dialog, you have to modify the file +`/source/APPLICATIONS/TOPPViewBase.C`. + +- Add the file extensions to the filter_all and filter_single variables of the getFileList_ method. + +To add your format to TOPP applications: + +- add the file extension to the extensions list of the respective parameter: + ``` + e.g. setValidStrings_("in_type", StringList::create("mzData,mzXML,mzML")); in FileInfo + ``` + +## How to create an icon file for a TOPP tool under Windows? + +- Create an .ico file: first, you need some graphics program (The GIMP is recommended) think of a motive and remind + yourself that you have limited space. Create at least a 16x16, 32x32, 48x48 and 64x64 pixel version and save each of + them in a separate layer of the respective size. Do not add any larger sized layers, since Win XP will not display any + icon then. When saving the image as type `.ico` the GIMP will ask you for the color depth of each layer. As it is + recommended to have multiple color depths of each icon-size, go back to the layers and duplicate each layer twice. + That should give you 12 layers. Now, save the image as `.ico` (e.g. TOPPView.ico) file, giving each group of equal + sized layers a 32 bit (8 bit transparency), 8 bit (1 bit transparency), 4 bit (1 bit transparency) color depth. + +```{attention} +Make sure to assign the higher color depth to the upper layers as Windows will not pick the highest possible color +otherwise. +``` + +- Create a resource file: Create a text file named `.rc` (e.g. TOPPView.rc) Insert the following line: 101 ICON + "TOPPView.ico" , replacing TOPPView with your binary name. Put both files in `OpenMS/source/APPLICATIONS/TOPP/` + (similar files for other TOPP tools already present). Re-run cmake and re-link your TOPP tool. + +Voila. You should have an iconized TOPP tool. + +## Develop your Tool in an external project using OpenMS + +To include the OpenMS library in one of your projects, we recommend to have a look at a small emulated external project +in our repository. We strongly suggest to use CMake for building your project together with OpenMS to make use of the +macros and environment information generated during the build of the OpenMS library. + +## The Common Tool Description (CTD) + +The CTD is a format developed from the OpenMS team to allow the user to use TOPP tools also in other workflow engines. +Each tool can output a CTD description of itself (the XML scheme for the CTD can be found here), which can then be used +by a node generator program to generate nodes for different workflow engines. The CTD mechanism is shared by OpenMS with +other mature libraries like SeqAn and BALL. An example for a node generation program are the Generic KNIME Nodes. The +most complete description on how to generate your own Generic KNIME Nodes based on a CTD (e.g. from your freshly +developed command line tool), can be found on the SeqAn documentation. We are working on a tutorial specifically +tailored to OpenMS.