summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--CMakeLists.txt4
-rw-r--r--appveyor.yml4
-rw-r--r--libmscgen/gd.c82
-rw-r--r--libmscgen/gd_intern.h2
-rw-r--r--libmscgen/mscgen_api.c4
-rw-r--r--src/CMakeLists.txt15
-rw-r--r--src/configimpl.l27
-rw-r--r--src/doctokenizer.l7
-rw-r--r--src/dot.cpp273
-rw-r--r--src/dot.h41
-rw-r--r--src/dotdirdeps.cpp8
-rw-r--r--src/dotfilepatcher.cpp152
-rw-r--r--src/dotfilepatcher.h21
-rw-r--r--src/dotgraph.cpp101
-rw-r--r--src/dotgraph.h9
-rw-r--r--src/dotgroupcollaboration.cpp11
-rw-r--r--src/dotlegendgraph.cpp72
-rw-r--r--src/dotlegendgraph.h35
-rw-r--r--src/dotnode.cpp4
-rw-r--r--src/dotrunner.cpp18
-rw-r--r--src/dotrunner.h8
-rw-r--r--src/doxygen.cpp1
-rw-r--r--src/index.cpp7
-rw-r--r--src/util.cpp6
24 files changed, 457 insertions, 455 deletions
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 7aa1c01..2644ceb 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -49,8 +49,8 @@ if (use_libclang)
endif()
endif()
-# use C++11 standard for compiling (libclang option requires it)
-set(CMAKE_CXX_STANDARD 11)
+# use C++14 standard for compiling (libclang option requires it)
+set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
set(CMAKE_CXX_EXTENSIONS ON)
diff --git a/appveyor.yml b/appveyor.yml
index d18474f..7969be0 100644
--- a/appveyor.yml
+++ b/appveyor.yml
@@ -29,9 +29,9 @@ init:
install:
# Static url: https://github.com/MiKTeX/miktex/issues/321#issuecomment-496286866
# The setup is small enough, and does not need to be cached
- - appveyor DownloadFile https://miktex.org/download/win/miktexsetup-x64.zip
+ - appveyor-retry appveyor DownloadFile https://miktex.org/download/win/miktexsetup-x64.zip
- 7z e miktexsetup-x64.zip
- - miktexsetup.exe --local-package-repository=C:\miktex-repository --package-set=essential download
+ - appveyor-retry miktexsetup.exe --local-package-repository=C:\miktex-repository --package-set=essential download
- miktexsetup.exe --local-package-repository=C:\miktex-repository --package-set=essential --shared install
- refreshenv
- pip install conan
diff --git a/libmscgen/gd.c b/libmscgen/gd.c
index 7f0a258..da7731d 100644
--- a/libmscgen/gd.c
+++ b/libmscgen/gd.c
@@ -501,7 +501,7 @@ BGD_DECLARE(int) gdImageColorClosestAlpha (gdImagePtr im, int r, int g, int b, i
#define RETURN_HWB(h, w, b) {HWB->H = h; HWB->W = w; HWB->B = b; return HWB;}
#define RETURN_RGB(r, g, b) {RGB->R = r; RGB->G = g; RGB->B = b; return RGB;}
#define HWB_UNDEFINED -1
-#define SETUP_RGB(s, r, g, b) {s.R = r/255.0; s.G = g/255.0; s.B = b/255.0;}
+#define SETUP_RGB(s, r, g, b) {s.R = r/255.0f; s.G = g/255.0f; s.B = b/255.0f;}
#define MIN(a,b) ((a)<(b)?(a):(b))
#define MIN3(a,b,c) ((a)<(b)?(MIN(a,c)):(MIN(b,c)))
@@ -567,7 +567,7 @@ HWB_Diff (int r1, int g1, int b1, int r2, int g2, int b2)
if ((HWB1.H == HWB_UNDEFINED) || (HWB2.H == HWB_UNDEFINED)) {
diff = 0; /* Undefined hues always match... */
} else {
- diff = fabs (HWB1.H - HWB2.H);
+ diff = fabsf(HWB1.H - HWB2.H);
if (diff > 3) {
diff = 6 - diff; /* Remember, it's a colour circle */
}
@@ -1191,7 +1191,7 @@ clip_1d (int *x0, int *y0, int *x1, int *y1, int mindim, int maxdim)
*x0 = mindim;
/* now, perhaps, adjust the far end of the line as well */
if (*x1 > maxdim) {
- *y1 += m * (maxdim - *x1);
+ *y1 += (int)(m * (maxdim - *x1));
*x1 = maxdim;
}
return 1;
@@ -1594,7 +1594,7 @@ BGD_DECLARE(void) gdImageLine (gdImagePtr im, int x1, int y1, int x2, int y2, in
TBB: but watch out for /0! */
double ac = cos (atan2 (dy, dx));
if (ac != 0) {
- wid = thick / ac;
+ wid = (int)(thick / ac);
} else {
wid = 1;
}
@@ -1654,7 +1654,7 @@ BGD_DECLARE(void) gdImageLine (gdImagePtr im, int x1, int y1, int x2, int y2, in
TBB: but watch out for /0! */
double as = sin (atan2 (dy, dx));
if (as != 0) {
- wid = thick / as;
+ wid = (int)(thick / as);
} else {
wid = 1;
}
@@ -1734,7 +1734,7 @@ BGD_DECLARE(void) gdImageDashedLine (gdImagePtr im, int x1, int y1, int x2, int
TBB: but watch out for /0! */
double as = sin (atan2 (dy, dx));
if (as != 0) {
- wid = thick / as;
+ wid = (int)(thick / as);
} else {
wid = 1;
}
@@ -1783,7 +1783,7 @@ BGD_DECLARE(void) gdImageDashedLine (gdImagePtr im, int x1, int y1, int x2, int
TBB: but watch out for /0! */
double as = sin (atan2 (dy, dx));
if (as != 0) {
- wid = thick / as;
+ wid = (int)(thick / as);
} else {
wid = 1;
}
@@ -3071,12 +3071,12 @@ BGD_DECLARE(void) gdImageCopyMerge (gdImagePtr dst, gdImagePtr src, int dstX, in
} else {
dc = gdImageGetPixel (dst, tox, toy);
- ncR = gdImageRed (src, c) * (pct / 100.0)
- + gdImageRed (dst, dc) * ((100 - pct) / 100.0);
- ncG = gdImageGreen (src, c) * (pct / 100.0)
- + gdImageGreen (dst, dc) * ((100 - pct) / 100.0);
- ncB = gdImageBlue (src, c) * (pct / 100.0)
- + gdImageBlue (dst, dc) * ((100 - pct) / 100.0);
+ ncR = (int)(gdImageRed (src, c) * (pct / 100.0)
+ + gdImageRed (dst, dc) * ((100 - pct) / 100.0));
+ ncG = (int)(gdImageGreen (src, c) * (pct / 100.0)
+ + gdImageGreen (dst, dc) * ((100 - pct) / 100.0));
+ ncB = (int)(gdImageBlue (src, c) * (pct / 100.0)
+ + gdImageBlue (dst, dc) * ((100 - pct) / 100.0));
/* Find a reasonable color */
nc = gdImageColorResolve (dst, ncR, ncG, ncB);
@@ -3144,15 +3144,15 @@ BGD_DECLARE(void) gdImageCopyMergeGray (gdImagePtr dst, gdImagePtr src, int dstX
nc = c;
} else {
dc = gdImageGetPixel (dst, tox, toy);
- g = 0.29900 * gdImageRed(dst, dc)
- + 0.58700 * gdImageGreen(dst, dc) + 0.11400 * gdImageBlue(dst, dc);
+ g = 0.29900f * gdImageRed(dst, dc)
+ + 0.58700f * gdImageGreen(dst, dc) + 0.11400f * gdImageBlue(dst, dc);
- ncR = gdImageRed (src, c) * (pct / 100.0)
- + g * ((100 - pct) / 100.0);
- ncG = gdImageGreen (src, c) * (pct / 100.0)
- + g * ((100 - pct) / 100.0);
- ncB = gdImageBlue (src, c) * (pct / 100.0)
- + g * ((100 - pct) / 100.0);
+ ncR = (int)(gdImageRed (src, c) * (pct / 100.0)
+ + g * ((100 - pct) / 100.0));
+ ncG = (int)(gdImageGreen (src, c) * (pct / 100.0)
+ + g * ((100 - pct) / 100.0));
+ ncB = (int)(gdImageBlue (src, c) * (pct / 100.0)
+ + g * ((100 - pct) / 100.0));
/* First look for an exact match */
nc = gdImageColorExact (dst, ncR, ncG, ncB);
@@ -3378,14 +3378,14 @@ BGD_DECLARE(void) gdImageCopyRotated (gdImagePtr dst,
for (dx = dstX - radius; (dx <= dstX + radius); dx++) {
double sxd = (dx - dstX) * aCos - (dy - dstY) * aSin;
double syd = (dy - dstY) * aCos + (dx - dstX) * aSin;
- int sx = sxd + scX;
- int sy = syd + scY;
+ int sx = (int)(sxd + scX);
+ int sy = (int)(syd + scY);
if ((sx >= srcX) && (sx < srcX + srcWidth) &&
(sy >= srcY) && (sy < srcY + srcHeight)) {
int c = gdImageGetPixel (src, sx, sy);
/* 2.0.34: transparency wins */
if (c == src->transparent) {
- gdImageSetPixel (dst, dx, dy, dst->transparent);
+ gdImageSetPixel (dst, (int)dx, (int)dy, dst->transparent);
} else if (!src->trueColor) {
/* Use a table to avoid an expensive
lookup on every single pixel */
@@ -3399,10 +3399,10 @@ BGD_DECLARE(void) gdImageCopyRotated (gdImagePtr dst,
gdImageAlpha (src,
c));
}
- gdImageSetPixel (dst, dx, dy, cmap[c]);
+ gdImageSetPixel (dst, (int)dx, (int)dy, cmap[c]);
} else {
gdImageSetPixel (dst,
- dx, dy,
+ (int)dx, (int)dy,
gdImageColorResolveAlpha (dst,
gdImageRed (src,
c),
@@ -3469,16 +3469,16 @@ BGD_DECLARE(void) gdImageCopyResampled (gdImagePtr dst,
for (x = dstX; (x < dstX + dstW); x++) {
float sy1, sy2, sx1, sx2;
float sx, sy;
- float spixels = 0.0;
- float red = 0.0, green = 0.0, blue = 0.0, alpha = 0.0;
- float alpha_factor, alpha_sum = 0.0, contrib_sum = 0.0;
+ float spixels = 0.0f;
+ float red = 0.0f, green = 0.0f, blue = 0.0f, alpha = 0.0f;
+ float alpha_factor, alpha_sum = 0.0f, contrib_sum = 0.0f;
sy1 = ((float)(y - dstY)) * (float)srcH / (float)dstH;
sy2 = ((float)(y + 1 - dstY)) * (float) srcH / (float) dstH;
sy = sy1;
do {
float yportion;
if (floorf(sy) == floorf(sy1)) {
- yportion = 1.0 - (sy - floorf(sy));
+ yportion = 1.0f - (sy - floorf(sy));
if (yportion > sy2 - sy1) {
yportion = sy2 - sy1;
}
@@ -3486,7 +3486,7 @@ BGD_DECLARE(void) gdImageCopyResampled (gdImagePtr dst,
} else if (sy == floorf(sy2)) {
yportion = sy2 - floorf(sy2);
} else {
- yportion = 1.0;
+ yportion = 1.0f;
}
sx1 = ((float)(x - dstX)) * (float) srcW / dstW;
sx2 = ((float)(x + 1 - dstX)) * (float) srcW / dstW;
@@ -3496,7 +3496,7 @@ BGD_DECLARE(void) gdImageCopyResampled (gdImagePtr dst,
float pcontribution;
int p;
if (floorf(sx) == floorf(sx1)) {
- xportion = 1.0 - (sx - floorf(sx));
+ xportion = 1.0f - (sx - floorf(sx));
if (xportion > sx2 - sx1) {
xportion = sx2 - sx1;
}
@@ -3504,7 +3504,7 @@ BGD_DECLARE(void) gdImageCopyResampled (gdImagePtr dst,
} else if (sx == floorf(sx2)) {
xportion = sx2 - floorf(sx2);
} else {
- xportion = 1.0;
+ xportion = 1.0f;
}
pcontribution = xportion * yportion;
p = gdImageGetTrueColorPixel(src, (int) sx + srcX, (int) sy + srcY);
@@ -3517,14 +3517,14 @@ BGD_DECLARE(void) gdImageCopyResampled (gdImagePtr dst,
alpha_sum += alpha_factor;
contrib_sum += pcontribution;
spixels += xportion * yportion;
- sx += 1.0;
+ sx += 1.0f;
}
while (sx < sx2);
sy += 1.0f;
}
while (sy < sy2);
- if (spixels != 0.0) {
+ if (spixels != 0.0f) {
red /= spixels;
green /= spixels;
blue /= spixels;
@@ -3539,14 +3539,14 @@ BGD_DECLARE(void) gdImageCopyResampled (gdImagePtr dst,
blue /= alpha_sum;
}
/* Clamping to allow for rounding errors above */
- if (red > 255.0) {
- red = 255.0;
+ if (red > 255.0f) {
+ red = 255.0f;
}
- if (green > 255.0) {
- green = 255.0;
+ if (green > 255.0f) {
+ green = 255.0f;
}
if (blue > 255.0f) {
- blue = 255.0;
+ blue = 255.0f;
}
if (alpha > gdAlphaMax) {
alpha = gdAlphaMax;
@@ -4373,7 +4373,7 @@ static void gdImageAALine (gdImagePtr im, int x1, int y1, int x2, int y2, int co
* This isn't a problem as computed dy/dx values came from ints above. */
ag = fabs(abs((int)dy) < abs((int)dx) ? cos(atan2(dy, dx)) : sin(atan2(dy, dx)));
if (ag != 0) {
- wid = thick / ag;
+ wid = (int)(thick / ag);
} else {
wid = 1;
}
diff --git a/libmscgen/gd_intern.h b/libmscgen/gd_intern.h
index 2e7264b..c9d7f2e 100644
--- a/libmscgen/gd_intern.h
+++ b/libmscgen/gd_intern.h
@@ -58,7 +58,7 @@ uchar_clamp(double clr, unsigned char max) {
result = (clr < 0) ? 0 : max;
}/* if */
- return result;
+ return (unsigned char)result;
}/* uchar_clamp*/
diff --git a/libmscgen/mscgen_api.c b/libmscgen/mscgen_api.c
index 0f6052a..31f5556 100644
--- a/libmscgen/mscgen_api.c
+++ b/libmscgen/mscgen_api.c
@@ -1329,7 +1329,7 @@ static void arcLine(Context *ctx,
/* Get co-ordinates of the arc end-point */
ADrawComputeArcPoint(sx, y - 1, ctx->opts.entitySpacing - 8,
- ctx->opts.loopArcHeight, 180 - 45,
+ ctx->opts.loopArcHeight, 180.0f - 45.0f,
&px, &py);
/* Draw a cross */
@@ -1393,7 +1393,7 @@ static void arcLine(Context *ctx,
/* Get co-ordinates of the arc end-point */
ADrawComputeArcPoint(sx, y - 1, ctx->opts.entitySpacing - 8,
- ctx->opts.loopArcHeight, 45,
+ ctx->opts.loopArcHeight, 45.0f,
&px, &py);
/* Draw a cross */
diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt
index 7233052..217f391 100644
--- a/src/CMakeLists.txt
+++ b/src/CMakeLists.txt
@@ -181,16 +181,17 @@ add_library(_doxygen STATIC
docparser.cpp
docsets.cpp
dot.cpp
- dotcallgraph.cpp
- dotclassgraph.cpp
- dotdirdeps.cpp
- dotfilepatcher.cpp
+ dotcallgraph.cpp
+ dotlegendgraph.cpp
+ dotclassgraph.cpp
+ dotdirdeps.cpp
+ dotfilepatcher.cpp
dotgfxhierarchytable.cpp
dotgraph.cpp
- dotgroupcollaboration.cpp
- dotincldepgraph.cpp
+ dotgroupcollaboration.cpp
+ dotincldepgraph.cpp
dotnode.cpp
- dotrunner.cpp
+ dotrunner.cpp
doxygen.cpp
eclipsehelp.cpp
emoji.cpp
diff --git a/src/configimpl.l b/src/configimpl.l
index 2d91e12..e52a757 100644
--- a/src/configimpl.l
+++ b/src/configimpl.l
@@ -30,6 +30,7 @@
#include <qregexp.h>
#include <qstack.h>
#include <qglobal.h>
+#include <qthread.h>
#include "configimpl.h"
#include "version.h"
@@ -1531,6 +1532,7 @@ void Config::checkAndCorrect()
// dotImageFormat = "png";
//}
+ // correct DOT_FONTNAME if needed
QCString &dotFontName=Config_getString(DOT_FONTNAME);
if (dotFontName=="FreeSans" || dotFontName=="FreeSans.ttf")
{
@@ -1538,7 +1540,32 @@ void Config::checkAndCorrect()
"You may want to clear or change DOT_FONTNAME.\n"
"Otherwise you run the risk that the wrong font is being used for dot generated graphs.\n");
}
+ else if (dotFontName.isEmpty())
+ {
+ dotFontName = "Helvetica";
+ }
+ // clip dotFontSize against the maximum bounds
+ int &dotFontSize = Config_getInt(DOT_FONTSIZE);
+ if (dotFontSize<4)
+ {
+ dotFontSize=4;
+ }
+ else if (dotFontSize>24)
+ {
+ dotFontSize=24;
+ }
+
+ // clip number of threads
+ int &dotNumThreads = Config_getInt(DOT_NUM_THREADS);
+ if (dotNumThreads>32)
+ {
+ dotNumThreads=32;
+ }
+ else if (dotNumThreads<=0)
+ {
+ dotNumThreads=QMAX(2,QThread::idealThreadCount()+1);
+ }
// check dot path
QCString &dotPath = Config_getString(DOT_PATH);
diff --git a/src/doctokenizer.l b/src/doctokenizer.l
index 311e445..4527855 100644
--- a/src/doctokenizer.l
+++ b/src/doctokenizer.l
@@ -353,6 +353,7 @@ ATTRNAME [a-z_A-Z\x80-\xFF][a-z_A-Z0-9\x80-\xFF\-]*
ATTRIB {ATTRNAME}{WS}*("="{WS}*(("\""[^\"]*"\"")|("'"[^\']*"'")|[^ \t\r\n'"><]+))?
URLCHAR [a-z_A-Z0-9\!\~\,\:\;\'\$\?\@\&\%\#\.\-\+\/\=]
URLMASK ({URLCHAR}+([({]{URLCHAR}*[)}])?)+
+URLPROTOCOL ("http:"|"https:"|"ftp:"|"file:"|"news:"|"irc")
FILESCHAR [a-z_A-Z0-9\\:\\\/\-\+&#]
FILEECHAR [a-z_A-Z0-9\-\+&#]
HFILEMASK ("."{FILESCHAR}*{FILEECHAR}+)+
@@ -624,17 +625,17 @@ REFWORD_NOCV {FILEMASK}|{LABELID}|{REFWORD2_NOCV}|{REFWORD3}|{REFWORD4_NOCV}
}
return TK_COMMAND_SEL();
}
-<St_Para>("http:"|"https:"|"ftp:"|"file:"|"news:"){URLMASK}/\. { // URL.
+<St_Para>{URLPROTOCOL}{URLMASK}/\. { // URL.
g_token->name=yytext;
g_token->isEMailAddr=FALSE;
return TK_URL;
}
-<St_Para>("http:"|"https:"|"ftp:"|"file:"|"news:"){URLMASK} { // URL
+<St_Para>{URLPROTOCOL}{URLMASK} { // URL
g_token->name=yytext;
g_token->isEMailAddr=FALSE;
return TK_URL;
}
-<St_Para>"<"("http:"|"https:"|"ftp:"|"file:"|"news:"){URLMASK}">" { // URL
+<St_Para>"<"{URLPROTOCOL}{URLMASK}">" { // URL
g_token->name=yytext;
g_token->name = g_token->name.mid(1,g_token->name.length()-2);
g_token->isEMailAddr=FALSE;
diff --git a/src/dot.cpp b/src/dot.cpp
index 5cdf92c..5ad3916 100644
--- a/src/dot.cpp
+++ b/src/dot.cpp
@@ -16,12 +16,6 @@
#include <stdlib.h>
#include <qdir.h>
-#include <qfile.h>
-#include <qqueue.h>
-#include <qthread.h>
-#include <qmutex.h>
-#include <qwaitcondition.h>
-#include <qregexp.h>
#include "config.h"
#include "dot.h"
@@ -37,34 +31,8 @@
#define MAP_CMD "cmapx"
-static int DOT_NUM_THREADS; // will be initialized in initDot
-
//--------------------------------------------------------------------
-void initDot()
-{
- DotGraph::DOT_FONTNAME = Config_getString(DOT_FONTNAME);
- if (DotGraph::DOT_FONTNAME.isEmpty())
- {
- DotGraph::DOT_FONTNAME="Helvetica";
- }
-
- DotGraph::DOT_FONTSIZE = Config_getInt(DOT_FONTSIZE);
- if (DotGraph::DOT_FONTSIZE<4) DotGraph::DOT_FONTSIZE=4;
-
- DOT_NUM_THREADS = Config_getInt(DOT_NUM_THREADS);
- if (DOT_NUM_THREADS > 32) DOT_NUM_THREADS = 32;
- if (DOT_NUM_THREADS <= 0) DOT_NUM_THREADS = QMAX(2,QThread::idealThreadCount()+1);
-
- // these are copied to be sure to be thread save
- DotRunner::DOT_CLEANUP = Config_getBool(DOT_CLEANUP);
- DotRunner::DOT_MULTI_TARGETS = Config_getBool(DOT_MULTI_TARGETS);
- DotRunner::DOT_EXE.init(Config_getString(DOT_PATH) + "dot");
-
- DotGraph::IMG_EXT = getDotImageExtension();
-}
-
-
static QCString g_dotFontPath;
static void setDotFontPath(const char *path)
@@ -102,95 +70,6 @@ static void unsetDotFontPath()
g_dotFontPath="";
}
-// extract size from a dot generated SVG file
-static bool readSVGSize(const QCString &fileName,int *width,int *height)
-{
- bool found=FALSE;
- QFile f(fileName);
- if (!f.open(IO_ReadOnly))
- {
- return FALSE;
- }
- const int maxLineLen=4096;
- char buf[maxLineLen];
- while (!f.atEnd() && !found)
- {
- int numBytes = f.readLine(buf,maxLineLen-1); // read line
- if (numBytes>0)
- {
- buf[numBytes]='\0';
- if (qstrncmp(buf,"<!--zoomable ",13)==0)
- {
- *width=-1;
- *height=-1;
- sscanf(buf,"<!--zoomable %d",height);
- //printf("Found zoomable for %s!\n",fileName.data());
- found=TRUE;
- }
- else if (sscanf(buf,"<svg width=\"%dpt\" height=\"%dpt\"",width,height)==2)
- {
- //printf("Found fixed size %dx%d for %s!\n",*width,*height,fileName.data());
- found=TRUE;
- }
- }
- else // read error!
- {
- //printf("Read error %d!\n",numBytes);
- return FALSE;
- }
- }
- return TRUE;
-}
-
-static void writeSVGNotSupported(FTextStream &out)
-{
- out << "<p><b>This browser is not able to show SVG: try Firefox, Chrome, Safari, or Opera instead.</b></p>";
-}
-
-// check if a reference to a SVG figure can be written and does so if possible.
-// return FALSE if not possible (for instance because the SVG file is not yet generated).
-bool writeSVGFigureLink(FTextStream &out,const QCString &relPath,
- const QCString &baseName,const QCString &absImgName)
-{
- int width=600,height=600;
- if (!readSVGSize(absImgName,&width,&height))
- {
- return FALSE;
- }
- if (width==-1)
- {
- if (height<=60)
- height=300;
- else
- height+=300; // add some extra space for zooming
- if (height>600) height=600; // clip to maximum height of 600 pixels
- out << "<div class=\"zoom\">";
- //out << "<object type=\"image/svg+xml\" data=\""
- //out << "<embed type=\"image/svg+xml\" src=\""
- out << "<iframe scrolling=\"no\" frameborder=\"0\" src=\""
- << relPath << baseName << ".svg\" width=\"100%\" height=\"" << height << "\">";
- }
- else
- {
- //out << "<object type=\"image/svg+xml\" data=\""
- //out << "<embed type=\"image/svg+xml\" src=\""
- out << "<iframe scrolling=\"no\" frameborder=\"0\" src=\""
- << relPath << baseName << ".svg\" width=\""
- << ((width*96+48)/72) << "\" height=\""
- << ((height*96+48)/72) << "\">";
- }
- writeSVGNotSupported(out);
- //out << "</object>";
- //out << "</embed>";
- out << "</iframe>";
- if (width==-1)
- {
- out << "</div>";
- }
-
- return TRUE;
-}
-
//--------------------------------------------------------------------
DotManager *DotManager::m_theInstance = 0;
@@ -204,15 +83,16 @@ DotManager *DotManager::instance()
return m_theInstance;
}
-DotManager::DotManager() : m_dotMaps(1009)
+DotManager::DotManager() : m_runners(1009), m_filePatchers(1009)
{
m_runners.setAutoDelete(TRUE);
- m_dotMaps.setAutoDelete(TRUE);
+ m_filePatchers.setAutoDelete(TRUE);
m_queue = new DotRunnerQueue;
int i;
- if (DOT_NUM_THREADS!=1)
+ int dotNumThreads = Config_getInt(DOT_NUM_THREADS);
+ if (dotNumThreads!=1)
{
- for (i=0;i<DOT_NUM_THREADS;i++)
+ for (i=0;i<dotNumThreads;i++)
{
DotWorkerThread *thread = new DotWorkerThread(m_queue);
thread->start();
@@ -253,62 +133,22 @@ DotRunner* DotManager::createRunner(const QCString& absDotName, const QCString&
return run;
}
-
-int DotManager::addMap(const QCString &file,const QCString &mapFile,
- const QCString &relPath,bool urlOnly,const QCString &context,
- const QCString &label)
-{
- DotFilePatcher *map = m_dotMaps.find(file);
- if (map==0)
- {
- map = new DotFilePatcher(file);
- m_dotMaps.append(file,map);
- }
- return map->addMap(mapFile,relPath,urlOnly,context,label);
-}
-
-int DotManager::addFigure(const QCString &file,const QCString &baseName,
- const QCString &figureName,bool heightCheck)
-{
- DotFilePatcher *map = m_dotMaps.find(file);
- if (map==0)
- {
- map = new DotFilePatcher(file);
- m_dotMaps.append(file,map);
- }
- return map->addFigure(baseName,figureName,heightCheck);
-}
-
-int DotManager::addSVGConversion(const QCString &file,const QCString &relPath,
- bool urlOnly,const QCString &context,bool zoomable,
- int graphId)
+DotFilePatcher *DotManager::createFilePatcher(const QCString &fileName)
{
- DotFilePatcher *map = m_dotMaps.find(file);
- if (map==0)
+ DotFilePatcher *patcher = m_filePatchers.find(fileName);
+ if (patcher==0)
{
- map = new DotFilePatcher(file);
- m_dotMaps.append(file,map);
+ patcher = new DotFilePatcher(fileName);
+ m_filePatchers.append(fileName,patcher);
}
- return map->addSVGConversion(relPath,urlOnly,context,zoomable,graphId);
+ return patcher;
}
-int DotManager::addSVGObject(const QCString &file,const QCString &baseName,
- const QCString &absImgName,const QCString &relPath)
-{
- DotFilePatcher *map = m_dotMaps.find(file);
- if (map==0)
- {
- map = new DotFilePatcher(file);
- m_dotMaps.append(file,map);
- }
- return map->addSVGObject(baseName,absImgName,relPath);
-}
-
-bool DotManager::run()
+bool DotManager::run() const
{
uint numDotRuns = m_runners.count();
- uint numDotMaps = m_dotMaps.count();
- if (numDotRuns+numDotMaps>1)
+ uint numFilePatchers = m_filePatchers.count();
+ if (numDotRuns+numFilePatchers>1)
{
if (m_workers.count()==0)
{
@@ -316,7 +156,7 @@ bool DotManager::run()
}
else
{
- msg("Generating dot graphs using %d parallel threads...\n",QMIN(numDotRuns+numDotMaps,m_workers.count()));
+ msg("Generating dot graphs using %d parallel threads...\n",QMIN(numDotRuns+numFilePatchers,m_workers.count()));
}
}
int i=1;
@@ -397,27 +237,27 @@ bool DotManager::run()
// patch the output file and insert the maps and figures
i=1;
- SDict<DotFilePatcher>::Iterator di(m_dotMaps);
- DotFilePatcher *map;
+ SDict<DotFilePatcher>::Iterator di(m_filePatchers);
+ const DotFilePatcher *fp;
// since patching the svg files may involve patching the header of the SVG
// (for zoomable SVGs), and patching the .html files requires reading that
// header after the SVG is patched, we first process the .svg files and
// then the other files.
- for (di.toFirst();(map=di.current());++di)
+ for (di.toFirst();(fp=di.current());++di)
{
- if (map->file().right(4)==".svg")
+ if (fp->isSVGFile())
{
- msg("Patching output file %d/%d\n",i,numDotMaps);
- if (!map->run()) return FALSE;
+ msg("Patching output file %d/%d\n",i,numFilePatchers);
+ if (!fp->run()) return FALSE;
i++;
}
}
- for (di.toFirst();(map=di.current());++di)
+ for (di.toFirst();(fp=di.current());++di)
{
- if (map->file().right(4)!=".svg")
+ if (!fp->isSVGFile())
{
- msg("Patching output file %d/%d\n",i,numDotMaps);
- if (!map->run()) return FALSE;
+ msg("Patching output file %d/%d\n",i,numFilePatchers);
+ if (!fp->run()) return FALSE;
i++;
}
}
@@ -426,63 +266,6 @@ bool DotManager::run()
//--------------------------------------------------------------------
-class GraphLegendDotGraph : public DotGraph
-{
- private:
- virtual QCString getBaseName() const
- {
- return "graph_legend";
- }
-
- virtual void computeTheGraph()
- {
- FTextStream md5stream(&m_theGraph);
- writeGraphHeader(md5stream,theTranslator->trLegendTitle());
- md5stream << " Node9 [shape=\"box\",label=\"Inherited\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",fillcolor=\"grey75\",style=\"filled\" fontcolor=\"black\"];\n";
- md5stream << " Node10 -> Node9 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"solid\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node10 [shape=\"box\",label=\"PublicBase\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"black\",URL=\"$classPublicBase" << Doxygen::htmlFileExtension << "\"];\n";
- md5stream << " Node11 -> Node10 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"solid\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node11 [shape=\"box\",label=\"Truncated\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"red\",URL=\"$classTruncated" << Doxygen::htmlFileExtension << "\"];\n";
- md5stream << " Node13 -> Node9 [dir=\"back\",color=\"darkgreen\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"solid\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node13 [shape=\"box\",label=\"ProtectedBase\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"black\",URL=\"$classProtectedBase" << Doxygen::htmlFileExtension << "\"];\n";
- md5stream << " Node14 -> Node9 [dir=\"back\",color=\"firebrick4\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"solid\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node14 [shape=\"box\",label=\"PrivateBase\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"black\",URL=\"$classPrivateBase" << Doxygen::htmlFileExtension << "\"];\n";
- md5stream << " Node15 -> Node9 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"solid\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node15 [shape=\"box\",label=\"Undocumented\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"grey75\"];\n";
- md5stream << " Node16 -> Node9 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"solid\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node16 [shape=\"box\",label=\"Templ< int >\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"black\",URL=\"$classTempl" << Doxygen::htmlFileExtension << "\"];\n";
- md5stream << " Node17 -> Node16 [dir=\"back\",color=\"orange\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"dashed\",label=\"< int >\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node17 [shape=\"box\",label=\"Templ< T >\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"black\",URL=\"$classTempl" << Doxygen::htmlFileExtension << "\"];\n";
- md5stream << " Node18 -> Node9 [dir=\"back\",color=\"darkorchid3\",fontsize=\"" << DOT_FONTSIZE << "\",style=\"dashed\",label=\"m_usedClass\",fontname=\"" << DOT_FONTNAME << "\"];\n";
- md5stream << " Node18 [shape=\"box\",label=\"Used\",fontsize=\"" << DOT_FONTSIZE << "\",height=0.2,width=0.4,fontname=\"" << DOT_FONTNAME << "\",color=\"black\",URL=\"$classUsed" << Doxygen::htmlFileExtension << "\"];\n";
- writeGraphFooter(md5stream);
- }
-
- virtual QCString getMapLabel() const
- {
- return "";
- }
-
- friend void generateGraphLegend(const char* path);
-};
-
-void generateGraphLegend(const char *path)
-{
- QDir d(path);
- GraphLegendDotGraph dg;
- FTextStream ts;
- dg.writeGraph(ts, GOF_BITMAP, EOF_Html, path, "", "", FALSE, 0);
-
- if (getDotImageExtension()=="svg")
- {
- DotManager::instance()->addSVGObject(
- dg.absBaseName()+Config_getString(HTML_FILE_EXTENSION),
- "graph_legend",
- dg.absImgName(),QCString());
- }
-
-}
-
void writeDotGraphFromFile(const char *inFile,const char *outDir,
const char *outFile,GraphOutputFormat format)
{
@@ -560,10 +343,8 @@ void writeDotImageMapFromFile(FTextStream &t,
if (imgExt=="svg") // vector graphics
{
- //writeSVGFigureLink(t,relPath,inFile,inFile+".svg");
- //DotFilePatcher patcher(inFile+".svg");
QCString svgName=outDir+"/"+baseName+".svg";
- writeSVGFigureLink(t,relPath,baseName,svgName);
+ DotFilePatcher::writeSVGFigureLink(t,relPath,baseName,svgName);
DotFilePatcher patcher(svgName);
patcher.addSVGConversion("",TRUE,context,TRUE,graphId);
patcher.run();
@@ -575,7 +356,7 @@ void writeDotImageMapFromFile(FTextStream &t,
t << "<img src=\"" << relPath << imgName << "\" alt=\""
<< imgName << "\" border=\"0\" usemap=\"#" << mapName << "\"/>" << endl;
- convertMapFile(tt, absOutFile, relPath ,TRUE, context);
+ DotFilePatcher::convertMapFile(tt, absOutFile, relPath ,TRUE, context);
if (!result.isEmpty())
{
t << "<map name=\"" << mapName << "\" id=\"" << mapName << "\">";
diff --git a/src/dot.h b/src/dot.h
index 124a32b..60f7f26 100644
--- a/src/dot.h
+++ b/src/dot.h
@@ -18,66 +18,43 @@
#include <qlist.h>
#include <qdict.h>
-#include <qwaitcondition.h>
-#include <qmutex.h>
-#include <qqueue.h>
-#include <qthread.h>
+#include <qcstring.h>
+
#include "sortdict.h"
-#include "qgstring.h"
-#include "qdir.h"
-#include "qcstring.h"
-#include "dotgraph.h"
+
+#include "dotgraph.h" // only for GraphOutputFormat
#include "dotfilepatcher.h"
#include "dotrunner.h"
class FTextStream;
class DotRunner;
class DotRunnerQueue;
-class DotWorkerThread;
-/** Singleton that manages dot relation actions */
+/** Singleton that manages parallel dot invocations and patching files for embedding image maps */
class DotManager
{
public:
static DotManager *instance();
- DotRunner* createRunner(const QCString& absDotName, const QCString& md5Hash);
- int addMap(const QCString &file,const QCString &mapFile,
- const QCString &relPath,bool urlOnly,
- const QCString &context,const QCString &label);
- int addFigure(const QCString &file,const QCString &baseName,
- const QCString &figureName,bool heightCheck);
- int addSVGConversion(const QCString &file,const QCString &relPath,
- bool urlOnly,const QCString &context,bool zoomable,int graphId);
- int addSVGObject(const QCString &file,const QCString &baseName,
- const QCString &figureNAme,const QCString &relPath);
- bool run();
+ DotRunner* createRunner(const QCString& absDotName, const QCString& md5Hash);
+ DotFilePatcher *createFilePatcher(const QCString &fileName);
+ bool run() const;
private:
DotManager();
virtual ~DotManager();
QDict<DotRunner> m_runners;
- SDict<DotFilePatcher> m_dotMaps;
+ SDict<DotFilePatcher> m_filePatchers;
static DotManager *m_theInstance;
DotRunnerQueue *m_queue;
QList<DotWorkerThread> m_workers;
};
-void initDot();
-
-/** Generated a graphs legend page */
-void generateGraphLegend(const char *path);
-
void writeDotGraphFromFile(const char *inFile,const char *outDir,
const char *outFile,GraphOutputFormat format);
void writeDotImageMapFromFile(FTextStream &t,
const QCString& inFile, const QCString& outDir,
const QCString& relPath,const QCString& baseName,
const QCString& context,int graphId=-1);
-bool writeSVGFigureLink(FTextStream &out,const QCString &relPath,
- const QCString &baseName,const QCString &absImgName);
-bool convertMapFile(FTextStream &t,const char *mapName,
- const QCString relPath, bool urlOnly=FALSE,
- const QCString &context=QCString());
#endif
diff --git a/src/dotdirdeps.cpp b/src/dotdirdeps.cpp
index 85906d1..98c7ca7 100644
--- a/src/dotdirdeps.cpp
+++ b/src/dotdirdeps.cpp
@@ -22,14 +22,16 @@
void writeDotDirDepGraph(FTextStream &t,const DirDef *dd,bool linkRelations)
{
+ int fontSize = Config_getInt(DOT_FONTSIZE);
+ QCString fontName = Config_getString(DOT_FONTNAME);
t << "digraph \"" << dd->displayName() << "\" {\n";
if (Config_getBool(DOT_TRANSPARENT))
{
t << " bgcolor=transparent;\n";
}
t << " compound=true\n";
- t << " node [ fontsize=\"" << DotGraph::DOT_FONTSIZE << "\", fontname=\"" << DotGraph::DOT_FONTNAME << "\"];\n";
- t << " edge [ labelfontsize=\"" << DotGraph::DOT_FONTSIZE << "\", labelfontname=\"" << DotGraph::DOT_FONTNAME << "\"];\n";
+ t << " node [ fontsize=\"" << fontSize << "\", fontname=\"" << fontName << "\"];\n";
+ t << " edge [ labelfontsize=\"" << fontSize << "\", labelfontname=\"" << fontName << "\"];\n";
QDict<DirDef> dirsInGraph(257);
@@ -39,7 +41,7 @@ void writeDotDirDepGraph(FTextStream &t,const DirDef *dd,bool linkRelations)
t << " subgraph cluster" << dd->parent()->getOutputFileBase() << " {\n";
t << " graph [ bgcolor=\"#ddddee\", pencolor=\"black\", label=\""
<< dd->parent()->shortName()
- << "\" fontname=\"" << DotGraph::DOT_FONTNAME << "\", fontsize=\"" << DotGraph::DOT_FONTSIZE << "\", URL=\"";
+ << "\" fontname=\"" << fontName << "\", fontsize=\"" << fontSize << "\", URL=\"";
t << dd->parent()->getOutputFileBase() << Doxygen::htmlFileExtension;
t << "\"]\n";
}
diff --git a/src/dotfilepatcher.cpp b/src/dotfilepatcher.cpp
index 91b7c78..92a5618 100644
--- a/src/dotfilepatcher.cpp
+++ b/src/dotfilepatcher.cpp
@@ -14,6 +14,7 @@
*/
#include "dotfilepatcher.h"
+#include "dotrunner.h"
#include "qstring.h"
#include "config.h"
@@ -209,7 +210,7 @@ static QCString replaceRef(const QCString &buf,const QCString relPath,
* map file was found
* \returns TRUE if successful.
*/
-bool convertMapFile(FTextStream &t,const char *mapName,
+bool DotFilePatcher::convertMapFile(FTextStream &t,const char *mapName,
const QCString relPath, bool urlOnly,
const QCString &context)
{
@@ -255,9 +256,9 @@ DotFilePatcher::DotFilePatcher(const char *patchFile)
m_maps.setAutoDelete(TRUE);
}
-QCString DotFilePatcher::file() const
+bool DotFilePatcher::isSVGFile() const
{
- return m_patchFile;
+ return m_patchFile.right(4)==".svg";
}
int DotFilePatcher::addMap(const QCString &mapFile,const QCString &relPath,
@@ -320,7 +321,7 @@ int DotFilePatcher::addSVGObject(const QCString &baseName,
return id;
}
-bool DotFilePatcher::run()
+bool DotFilePatcher::run() const
{
//printf("DotFilePatcher::run(): %s\n",m_patchFile.data());
bool interactiveSVG_local = Config_getBool(INTERACTIVE_SVG);
@@ -479,7 +480,7 @@ bool DotFilePatcher::run()
Map *map = m_maps.at(mapId);
//printf("patching FIG %d in file %s with contents of %s\n",
// mapId,m_patchFile.data(),map->mapFile.data());
- if (!DotGraph::writeVecGfxFigure(t,map->label,map->mapFile))
+ if (!writeVecGfxFigure(t,map->label,map->mapFile))
{
err("problem writing FIG %d figure!\n",mapId);
return FALSE;
@@ -537,3 +538,144 @@ bool DotFilePatcher::run()
QDir::current().remove(tmpName);
return TRUE;
}
+
+//---------------------------------------------------------------------------------------------
+
+
+// extract size from a dot generated SVG file
+static bool readSVGSize(const QCString &fileName,int *width,int *height)
+{
+ bool found=FALSE;
+ QFile f(fileName);
+ if (!f.open(IO_ReadOnly))
+ {
+ return FALSE;
+ }
+ const int maxLineLen=4096;
+ char buf[maxLineLen];
+ while (!f.atEnd() && !found)
+ {
+ int numBytes = f.readLine(buf,maxLineLen-1); // read line
+ if (numBytes>0)
+ {
+ buf[numBytes]='\0';
+ if (qstrncmp(buf,"<!--zoomable ",13)==0)
+ {
+ *width=-1;
+ *height=-1;
+ sscanf(buf,"<!--zoomable %d",height);
+ //printf("Found zoomable for %s!\n",fileName.data());
+ found=TRUE;
+ }
+ else if (sscanf(buf,"<svg width=\"%dpt\" height=\"%dpt\"",width,height)==2)
+ {
+ //printf("Found fixed size %dx%d for %s!\n",*width,*height,fileName.data());
+ found=TRUE;
+ }
+ }
+ else // read error!
+ {
+ //printf("Read error %d!\n",numBytes);
+ return FALSE;
+ }
+ }
+ return TRUE;
+}
+
+static void writeSVGNotSupported(FTextStream &out)
+{
+ out << "<p><b>This browser is not able to show SVG: try Firefox, Chrome, Safari, or Opera instead.</b></p>";
+}
+
+/// Check if a reference to a SVG figure can be written and do so if possible.
+/// Returns FALSE if not possible (for instance because the SVG file is not yet generated).
+bool DotFilePatcher::writeSVGFigureLink(FTextStream &out,const QCString &relPath,
+ const QCString &baseName,const QCString &absImgName)
+{
+ int width=600,height=600;
+ if (!readSVGSize(absImgName,&width,&height))
+ {
+ return FALSE;
+ }
+ if (width==-1)
+ {
+ if (height<=60) height=300; else height+=300; // add some extra space for zooming
+ if (height>600) height=600; // clip to maximum height of 600 pixels
+ out << "<div class=\"zoom\">";
+ //out << "<object type=\"image/svg+xml\" data=\""
+ //out << "<embed type=\"image/svg+xml\" src=\""
+ out << "<iframe scrolling=\"no\" frameborder=\"0\" src=\""
+ << relPath << baseName << ".svg\" width=\"100%\" height=\"" << height << "\">";
+ }
+ else
+ {
+ //out << "<object type=\"image/svg+xml\" data=\""
+ //out << "<embed type=\"image/svg+xml\" src=\""
+ out << "<iframe scrolling=\"no\" frameborder=\"0\" src=\""
+ << relPath << baseName << ".svg\" width=\""
+ << ((width*96+48)/72) << "\" height=\""
+ << ((height*96+48)/72) << "\">";
+ }
+ writeSVGNotSupported(out);
+ //out << "</object>";
+ //out << "</embed>";
+ out << "</iframe>";
+ if (width==-1)
+ {
+ out << "</div>";
+ }
+
+ return TRUE;
+}
+
+bool DotFilePatcher::writeVecGfxFigure(FTextStream &out,const QCString &baseName,
+ const QCString &figureName)
+{
+ int width=400,height=550;
+ if (Config_getBool(USE_PDFLATEX))
+ {
+ if (!DotRunner::readBoundingBox(figureName+".pdf",&width,&height,FALSE))
+ {
+ //printf("writeVecGfxFigure()=0\n");
+ return FALSE;
+ }
+ }
+ else
+ {
+ if (!DotRunner::readBoundingBox(figureName+".eps",&width,&height,TRUE))
+ {
+ //printf("writeVecGfxFigure()=0\n");
+ return FALSE;
+ }
+ }
+ //printf("Got PDF/EPS size %d,%d\n",width,height);
+ int maxWidth = 350; /* approx. page width in points, excl. margins */
+ int maxHeight = 550; /* approx. page height in points, excl. margins */
+ out << "\\nopagebreak\n"
+ "\\begin{figure}[H]\n"
+ "\\begin{center}\n"
+ "\\leavevmode\n";
+ if (width>maxWidth || height>maxHeight) // figure too big for page
+ {
+ // c*width/maxWidth > c*height/maxHeight, where c=maxWidth*maxHeight>0
+ if (width*maxHeight>height*maxWidth)
+ {
+ out << "\\includegraphics[width=" << maxWidth << "pt]";
+ }
+ else
+ {
+ out << "\\includegraphics[height=" << maxHeight << "pt]";
+ }
+ }
+ else
+ {
+ out << "\\includegraphics[width=" << width << "pt]";
+ }
+
+ out << "{" << baseName << "}\n"
+ "\\end{center}\n"
+ "\\end{figure}\n";
+
+ //printf("writeVecGfxFigure()=1\n");
+ return TRUE;
+}
diff --git a/src/dotfilepatcher.h b/src/dotfilepatcher.h
index dd5c511..b68208d 100644
--- a/src/dotfilepatcher.h
+++ b/src/dotfilepatcher.h
@@ -19,21 +19,37 @@
#include "qcstring.h"
#include "qlist.h"
+class FTextStream;
+
/** Helper class to insert a set of map file into an output file */
class DotFilePatcher
{
public:
DotFilePatcher(const char *patchFile);
+
int addMap(const QCString &mapFile,const QCString &relPath,
bool urlOnly,const QCString &context,const QCString &label);
+
int addFigure(const QCString &baseName,
const QCString &figureName,bool heightCheck);
+
int addSVGConversion(const QCString &relPath,bool urlOnly,
const QCString &context,bool zoomable,int graphId);
+
int addSVGObject(const QCString &baseName, const QCString &figureName,
const QCString &relPath);
- bool run();
- QCString file() const;
+ bool run() const;
+ bool isSVGFile() const;
+
+ static bool convertMapFile(FTextStream &t,const char *mapName,
+ const QCString relPath, bool urlOnly=FALSE,
+ const QCString &context=QCString());
+
+ static bool writeSVGFigureLink(FTextStream &out,const QCString &relPath,
+ const QCString &baseName,const QCString &absImgName);
+
+ static bool writeVecGfxFigure(FTextStream& out, const QCString& baseName,
+ const QCString& figureName);
private:
struct Map
@@ -50,4 +66,5 @@ class DotFilePatcher
QCString m_patchFile;
};
+
#endif
diff --git a/src/dotgraph.cpp b/src/dotgraph.cpp
index ca6bcca..df64d66 100644
--- a/src/dotgraph.cpp
+++ b/src/dotgraph.cpp
@@ -24,11 +24,12 @@
#include "dotrunner.h"
#include "dotgraph.h"
#include "dotnode.h"
+#include "dotfilepatcher.h"
#define MAP_CMD "cmapx"
-QCString DotGraph::DOT_FONTNAME; // will be initialized in initDot
-int DotGraph::DOT_FONTSIZE; // will be initialized in initDot
+//QCString DotGraph::DOT_FONTNAME; // will be initialized in initDot
+//int DotGraph::DOT_FONTSIZE; // will be initialized in initDot
/*! Checks if a file "baseName".md5 exists. If so the contents
* are compared with \a md5. If equal FALSE is returned.
@@ -90,7 +91,7 @@ static bool insertMapFile(FTextStream &out,const QCString &mapFile,
{
QGString tmpstr;
FTextStream tmpout(&tmpstr);
- convertMapFile(tmpout,mapFile,relPath,FALSE);
+ DotFilePatcher::convertMapFile(tmpout,mapFile,relPath,FALSE);
if (!tmpstr.isEmpty())
{
out << "<map name=\"" << mapLabel << "\" id=\"" << mapLabel << "\">" << endl;
@@ -104,12 +105,10 @@ static bool insertMapFile(FTextStream &out,const QCString &mapFile,
//--------------------------------------------------------------------
-QCString DotGraph::IMG_EXT;
-
QCString DotGraph::imgName() const
{
return m_baseName + ((m_graphFormat == GOF_BITMAP) ?
- ("." + IMG_EXT) : (Config_getBool(USE_PDFLATEX) ? ".pdf" : ".eps"));
+ ("." + getDotImageExtension()) : (Config_getBool(USE_PDFLATEX) ? ".pdf" : ".eps"));
}
QCString DotGraph::writeGraph(
@@ -209,6 +208,7 @@ bool DotGraph::prepareDotFile()
void DotGraph::generateCode(FTextStream &t)
{
+ QCString imgExt = getDotImageExtension();
if (m_graphFormat==GOF_BITMAP && m_textFormat==EOF_DocBook)
{
t << "<para>" << endl;
@@ -216,7 +216,7 @@ void DotGraph::generateCode(FTextStream &t)
t << " <mediaobject>" << endl;
t << " <imageobject>" << endl;
t << " <imagedata";
- t << " width=\"50%\" align=\"center\" valign=\"middle\" scalefit=\"0\" fileref=\"" << m_relPath << m_baseName << "." << IMG_EXT << "\">";
+ t << " width=\"50%\" align=\"center\" valign=\"middle\" scalefit=\"0\" fileref=\"" << m_relPath << m_baseName << "." << imgExt << "\">";
t << "</imagedata>" << endl;
t << " </imageobject>" << endl;
t << " </mediaobject>" << endl;
@@ -225,16 +225,20 @@ void DotGraph::generateCode(FTextStream &t)
}
else if (m_graphFormat==GOF_BITMAP && m_generateImageMap) // produce HTML to include the image
{
- if (IMG_EXT=="svg") // add link to SVG file without map file
+ if (imgExt=="svg") // add link to SVG file without map file
{
if (!m_noDivTag) t << "<div class=\"center\">";
- if (m_regenerate || !writeSVGFigureLink(t,m_relPath,m_baseName,absImgName())) // need to patch the links in the generated SVG file
+ if (m_regenerate || !DotFilePatcher::writeSVGFigureLink(t,m_relPath,m_baseName,absImgName())) // need to patch the links in the generated SVG file
{
if (m_regenerate)
{
- DotManager::instance()->addSVGConversion(absImgName(),m_relPath,FALSE,QCString(),m_zoomable,m_graphId);
+ DotManager::instance()->
+ createFilePatcher(absImgName())->
+ addSVGConversion(m_relPath,FALSE,QCString(),m_zoomable,m_graphId);
}
- int mapId = DotManager::instance()->addSVGObject(m_fileName,m_baseName,absImgName(),m_relPath);
+ int mapId = DotManager::instance()->
+ createFilePatcher(m_fileName)->
+ addSVGObject(m_baseName,absImgName(),m_relPath);
t << "<!-- SVG " << mapId << " -->" << endl;
}
if (!m_noDivTag) t << "</div>" << endl;
@@ -247,16 +251,20 @@ void DotGraph::generateCode(FTextStream &t)
t << endl;
if (m_regenerate || !insertMapFile(t, absMapName(), m_relPath, getMapLabel()))
{
- int mapId = DotManager::instance()->addMap(m_fileName, absMapName(), m_relPath, m_urlOnly, QCString(), getMapLabel());
+ int mapId = DotManager::instance()->
+ createFilePatcher(m_fileName)->
+ addMap(absMapName(), m_relPath, m_urlOnly, QCString(), getMapLabel());
t << "<!-- MAP " << mapId << " -->" << endl;
}
}
}
else if (m_graphFormat==GOF_EPS) // produce tex to include the .eps image
{
- if (m_regenerate || !writeVecGfxFigure(t,m_baseName,absBaseName()))
+ if (m_regenerate || !DotFilePatcher::writeVecGfxFigure(t,m_baseName,absBaseName()))
{
- int figId = DotManager::instance()->addFigure(m_fileName,m_baseName,absBaseName(),FALSE /*TRUE*/);
+ int figId = DotManager::instance()->
+ createFilePatcher(m_fileName)->
+ addFigure(m_baseName,absBaseName(),FALSE /*TRUE*/);
t << endl << "% FIG " << figId << endl;
}
}
@@ -264,6 +272,8 @@ void DotGraph::generateCode(FTextStream &t)
void DotGraph::writeGraphHeader(FTextStream &t,const QCString &title)
{
+ int fontSize = Config_getInt(DOT_FONTSIZE);
+ QCString fontName = Config_getString(DOT_FONTNAME);
t << "digraph ";
if (title.isEmpty())
{
@@ -284,12 +294,12 @@ void DotGraph::writeGraphHeader(FTextStream &t,const QCString &title)
{
t << " bgcolor=\"transparent\";" << endl;
}
- t << " edge [fontname=\"" << DOT_FONTNAME << "\","
- "fontsize=\"" << DOT_FONTSIZE << "\","
- "labelfontname=\"" << DOT_FONTNAME << "\","
- "labelfontsize=\"" << DOT_FONTSIZE << "\"];\n";
- t << " node [fontname=\"" << DOT_FONTNAME << "\","
- "fontsize=\"" << DOT_FONTSIZE << "\",shape=record];\n";
+ t << " edge [fontname=\"" << fontName << "\","
+ "fontsize=\"" << fontSize << "\","
+ "labelfontname=\"" << fontName << "\","
+ "labelfontsize=\"" << fontSize << "\"];\n";
+ t << " node [fontname=\"" << fontName << "\","
+ "fontsize=\"" << fontSize << "\",shape=record];\n";
}
void DotGraph::writeGraphFooter(FTextStream &t)
@@ -347,54 +357,3 @@ void DotGraph::computeGraph(DotNode *root,
graphStr=buf.data();
}
-bool DotGraph::writeVecGfxFigure(FTextStream &out,const QCString &baseName,
- const QCString &figureName)
-{
- int width=400,height=550;
- if (Config_getBool(USE_PDFLATEX))
- {
- if (!DotRunner::readBoundingBox(figureName+".pdf",&width,&height,FALSE))
- {
- //printf("writeVecGfxFigure()=0\n");
- return FALSE;
- }
- }
- else
- {
- if (!DotRunner::readBoundingBox(figureName+".eps",&width,&height,TRUE))
- {
- //printf("writeVecGfxFigure()=0\n");
- return FALSE;
- }
- }
- //printf("Got PDF/EPS size %d,%d\n",width,height);
- int maxWidth = 350; /* approx. page width in points, excl. margins */
- int maxHeight = 550; /* approx. page height in points, excl. margins */
- out << "\\nopagebreak\n"
- "\\begin{figure}[H]\n"
- "\\begin{center}\n"
- "\\leavevmode\n";
- if (width>maxWidth || height>maxHeight) // figure too big for page
- {
- // c*width/maxWidth > c*height/maxHeight, where c=maxWidth*maxHeight>0
- if (width*maxHeight>height*maxWidth)
- {
- out << "\\includegraphics[width=" << maxWidth << "pt]";
- }
- else
- {
- out << "\\includegraphics[height=" << maxHeight << "pt]";
- }
- }
- else
- {
- out << "\\includegraphics[width=" << width << "pt]";
- }
-
- out << "{" << baseName << "}\n"
- "\\end{center}\n"
- "\\end{figure}\n";
-
- //printf("writeVecGfxFigure()=1\n");
- return TRUE;
-}
diff --git a/src/dotgraph.h b/src/dotgraph.h
index 27d6938..0eda3a8 100644
--- a/src/dotgraph.h
+++ b/src/dotgraph.h
@@ -34,11 +34,6 @@ class DotGraph
DotGraph() : m_curNodeNumber(0), m_doNotAddImageToIndex(FALSE), m_noDivTag(FALSE), m_zoomable(TRUE), m_urlOnly(FALSE) {}
virtual ~DotGraph() {}
- static QCString DOT_FONTNAME; // will be initialized in initDot
- static int DOT_FONTSIZE; // will be initialized in initDot
-
- static bool writeVecGfxFigure(FTextStream& out, const QCString& baseName, const QCString& figureName);
-
protected:
/** returns node numbers. The Counter is reset by the constructor */
int getNextNodeNumber() { return ++m_curNodeNumber; }
@@ -72,10 +67,6 @@ class DotGraph
virtual void computeTheGraph() = 0;
- static QCString IMG_EXT;
-
- friend void initDot();
-
QCString absBaseName() const { return m_absPath + m_baseName; }
QCString absDotName() const { return m_absPath + m_baseName + ".dot"; }
QCString imgName() const;
diff --git a/src/dotgroupcollaboration.cpp b/src/dotgroupcollaboration.cpp
index be55ac0..f9a11e7 100644
--- a/src/dotgroupcollaboration.cpp
+++ b/src/dotgroupcollaboration.cpp
@@ -356,9 +356,10 @@ bool DotGroupCollaboration::isTrivial() const
return m_usedNodes->count() <= 1;
}
-void DotGroupCollaboration::writeGraphHeader(FTextStream &t,
- const QCString &title) const
+void DotGroupCollaboration::writeGraphHeader(FTextStream &t,const QCString &title) const
{
+ int fontSize = Config_getInt(DOT_FONTSIZE);
+ QCString fontName = Config_getString(DOT_FONTNAME);
t << "digraph ";
if (title.isEmpty())
{
@@ -374,8 +375,8 @@ void DotGroupCollaboration::writeGraphHeader(FTextStream &t,
{
t << " bgcolor=\"transparent\";" << endl;
}
- t << " edge [fontname=\"" << DOT_FONTNAME << "\",fontsize=\"" << DOT_FONTSIZE << "\","
- "labelfontname=\"" << DOT_FONTNAME << "\",labelfontsize=\"" << DOT_FONTSIZE << "\"];\n";
- t << " node [fontname=\"" << DOT_FONTNAME << "\",fontsize=\"" << DOT_FONTSIZE << "\",shape=box];\n";
+ t << " edge [fontname=\"" << fontName << "\",fontsize=\"" << fontSize << "\","
+ "labelfontname=\"" << fontName << "\",labelfontsize=\"" << fontSize << "\"];\n";
+ t << " node [fontname=\"" << fontName << "\",fontsize=\"" << fontSize << "\",shape=box];\n";
t << " rankdir=LR;\n";
}
diff --git a/src/dotlegendgraph.cpp b/src/dotlegendgraph.cpp
new file mode 100644
index 0000000..98e1f88
--- /dev/null
+++ b/src/dotlegendgraph.cpp
@@ -0,0 +1,72 @@
+/******************************************************************************
+*
+* Copyright (C) 1997-2019 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 "dotlegendgraph.h"
+#include "util.h"
+#include "config.h"
+#include "doxygen.h"
+#include "dot.h"
+#include "language.h"
+#include "dotfilepatcher.h"
+
+void DotLegendGraph::writeGraph(const char *path)
+{
+ FTextStream ts;
+ DotGraph::writeGraph(ts, GOF_BITMAP, EOF_Html, path, "", "", FALSE, 0);
+
+ if (getDotImageExtension()=="svg")
+ {
+ DotManager::instance()->
+ createFilePatcher(absBaseName()+Config_getString(HTML_FILE_EXTENSION))->
+ addSVGObject("graph_legend", absImgName(),QCString());
+ }
+}
+
+QCString DotLegendGraph::getBaseName() const
+{
+ return "graph_legend";
+}
+
+void DotLegendGraph::computeTheGraph()
+{
+ int fontSize = Config_getInt(DOT_FONTSIZE);
+ QCString fontName = Config_getString(DOT_FONTNAME);
+ FTextStream md5stream(&m_theGraph);
+ writeGraphHeader(md5stream,theTranslator->trLegendTitle());
+ md5stream << " Node9 [shape=\"box\",label=\"Inherited\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",fillcolor=\"grey75\",style=\"filled\" fontcolor=\"black\"];\n";
+ md5stream << " Node10 -> Node9 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << fontSize << "\",style=\"solid\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node10 [shape=\"box\",label=\"PublicBase\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"black\"];\n";
+ md5stream << " Node11 -> Node10 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << fontSize << "\",style=\"solid\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node11 [shape=\"box\",label=\"Truncated\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"red\"];\n";
+ md5stream << " Node13 -> Node9 [dir=\"back\",color=\"darkgreen\",fontsize=\"" << fontSize << "\",style=\"solid\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node13 [shape=\"box\",label=\"ProtectedBase\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"black\"];\n";
+ md5stream << " Node14 -> Node9 [dir=\"back\",color=\"firebrick4\",fontsize=\"" << fontSize << "\",style=\"solid\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node14 [shape=\"box\",label=\"PrivateBase\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"black\"];\n";
+ md5stream << " Node15 -> Node9 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << fontSize << "\",style=\"solid\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node15 [shape=\"box\",label=\"Undocumented\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"grey75\"];\n";
+ md5stream << " Node16 -> Node9 [dir=\"back\",color=\"midnightblue\",fontsize=\"" << fontSize << "\",style=\"solid\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node16 [shape=\"box\",label=\"Templ< int >\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"black\"];\n";
+ md5stream << " Node17 -> Node16 [dir=\"back\",color=\"orange\",fontsize=\"" << fontSize << "\",style=\"dashed\",label=\"< int >\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node17 [shape=\"box\",label=\"Templ< T >\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"black\"];\n";
+ md5stream << " Node18 -> Node9 [dir=\"back\",color=\"darkorchid3\",fontsize=\"" << fontSize << "\",style=\"dashed\",label=\"m_usedClass\",fontname=\"" << fontName << "\"];\n";
+ md5stream << " Node18 [shape=\"box\",label=\"Used\",fontsize=\"" << fontSize << "\",height=0.2,width=0.4,fontname=\"" << fontName << "\",color=\"black\"];\n";
+ writeGraphFooter(md5stream);
+}
+
+QCString DotLegendGraph::getMapLabel() const
+{
+ return "";
+}
+
diff --git a/src/dotlegendgraph.h b/src/dotlegendgraph.h
new file mode 100644
index 0000000..2d8eeec
--- /dev/null
+++ b/src/dotlegendgraph.h
@@ -0,0 +1,35 @@
+/******************************************************************************
+*
+* Copyright (C) 1997-2019 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.
+*
+*/
+
+#ifndef DOTLEGENDGRAPH_H
+#define DOTLEGENDGRAPH_H
+
+#include "dotgraph.h"
+
+/** Representation of a legend explaining the meaning of boxes, arrows, and colors */
+class DotLegendGraph : public DotGraph
+{
+ public:
+ void writeGraph(const char *path);
+
+ private:
+ virtual QCString getBaseName() const;
+ virtual void computeTheGraph();
+ virtual QCString getMapLabel() const;
+
+};
+
+#endif
+
diff --git a/src/dotnode.cpp b/src/dotnode.cpp
index ae06fb2..491bcb5 100644
--- a/src/dotnode.cpp
+++ b/src/dotnode.cpp
@@ -540,7 +540,7 @@ void DotNode::writeArrow(FTextStream &t,
if (pointBack && !umlUseArrow) t << "dir=\"back\",";
t << "color=\"" << eProps->edgeColorMap[ei->color()]
- << "\",fontsize=\"" << DotGraph::DOT_FONTSIZE << "\",";
+ << "\",fontsize=\"" << Config_getInt(DOT_FONTSIZE) << "\",";
t << "style=\"" << eProps->edgeStyleMap[ei->style()] << "\"";
if (!ei->label().isEmpty())
{
@@ -559,7 +559,7 @@ void DotNode::writeArrow(FTextStream &t,
t << ",arrowhead=\"" << eProps->arrowStyleMap[ei->color()] << "\"";
}
- if (format==GOF_BITMAP) t << ",fontname=\"" << DotGraph::DOT_FONTNAME << "\"";
+ if (format==GOF_BITMAP) t << ",fontname=\"" << Config_getString(DOT_FONTNAME) << "\"";
t << "];" << endl;
}
diff --git a/src/dotrunner.cpp b/src/dotrunner.cpp
index 3a621c7..c01a4e5 100644
--- a/src/dotrunner.cpp
+++ b/src/dotrunner.cpp
@@ -28,6 +28,7 @@
#define MAX_LATEX_GRAPH_INCH 150
#define MAX_LATEX_GRAPH_SIZE (MAX_LATEX_GRAPH_INCH * 72)
+//-----------------------------------------------------------------------------------------
// since dot silently reproduces the input file when it does not
// support the PNG format, we need to check the result.
@@ -142,12 +143,11 @@ bool DotRunner::readBoundingBox(const char *fileName,int *width,int *height,bool
return FALSE;
}
-bool DotRunner::DOT_CLEANUP;
-bool DotRunner::DOT_MULTI_TARGETS;
-DotConstString DotRunner::DOT_EXE;
+//---------------------------------------------------------------------------------
DotRunner::DotRunner(const QCString& absDotName, const QCString& md5Hash)
- : m_file(absDotName), m_md5Hash(md5Hash), m_cleanUp(DOT_CLEANUP)
+ : m_file(absDotName), m_md5Hash(md5Hash), m_cleanUp(Config_getBool(DOT_CLEANUP)),
+ m_dotExe(Config_getString(DOT_PATH)+"dot")
{
m_jobs.setAutoDelete(TRUE);
}
@@ -183,7 +183,7 @@ bool DotRunner::run()
DotJob *s;
// create output
- if (DOT_MULTI_TARGETS)
+ if (Config_getBool(DOT_MULTI_TARGETS))
{
dotArgs=QCString("\"")+m_file.data()+"\"";
for (li.toFirst();(s=li.current());++li)
@@ -191,14 +191,14 @@ bool DotRunner::run()
dotArgs+=' ';
dotArgs+=s->args.data();
}
- if ((exitCode=portable_system(DOT_EXE.data(),dotArgs,FALSE))!=0) goto error;
+ if ((exitCode=portable_system(m_dotExe.data(),dotArgs,FALSE))!=0) goto error;
}
else
{
for (li.toFirst();(s=li.current());++li)
{
dotArgs=QCString("\"")+m_file.data()+"\" "+s->args.data();
- if ((exitCode=portable_system(DOT_EXE.data(),dotArgs,FALSE))!=0) goto error;
+ if ((exitCode=portable_system(m_dotExe.data(),dotArgs,FALSE))!=0) goto error;
}
}
@@ -214,7 +214,7 @@ bool DotRunner::run()
{
if (!resetPDFSize(width,height,getBaseNameOfOutput(s->output.data()))) goto error;
dotArgs=QCString("\"")+m_file.data()+"\" "+s->args.data();
- if ((exitCode=portable_system(DOT_EXE.data(),dotArgs,FALSE))!=0) goto error;
+ if ((exitCode=portable_system(m_dotExe.data(),dotArgs,FALSE))!=0) goto error;
}
}
@@ -245,7 +245,7 @@ bool DotRunner::run()
return TRUE;
error:
err("Problems running dot: exit code=%d, command='%s', arguments='%s'\n",
- exitCode,DOT_EXE.data(),dotArgs.data());
+ exitCode,m_dotExe.data(),dotArgs.data());
return FALSE;
}
diff --git a/src/dotrunner.h b/src/dotrunner.h
index 4128fe8..1b68c18 100644
--- a/src/dotrunner.h
+++ b/src/dotrunner.h
@@ -34,7 +34,6 @@ class DotConstString
DotConstString(const DotConstString &s) : m_str(0) { set(s.data()); }
const char *data() const { return m_str; }
bool isEmpty() const { return m_str==0 || m_str[0]=='\0'; }
- void init(const char *s) { set(s); }
private:
void set(char const* s)
@@ -101,14 +100,9 @@ class DotRunner
private:
DotConstString m_file;
DotConstString m_md5Hash;
+ DotConstString m_dotExe;
bool m_cleanUp;
QList<DotJob> m_jobs;
-
- static bool DOT_CLEANUP;
- static bool DOT_MULTI_TARGETS;
- static DotConstString DOT_EXE;
- friend void initDot();
-
};
/** Queue of dot jobs to run. */
diff --git a/src/doxygen.cpp b/src/doxygen.cpp
index a6455fc..f8e54de 100644
--- a/src/doxygen.cpp
+++ b/src/doxygen.cpp
@@ -11680,7 +11680,6 @@ void generateOutput()
}
initSearchIndexer();
- initDot();
bool generateHtml = Config_getBool(GENERATE_HTML);
bool generateLatex = Config_getBool(GENERATE_LATEX);
diff --git a/src/index.cpp b/src/index.cpp
index 0631ee4..f5faea4 100644
--- a/src/index.cpp
+++ b/src/index.cpp
@@ -41,6 +41,7 @@
#include "ftvhelp.h"
#include "dot.h"
#include "dotgfxhierarchytable.h"
+#include "dotlegendgraph.h"
#include "pagedef.h"
#include "dirdef.h"
#include "vhdldocgen.h"
@@ -3919,7 +3920,9 @@ void writeGraphInfo(OutputList &ol)
if (!Config_getBool(HAVE_DOT) || !Config_getBool(GENERATE_HTML)) return;
ol.pushGeneratorState();
ol.disableAllBut(OutputGenerator::Html);
- generateGraphLegend(Config_getString(HTML_OUTPUT));
+
+ DotLegendGraph gd;
+ gd.writeGraph(Config_getString(HTML_OUTPUT));
bool &stripCommentsStateRef = Config_getBool(STRIP_CODE_COMMENTS);
bool oldStripCommentsState = stripCommentsStateRef;
@@ -3944,7 +3947,7 @@ void writeGraphInfo(OutputList &ol)
legendDocs = legendDocs.left(s+8) + "[!-- SVG 0 --]\n" + legendDocs.mid(e);
//printf("legendDocs=%s\n",legendDocs.data());
}
- FileDef *fd = createFileDef("","graph_legend");
+ FileDef *fd = createFileDef("","graph_legend.dox");
ol.generateDoc("graph_legend",1,fd,0,legendDocs,FALSE,FALSE);
delete fd;
diff --git a/src/util.cpp b/src/util.cpp
index 8816de1..4dc7c71 100644
--- a/src/util.cpp
+++ b/src/util.cpp
@@ -9051,9 +9051,9 @@ bool mainPageHasTitle()
QCString getDotImageExtension(void)
{
- QCString imgExt = Config_getEnum(DOT_IMAGE_FORMAT);
- imgExt = imgExt.replace( QRegExp(":.*"), "" );
- return imgExt;
+ QCString imgExt = Config_getEnum(DOT_IMAGE_FORMAT);
+ int i= imgExt.find(':'); // strip renderer part when using e.g. 'png:cairo:gd' as format
+ return i==-1 ? imgExt : imgExt.left(i);
}
bool openOutputFile(const char *outFile,QFile &f)