diff --git a/README.txt b/README.txt new file mode 100644 index 0000000000000000000000000000000000000000..030670ed8324ad7b7ba5506d33fc56f0c44300c5 --- /dev/null +++ b/README.txt @@ -0,0 +1,11 @@ +This is a code example of modification of DMPs. + +Requirements: + +g++ compiler + +Armadillo C++ Linear Algebra Library +http://arma.sourceforge.net/ + +Note: Before installing Armadillo, it's required to have LAPACK and BLAS installed, along with the corresponding development/header files. + diff --git a/gnuplot-cpp/Makefile b/gnuplot-cpp/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..9dbfe1a88dd3ff5e13f887eb6e9ddd7bff97003f --- /dev/null +++ b/gnuplot-cpp/Makefile @@ -0,0 +1,20 @@ +CFLAGS = -ggdb +DEFINES = -DDEBUGGA +INCLUDES = +LIBS = -lstdc++ +EXAMPLE = example.o +CC=g++ + +.cc.o: + $(CC) -c $(CFLAGS) $(DEFINES) $(INCLUDES) $< + +all:: example + +gnuplot_i.o: gnuplot_i.hpp +example.o: example.cc + +example: $(EXAMPLE) + $(CC) -o $@ $(CFLAGS) $(EXAMPLE) $(LIBS) + +clean: + rm -f $(EXAMPLE) example diff --git a/gnuplot-cpp/doc/Doxyfile b/gnuplot-cpp/doc/Doxyfile new file mode 100644 index 0000000000000000000000000000000000000000..ee1462ca1d337f2f035029f5aa18694e8a48dd70 --- /dev/null +++ b/gnuplot-cpp/doc/Doxyfile @@ -0,0 +1,246 @@ +# Doxyfile 1.5.6 + +#--------------------------------------------------------------------------- +# Project related configuration options +#--------------------------------------------------------------------------- +DOXYFILE_ENCODING = UTF-8 +PROJECT_NAME = gnuplot-cpp +PROJECT_NUMBER = 0.9 +OUTPUT_DIRECTORY = ./ +CREATE_SUBDIRS = YES +OUTPUT_LANGUAGE = English +BRIEF_MEMBER_DESC = YES +REPEAT_BRIEF = YES +ABBREVIATE_BRIEF = +ALWAYS_DETAILED_SEC = NO +INLINE_INHERITED_MEMB = NO +FULL_PATH_NAMES = NO +STRIP_FROM_PATH = +STRIP_FROM_INC_PATH = +SHORT_NAMES = NO +JAVADOC_AUTOBRIEF = NO +QT_AUTOBRIEF = NO +MULTILINE_CPP_IS_BRIEF = NO +DETAILS_AT_TOP = NO +INHERIT_DOCS = YES +SEPARATE_MEMBER_PAGES = NO +TAB_SIZE = 8 +ALIASES = +OPTIMIZE_OUTPUT_FOR_C = NO +OPTIMIZE_OUTPUT_JAVA = NO +OPTIMIZE_FOR_FORTRAN = NO +OPTIMIZE_OUTPUT_VHDL = NO +BUILTIN_STL_SUPPORT = NO +CPP_CLI_SUPPORT = NO +SIP_SUPPORT = NO +IDL_PROPERTY_SUPPORT = YES +DISTRIBUTE_GROUP_DOC = NO +SUBGROUPING = YES +TYPEDEF_HIDES_STRUCT = NO +#--------------------------------------------------------------------------- +# Build related configuration options +#--------------------------------------------------------------------------- +EXTRACT_ALL = YES +EXTRACT_PRIVATE = NO +EXTRACT_STATIC = NO +EXTRACT_LOCAL_CLASSES = YES +EXTRACT_LOCAL_METHODS = NO +EXTRACT_ANON_NSPACES = NO +HIDE_UNDOC_MEMBERS = NO +HIDE_UNDOC_CLASSES = NO +HIDE_FRIEND_COMPOUNDS = NO +HIDE_IN_BODY_DOCS = NO +INTERNAL_DOCS = NO +CASE_SENSE_NAMES = NO +HIDE_SCOPE_NAMES = NO +SHOW_INCLUDE_FILES = YES +INLINE_INFO = YES +SORT_MEMBER_DOCS = YES +SORT_BRIEF_DOCS = NO +SORT_GROUP_NAMES = NO +SORT_BY_SCOPE_NAME = NO +GENERATE_TODOLIST = YES +GENERATE_TESTLIST = YES +GENERATE_BUGLIST = YES +GENERATE_DEPRECATEDLIST= YES +ENABLED_SECTIONS = +MAX_INITIALIZER_LINES = 30 +SHOW_USED_FILES = YES +SHOW_DIRECTORIES = NO +SHOW_FILES = YES +SHOW_NAMESPACES = YES +FILE_VERSION_FILTER = +#--------------------------------------------------------------------------- +# configuration options related to warning and progress messages +#--------------------------------------------------------------------------- +QUIET = NO +WARNINGS = YES +WARN_IF_UNDOCUMENTED = YES +WARN_IF_DOC_ERROR = YES +WARN_NO_PARAMDOC = NO +WARN_FORMAT = "$file:$line: $text" +WARN_LOGFILE = +#--------------------------------------------------------------------------- +# configuration options related to the input files +#--------------------------------------------------------------------------- +INPUT = ../ +INPUT_ENCODING = UTF-8 +FILE_PATTERNS = +RECURSIVE = NO +EXCLUDE = +EXCLUDE_SYMLINKS = NO +EXCLUDE_PATTERNS = +EXCLUDE_SYMBOLS = +EXAMPLE_PATH = ../example.cc +EXAMPLE_PATTERNS = +EXAMPLE_RECURSIVE = NO +IMAGE_PATH = +INPUT_FILTER = +FILTER_PATTERNS = +FILTER_SOURCE_FILES = NO +#--------------------------------------------------------------------------- +# configuration options related to source browsing +#--------------------------------------------------------------------------- +SOURCE_BROWSER = YES +INLINE_SOURCES = YES +STRIP_CODE_COMMENTS = YES +REFERENCED_BY_RELATION = YES +REFERENCES_RELATION = YES +REFERENCES_LINK_SOURCE = YES +USE_HTAGS = NO +VERBATIM_HEADERS = YES +#--------------------------------------------------------------------------- +# configuration options related to the alphabetical class index +#--------------------------------------------------------------------------- +ALPHABETICAL_INDEX = NO +COLS_IN_ALPHA_INDEX = 5 +IGNORE_PREFIX = +#--------------------------------------------------------------------------- +# configuration options related to the HTML output +#--------------------------------------------------------------------------- +GENERATE_HTML = YES +HTML_OUTPUT = html +HTML_FILE_EXTENSION = .html +HTML_HEADER = +HTML_FOOTER = +HTML_STYLESHEET = +HTML_ALIGN_MEMBERS = YES +GENERATE_HTMLHELP = NO +GENERATE_DOCSET = NO +DOCSET_FEEDNAME = "Doxygen generated docs" +DOCSET_BUNDLE_ID = org.doxygen.Project +HTML_DYNAMIC_SECTIONS = NO +CHM_FILE = +HHC_LOCATION = +GENERATE_CHI = NO +CHM_INDEX_ENCODING = +BINARY_TOC = NO +TOC_EXPAND = NO +DISABLE_INDEX = NO +ENUM_VALUES_PER_LINE = 4 +GENERATE_TREEVIEW = NO +TREEVIEW_WIDTH = 250 +FORMULA_FONTSIZE = 10 +#--------------------------------------------------------------------------- +# configuration options related to the LaTeX output +#--------------------------------------------------------------------------- +GENERATE_LATEX = YES +LATEX_OUTPUT = latex +LATEX_CMD_NAME = latex +MAKEINDEX_CMD_NAME = makeindex +COMPACT_LATEX = NO +PAPER_TYPE = a4wide +EXTRA_PACKAGES = +LATEX_HEADER = +PDF_HYPERLINKS = NO +USE_PDFLATEX = YES +LATEX_BATCHMODE = NO +LATEX_HIDE_INDICES = NO +#--------------------------------------------------------------------------- +# configuration options related to the RTF output +#--------------------------------------------------------------------------- +GENERATE_RTF = NO +RTF_OUTPUT = rtf +COMPACT_RTF = NO +RTF_HYPERLINKS = NO +RTF_STYLESHEET_FILE = +RTF_EXTENSIONS_FILE = +#--------------------------------------------------------------------------- +# configuration options related to the man page output +#--------------------------------------------------------------------------- +GENERATE_MAN = NO +MAN_OUTPUT = man +MAN_EXTENSION = .3 +MAN_LINKS = NO +#--------------------------------------------------------------------------- +# configuration options related to the XML output +#--------------------------------------------------------------------------- +GENERATE_XML = NO +XML_OUTPUT = xml +XML_SCHEMA = +XML_DTD = +XML_PROGRAMLISTING = YES +#--------------------------------------------------------------------------- +# configuration options for the AutoGen Definitions output +#--------------------------------------------------------------------------- +GENERATE_AUTOGEN_DEF = NO +#--------------------------------------------------------------------------- +# configuration options related to the Perl module output +#--------------------------------------------------------------------------- +GENERATE_PERLMOD = NO +PERLMOD_LATEX = NO +PERLMOD_PRETTY = YES +PERLMOD_MAKEVAR_PREFIX = +#--------------------------------------------------------------------------- +# Configuration options related to the preprocessor +#--------------------------------------------------------------------------- +ENABLE_PREPROCESSING = YES +MACRO_EXPANSION = NO +EXPAND_ONLY_PREDEF = NO +SEARCH_INCLUDES = YES +INCLUDE_PATH = +INCLUDE_FILE_PATTERNS = +PREDEFINED = +EXPAND_AS_DEFINED = +SKIP_FUNCTION_MACROS = YES +#--------------------------------------------------------------------------- +# Configuration::additions related to external references +#--------------------------------------------------------------------------- +TAGFILES = +GENERATE_TAGFILE = +ALLEXTERNALS = NO +EXTERNAL_GROUPS = YES +PERL_PATH = /usr/bin/perl +#--------------------------------------------------------------------------- +# Configuration options related to the dot tool +#--------------------------------------------------------------------------- +CLASS_DIAGRAMS = YES +MSCGEN_PATH = +HIDE_UNDOC_RELATIONS = YES +HAVE_DOT = NO +DOT_FONTNAME = FreeSans +DOT_FONTPATH = +CLASS_GRAPH = YES +COLLABORATION_GRAPH = YES +GROUP_GRAPHS = YES +UML_LOOK = NO +TEMPLATE_RELATIONS = NO +INCLUDE_GRAPH = YES +INCLUDED_BY_GRAPH = YES +CALL_GRAPH = NO +CALLER_GRAPH = NO +GRAPHICAL_HIERARCHY = YES +DIRECTORY_GRAPH = YES +DOT_IMAGE_FORMAT = png +DOT_PATH = +DOTFILE_DIRS = +DOT_GRAPH_MAX_NODES = 50 +MAX_DOT_GRAPH_DEPTH = 0 +DOT_TRANSPARENT = YES +DOT_MULTI_TARGETS = NO +GENERATE_LEGEND = YES +DOT_CLEANUP = YES +#--------------------------------------------------------------------------- +# Configuration::additions related to the search engine +#--------------------------------------------------------------------------- +SEARCHENGINE = NO diff --git a/gnuplot-cpp/example b/gnuplot-cpp/example new file mode 100755 index 0000000000000000000000000000000000000000..73a6e690c79be95da0ff2781261f576768c005fd Binary files /dev/null and b/gnuplot-cpp/example differ diff --git a/gnuplot-cpp/example.cc b/gnuplot-cpp/example.cc new file mode 100644 index 0000000000000000000000000000000000000000..3bbb69ee3d70e01e06c776bd749c1205b1de1b0f --- /dev/null +++ b/gnuplot-cpp/example.cc @@ -0,0 +1,260 @@ +// Example for C++ Interface to Gnuplot + +// requirements: +// * gnuplot has to be installed (http://www.gnuplot.info/download.html) +// * for Windows: set Path-Variable for Gnuplot path (e.g. C:/program files/gnuplot/bin) +// or set Gnuplot path with: Gnuplot::set_GNUPlotPath(const std::string &path); + + +#include <iostream> +#include "gnuplot_i.hpp" //Gnuplot class handles POSIX-Pipe-communikation with Gnuplot + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + #include <conio.h> //for getch(), needed in wait_for_key() + #include <windows.h> //for Sleep() + void sleep(int i) { Sleep(i*1000); } +#endif + + +#define SLEEP_LGTH 2 // sleep time in seconds +#define NPOINTS 50 // length of array + +void wait_for_key(); // Programm halts until keypress + +using std::cout; +using std::endl; + +int main(int argc, char* argv[]) +{ + // if path-variable for gnuplot is not set, do it with: + // Gnuplot::set_GNUPlotPath("C:/program files/gnuplot/bin/"); + + // set a special standard terminal for showonscreen (normally not needed), + // e.g. Mac users who want to use x11 instead of aqua terminal: + // Gnuplot::set_terminal_std("x11"); + + cout << "*** example of gnuplot control through C++ ***" << endl << endl; + + // + // Using the GnuplotException class + // + try + { + Gnuplot g1("lines"); + + // + // Slopes + // + cout << "*** plotting slopes" << endl; + g1.set_title("Slopes\\nNew Line"); + + cout << "y = x" << endl; + g1.plot_slope(1.0,0.0,"y=x"); + + cout << "y = 2*x" << endl; + g1.plot_slope(2.0,0.0,"y=2x"); + + cout << "y = -x" << endl; + g1.plot_slope(-1.0,0.0,"y=-x"); + g1.unset_title(); + + // + // Equations + // + g1.reset_plot(); + cout << endl << endl << "*** various equations" << endl; + + cout << "y = sin(x)" << endl; + g1.plot_equation("sin(x)","sine"); + + cout << "y = log(x)" << endl; + g1.plot_equation("log(x)","logarithm"); + + cout << "y = sin(x) * cos(2*x)" << endl; + g1.plot_equation("sin(x)*cos(2*x)","sine product"); + + // + // Styles + // + g1.reset_plot(); + cout << endl << endl << "*** showing styles" << endl; + + cout << "sine in points" << endl; + g1.set_pointsize(0.8).set_style("points"); + g1.plot_equation("sin(x)","points"); + + cout << "sine in impulses" << endl; + g1.set_style("impulses"); + g1.plot_equation("sin(x)","impulses"); + + cout << "sine in steps" << endl; + g1.set_style("steps"); + g1.plot_equation("sin(x)","steps"); + + // + // Save to ps + // + g1.reset_all(); + cout << endl << endl << "*** save to ps " << endl; + + cout << "y = sin(x) saved to test_output.ps in working directory" << endl; + g1.savetops("test_output"); + g1.set_style("lines").set_samples(300).set_xrange(0,5); + g1.plot_equation("sin(12*x)*exp(-x)").plot_equation("exp(-x)"); + + g1.showonscreen(); // window output + + + // + // User defined 1d, 2d and 3d point sets + // + std::vector<double> x, y, y2, dy, z; + + for (int i = 0; i < NPOINTS; i++) // fill double arrays x, y, z + { + x.push_back((double)i); // x[i] = i + y.push_back((double)i * (double)i); // y[i] = i^2 + z.push_back( x[i]*y[i] ); // z[i] = x[i]*y[i] = i^3 + dy.push_back((double)i * (double)i / (double) 10); // dy[i] = i^2 / 10 + } + y2.push_back(0.00); y2.push_back(0.78); y2.push_back(0.97); y2.push_back(0.43); + y2.push_back(-0.44); y2.push_back(-0.98); y2.push_back(-0.77); y2.push_back(0.02); + + + g1.reset_all(); + cout << endl << endl << "*** user-defined lists of doubles" << endl; + g1.set_style("impulses").plot_x(y,"user-defined doubles"); + + g1.reset_plot(); + cout << endl << endl << "*** user-defined lists of points (x,y)" << endl; + g1.set_grid(); + g1.set_style("points").plot_xy(x,y,"user-defined points 2d"); + + g1.reset_plot(); + cout << endl << endl << "*** user-defined lists of points (x,y,z)" << endl; + g1.unset_grid(); + g1.plot_xyz(x,y,z,"user-defined points 3d"); + + wait_for_key(); + + g1.reset_plot(); + cout << endl << endl << "*** user-defined lists of points (x,y,dy)" << endl; + g1.plot_xy_err(x,y,dy,"user-defined points 2d with errorbars"); + + + // + // Multiple output screens + // + cout << endl << endl; + cout << "*** multiple output windows" << endl; + + g1.reset_plot(); + g1.set_style("lines"); + cout << "window 1: sin(x)" << endl; + g1.set_grid().set_samples(600).set_xrange(0,300); + g1.plot_equation("sin(x)+sin(x*1.1)"); + + g1.set_xautoscale().replot(); + + Gnuplot g2; + cout << "window 2: user defined points" << endl; + g2.plot_x(y2,"points"); + g2.set_smooth().plot_x(y2,"cspline"); + g2.set_smooth("bezier").plot_x(y2,"bezier"); + g2.unset_smooth(); + + Gnuplot g3("lines"); + cout << "window 3: log(x)/x" << endl; + g3.set_grid(); + g3.plot_equation("log(x)/x","log(x)/x"); + + Gnuplot g4("lines"); + cout << "window 4: splot x*x+y*y" << endl; + g4.set_zrange(0,100); + g4.set_xlabel("x-axis").set_ylabel("y-axis").set_zlabel("z-axis"); + g4.plot_equation3d("x*x+y*y"); + + Gnuplot g5("lines"); + cout << "window 5: splot with hidden3d" << endl; + g5.set_isosamples(25).set_hidden3d(); + g5.plot_equation3d("x*y*y"); + + Gnuplot g6("lines"); + cout << "window 6: splot with contour" << endl; + g6.set_isosamples(60).set_contour(); + g6.unset_surface().plot_equation3d("sin(x)*sin(y)+4"); + + g6.set_surface().replot(); + + Gnuplot g7("lines"); + cout << "window 7: set_samples" << endl; + g7.set_xrange(-30,20).set_samples(40); + g7.plot_equation("besj0(x)*0.12e1").plot_equation("(x**besj0(x))-2.5"); + + g7.set_samples(400).replot(); + + Gnuplot g8("filledcurves"); + cout << "window 8: filledcurves" << endl; + g8.set_legend("outside right top").set_xrange(-5,5); + g8.plot_equation("x*x").plot_equation("-x*x+4"); + + // + // Plot an image + // + Gnuplot g9; + cout << "window 9: plot_image" << endl; + const int iWidth = 255; + const int iHeight = 255; + g9.set_xrange(0,iWidth).set_yrange(0,iHeight).set_cbrange(0,255); + g9.cmd("set palette gray"); + unsigned char ucPicBuf[iWidth*iHeight]; + // generate a greyscale image + for(int iIndex = 0; iIndex < iHeight*iWidth; iIndex++) + { + ucPicBuf[iIndex] = iIndex%255; + } + g9.plot_image(ucPicBuf,iWidth,iHeight,"greyscale"); + + g9.set_pointsize(0.6).unset_legend().plot_slope(0.8,20); + + // + // manual control + // + Gnuplot g10; + cout << "window 10: manual control" << endl; + g10.cmd("set samples 400").cmd("plot abs(x)/2"); // either with cmd() + g10 << "replot sqrt(x)" << "replot sqrt(-x)"; // or with << + + wait_for_key(); + + } + catch (GnuplotException ge) + { + cout << ge.what() << endl; + } + + + cout << endl << "*** end of gnuplot example" << endl; + + return 0; + +} + + + +void wait_for_key () +{ +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) // every keypress registered, also arrow keys + cout << endl << "Press any key to continue..." << endl; + + FlushConsoleInputBuffer(GetStdHandle(STD_INPUT_HANDLE)); + _getch(); +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + cout << endl << "Press ENTER to continue..." << endl; + + std::cin.clear(); + std::cin.ignore(std::cin.rdbuf()->in_avail()); + std::cin.get(); +#endif + return; +} diff --git a/gnuplot-cpp/gnuplot_i.hpp b/gnuplot-cpp/gnuplot_i.hpp new file mode 100644 index 0000000000000000000000000000000000000000..7d0a95d1fd69276a155eb9d6b68570fd654a254e --- /dev/null +++ b/gnuplot-cpp/gnuplot_i.hpp @@ -0,0 +1,1957 @@ +//////////////////////////////////////////////////////////////////////////////// +/// +/// \brief A C++ interface to gnuplot. +/// +/// +/// The interface uses pipes and so won't run on a system that doesn't have +/// POSIX pipe support Tested on Windows (MinGW and Visual C++) and Linux (GCC) +/// +/// Version history: +/// 0. C interface +/// by N. Devillard (27/01/03) +/// 1. C++ interface: direct translation from the C interface +/// by Rajarshi Guha (07/03/03) +/// 2. corrections for Win32 compatibility +/// by V. Chyzhdzenka (20/05/03) +/// 3. some member functions added, corrections for Win32 and Linux +/// compatibility +/// by M. Burgis (10/03/08) +/// +/// Requirements: +/// * gnuplot has to be installed (http://www.gnuplot.info/download.html) +/// * for Windows: set Path-Variable for Gnuplot path +/// (e.g. C:/program files/gnuplot/bin) +/// or set Gnuplot path with: +/// Gnuplot::set_GNUPlotPath(const std::string &path); +/// +//////////////////////////////////////////////////////////////////////////////// + + +#ifndef _GNUPLOT_PIPES_H_ +#define _GNUPLOT_PIPES_H_ + + +#include <iostream> +#include <string> +#include <vector> +#include <fstream> +#include <sstream> // for std::ostringstream +#include <stdexcept> +#include <cstdio> +#include <cstdlib> // for getenv() +#include <list> // for std::list + + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) +//defined for 32 and 64-bit environments + #include <io.h> // for _access(), _mktemp() + #define GP_MAX_TMP_FILES 27 // 27 temporary files it's Microsoft restriction +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) +//all UNIX-like OSs (Linux, *BSD, MacOSX, Solaris, ...) + #include <unistd.h> // for access(), mkstemp() + #define GP_MAX_TMP_FILES 64 +#else + #error unsupported or unknown operating system +#endif + +//declare classes in global namespace + + +class GnuplotException : public std::runtime_error +{ + public: + GnuplotException(const std::string &msg) : std::runtime_error(msg){} +}; + + + +class Gnuplot +{ + private: + + //---------------------------------------------------------------------------------- + // member data + ///\brief pointer to the stream that can be used to write to the pipe + FILE *gnucmd; + ///\brief validation of gnuplot session + bool valid; + ///\brief true = 2d, false = 3d + bool two_dim; + ///\brief number of plots in session + int nplots; + ///\brief functions and data are displayed in a defined styles + std::string pstyle; + ///\brief interpolate and approximate data in defined styles (e.g. spline) + std::string smooth; + ///\brief list of created tmpfiles + std::vector<std::string> tmpfile_list; + + //---------------------------------------------------------------------------------- + // static data + ///\brief number of all tmpfiles (number of tmpfiles restricted) + static int tmpfile_num; + ///\brief name of executed GNUPlot file + static std::string m_sGNUPlotFileName; + ///\brief gnuplot path + static std::string m_sGNUPlotPath; + ///\brief standart terminal, used by showonscreen + static std::string terminal_std; + + //---------------------------------------------------------------------------------- + // member functions (auxiliary functions) + // --------------------------------------------------- + ///\brief get_program_path(); and popen(); + /// + /// \param --> void + /// + /// \return <-- void + // --------------------------------------------------- + void init(); + // --------------------------------------------------- + ///\brief creates tmpfile and returns its name + /// + /// \param tmp --> points to the tempfile + /// + /// \return <-- the name of the tempfile + // --------------------------------------------------- + std::string create_tmpfile(std::ofstream &tmp); + + //---------------------------------------------------------------------------------- + ///\brief gnuplot path found? + /// + /// \param --- + /// + /// \return <-- found the gnuplot path (yes == true, no == false) + // --------------------------------------------------------------------------------- + static bool get_program_path(); + + // --------------------------------------------------------------------------------- + ///\brief checks if file is available + /// + /// \param filename --> the filename + /// \param mode --> the mode [optional,default value = 0] + /// + /// \return file exists (yes == true, no == false) + // --------------------------------------------------------------------------------- + bool file_available(const std::string &filename); + + // --------------------------------------------------------------------------------- + ///\brief checks if file exists + /// + /// \param filename --> the filename + /// \param mode --> the mode [optional,default value = 0] + /// + /// \return file exists (yes == true, no == false) + // --------------------------------------------------------------------------------- + static bool file_exists(const std::string &filename, int mode=0); + + public: + + // ---------------------------------------------------------------------------- + /// \brief optional function: set Gnuplot path manual + /// attention: for windows: path with slash '/' not backslash '\' + /// + /// \param path --> the gnuplot path + /// + /// \return true on success, false otherwise + // ---------------------------------------------------------------------------- + static bool set_GNUPlotPath(const std::string &path); + + + // ---------------------------------------------------------------------------- + /// optional: set standart terminal, used by showonscreen + /// defaults: Windows - win, Linux - x11, Mac - aqua + /// + /// \param type --> the terminal type + /// + /// \return --- + // ---------------------------------------------------------------------------- + static void set_terminal_std(const std::string &type); + + //----------------------------------------------------------------------------- + // constructors + // ---------------------------------------------------------------------------- + + + ///\brief set a style during construction + Gnuplot(const std::string &style = "points"); + + /// plot a single std::vector at one go + Gnuplot(const std::vector<double> &x, + const std::string &title = "", + const std::string &style = "points", + const std::string &labelx = "x", + const std::string &labely = "y"); + + /// plot pairs std::vector at one go + Gnuplot(const std::vector<double> &x, + const std::vector<double> &y, + const std::string &title = "", + const std::string &style = "points", + const std::string &labelx = "x", + const std::string &labely = "y"); + + /// plot triples std::vector at one go + Gnuplot(const std::vector<double> &x, + const std::vector<double> &y, + const std::vector<double> &z, + const std::string &title = "", + const std::string &style = "points", + const std::string &labelx = "x", + const std::string &labely = "y", + const std::string &labelz = "z"); + + /// destructor: needed to delete temporary files + ~Gnuplot(); + + + //---------------------------------------------------------------------------------- + + /// send a command to gnuplot + Gnuplot& cmd(const std::string &cmdstr); + // --------------------------------------------------------------------------------- + ///\brief Sends a command to an active gnuplot session, identical to cmd() + /// send a command to gnuplot using the << operator + /// + /// \param cmdstr --> the command string + /// + /// \return <-- a reference to the gnuplot object + // --------------------------------------------------------------------------------- + inline Gnuplot& operator<<(const std::string &cmdstr){ + cmd(cmdstr); + return(*this); + } + + + + //---------------------------------------------------------------------------------- + // show on screen or write to file + + /// sets terminal type to terminal_std + Gnuplot& showonscreen(); // window output is set by default (win/x11/aqua) + + /// saves a gnuplot session to a postscript file, filename without extension + Gnuplot& savetops(const std::string &filename = "gnuplot_output"); + + + //---------------------------------------------------------------------------------- + // set and unset + + /// set line style (some of these styles require additional information): + /// lines, points, linespoints, impulses, dots, steps, fsteps, histeps, + /// boxes, histograms, filledcurves + Gnuplot& set_style(const std::string &stylestr = "points"); + + /// interpolation and approximation of data, arguments: + /// csplines, bezier, acsplines (for data values > 0), sbezier, unique, frequency + /// (works only with plot_x, plot_xy, plotfile_x, plotfile_xy + /// (if smooth is set, set_style has no effekt on data plotting) + Gnuplot& set_smooth(const std::string &stylestr = "csplines"); + + // ---------------------------------------------------------------------- + /// \brief unset smooth + /// attention: smooth is not set by default + /// + /// \param --- + /// + /// \return <-- a reference to a gnuplot object + // ---------------------------------------------------------------------- + inline Gnuplot& unset_smooth(){ smooth = ""; return *this;}; + + + /// scales the size of the points used in plots + Gnuplot& set_pointsize(const double pointsize = 1.0); + + /// turns grid on/off + inline Gnuplot& set_grid() {cmd("set grid");return *this;}; + /// grid is not set by default + inline Gnuplot& unset_grid(){cmd("unset grid");return *this;}; + + // ----------------------------------------------- + /// set the mulitplot mode + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& set_multiplot(){cmd("set multiplot") ;return *this;}; + + // ----------------------------------------------- + /// unsets the mulitplot mode + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& unset_multiplot(){cmd("unset multiplot");return *this;}; + + + + /// set sampling rate of functions, or for interpolating data + Gnuplot& set_samples(const int samples = 100); + /// set isoline density (grid) for plotting functions as surfaces (for 3d plots) + Gnuplot& set_isosamples(const int isolines = 10); + + // -------------------------------------------------------------------------- + /// enables/disables hidden line removal for surface plotting (for 3d plot) + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // -------------------------------------------------------------------------- + Gnuplot& set_hidden3d(){cmd("set hidden3d");return *this;}; + + // --------------------------------------------------------------------------- + /// hidden3d is not set by default + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // --------------------------------------------------------------------------- + inline Gnuplot& unset_hidden3d(){cmd("unset hidden3d"); return *this;}; + + /// enables/disables contour drawing for surfaces (for 3d plot) + /// base, surface, both + Gnuplot& set_contour(const std::string &position = "base"); + // -------------------------------------------------------------------------- + /// contour is not set by default, it disables contour drawing for surfaces + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ------------------------------------------------------------------ + inline Gnuplot& unset_contour(){cmd("unset contour");return *this;}; + + // ------------------------------------------------------------ + /// enables/disables the display of surfaces (for 3d plot) + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ------------------------------------------------------------------ + inline Gnuplot& set_surface(){cmd("set surface");return *this;}; + + // ---------------------------------------------------------- + /// surface is set by default, + /// it disables the display of surfaces (for 3d plot) + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ------------------------------------------------------------------ + inline Gnuplot& unset_surface(){cmd("unset surface"); return *this;} + + + /// switches legend on/off + /// position: inside/outside, left/center/right, top/center/bottom, nobox/box + Gnuplot& set_legend(const std::string &position = "default"); + + // ------------------------------------------------------------------ + /// \brief Switches legend off + /// attention:legend is set by default + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ------------------------------------------------------------------ + inline Gnuplot& unset_legend(){cmd("unset key"); return *this;} + + // ----------------------------------------------------------------------- + /// \brief sets and clears the title of a gnuplot session + /// + /// \param title --> the title of the plot [optional, default == ""] + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------------------------------- + inline Gnuplot& set_title(const std::string &title = "") + { + std::string cmdstr; + cmdstr = "set title \""; + cmdstr+=title; + cmdstr+="\""; + *this<<cmdstr; + return *this; + } + + //---------------------------------------------------------------------------------- + ///\brief Clears the title of a gnuplot session + /// The title is not set by default. + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // --------------------------------------------------------------------------------- + inline Gnuplot& unset_title(){this->set_title();return *this;} + + + /// set x axis label + Gnuplot& set_ylabel(const std::string &label = "x"); + /// set y axis label + Gnuplot& set_xlabel(const std::string &label = "y"); + /// set z axis label + Gnuplot& set_zlabel(const std::string &label = "z"); + + /// set axis - ranges + Gnuplot& set_xrange(const double iFrom, + const double iTo); + /// set y-axis - ranges + Gnuplot& set_yrange(const double iFrom, + const double iTo); + /// set z-axis - ranges + Gnuplot& set_zrange(const double iFrom, + const double iTo); + /// autoscale axis (set by default) of xaxis + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& set_xautoscale(){cmd("set xrange restore");cmd("set autoscale x");return *this;}; + + // ----------------------------------------------- + /// autoscale axis (set by default) of yaxis + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& set_yautoscale(){cmd("set yrange restore");cmd("set autoscale y");return *this;}; + + // ----------------------------------------------- + /// autoscale axis (set by default) of zaxis + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& set_zautoscale(){cmd("set zrange restore");cmd("set autoscale z");return *this;}; + + + /// turns on/off log scaling for the specified xaxis (logscale is not set by default) + Gnuplot& set_xlogscale(const double base = 10); + /// turns on/off log scaling for the specified yaxis (logscale is not set by default) + Gnuplot& set_ylogscale(const double base = 10); + /// turns on/off log scaling for the specified zaxis (logscale is not set by default) + Gnuplot& set_zlogscale(const double base = 10); + + // ----------------------------------------------- + /// turns off log scaling for the x axis + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& unset_xlogscale(){cmd("unset logscale x"); return *this;}; + + // ----------------------------------------------- + /// turns off log scaling for the y axis + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& unset_ylogscale(){cmd("unset logscale y"); return *this;}; + + // ----------------------------------------------- + /// turns off log scaling for the z axis + /// + /// \param --- + /// + /// \return <-- reference to the gnuplot object + // ----------------------------------------------- + inline Gnuplot& unset_zlogscale(){cmd("unset logscale z"); return *this;}; + + + /// set palette range (autoscale by default) + Gnuplot& set_cbrange(const double iFrom, const double iTo); + + + //---------------------------------------------------------------------------------- + // plot + + /// plot a single std::vector: x + /// from file + Gnuplot& plotfile_x(const std::string &filename, + const unsigned int column = 1, + const std::string &title = ""); + /// from std::vector + template<typename X> + Gnuplot& plot_x(const X& x, const std::string &title = ""); + + + /// plot x,y pairs: x y + /// from file + Gnuplot& plotfile_xy(const std::string &filename, + const unsigned int column_x = 1, + const unsigned int column_y = 2, + const std::string &title = ""); + /// from data + template<typename X, typename Y> + Gnuplot& plot_xy(const X& x, const Y& y, const std::string &title = ""); + + + /// plot x,y pairs with dy errorbars: x y dy + /// from file + Gnuplot& plotfile_xy_err(const std::string &filename, + const unsigned int column_x = 1, + const unsigned int column_y = 2, + const unsigned int column_dy = 3, + const std::string &title = ""); + /// from data + template<typename X, typename Y, typename E> + Gnuplot& plot_xy_err(const X &x, const Y &y, const E &dy, + const std::string &title = ""); + + + /// plot x,y,z triples: x y z + /// from file + Gnuplot& plotfile_xyz(const std::string &filename, + const unsigned int column_x = 1, + const unsigned int column_y = 2, + const unsigned int column_z = 3, + const std::string &title = ""); + /// from std::vector + template<typename X, typename Y, typename Z> + Gnuplot& plot_xyz(const X &x, + const Y &y, + const Z &z, + const std::string &title = ""); + + + + /// plot an equation of the form: y = ax + b, you supply a and b + Gnuplot& plot_slope(const double a, + const double b, + const std::string &title = ""); + + + /// plot an equation supplied as a std::string y=f(x), write only the function f(x) not y= + /// the independent variable has to be x + /// binary operators: ** exponentiation, * multiply, / divide, + add, - substract, % modulo + /// unary operators: - minus, ! factorial + /// elementary functions: rand(x), abs(x), sgn(x), ceil(x), floor(x), int(x), imag(x), real(x), arg(x), + /// sqrt(x), exp(x), log(x), log10(x), sin(x), cos(x), tan(x), asin(x), acos(x), atan(x), atan2(y,x), + /// sinh(x), cosh(x), tanh(x), asinh(x), acosh(x), atanh(x) + /// special functions: erf(x), erfc(x), inverf(x), gamma(x), igamma(a,x), lgamma(x), ibeta(p,q,x), + /// besj0(x), besj1(x), besy0(x), besy1(x), lambertw(x) + /// statistical fuctions: norm(x), invnorm(x) + Gnuplot& plot_equation(const std::string &equation, + const std::string &title = ""); + + /// plot an equation supplied as a std::string z=f(x,y), write only the function f(x,y) not z= + /// the independent variables have to be x and y + Gnuplot& plot_equation3d(const std::string &equation, + const std::string &title = ""); + + + /// plot image + Gnuplot& plot_image(const unsigned char *ucPicBuf, + const unsigned int iWidth, + const unsigned int iHeight, + const std::string &title = ""); + + + //---------------------------------------------------------------------------------- + ///\brief replot repeats the last plot or splot command. + /// this can be useful for viewing a plot with different set options, + /// or when generating the same plot for several devices (showonscreen, savetops) + /// + /// \param --- + /// + /// \return --- + //---------------------------------------------------------------------------------- + inline Gnuplot& replot(void){if (nplots > 0) cmd("replot");return *this;}; + + /// resets a gnuplot session (next plot will erase previous ones) + Gnuplot& reset_plot(); + + /// resets a gnuplot session and sets all variables to default + Gnuplot& reset_all(); + + /// deletes temporary files + void remove_tmpfiles(); + + // ------------------------------------------------------------------- + /// \brief Is the gnuplot session valid ?? + /// + /// + /// \param --- + /// + /// \return true if valid, false if not + // ------------------------------------------------------------------- + inline bool is_valid(){return(valid);}; + +}; + +//------------------------------------------------------------------------------ +// +// initialize static data +// +int Gnuplot::tmpfile_num = 0; + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) +std::string Gnuplot::m_sGNUPlotFileName = "pgnuplot.exe"; +std::string Gnuplot::m_sGNUPlotPath = "C:/program files/gnuplot/bin/"; +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) +std::string Gnuplot::m_sGNUPlotFileName = "gnuplot"; +std::string Gnuplot::m_sGNUPlotPath = "/usr/local/bin/"; +#endif + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) +std::string Gnuplot::terminal_std = "windows"; +#elif ( defined(unix) || defined(__unix) || defined(__unix__) ) && !defined(__APPLE__) +std::string Gnuplot::terminal_std = "x11"; +#elif defined(__APPLE__) +std::string Gnuplot::terminal_std = "aqua"; +#endif + +//------------------------------------------------------------------------------ +// +// constructor: set a style during construction +// +inline Gnuplot::Gnuplot(const std::string &style) + :gnucmd(NULL) ,valid(false) ,two_dim(false) ,nplots(0) + +{ + init(); + set_style(style); +} + +//------------------------------------------------------------------------------ +// +// constructor: open a new session, plot a signal (x) +// +inline Gnuplot::Gnuplot(const std::vector<double> &x, + const std::string &title, + const std::string &style, + const std::string &labelx, + const std::string &labely) + :gnucmd(NULL) ,valid(false) ,two_dim(false) ,nplots(0) +{ + init(); + + set_style(style); + set_xlabel(labelx); + set_ylabel(labely); + + plot_x(x,title); +} + + +//------------------------------------------------------------------------------ +// +// constructor: open a new session, plot a signal (x,y) +// +inline Gnuplot::Gnuplot(const std::vector<double> &x, + const std::vector<double> &y, + const std::string &title, + const std::string &style, + const std::string &labelx, + const std::string &labely) + :gnucmd(NULL) ,valid(false) ,two_dim(false) ,nplots(0) +{ + init(); + + set_style(style); + set_xlabel(labelx); + set_ylabel(labely); + + plot_xy(x,y,title); +} + + +//------------------------------------------------------------------------------ +// +// constructor: open a new session, plot a signal (x,y,z) +// +inline Gnuplot::Gnuplot(const std::vector<double> &x, + const std::vector<double> &y, + const std::vector<double> &z, + const std::string &title, + const std::string &style, + const std::string &labelx, + const std::string &labely, + const std::string &labelz) + :gnucmd(NULL) ,valid(false) ,two_dim(false) ,nplots(0) +{ + init(); + + set_style(style); + set_xlabel(labelx); + set_ylabel(labely); + set_zlabel(labelz); + + plot_xyz(x,y,z,title); +} + + +//------------------------------------------------------------------------------ +// +/// Plots a 2d graph from a list of doubles: x +// +template<typename X> +Gnuplot& Gnuplot::plot_x(const X& x, const std::string &title) +{ + if (x.size() == 0) + { + throw GnuplotException("std::vector too small"); + return *this; + } + + std::ofstream tmp; + std::string name = create_tmpfile(tmp); + if (name == "") + return *this; + + // + // write the data to file + // + for (unsigned int i = 0; i < x.size(); i++) + tmp << x[i] << std::endl; + + tmp.flush(); + tmp.close(); + + + plotfile_x(name, 1, title); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +/// Plots a 2d graph from a list of doubles: x y +// +template<typename X, typename Y> +Gnuplot& Gnuplot::plot_xy(const X& x, const Y& y, const std::string &title) +{ + if (x.size() == 0 || y.size() == 0) + { + throw GnuplotException("std::vectors too small"); + return *this; + } + + if (x.size() != y.size()) + { + throw GnuplotException("Length of the std::vectors differs"); + return *this; + } + + + std::ofstream tmp; + std::string name = create_tmpfile(tmp); + if (name == "") + return *this; + + // + // write the data to file + // + for (unsigned int i = 0; i < x.size(); i++) + tmp << x[i] << " " << y[i] << std::endl; + + tmp.flush(); + tmp.close(); + + + plotfile_xy(name, 1, 2, title); + + return *this; +} + +///----------------------------------------------------------------------------- +/// +/// plot x,y pairs with dy errorbars +/// +template<typename X, typename Y, typename E> +Gnuplot& Gnuplot::plot_xy_err(const X &x, + const Y &y, + const E &dy, + const std::string &title) +{ + if (x.size() == 0 || y.size() == 0 || dy.size() == 0) + { + throw GnuplotException("std::vectors too small"); + return *this; + } + + if (x.size() != y.size() || y.size() != dy.size()) + { + throw GnuplotException("Length of the std::vectors differs"); + return *this; + } + + + std::ofstream tmp; + std::string name = create_tmpfile(tmp); + if (name == "") + return *this; + + // + // write the data to file + // + for (unsigned int i = 0; i < x.size(); i++) + tmp << x[i] << " " << y[i] << " " << dy[i] << std::endl; + + tmp.flush(); + tmp.close(); + + + // Do the actual plot + plotfile_xy_err(name, 1, 2, 3, title); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// Plots a 3d graph from a list of doubles: x y z +// +template<typename X, typename Y, typename Z> +Gnuplot& Gnuplot::plot_xyz(const X &x, + const Y &y, + const Z &z, + const std::string &title) +{ + if (x.size() == 0 || y.size() == 0 || z.size() == 0) + { + throw GnuplotException("std::vectors too small"); + return *this; + } + + if (x.size() != y.size() || x.size() != z.size()) + { + throw GnuplotException("Length of the std::vectors differs"); + return *this; + } + + + std::ofstream tmp; + std::string name = create_tmpfile(tmp); + if (name == "") + return *this; + + // + // write the data to file + // + for (unsigned int i = 0; i < x.size(); i++) + tmp << x[i] << " " << y[i] << " " << z[i] <<std::endl; + + tmp.flush(); + tmp.close(); + + + plotfile_xyz(name, 1, 2, 3, title); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// define static member function: set Gnuplot path manual +// for windows: path with slash '/' not backslash '\' +// +bool Gnuplot::set_GNUPlotPath(const std::string &path) +{ + + std::string tmp = path + "/" + Gnuplot::m_sGNUPlotFileName; + + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + if ( Gnuplot::file_exists(tmp,0) ) // check existence +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if ( Gnuplot::file_exists(tmp,1) ) // check existence and execution permission +#endif + { + Gnuplot::m_sGNUPlotPath = path; + return true; + } + else + { + Gnuplot::m_sGNUPlotPath.clear(); + return false; + } +} + + +//------------------------------------------------------------------------------ +// +// define static member function: set standart terminal, used by showonscreen +// defaults: Windows - win, Linux - x11, Mac - aqua +// +void Gnuplot::set_terminal_std(const std::string &type) +{ +#if defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if (type.find("x11") != std::string::npos && getenv("DISPLAY") == NULL) + { + throw GnuplotException("Can't find DISPLAY variable"); + } +#endif + + + Gnuplot::terminal_std = type; + return; +} + + +//------------------------------------------------------------------------------ +// +// A string tokenizer taken from http://www.sunsite.ualberta.ca/Documentation/ +// /Gnu/libstdc++-2.90.8/html/21_strings/stringtok_std_h.txt +// +template <typename Container> +void stringtok (Container &container, + std::string const &in, + const char * const delimiters = " \t\n") +{ + const std::string::size_type len = in.length(); + std::string::size_type i = 0; + + while ( i < len ) + { + // eat leading whitespace + i = in.find_first_not_of (delimiters, i); + + if (i == std::string::npos) + return; // nothing left but white space + + // find the end of the token + std::string::size_type j = in.find_first_of (delimiters, i); + + // push token + if (j == std::string::npos) + { + container.push_back (in.substr(i)); + return; + } + else + container.push_back (in.substr(i, j-i)); + + // set up for next loop + i = j + 1; + } + + return; +} + + +//------------------------------------------------------------------------------ +// +// Destructor: needed to delete temporary files +// +Gnuplot::~Gnuplot() +{ +// remove_tmpfiles(); + + // A stream opened by popen() should be closed by pclose() +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + if (_pclose(gnucmd) == -1) +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if (pclose(gnucmd) == -1) +#endif + throw GnuplotException("Problem closing communication to gnuplot"); +} + + +//------------------------------------------------------------------------------ +// +// Resets a gnuplot session (next plot will erase previous ones) +// +Gnuplot& Gnuplot::reset_plot() +{ +// remove_tmpfiles(); + + nplots = 0; + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// resets a gnuplot session and sets all varibles to default +// +Gnuplot& Gnuplot::reset_all() +{ +// remove_tmpfiles(); + + nplots = 0; + cmd("reset"); + cmd("clear"); + pstyle = "points"; + smooth = ""; + showonscreen(); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// Change the plotting style of a gnuplot session +// +Gnuplot& Gnuplot::set_style(const std::string &stylestr) +{ + if (stylestr.find("lines") == std::string::npos && + stylestr.find("points") == std::string::npos && + stylestr.find("linespoints") == std::string::npos && + stylestr.find("impulses") == std::string::npos && + stylestr.find("dots") == std::string::npos && + stylestr.find("steps") == std::string::npos && + stylestr.find("fsteps") == std::string::npos && + stylestr.find("histeps") == std::string::npos && + stylestr.find("boxes") == std::string::npos && // 1-4 columns of data are required + stylestr.find("filledcurves") == std::string::npos && + stylestr.find("histograms") == std::string::npos ) //only for one data column +// stylestr.find("labels") == std::string::npos && // 3 columns of data are required +// stylestr.find("xerrorbars") == std::string::npos && // 3-4 columns of data are required +// stylestr.find("xerrorlines") == std::string::npos && // 3-4 columns of data are required +// stylestr.find("errorbars") == std::string::npos && // 3-4 columns of data are required +// stylestr.find("errorlines") == std::string::npos && // 3-4 columns of data are required +// stylestr.find("yerrorbars") == std::string::npos && // 3-4 columns of data are required +// stylestr.find("yerrorlines") == std::string::npos && // 3-4 columns of data are required +// stylestr.find("boxerrorbars") == std::string::npos && // 3-5 columns of data are required +// stylestr.find("xyerrorbars") == std::string::npos && // 4,6,7 columns of data are required +// stylestr.find("xyerrorlines") == std::string::npos && // 4,6,7 columns of data are required +// stylestr.find("boxxyerrorbars") == std::string::npos && // 4,6,7 columns of data are required +// stylestr.find("financebars") == std::string::npos && // 5 columns of data are required +// stylestr.find("candlesticks") == std::string::npos && // 5 columns of data are required +// stylestr.find("vectors") == std::string::npos && +// stylestr.find("image") == std::string::npos && +// stylestr.find("rgbimage") == std::string::npos && +// stylestr.find("pm3d") == std::string::npos ) + { + pstyle = std::string("points"); + } + else + { + pstyle = stylestr; + } + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// smooth: interpolation and approximation of data +// +Gnuplot& Gnuplot::set_smooth(const std::string &stylestr) +{ + if (stylestr.find("unique") == std::string::npos && + stylestr.find("frequency") == std::string::npos && + stylestr.find("csplines") == std::string::npos && + stylestr.find("acsplines") == std::string::npos && + stylestr.find("bezier") == std::string::npos && + stylestr.find("sbezier") == std::string::npos ) + { + smooth = ""; + } + else + { + smooth = stylestr; + } + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// sets terminal type to windows / x11 +// +Gnuplot& Gnuplot::showonscreen() +{ + cmd("set output"); + cmd("set terminal " + Gnuplot::terminal_std); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// saves a gnuplot session to a postscript file +// +Gnuplot& Gnuplot::savetops(const std::string &filename) +{ + cmd("set terminal postscript color"); + + std::ostringstream cmdstr; + cmdstr << "set output \"" << filename << ".ps\""; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// Switches legend on +// +Gnuplot& Gnuplot::set_legend(const std::string &position) +{ + std::ostringstream cmdstr; + cmdstr << "set key " << position; + + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// turns on log scaling for the x axis +// +Gnuplot& Gnuplot::set_xlogscale(const double base) +{ + std::ostringstream cmdstr; + + cmdstr << "set logscale x " << base; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// turns on log scaling for the y axis +// +Gnuplot& Gnuplot::set_ylogscale(const double base) +{ + std::ostringstream cmdstr; + + cmdstr << "set logscale y " << base; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// turns on log scaling for the z axis +// +Gnuplot& Gnuplot::set_zlogscale(const double base) +{ + std::ostringstream cmdstr; + + cmdstr << "set logscale z " << base; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// scales the size of the points used in plots +// +Gnuplot& Gnuplot::set_pointsize(const double pointsize) +{ + std::ostringstream cmdstr; + cmdstr << "set pointsize " << pointsize; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// set isoline density (grid) for plotting functions as surfaces +// +Gnuplot& Gnuplot::set_samples(const int samples) +{ + std::ostringstream cmdstr; + cmdstr << "set samples " << samples; + cmd(cmdstr.str()); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// set isoline density (grid) for plotting functions as surfaces +// +Gnuplot& Gnuplot::set_isosamples(const int isolines) +{ + std::ostringstream cmdstr; + cmdstr << "set isosamples " << isolines; + cmd(cmdstr.str()); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// enables contour drawing for surfaces set contour {base | surface | both} +// + +Gnuplot& Gnuplot::set_contour(const std::string &position) +{ + if (position.find("base") == std::string::npos && + position.find("surface") == std::string::npos && + position.find("both") == std::string::npos ) + { + cmd("set contour base"); + } + else + { + cmd("set contour " + position); + } + + return *this; +} + +//------------------------------------------------------------------------------ +// +// set labels +// +// set the xlabel +Gnuplot& Gnuplot::set_xlabel(const std::string &label) +{ + std::ostringstream cmdstr; + + cmdstr << "set xlabel \"" << label << "\""; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// set the ylabel +// +Gnuplot& Gnuplot::set_ylabel(const std::string &label) +{ + std::ostringstream cmdstr; + + cmdstr << "set ylabel \"" << label << "\""; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// set the zlabel +// +Gnuplot& Gnuplot::set_zlabel(const std::string &label) +{ + std::ostringstream cmdstr; + + cmdstr << "set zlabel \"" << label << "\""; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// set range +// +// set the xrange +Gnuplot& Gnuplot::set_xrange(const double iFrom, + const double iTo) +{ + std::ostringstream cmdstr; + + cmdstr << "set xrange[" << iFrom << ":" << iTo << "]"; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// set the yrange +// +Gnuplot& Gnuplot::set_yrange(const double iFrom, + const double iTo) +{ + std::ostringstream cmdstr; + + cmdstr << "set yrange[" << iFrom << ":" << iTo << "]"; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// set the zrange +// +Gnuplot& Gnuplot::set_zrange(const double iFrom, + const double iTo) +{ + std::ostringstream cmdstr; + + cmdstr << "set zrange[" << iFrom << ":" << iTo << "]"; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// set the palette range +// +Gnuplot& Gnuplot::set_cbrange(const double iFrom, + const double iTo) +{ + std::ostringstream cmdstr; + + cmdstr << "set cbrange[" << iFrom << ":" << iTo << "]"; + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// Plots a linear equation y=ax+b (where you supply the +// slope a and intercept b) +// +Gnuplot& Gnuplot::plot_slope(const double a, + const double b, + const std::string &title) +{ + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == true) + cmdstr << "replot "; + else + cmdstr << "plot "; + + cmdstr << a << " * x + " << b << " title \""; + + if (title == "") + cmdstr << "f(x) = " << a << " * x + " << b; + else + cmdstr << title; + + cmdstr << "\" with " << pstyle; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// Plot an equation supplied as a std::string y=f(x) (only f(x) expected) +// +Gnuplot& Gnuplot::plot_equation(const std::string &equation, + const std::string &title) +{ + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == true) + cmdstr << "replot "; + else + cmdstr << "plot "; + + cmdstr << equation << " title \""; + + if (title == "") + cmdstr << "f(x) = " << equation; + else + cmdstr << title; + + cmdstr << "\" with " << pstyle; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + +//------------------------------------------------------------------------------ +// +// plot an equation supplied as a std::string y=(x) +// +Gnuplot& Gnuplot::plot_equation3d(const std::string &equation, + const std::string &title) +{ + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == false) + cmdstr << "replot "; + else + cmdstr << "splot "; + + cmdstr << equation << " title \""; + + if (title == "") + cmdstr << "f(x,y) = " << equation; + else + cmdstr << title; + + cmdstr << "\" with " << pstyle; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// Plots a 2d graph from a list of doubles (x) saved in a file +// +Gnuplot& Gnuplot::plotfile_x(const std::string &filename, + const unsigned int column, + const std::string &title) +{ + // + // check if file exists + // + file_available(filename); + + + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == true) + cmdstr << "replot "; + else + cmdstr << "plot "; + + cmdstr << "\"" << filename << "\" using " << column; + + if (title == "") + cmdstr << " notitle "; + else + cmdstr << " title \"" << title << "\" "; + + if(smooth == "") + cmdstr << "with " << pstyle; + else + cmdstr << "smooth " << smooth; + + // + // Do the actual plot + // + cmd(cmdstr.str()); //nplots++; two_dim = true; already in cmd(); + + return *this; +} + + + +//------------------------------------------------------------------------------ +// +// Plots a 2d graph from a list of doubles (x y) saved in a file +// +Gnuplot& Gnuplot::plotfile_xy(const std::string &filename, + const unsigned int column_x, + const unsigned int column_y, + const std::string &title) +{ + // + // check if file exists + // + file_available(filename); + + + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == true) + cmdstr << "replot "; + else + cmdstr << "plot "; + + cmdstr << "\"" << filename << "\" using " << column_x << ":" << column_y; + + if (title == "") + cmdstr << " notitle "; + else + cmdstr << " title \"" << title << "\" "; + + if(smooth == "") + cmdstr << "with " << pstyle; + else + cmdstr << "smooth " << smooth; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// Plots a 2d graph with errorbars from a list of doubles (x y dy) in a file +// +Gnuplot& Gnuplot::plotfile_xy_err(const std::string &filename, + const unsigned int column_x, + const unsigned int column_y, + const unsigned int column_dy, + const std::string &title) +{ + // + // check if file exists + // + file_available(filename); + + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == true) + cmdstr << "replot "; + else + cmdstr << "plot "; + + cmdstr << "\"" << filename << "\" using " + << column_x << ":" << column_y << ":" << column_dy + << " with errorbars "; + + if (title == "") + cmdstr << " notitle "; + else + cmdstr << " title \"" << title << "\" "; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + + +//------------------------------------------------------------------------------ +// +// Plots a 3d graph from a list of doubles (x y z) saved in a file +// +Gnuplot& Gnuplot::plotfile_xyz(const std::string &filename, + const unsigned int column_x, + const unsigned int column_y, + const unsigned int column_z, + const std::string &title) +{ + // + // check if file exists + // + file_available(filename); + + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == false) + cmdstr << "replot "; + else + cmdstr << "splot "; + + cmdstr << "\"" << filename << "\" using " << column_x << ":" << column_y + << ":" << column_z; + + if (title == "") + cmdstr << " notitle with " << pstyle; + else + cmdstr << " title \"" << title << "\" with " << pstyle; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + + + +//------------------------------------------------------------------------------ +// +/// * note that this function is not valid for versions of GNUPlot below 4.2 +// +Gnuplot& Gnuplot::plot_image(const unsigned char * ucPicBuf, + const unsigned int iWidth, + const unsigned int iHeight, + const std::string &title) +{ + std::ofstream tmp; + std::string name = create_tmpfile(tmp); + if (name == "") + return *this; + + // + // write the data to file + // + int iIndex = 0; + for(int iRow = 0; iRow < iHeight; iRow++) + { + for(int iColumn = 0; iColumn < iWidth; iColumn++) + { + tmp << iColumn << " " << iRow << " " + << static_cast<float>(ucPicBuf[iIndex++]) << std::endl; + } + } + + tmp.flush(); + tmp.close(); + + + std::ostringstream cmdstr; + // + // command to be sent to gnuplot + // + if (nplots > 0 && two_dim == true) + cmdstr << "replot "; + else + cmdstr << "plot "; + + if (title == "") + cmdstr << "\"" << name << "\" with image"; + else + cmdstr << "\"" << name << "\" title \"" << title << "\" with image"; + + // + // Do the actual plot + // + cmd(cmdstr.str()); + + return *this; +} + + + +//------------------------------------------------------------------------------ +// +// Sends a command to an active gnuplot session +// +Gnuplot& Gnuplot::cmd(const std::string &cmdstr) +{ + if( !(valid) ) + { + return *this; + } + + + // int fputs ( const char * str, FILE * stream ); + // writes the string str to the stream. + // The function begins copying from the address specified (str) until it + // reaches the terminating null character ('\0'). This final + // null-character is not copied to the stream. + fputs( (cmdstr+"\n").c_str(), gnucmd ); + + // int fflush ( FILE * stream ); + // If the given stream was open for writing and the last i/o operation was + // an output operation, any unwritten data in the output buffer is written + // to the file. If the argument is a null pointer, all open files are + // flushed. The stream remains open after this call. + fflush(gnucmd); + + + if( cmdstr.find("replot") != std::string::npos ) + { + return *this; + } + else if( cmdstr.find("splot") != std::string::npos ) + { + two_dim = false; + nplots++; + } + else if( cmdstr.find("plot") != std::string::npos ) + { + two_dim = true; + nplots++; + } + + return *this; +} + + + +//------------------------------------------------------------------------------ +// +// Opens up a gnuplot session, ready to receive commands +// +void Gnuplot::init() +{ + // char * getenv ( const char * name ); get value of environment variable + // Retrieves a C string containing the value of the environment variable + // whose name is specified as argument. If the requested variable is not + // part of the environment list, the function returns a NULL pointer. +#if ( defined(unix) || defined(__unix) || defined(__unix__) ) && !defined(__APPLE__) + if (getenv("DISPLAY") == NULL) + { + valid = false; + throw GnuplotException("Can't find DISPLAY variable"); + } +#endif + + + // if gnuplot not available + if (!Gnuplot::get_program_path()) + { + valid = false; + throw GnuplotException("Can't find gnuplot"); + } + + + // + // open pipe + // + std::string tmp = Gnuplot::m_sGNUPlotPath + "/" + + Gnuplot::m_sGNUPlotFileName; + + // FILE *popen(const char *command, const char *mode); + // The popen() function shall execute the command specified by the string + // command, create a pipe between the calling program and the executed + // command, and return a pointer to a stream that can be used to either read + // from or write to the pipe. +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + gnucmd = _popen(tmp.c_str(),"w"); +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + gnucmd = popen(tmp.c_str(),"w"); +#endif + + // popen() shall return a pointer to an open stream that can be used to read + // or write to the pipe. Otherwise, it shall return a null pointer and may + // set errno to indicate the error. + if (!gnucmd) + { + valid = false; + throw GnuplotException("Couldn't open connection to gnuplot"); + } + + nplots = 0; + valid = true; + smooth = ""; + + //set terminal type + showonscreen(); + + return; +} + + +//------------------------------------------------------------------------------ +// +// Find out if a command lives in m_sGNUPlotPath or in PATH +// +bool Gnuplot::get_program_path() +{ + // + // first look in m_sGNUPlotPath for Gnuplot + // + std::string tmp = Gnuplot::m_sGNUPlotPath + "/" + + Gnuplot::m_sGNUPlotFileName; + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + if ( Gnuplot::file_exists(tmp,0) ) // check existence +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if ( Gnuplot::file_exists(tmp,1) ) // check existence and execution permission +#endif + { + return true; + } + + + // + // second look in PATH for Gnuplot + // + char *path; + // Retrieves a C string containing the value of environment variable PATH + path = getenv("PATH"); + + + if (path == NULL) + { + throw GnuplotException("Path is not set"); + return false; + } + else + { + std::list<std::string> ls; + + //split path (one long string) into list ls of strings +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + stringtok(ls,path,";"); +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + stringtok(ls,path,":"); +#endif + + // scan list for Gnuplot program files + for (std::list<std::string>::const_iterator i = ls.begin(); + i != ls.end(); ++i) + { + tmp = (*i) + "/" + Gnuplot::m_sGNUPlotFileName; +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + if ( Gnuplot::file_exists(tmp,0) ) // check existence +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if ( Gnuplot::file_exists(tmp,1) ) // check existence and execution permission +#endif + { + Gnuplot::m_sGNUPlotPath = *i; // set m_sGNUPlotPath + return true; + } + } + + tmp = "Can't find gnuplot neither in PATH nor in \"" + + Gnuplot::m_sGNUPlotPath + "\""; + throw GnuplotException(tmp); + + Gnuplot::m_sGNUPlotPath = ""; + return false; + } +} + + + +//------------------------------------------------------------------------------ +// +// check if file exists +// +bool Gnuplot::file_exists(const std::string &filename, int mode) +{ + if ( mode < 0 || mode > 7) + { + throw std::runtime_error("In function \"Gnuplot::file_exists\": mode\ + has to be an integer between 0 and 7"); + return false; + } + + // int _access(const char *path, int mode); + // returns 0 if the file has the given mode, + // it returns -1 if the named file does not exist or is not accessible in + // the given mode + // mode = 0 (F_OK) (default): checks file for existence only + // mode = 1 (X_OK): execution permission + // mode = 2 (W_OK): write permission + // mode = 4 (R_OK): read permission + // mode = 6 : read and write permission + // mode = 7 : read, write and execution permission +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + if (_access(filename.c_str(), mode) == 0) +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if (access(filename.c_str(), mode) == 0) +#endif + { + return true; + } + else + { + return false; + } + +} + +bool Gnuplot::file_available(const std::string &filename){ + std::ostringstream except; + if( Gnuplot::file_exists(filename,0) ) // check existence + { + if( !(Gnuplot::file_exists(filename,4)) ){// check read permission + except << "No read permission for File \"" << filename << "\""; + throw GnuplotException( except.str() ); + return false; + } + } + else{ + except << "File \"" << filename << "\" does not exist"; + throw GnuplotException( except.str() ); + return false; + } +} + + + +//------------------------------------------------------------------------------ +// +// Opens a temporary file +// +std::string Gnuplot::create_tmpfile(std::ofstream &tmp) +{ + +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + char name[] = "gnuplotiXXXXXX"; //tmp file in working directory +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + char name[] = "/tmp/gnuplotiXXXXXX"; // tmp file in /tmp +#endif + + // + // check if maximum number of temporary files reached + // + if (Gnuplot::tmpfile_num == GP_MAX_TMP_FILES - 1) + { + std::ostringstream except; + except << "Maximum number of temporary files reached (" + << GP_MAX_TMP_FILES << "): cannot open more files" << std::endl; + + throw GnuplotException( except.str() ); + return ""; + } + + // int mkstemp(char *name); + // shall replace the contents of the string pointed to by "name" by a unique + // filename, and return a file descriptor for the file open for reading and + // writing. Otherwise, -1 shall be returned if no suitable file could be + // created. The string in template should look like a filename with six + // trailing 'X' s; mkstemp() replaces each 'X' with a character from the + // portable filename character set. The characters are chosen such that the + // resulting name does not duplicate the name of an existing file at the + // time of a call to mkstemp() + + + // + // open temporary files for output + // +#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__) + if (_mktemp(name) == NULL) +#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__) + if (mkstemp(name) == -1) +#endif + { + std::ostringstream except; + except << "Cannot create temporary file \"" << name << "\""; + throw GnuplotException(except.str()); + return ""; + } + + tmp.open(name); + if (tmp.bad()) + { + std::ostringstream except; + except << "Cannot create temporary file \"" << name << "\""; + throw GnuplotException(except.str()); + return ""; + } + + // + // Save the temporary filename + // + tmpfile_list.push_back(name); + Gnuplot::tmpfile_num++; + + return name; +} + +void Gnuplot::remove_tmpfiles(){ + if ((tmpfile_list).size() > 0) + { + for (unsigned int i = 0; i < tmpfile_list.size(); i++) + remove( tmpfile_list[i].c_str() ); + + Gnuplot::tmpfile_num -= tmpfile_list.size(); + } +} +#endif diff --git a/gnuplot-cpp/test_output.ps b/gnuplot-cpp/test_output.ps new file mode 100644 index 0000000000000000000000000000000000000000..91d5ce83112732ad4f79cacff6e7e08e6f02976b --- /dev/null +++ b/gnuplot-cpp/test_output.ps @@ -0,0 +1,1899 @@ +%!PS-Adobe-2.0 +%%Title: test_output.ps +%%Creator: gnuplot 5.0 patchlevel 1 +%%CreationDate: Mon Feb 15 14:56:20 2016 +%%DocumentFonts: (atend) +%%BoundingBox: 50 50 554 770 +%%Orientation: Landscape +%%Pages: (atend) +%%EndComments +%%BeginProlog +/gnudict 256 dict def +gnudict begin +% +% The following true/false flags may be edited by hand if desired. +% The unit line width and grayscale image gamma correction may also be changed. +% +/Color true def +/Blacktext false def +/Solid false def +/Dashlength 1 def +/Landscape true def +/Level1 false def +/Level3 false def +/Rounded false def +/ClipToBoundingBox false def +/SuppressPDFMark false def +/TransparentPatterns false def +/gnulinewidth 5.000 def +/userlinewidth gnulinewidth def +/Gamma 1.0 def +/BackgroundColor {-1.000 -1.000 -1.000} def +% +/vshift -46 def +/dl1 { + 10.0 Dashlength userlinewidth gnulinewidth div mul mul mul + Rounded { currentlinewidth 0.75 mul sub dup 0 le { pop 0.01 } if } if +} def +/dl2 { + 10.0 Dashlength userlinewidth gnulinewidth div mul mul mul + Rounded { currentlinewidth 0.75 mul add } if +} def +/hpt_ 31.5 def +/vpt_ 31.5 def +/hpt hpt_ def +/vpt vpt_ def +/doclip { + ClipToBoundingBox { + newpath 50 50 moveto 554 50 lineto 554 770 lineto 50 770 lineto closepath + clip + } if +} def +% +% Gnuplot Prolog Version 5.0 (Dec 2014) +% +%/SuppressPDFMark true def +% +/M {moveto} bind def +/L {lineto} bind def +/R {rmoveto} bind def +/V {rlineto} bind def +/N {newpath moveto} bind def +/Z {closepath} bind def +/C {setrgbcolor} bind def +/f {rlineto fill} bind def +/g {setgray} bind def +/Gshow {show} def % May be redefined later in the file to support UTF-8 +/vpt2 vpt 2 mul def +/hpt2 hpt 2 mul def +/Lshow {currentpoint stroke M 0 vshift R + Blacktext {gsave 0 setgray textshow grestore} {textshow} ifelse} def +/Rshow {currentpoint stroke M dup stringwidth pop neg vshift R + Blacktext {gsave 0 setgray textshow grestore} {textshow} ifelse} def +/Cshow {currentpoint stroke M dup stringwidth pop -2 div vshift R + Blacktext {gsave 0 setgray textshow grestore} {textshow} ifelse} def +/UP {dup vpt_ mul /vpt exch def hpt_ mul /hpt exch def + /hpt2 hpt 2 mul def /vpt2 vpt 2 mul def} def +/DL {Color {setrgbcolor Solid {pop []} if 0 setdash} + {pop pop pop 0 setgray Solid {pop []} if 0 setdash} ifelse} def +/BL {stroke userlinewidth 2 mul setlinewidth + Rounded {1 setlinejoin 1 setlinecap} if} def +/AL {stroke userlinewidth 2 div setlinewidth + Rounded {1 setlinejoin 1 setlinecap} if} def +/UL {dup gnulinewidth mul /userlinewidth exch def + dup 1 lt {pop 1} if 10 mul /udl exch def} def +/PL {stroke userlinewidth setlinewidth + Rounded {1 setlinejoin 1 setlinecap} if} def +3.8 setmiterlimit +% Classic Line colors (version 5.0) +/LCw {1 1 1} def +/LCb {0 0 0} def +/LCa {0 0 0} def +/LC0 {1 0 0} def +/LC1 {0 1 0} def +/LC2 {0 0 1} def +/LC3 {1 0 1} def +/LC4 {0 1 1} def +/LC5 {1 1 0} def +/LC6 {0 0 0} def +/LC7 {1 0.3 0} def +/LC8 {0.5 0.5 0.5} def +% Default dash patterns (version 5.0) +/LTw {PL [] 1 setgray} def +/LTb {BL [] LCb DL} def +/LTa {AL [1 udl mul 2 udl mul] 0 setdash LCa setrgbcolor} def +/LT0 {PL [] LC0 DL} def +/LT1 {PL [2 dl1 3 dl2] LC1 DL} def +/LT2 {PL [1 dl1 1.5 dl2] LC2 DL} def +/LT3 {PL [6 dl1 2 dl2 1 dl1 2 dl2] LC3 DL} def +/LT4 {PL [1 dl1 2 dl2 6 dl1 2 dl2 1 dl1 2 dl2] LC4 DL} def +/LT5 {PL [4 dl1 2 dl2] LC5 DL} def +/LT6 {PL [1.5 dl1 1.5 dl2 1.5 dl1 1.5 dl2 1.5 dl1 6 dl2] LC6 DL} def +/LT7 {PL [3 dl1 3 dl2 1 dl1 3 dl2] LC7 DL} def +/LT8 {PL [2 dl1 2 dl2 2 dl1 6 dl2] LC8 DL} def +/SL {[] 0 setdash} def +/Pnt {stroke [] 0 setdash gsave 1 setlinecap M 0 0 V stroke grestore} def +/Dia {stroke [] 0 setdash 2 copy vpt add M + hpt neg vpt neg V hpt vpt neg V + hpt vpt V hpt neg vpt V closepath stroke + Pnt} def +/Pls {stroke [] 0 setdash vpt sub M 0 vpt2 V + currentpoint stroke M + hpt neg vpt neg R hpt2 0 V stroke + } def +/Box {stroke [] 0 setdash 2 copy exch hpt sub exch vpt add M + 0 vpt2 neg V hpt2 0 V 0 vpt2 V + hpt2 neg 0 V closepath stroke + Pnt} def +/Crs {stroke [] 0 setdash exch hpt sub exch vpt add M + hpt2 vpt2 neg V currentpoint stroke M + hpt2 neg 0 R hpt2 vpt2 V stroke} def +/TriU {stroke [] 0 setdash 2 copy vpt 1.12 mul add M + hpt neg vpt -1.62 mul V + hpt 2 mul 0 V + hpt neg vpt 1.62 mul V closepath stroke + Pnt} def +/Star {2 copy Pls Crs} def +/BoxF {stroke [] 0 setdash exch hpt sub exch vpt add M + 0 vpt2 neg V hpt2 0 V 0 vpt2 V + hpt2 neg 0 V closepath fill} def +/TriUF {stroke [] 0 setdash vpt 1.12 mul add M + hpt neg vpt -1.62 mul V + hpt 2 mul 0 V + hpt neg vpt 1.62 mul V closepath fill} def +/TriD {stroke [] 0 setdash 2 copy vpt 1.12 mul sub M + hpt neg vpt 1.62 mul V + hpt 2 mul 0 V + hpt neg vpt -1.62 mul V closepath stroke + Pnt} def +/TriDF {stroke [] 0 setdash vpt 1.12 mul sub M + hpt neg vpt 1.62 mul V + hpt 2 mul 0 V + hpt neg vpt -1.62 mul V closepath fill} def +/DiaF {stroke [] 0 setdash vpt add M + hpt neg vpt neg V hpt vpt neg V + hpt vpt V hpt neg vpt V closepath fill} def +/Pent {stroke [] 0 setdash 2 copy gsave + translate 0 hpt M 4 {72 rotate 0 hpt L} repeat + closepath stroke grestore Pnt} def +/PentF {stroke [] 0 setdash gsave + translate 0 hpt M 4 {72 rotate 0 hpt L} repeat + closepath fill grestore} def +/Circle {stroke [] 0 setdash 2 copy + hpt 0 360 arc stroke Pnt} def +/CircleF {stroke [] 0 setdash hpt 0 360 arc fill} def +/C0 {BL [] 0 setdash 2 copy moveto vpt 90 450 arc} bind def +/C1 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 0 90 arc closepath fill + vpt 0 360 arc closepath} bind def +/C2 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 90 180 arc closepath fill + vpt 0 360 arc closepath} bind def +/C3 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 0 180 arc closepath fill + vpt 0 360 arc closepath} bind def +/C4 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 180 270 arc closepath fill + vpt 0 360 arc closepath} bind def +/C5 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 0 90 arc + 2 copy moveto + 2 copy vpt 180 270 arc closepath fill + vpt 0 360 arc} bind def +/C6 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 90 270 arc closepath fill + vpt 0 360 arc closepath} bind def +/C7 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 0 270 arc closepath fill + vpt 0 360 arc closepath} bind def +/C8 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 270 360 arc closepath fill + vpt 0 360 arc closepath} bind def +/C9 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 270 450 arc closepath fill + vpt 0 360 arc closepath} bind def +/C10 {BL [] 0 setdash 2 copy 2 copy moveto vpt 270 360 arc closepath fill + 2 copy moveto + 2 copy vpt 90 180 arc closepath fill + vpt 0 360 arc closepath} bind def +/C11 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 0 180 arc closepath fill + 2 copy moveto + 2 copy vpt 270 360 arc closepath fill + vpt 0 360 arc closepath} bind def +/C12 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 180 360 arc closepath fill + vpt 0 360 arc closepath} bind def +/C13 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 0 90 arc closepath fill + 2 copy moveto + 2 copy vpt 180 360 arc closepath fill + vpt 0 360 arc closepath} bind def +/C14 {BL [] 0 setdash 2 copy moveto + 2 copy vpt 90 360 arc closepath fill + vpt 0 360 arc} bind def +/C15 {BL [] 0 setdash 2 copy vpt 0 360 arc closepath fill + vpt 0 360 arc closepath} bind def +/Rec {newpath 4 2 roll moveto 1 index 0 rlineto 0 exch rlineto + neg 0 rlineto closepath} bind def +/Square {dup Rec} bind def +/Bsquare {vpt sub exch vpt sub exch vpt2 Square} bind def +/S0 {BL [] 0 setdash 2 copy moveto 0 vpt rlineto BL Bsquare} bind def +/S1 {BL [] 0 setdash 2 copy vpt Square fill Bsquare} bind def +/S2 {BL [] 0 setdash 2 copy exch vpt sub exch vpt Square fill Bsquare} bind def +/S3 {BL [] 0 setdash 2 copy exch vpt sub exch vpt2 vpt Rec fill Bsquare} bind def +/S4 {BL [] 0 setdash 2 copy exch vpt sub exch vpt sub vpt Square fill Bsquare} bind def +/S5 {BL [] 0 setdash 2 copy 2 copy vpt Square fill + exch vpt sub exch vpt sub vpt Square fill Bsquare} bind def +/S6 {BL [] 0 setdash 2 copy exch vpt sub exch vpt sub vpt vpt2 Rec fill Bsquare} bind def +/S7 {BL [] 0 setdash 2 copy exch vpt sub exch vpt sub vpt vpt2 Rec fill + 2 copy vpt Square fill Bsquare} bind def +/S8 {BL [] 0 setdash 2 copy vpt sub vpt Square fill Bsquare} bind def +/S9 {BL [] 0 setdash 2 copy vpt sub vpt vpt2 Rec fill Bsquare} bind def +/S10 {BL [] 0 setdash 2 copy vpt sub vpt Square fill 2 copy exch vpt sub exch vpt Square fill + Bsquare} bind def +/S11 {BL [] 0 setdash 2 copy vpt sub vpt Square fill 2 copy exch vpt sub exch vpt2 vpt Rec fill + Bsquare} bind def +/S12 {BL [] 0 setdash 2 copy exch vpt sub exch vpt sub vpt2 vpt Rec fill Bsquare} bind def +/S13 {BL [] 0 setdash 2 copy exch vpt sub exch vpt sub vpt2 vpt Rec fill + 2 copy vpt Square fill Bsquare} bind def +/S14 {BL [] 0 setdash 2 copy exch vpt sub exch vpt sub vpt2 vpt Rec fill + 2 copy exch vpt sub exch vpt Square fill Bsquare} bind def +/S15 {BL [] 0 setdash 2 copy Bsquare fill Bsquare} bind def +/D0 {gsave translate 45 rotate 0 0 S0 stroke grestore} bind def +/D1 {gsave translate 45 rotate 0 0 S1 stroke grestore} bind def +/D2 {gsave translate 45 rotate 0 0 S2 stroke grestore} bind def +/D3 {gsave translate 45 rotate 0 0 S3 stroke grestore} bind def +/D4 {gsave translate 45 rotate 0 0 S4 stroke grestore} bind def +/D5 {gsave translate 45 rotate 0 0 S5 stroke grestore} bind def +/D6 {gsave translate 45 rotate 0 0 S6 stroke grestore} bind def +/D7 {gsave translate 45 rotate 0 0 S7 stroke grestore} bind def +/D8 {gsave translate 45 rotate 0 0 S8 stroke grestore} bind def +/D9 {gsave translate 45 rotate 0 0 S9 stroke grestore} bind def +/D10 {gsave translate 45 rotate 0 0 S10 stroke grestore} bind def +/D11 {gsave translate 45 rotate 0 0 S11 stroke grestore} bind def +/D12 {gsave translate 45 rotate 0 0 S12 stroke grestore} bind def +/D13 {gsave translate 45 rotate 0 0 S13 stroke grestore} bind def +/D14 {gsave translate 45 rotate 0 0 S14 stroke grestore} bind def +/D15 {gsave translate 45 rotate 0 0 S15 stroke grestore} bind def +/DiaE {stroke [] 0 setdash vpt add M + hpt neg vpt neg V hpt vpt neg V + hpt vpt V hpt neg vpt V closepath stroke} def +/BoxE {stroke [] 0 setdash exch hpt sub exch vpt add M + 0 vpt2 neg V hpt2 0 V 0 vpt2 V + hpt2 neg 0 V closepath stroke} def +/TriUE {stroke [] 0 setdash vpt 1.12 mul add M + hpt neg vpt -1.62 mul V + hpt 2 mul 0 V + hpt neg vpt 1.62 mul V closepath stroke} def +/TriDE {stroke [] 0 setdash vpt 1.12 mul sub M + hpt neg vpt 1.62 mul V + hpt 2 mul 0 V + hpt neg vpt -1.62 mul V closepath stroke} def +/PentE {stroke [] 0 setdash gsave + translate 0 hpt M 4 {72 rotate 0 hpt L} repeat + closepath stroke grestore} def +/CircE {stroke [] 0 setdash + hpt 0 360 arc stroke} def +/Opaque {gsave closepath 1 setgray fill grestore 0 setgray closepath} def +/DiaW {stroke [] 0 setdash vpt add M + hpt neg vpt neg V hpt vpt neg V + hpt vpt V hpt neg vpt V Opaque stroke} def +/BoxW {stroke [] 0 setdash exch hpt sub exch vpt add M + 0 vpt2 neg V hpt2 0 V 0 vpt2 V + hpt2 neg 0 V Opaque stroke} def +/TriUW {stroke [] 0 setdash vpt 1.12 mul add M + hpt neg vpt -1.62 mul V + hpt 2 mul 0 V + hpt neg vpt 1.62 mul V Opaque stroke} def +/TriDW {stroke [] 0 setdash vpt 1.12 mul sub M + hpt neg vpt 1.62 mul V + hpt 2 mul 0 V + hpt neg vpt -1.62 mul V Opaque stroke} def +/PentW {stroke [] 0 setdash gsave + translate 0 hpt M 4 {72 rotate 0 hpt L} repeat + Opaque stroke grestore} def +/CircW {stroke [] 0 setdash + hpt 0 360 arc Opaque stroke} def +/BoxFill {gsave Rec 1 setgray fill grestore} def +/Density { + /Fillden exch def + currentrgbcolor + /ColB exch def /ColG exch def /ColR exch def + /ColR ColR Fillden mul Fillden sub 1 add def + /ColG ColG Fillden mul Fillden sub 1 add def + /ColB ColB Fillden mul Fillden sub 1 add def + ColR ColG ColB setrgbcolor} def +/BoxColFill {gsave Rec PolyFill} def +/PolyFill {gsave Density fill grestore grestore} def +/h {rlineto rlineto rlineto gsave closepath fill grestore} bind def +% +% PostScript Level 1 Pattern Fill routine for rectangles +% Usage: x y w h s a XX PatternFill +% x,y = lower left corner of box to be filled +% w,h = width and height of box +% a = angle in degrees between lines and x-axis +% XX = 0/1 for no/yes cross-hatch +% +/PatternFill {gsave /PFa [ 9 2 roll ] def + PFa 0 get PFa 2 get 2 div add PFa 1 get PFa 3 get 2 div add translate + PFa 2 get -2 div PFa 3 get -2 div PFa 2 get PFa 3 get Rec + TransparentPatterns {} {gsave 1 setgray fill grestore} ifelse + clip + currentlinewidth 0.5 mul setlinewidth + /PFs PFa 2 get dup mul PFa 3 get dup mul add sqrt def + 0 0 M PFa 5 get rotate PFs -2 div dup translate + 0 1 PFs PFa 4 get div 1 add floor cvi + {PFa 4 get mul 0 M 0 PFs V} for + 0 PFa 6 get ne { + 0 1 PFs PFa 4 get div 1 add floor cvi + {PFa 4 get mul 0 2 1 roll M PFs 0 V} for + } if + stroke grestore} def +% +/languagelevel where + {pop languagelevel} {1} ifelse +dup 2 lt + {/InterpretLevel1 true def + /InterpretLevel3 false def} + {/InterpretLevel1 Level1 def + 2 gt + {/InterpretLevel3 Level3 def} + {/InterpretLevel3 false def} + ifelse } + ifelse +% +% PostScript level 2 pattern fill definitions +% +/Level2PatternFill { +/Tile8x8 {/PaintType 2 /PatternType 1 /TilingType 1 /BBox [0 0 8 8] /XStep 8 /YStep 8} + bind def +/KeepColor {currentrgbcolor [/Pattern /DeviceRGB] setcolorspace} bind def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop 0 0 M 8 8 L 0 8 M 8 0 L stroke} +>> matrix makepattern +/Pat1 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop 0 0 M 8 8 L 0 8 M 8 0 L stroke + 0 4 M 4 8 L 8 4 L 4 0 L 0 4 L stroke} +>> matrix makepattern +/Pat2 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop 0 0 M 0 8 L + 8 8 L 8 0 L 0 0 L fill} +>> matrix makepattern +/Pat3 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop -4 8 M 8 -4 L + 0 12 M 12 0 L stroke} +>> matrix makepattern +/Pat4 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop -4 0 M 8 12 L + 0 -4 M 12 8 L stroke} +>> matrix makepattern +/Pat5 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop -2 8 M 4 -4 L + 0 12 M 8 -4 L 4 12 M 10 0 L stroke} +>> matrix makepattern +/Pat6 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop -2 0 M 4 12 L + 0 -4 M 8 12 L 4 -4 M 10 8 L stroke} +>> matrix makepattern +/Pat7 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop 8 -2 M -4 4 L + 12 0 M -4 8 L 12 4 M 0 10 L stroke} +>> matrix makepattern +/Pat8 exch def +<< Tile8x8 + /PaintProc {0.5 setlinewidth pop 0 -2 M 12 4 L + -4 0 M 12 8 L -4 4 M 8 10 L stroke} +>> matrix makepattern +/Pat9 exch def +/Pattern1 {PatternBgnd KeepColor Pat1 setpattern} bind def +/Pattern2 {PatternBgnd KeepColor Pat2 setpattern} bind def +/Pattern3 {PatternBgnd KeepColor Pat3 setpattern} bind def +/Pattern4 {PatternBgnd KeepColor Landscape {Pat5} {Pat4} ifelse setpattern} bind def +/Pattern5 {PatternBgnd KeepColor Landscape {Pat4} {Pat5} ifelse setpattern} bind def +/Pattern6 {PatternBgnd KeepColor Landscape {Pat9} {Pat6} ifelse setpattern} bind def +/Pattern7 {PatternBgnd KeepColor Landscape {Pat8} {Pat7} ifelse setpattern} bind def +} def +% +% +%End of PostScript Level 2 code +% +/PatternBgnd { + TransparentPatterns {} {gsave 1 setgray fill grestore} ifelse +} def +% +% Substitute for Level 2 pattern fill codes with +% grayscale if Level 2 support is not selected. +% +/Level1PatternFill { +/Pattern1 {0.250 Density} bind def +/Pattern2 {0.500 Density} bind def +/Pattern3 {0.750 Density} bind def +/Pattern4 {0.125 Density} bind def +/Pattern5 {0.375 Density} bind def +/Pattern6 {0.625 Density} bind def +/Pattern7 {0.875 Density} bind def +} def +% +% Now test for support of Level 2 code +% +Level1 {Level1PatternFill} {Level2PatternFill} ifelse +% +/Symbol-Oblique /Symbol findfont [1 0 .167 1 0 0] makefont +dup length dict begin {1 index /FID eq {pop pop} {def} ifelse} forall +currentdict end definefont pop +% +/MFshow { + { dup 5 get 3 ge + { 5 get 3 eq {gsave} {grestore} ifelse } + {dup dup 0 get findfont exch 1 get scalefont setfont + [ currentpoint ] exch dup 2 get 0 exch R dup 5 get 2 ne {dup dup 6 + get exch 4 get {textshow} {stringwidth pop 0 R} ifelse }if dup 5 get 0 eq + {dup 3 get {2 get neg 0 exch R pop} {pop aload pop M} ifelse} {dup 5 + get 1 eq {dup 2 get exch dup 3 get exch 6 get stringwidth pop -2 div + dup 0 R} {dup 6 get stringwidth pop -2 div 0 R 6 get + textshow 2 index {aload pop M neg 3 -1 roll neg R pop pop} {pop pop pop + pop aload pop M} ifelse }ifelse }ifelse } + ifelse } + forall} def +/Gswidth {dup type /stringtype eq {stringwidth} {pop (n) stringwidth} ifelse} def +/MFwidth {0 exch { dup 5 get 3 ge { 5 get 3 eq { 0 } { pop } ifelse } + {dup 3 get{dup dup 0 get findfont exch 1 get scalefont setfont + 6 get Gswidth pop add} {pop} ifelse} ifelse} forall} def +/MLshow { currentpoint stroke M + 0 exch R + Blacktext {gsave 0 setgray MFshow grestore} {MFshow} ifelse } bind def +/MRshow { currentpoint stroke M + exch dup MFwidth neg 3 -1 roll R + Blacktext {gsave 0 setgray MFshow grestore} {MFshow} ifelse } bind def +/MCshow { currentpoint stroke M + exch dup MFwidth -2 div 3 -1 roll R + Blacktext {gsave 0 setgray MFshow grestore} {MFshow} ifelse } bind def +/XYsave { [( ) 1 2 true false 3 ()] } bind def +/XYrestore { [( ) 1 2 true false 4 ()] } bind def +Level1 SuppressPDFMark or +{} { +/SDict 10 dict def +systemdict /pdfmark known not { + userdict /pdfmark systemdict /cleartomark get put +} if +SDict begin [ + /Title (test_output.ps) + /Subject (gnuplot plot) + /Creator (gnuplot 5.0 patchlevel 1) + /Author (martinka) +% /Producer (gnuplot) +% /Keywords () + /CreationDate (Mon Feb 15 14:56:20 2016) + /DOCINFO pdfmark +end +} ifelse +end +% +% Support for boxed text - Ethan A Merritt May 2005 +% +/InitTextBox { userdict /TBy2 3 -1 roll put userdict /TBx2 3 -1 roll put + userdict /TBy1 3 -1 roll put userdict /TBx1 3 -1 roll put + /Boxing true def } def +/ExtendTextBox { Boxing + { gsave dup false charpath pathbbox + dup TBy2 gt {userdict /TBy2 3 -1 roll put} {pop} ifelse + dup TBx2 gt {userdict /TBx2 3 -1 roll put} {pop} ifelse + dup TBy1 lt {userdict /TBy1 3 -1 roll put} {pop} ifelse + dup TBx1 lt {userdict /TBx1 3 -1 roll put} {pop} ifelse + grestore } if } def +/PopTextBox { newpath TBx1 TBxmargin sub TBy1 TBymargin sub M + TBx1 TBxmargin sub TBy2 TBymargin add L + TBx2 TBxmargin add TBy2 TBymargin add L + TBx2 TBxmargin add TBy1 TBymargin sub L closepath } def +/DrawTextBox { PopTextBox stroke /Boxing false def} def +/FillTextBox { gsave PopTextBox 1 1 1 setrgbcolor fill grestore /Boxing false def} def +0 0 0 0 InitTextBox +/TBxmargin 20 def +/TBymargin 20 def +/Boxing false def +/textshow { ExtendTextBox Gshow } def +% +%%EndProlog +%%Page: 1 1 +gnudict begin +gsave +doclip +50 50 translate +0.100 0.100 scale +90 rotate +0 -5040 translate +0 setgray +newpath +(Helvetica) findfont 140 scalefont setfont +BackgroundColor 0 lt 3 1 roll 0 lt exch 0 lt or or not {gsave BackgroundColor C clippath fill grestore} if +1.000 UL +LTb +LCb setrgbcolor +546 280 M +63 0 V +6338 0 R +-63 0 V +stroke +462 280 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.8)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 790 M +63 0 V +6338 0 R +-63 0 V +stroke +462 790 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.6)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 1300 M +63 0 V +6338 0 R +-63 0 V +stroke +462 1300 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.4)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 1810 M +63 0 V +6338 0 R +-63 0 V +stroke +462 1810 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.2)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 2320 M +63 0 V +6338 0 R +-63 0 V +stroke +462 2320 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 2831 M +63 0 V +6338 0 R +-63 0 V +stroke +462 2831 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.2)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 3341 M +63 0 V +6338 0 R +-63 0 V +stroke +462 3341 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.4)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 3851 M +63 0 V +6338 0 R +-63 0 V +stroke +462 3851 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.6)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 4361 M +63 0 V +6338 0 R +-63 0 V +stroke +462 4361 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.8)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 4871 M +63 0 V +6338 0 R +-63 0 V +stroke +462 4871 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 1)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 280 M +0 63 V +0 4528 R +0 -63 V +stroke +546 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +1826 280 M +0 63 V +0 4528 R +0 -63 V +stroke +1826 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 1)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +3106 280 M +0 63 V +0 4528 R +0 -63 V +stroke +3106 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 2)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +4387 280 M +0 63 V +0 4528 R +0 -63 V +stroke +4387 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 3)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +5667 280 M +0 63 V +0 4528 R +0 -63 V +stroke +5667 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 4)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +6947 280 M +0 63 V +0 4528 R +0 -63 V +stroke +6947 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 5)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +1.000 UL +LTb +LCb setrgbcolor +546 4871 N +546 280 L +6401 0 V +0 4591 V +-6401 0 V +Z stroke +1.000 UP +1.000 UL +LTb +LCb setrgbcolor +% Begin plot #1 +1.000 UL +LTb +0.58 0.00 0.83 C LCb setrgbcolor +6296 4738 M +[ [(Helvetica) 140.0 0.0 true true 0 (f\(x\) = sin\(12*x\)*exp\(-x\))] +] -46.7 MRshow +1.000 UL +LTb +0.58 0.00 0.83 C 6380 4738 M +399 0 V +546 2320 M +21 500 V +22 464 V +21 410 V +22 342 V +21 263 V +21 175 V +22 84 V +21 -8 V +22 -96 V +21 -178 V +21 -249 V +22 -309 V +21 -355 V +22 -384 V +21 -398 V +22 -395 V +21 -377 V +21 -344 V +22 -299 V +974 923 L +996 744 L +21 -111 V +21 -41 V +22 30 V +21 97 V +22 156 V +21 209 V +21 252 V +22 282 V +21 301 V +22 307 V +21 300 V +21 283 V +22 254 V +21 216 V +22 170 V +21 121 V +22 66 V +21 13 V +21 -41 V +22 -91 V +21 -136 V +22 -173 V +21 -202 V +21 -223 V +22 -235 V +21 -235 V +22 -228 V +21 -211 V +21 -186 V +22 -154 V +21 -119 V +22 -78 V +21 -37 V +21 5 V +22 45 V +21 82 V +22 115 V +21 141 V +21 163 V +22 175 V +21 182 V +22 180 V +21 171 V +22 156 V +21 136 V +21 110 V +22 81 V +21 49 V +22 17 V +21 -14 V +21 -45 V +22 -72 V +21 -97 V +22 -115 V +21 -129 V +21 -137 V +22 -140 V +21 -137 V +22 -128 V +21 -115 V +21 -98 V +22 -77 V +21 -55 V +22 -29 V +21 -5 V +21 20 V +22 42 V +21 62 V +22 79 V +21 93 V +22 102 V +21 107 V +21 107 V +22 104 V +21 96 V +22 84 V +21 70 V +21 54 V +22 35 V +21 16 V +22 -3 V +21 -21 V +21 -38 V +22 -53 V +21 -65 V +22 -74 V +21 -80 V +21 -83 V +22 -82 V +21 -78 V +22 -71 V +21 -61 V +22 -50 V +21 -36 V +21 -22 V +22 -8 V +21 7 V +22 21 V +21 34 V +21 44 V +22 52 V +21 59 V +22 63 V +21 64 V +stroke 3222 2305 M +21 62 V +22 59 V +21 52 V +22 44 V +21 35 V +21 24 V +22 14 V +21 1 V +22 -9 V +21 -19 V +21 -29 V +22 -37 V +21 -42 V +22 -47 V +21 -48 V +22 -49 V +21 -48 V +21 -43 V +22 -38 V +21 -32 V +22 -24 V +21 -16 V +21 -7 V +22 2 V +21 10 V +22 17 V +21 24 V +21 30 V +22 34 V +21 37 V +22 38 V +21 37 V +21 35 V +22 33 V +21 27 V +22 23 V +21 16 V +22 10 V +21 3 V +21 -3 V +22 -10 V +21 -15 V +22 -21 V +21 -24 V +21 -27 V +22 -28 V +21 -29 V +22 -29 V +21 -26 V +21 -24 V +22 -20 V +21 -16 V +22 -11 V +21 -6 V +21 0 V +22 4 V +21 9 V +22 13 V +21 17 V +21 20 V +22 21 V +21 22 V +22 22 V +21 22 V +22 20 V +21 17 V +21 14 V +22 11 V +21 7 V +22 3 V +21 -1 V +21 -4 V +22 -8 V +21 -11 V +22 -14 V +21 -16 V +21 -16 V +22 -18 V +21 -17 V +22 -16 V +21 -14 V +21 -13 V +22 -10 V +21 -8 V +22 -4 V +21 -1 V +22 1 V +21 5 V +21 7 V +22 9 V +21 11 V +22 13 V +21 13 V +21 13 V +22 13 V +21 12 V +22 11 V +21 9 V +21 7 V +22 5 V +21 3 V +22 0 V +21 -2 V +21 -5 V +stroke 5448 2371 M +22 -6 V +21 -7 V +22 -9 V +21 -10 V +21 -10 V +22 -10 V +21 -10 V +22 -9 V +21 -8 V +22 -6 V +21 -5 V +21 -3 V +22 -2 V +21 1 V +22 2 V +21 4 V +21 5 V +22 6 V +21 7 V +22 8 V +21 8 V +21 7 V +22 8 V +21 6 V +22 6 V +21 5 V +21 3 V +22 2 V +21 0 V +22 0 V +21 -2 V +21 -4 V +22 -4 V +21 -5 V +22 -6 V +21 -6 V +22 -6 V +21 -6 V +21 -5 V +22 -5 V +21 -4 V +22 -3 V +21 -2 V +21 -2 V +22 0 V +21 1 V +22 2 V +21 3 V +21 4 V +22 4 V +21 4 V +22 5 V +21 4 V +21 5 V +22 4 V +21 3 V +22 3 V +21 3 V +22 1 V +21 1 V +21 -1 V +22 -1 V +21 -1 V +22 -3 V +21 -3 V +21 -3 V +22 -3 V +21 -4 V +22 -3 V +21 -4 V +% End plot #1 +stroke +2.000 UL +LTb +LCb setrgbcolor +1.000 UL +LTb +LCb setrgbcolor +546 4871 N +546 280 L +6401 0 V +0 4591 V +-6401 0 V +Z stroke +1.000 UP +1.000 UL +LTb +LCb setrgbcolor +stroke +grestore +end +showpage +%%Page: 2 2 +gnudict begin +gsave +doclip +50 50 translate +0.100 0.100 scale +90 rotate +0 -5040 translate +0 setgray +newpath +(Helvetica) findfont 140 scalefont setfont +BackgroundColor 0 lt 3 1 roll 0 lt exch 0 lt or or not {gsave BackgroundColor C clippath fill grestore} if +1.000 UL +LTb +LCb setrgbcolor +546 280 M +63 0 V +6338 0 R +-63 0 V +stroke +462 280 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.8)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 790 M +63 0 V +6338 0 R +-63 0 V +stroke +462 790 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.6)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 1300 M +63 0 V +6338 0 R +-63 0 V +stroke +462 1300 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.4)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 1810 M +63 0 V +6338 0 R +-63 0 V +stroke +462 1810 M +[ [(Helvetica) 140.0 0.0 true true 0 (-0.2)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 2320 M +63 0 V +6338 0 R +-63 0 V +stroke +462 2320 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 2831 M +63 0 V +6338 0 R +-63 0 V +stroke +462 2831 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.2)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 3341 M +63 0 V +6338 0 R +-63 0 V +stroke +462 3341 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.4)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 3851 M +63 0 V +6338 0 R +-63 0 V +stroke +462 3851 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.6)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 4361 M +63 0 V +6338 0 R +-63 0 V +stroke +462 4361 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0.8)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 4871 M +63 0 V +6338 0 R +-63 0 V +stroke +462 4871 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 1)] +] -46.7 MRshow +1.000 UL +LTb +LCb setrgbcolor +546 280 M +0 63 V +0 4528 R +0 -63 V +stroke +546 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 0)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +1826 280 M +0 63 V +0 4528 R +0 -63 V +stroke +1826 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 1)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +3106 280 M +0 63 V +0 4528 R +0 -63 V +stroke +3106 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 2)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +4387 280 M +0 63 V +0 4528 R +0 -63 V +stroke +4387 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 3)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +5667 280 M +0 63 V +0 4528 R +0 -63 V +stroke +5667 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 4)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +6947 280 M +0 63 V +0 4528 R +0 -63 V +stroke +6947 140 M +[ [(Helvetica) 140.0 0.0 true true 0 ( 5)] +] -46.7 MCshow +1.000 UL +LTb +LCb setrgbcolor +1.000 UL +LTb +LCb setrgbcolor +546 4871 N +546 280 L +6401 0 V +0 4591 V +-6401 0 V +Z stroke +1.000 UP +1.000 UL +LTb +LCb setrgbcolor +% Begin plot #1 +1.000 UL +LTb +0.58 0.00 0.83 C LCb setrgbcolor +6296 4738 M +[ [(Helvetica) 140.0 0.0 true true 0 (f\(x\) = sin\(12*x\)*exp\(-x\))] +] -46.7 MRshow +1.000 UL +LTb +0.58 0.00 0.83 C 6380 4738 M +399 0 V +546 2320 M +21 500 V +22 464 V +21 410 V +22 342 V +21 263 V +21 175 V +22 84 V +21 -8 V +22 -96 V +21 -178 V +21 -249 V +22 -309 V +21 -355 V +22 -384 V +21 -398 V +22 -395 V +21 -377 V +21 -344 V +22 -299 V +974 923 L +996 744 L +21 -111 V +21 -41 V +22 30 V +21 97 V +22 156 V +21 209 V +21 252 V +22 282 V +21 301 V +22 307 V +21 300 V +21 283 V +22 254 V +21 216 V +22 170 V +21 121 V +22 66 V +21 13 V +21 -41 V +22 -91 V +21 -136 V +22 -173 V +21 -202 V +21 -223 V +22 -235 V +21 -235 V +22 -228 V +21 -211 V +21 -186 V +22 -154 V +21 -119 V +22 -78 V +21 -37 V +21 5 V +22 45 V +21 82 V +22 115 V +21 141 V +21 163 V +22 175 V +21 182 V +22 180 V +21 171 V +22 156 V +21 136 V +21 110 V +22 81 V +21 49 V +22 17 V +21 -14 V +21 -45 V +22 -72 V +21 -97 V +22 -115 V +21 -129 V +21 -137 V +22 -140 V +21 -137 V +22 -128 V +21 -115 V +21 -98 V +22 -77 V +21 -55 V +22 -29 V +21 -5 V +21 20 V +22 42 V +21 62 V +22 79 V +21 93 V +22 102 V +21 107 V +21 107 V +22 104 V +21 96 V +22 84 V +21 70 V +21 54 V +22 35 V +21 16 V +22 -3 V +21 -21 V +21 -38 V +22 -53 V +21 -65 V +22 -74 V +21 -80 V +21 -83 V +22 -82 V +21 -78 V +22 -71 V +21 -61 V +22 -50 V +21 -36 V +21 -22 V +22 -8 V +21 7 V +22 21 V +21 34 V +21 44 V +22 52 V +21 59 V +22 63 V +21 64 V +stroke 3222 2305 M +21 62 V +22 59 V +21 52 V +22 44 V +21 35 V +21 24 V +22 14 V +21 1 V +22 -9 V +21 -19 V +21 -29 V +22 -37 V +21 -42 V +22 -47 V +21 -48 V +22 -49 V +21 -48 V +21 -43 V +22 -38 V +21 -32 V +22 -24 V +21 -16 V +21 -7 V +22 2 V +21 10 V +22 17 V +21 24 V +21 30 V +22 34 V +21 37 V +22 38 V +21 37 V +21 35 V +22 33 V +21 27 V +22 23 V +21 16 V +22 10 V +21 3 V +21 -3 V +22 -10 V +21 -15 V +22 -21 V +21 -24 V +21 -27 V +22 -28 V +21 -29 V +22 -29 V +21 -26 V +21 -24 V +22 -20 V +21 -16 V +22 -11 V +21 -6 V +21 0 V +22 4 V +21 9 V +22 13 V +21 17 V +21 20 V +22 21 V +21 22 V +22 22 V +21 22 V +22 20 V +21 17 V +21 14 V +22 11 V +21 7 V +22 3 V +21 -1 V +21 -4 V +22 -8 V +21 -11 V +22 -14 V +21 -16 V +21 -16 V +22 -18 V +21 -17 V +22 -16 V +21 -14 V +21 -13 V +22 -10 V +21 -8 V +22 -4 V +21 -1 V +22 1 V +21 5 V +21 7 V +22 9 V +21 11 V +22 13 V +21 13 V +21 13 V +22 13 V +21 12 V +22 11 V +21 9 V +21 7 V +22 5 V +21 3 V +22 0 V +21 -2 V +21 -5 V +stroke 5448 2371 M +22 -6 V +21 -7 V +22 -9 V +21 -10 V +21 -10 V +22 -10 V +21 -10 V +22 -9 V +21 -8 V +22 -6 V +21 -5 V +21 -3 V +22 -2 V +21 1 V +22 2 V +21 4 V +21 5 V +22 6 V +21 7 V +22 8 V +21 8 V +21 7 V +22 8 V +21 6 V +22 6 V +21 5 V +21 3 V +22 2 V +21 0 V +22 0 V +21 -2 V +21 -4 V +22 -4 V +21 -5 V +22 -6 V +21 -6 V +22 -6 V +21 -6 V +21 -5 V +22 -5 V +21 -4 V +22 -3 V +21 -2 V +21 -2 V +22 0 V +21 1 V +22 2 V +21 3 V +21 4 V +22 4 V +21 4 V +22 5 V +21 4 V +21 5 V +22 4 V +21 3 V +22 3 V +21 3 V +22 1 V +21 1 V +21 -1 V +22 -1 V +21 -1 V +22 -3 V +21 -3 V +21 -3 V +22 -3 V +21 -4 V +22 -3 V +21 -4 V +% End plot #1 +% Begin plot #2 +stroke +LTb +0.00 0.62 0.45 C LCb setrgbcolor +6296 4598 M +[ [(Helvetica) 140.0 0.0 true true 0 (f\(x\) = exp\(-x\))] +] -46.7 MRshow +1.000 UL +LTb +0.00 0.62 0.45 C 6380 4598 M +399 0 V +546 4871 M +21 -42 V +22 -42 V +21 -41 V +22 -40 V +21 -40 V +21 -38 V +22 -39 V +21 -37 V +22 -37 V +21 -37 V +21 -36 V +22 -35 V +21 -34 V +22 -34 V +21 -34 V +22 -33 V +21 -32 V +21 -32 V +22 -31 V +21 -31 V +22 -30 V +21 -30 V +21 -29 V +22 -29 V +21 -28 V +22 -28 V +21 -28 V +21 -27 V +22 -26 V +21 -26 V +22 -26 V +21 -25 V +21 -25 V +22 -24 V +21 -24 V +22 -24 V +21 -23 V +22 -23 V +21 -22 V +21 -22 V +22 -22 V +21 -21 V +22 -21 V +21 -21 V +21 -20 V +22 -20 V +21 -19 V +22 -20 V +21 -19 V +21 -18 V +22 -19 V +21 -18 V +22 -17 V +21 -18 V +21 -17 V +22 -17 V +21 -16 V +22 -17 V +21 -16 V +21 -15 V +22 -16 V +21 -15 V +22 -15 V +21 -15 V +22 -14 V +21 -15 V +21 -14 V +22 -13 V +21 -14 V +22 -13 V +21 -14 V +21 -12 V +22 -13 V +21 -13 V +22 -12 V +21 -12 V +21 -12 V +22 -11 V +21 -12 V +22 -11 V +21 -11 V +21 -11 V +22 -11 V +21 -11 V +22 -10 V +21 -10 V +21 -10 V +22 -10 V +21 -10 V +22 -9 V +21 -10 V +22 -9 V +21 -9 V +21 -9 V +22 -9 V +21 -8 V +22 -9 V +21 -8 V +21 -8 V +22 -8 V +21 -8 V +22 -8 V +stroke 2730 2784 M +21 -8 V +21 -7 V +22 -8 V +21 -7 V +22 -7 V +21 -7 V +21 -7 V +22 -7 V +21 -7 V +22 -7 V +21 -6 V +22 -6 V +21 -7 V +21 -6 V +22 -6 V +21 -6 V +22 -6 V +21 -6 V +21 -5 V +22 -6 V +21 -5 V +22 -6 V +21 -5 V +21 -5 V +22 -6 V +21 -5 V +22 -5 V +21 -4 V +21 -5 V +22 -5 V +21 -5 V +22 -4 V +21 -5 V +21 -4 V +22 -5 V +21 -4 V +22 -4 V +21 -4 V +22 -4 V +21 -4 V +21 -4 V +22 -4 V +21 -4 V +22 -4 V +21 -3 V +21 -4 V +22 -3 V +21 -4 V +22 -3 V +21 -4 V +21 -3 V +22 -3 V +21 -4 V +22 -3 V +21 -3 V +21 -3 V +22 -3 V +21 -3 V +22 -3 V +21 -3 V +22 -3 V +21 -2 V +21 -3 V +22 -3 V +21 -2 V +22 -3 V +21 -2 V +21 -3 V +22 -2 V +21 -3 V +22 -2 V +21 -3 V +21 -2 V +22 -2 V +21 -2 V +22 -3 V +21 -2 V +21 -2 V +22 -2 V +21 -2 V +22 -2 V +21 -2 V +21 -2 V +22 -2 V +21 -2 V +22 -2 V +21 -1 V +22 -2 V +21 -2 V +21 -2 V +22 -1 V +21 -2 V +22 -2 V +21 -1 V +21 -2 V +22 -2 V +21 -1 V +22 -2 V +21 -1 V +21 -2 V +22 -1 V +21 -1 V +22 -2 V +21 -1 V +stroke 4956 2402 M +21 -2 V +22 -1 V +21 -1 V +22 -1 V +21 -2 V +22 -1 V +21 -1 V +21 -1 V +22 -2 V +21 -1 V +22 -1 V +21 -1 V +21 -1 V +22 -1 V +21 -1 V +22 -1 V +21 -1 V +21 -1 V +22 -1 V +21 -1 V +22 -1 V +21 -1 V +21 -1 V +22 -1 V +21 -1 V +22 -1 V +21 -1 V +21 -1 V +22 0 V +21 -1 V +22 -1 V +21 -1 V +22 -1 V +21 0 V +21 -1 V +22 -1 V +21 -1 V +22 0 V +21 -1 V +21 -1 V +22 -1 V +21 0 V +22 -1 V +21 -1 V +21 0 V +22 -1 V +21 0 V +22 -1 V +21 -1 V +21 0 V +22 -1 V +21 0 V +22 -1 V +21 -1 V +21 0 V +22 -1 V +21 0 V +22 -1 V +21 0 V +22 -1 V +21 0 V +21 -1 V +22 0 V +21 -1 V +22 0 V +21 -1 V +21 0 V +22 0 V +21 -1 V +22 0 V +21 -1 V +21 0 V +22 -1 V +21 0 V +22 0 V +21 -1 V +21 0 V +22 0 V +21 -1 V +22 0 V +21 -1 V +22 0 V +21 0 V +21 -1 V +22 0 V +21 0 V +22 -1 V +21 0 V +21 0 V +22 0 V +21 -1 V +22 0 V +21 0 V +% End plot #2 +stroke +2.000 UL +LTb +LCb setrgbcolor +1.000 UL +LTb +LCb setrgbcolor +546 4871 N +546 280 L +6401 0 V +0 4591 V +-6401 0 V +Z stroke +1.000 UP +1.000 UL +LTb +LCb setrgbcolor +stroke +grestore +end +showpage +%%Trailer +%%DocumentFonts: Helvetica +%%Pages: 2