/****************************************************************************** * * Copyright (C) 1997-2021 by Dimitri van Heesch. * * Permission to use, copy, modify, and distribute this software and its * documentation under the terms of the GNU General Public License is hereby * granted. No representations are made about the suitability of this software * for any purpose. It is provided "as is" without express or implied warranty. * See the GNU General Public License for more details. * * Documents produced by Doxygen are derivative works derived from the * input used in their production; they are not affected by this license. * */ #include #include "msc.h" #include "portable.h" #include "config.h" #include "message.h" #include "docparser.h" #include "doxygen.h" #include "index.h" #include "util.h" #include "mscgen_api.h" #include "dir.h" static const int maxCmdLine = 40960; static bool convertMapFile(std::ostream &t,const char *mapName,const QCString relPath, const QCString &context) { std::ifstream f(mapName,std::ifstream::in); if (!f.is_open()) { err("failed to open map file %s for inclusion in the docs!\n" "If you installed Graphviz/dot after a previous failing run, \n" "try deleting the output directory and rerun doxygen.\n",mapName); return false; } const int maxLineLen=1024; char url[maxLineLen]; char ref[maxLineLen]; int x1,y1,x2,y2; std::string line; while (getline(f,line)) { bool isRef = false; //printf("ReadLine '%s'\n",line.c_str()); if (qstrncmp(line.c_str(),"rect",4)==0) { // obtain the url and the coordinates in the order used by graphviz-1.5 sscanf(line.c_str(),"rect %s %d,%d %d,%d",url,&x1,&y1,&x2,&y2); if (qstrcmp(url,"\\ref")==0 || qstrcmp(url,"@ref")==0) { isRef = true; sscanf(line.c_str(),"rect %s %s %d,%d %d,%d",ref,url,&x1,&y1,&x2,&y2); } // sanity checks if (y2ref(),TRUE); if (!df->file().isEmpty()) t << df->file() << Doxygen::htmlFileExtension; if (!df->anchor().isEmpty()) t << "#" << df->anchor(); delete df; } else { t << url; } t << "\" shape=\"rect\" coords=\"" << x1 << "," << y1 << "," << x2 << "," << y2 << "\"" << " alt=\"\"/>\n"; } } return true; } void writeMscGraphFromFile(const char *inFile,const char *outDir, const char *outFile,MscOutputFormat format) { QCString absOutFile = outDir; absOutFile+=Portable::pathSeparator(); absOutFile+=outFile; mscgen_format_t msc_format; QCString imgName = absOutFile; switch (format) { case MSC_BITMAP: msc_format = mscgen_format_png; imgName+=".png"; break; case MSC_EPS: msc_format = mscgen_format_eps; imgName+=".eps"; break; case MSC_SVG: msc_format = mscgen_format_svg; imgName+=".svg"; break; default: return; } int code; if ((code=mscgen_generate(inFile,imgName,msc_format))!=0) { err("Problems generating msc output (error=%s). Look for typos in you msc file %s\n", mscgen_error2str(code),inFile); return; } if ( (format==MSC_EPS) && (Config_getBool(USE_PDFLATEX)) ) { QCString epstopdfArgs(maxCmdLine); epstopdfArgs.sprintf("\"%s.eps\" --outfile=\"%s.pdf\"", absOutFile.data(),absOutFile.data()); Portable::sysTimerStart(); if (Portable::system("epstopdf",epstopdfArgs)!=0) { err("Problems running epstopdf. Check your TeX installation!\n"); } Portable::sysTimerStop(); } Doxygen::indexList->addImageFile(imgName); } static QCString getMscImageMapFromFile(const QCString& inFile, const QCString& outDir, const QCString& relPath,const QCString& context, bool writeSVGMap) { QCString outFile = inFile + ".map"; int code; if ((code=mscgen_generate(inFile,outFile, writeSVGMap ? mscgen_format_svgmap : mscgen_format_pngmap))!=0) { err("Problems generating msc output (error=%s). Look for typos in you msc file %s\n", mscgen_error2str(code),inFile.data()); return ""; } std::ostringstream t(std::ios_base::ate); convertMapFile(t, outFile, relPath, context); QCString result = t.str(); Dir().remove(outFile.str()); return result; } void writeMscImageMapFromFile(std::ostream &t,const QCString &inFile, const QCString &outDir, const QCString &relPath, const QCString &baseName, const QCString &context, MscOutputFormat format ) { QCString mapName = baseName+".map"; t << "\""\n"; t << "" << imap << "\n"; } else { t << "\" alt=\"" << baseName << "\" border=\"0\"/>\n"; } }