Doxygen
dotnode.cpp
浏览该文件的文档.
1 /******************************************************************************
2 *
3 * Copyright (C) 1997-2019 by Dimitri van Heesch.
4 *
5 * Permission to use, copy, modify, and distribute this software and its
6 * documentation under the terms of the GNU General Public License is hereby
7 * granted. No representations are made about the suitability of this software
8 * for any purpose. It is provided "as is" without express or implied warranty.
9 * See the GNU General Public License for more details.
10 *
11 * Documents produced by Doxygen are derivative works derived from the
12 * input used in their production; they are not affected by this license.
13 *
14 */
15 
16 #include "dotnode.h"
17 #include "classdef.h"
18 #include "config.h"
19 #include "memberlist.h"
20 #include "membergroup.h"
21 #include "language.h"
22 #include "doxygen.h"
23 #include "util.h"
24 #include "textstream.h"
25 
26 /** Helper struct holding the properties of a edge in a dot graph. */
28 {
29  const char * const *edgeColorMap;
30  const char * const *arrowStyleMap;
31  const char * const *edgeStyleMap;
32 };
33 
34 /*! mapping from protection levels to color names */
35 static const char *normalEdgeColorMap[] =
36 {
37  "midnightblue", // Public
38  "darkgreen", // Protected
39  "firebrick4", // Private
40  "darkorchid3", // "use" relation
41  "grey75", // Undocumented
42  "orange", // template relation
43  "orange" // type constraint
44 };
45 
46 static const char *normalArrowStyleMap[] =
47 {
48  "empty", // Public
49  "empty", // Protected
50  "empty", // Private
51  "open", // "use" relation
52  0, // Undocumented
53  0 // template relation
54 };
55 
56 static const char *normalEdgeStyleMap[] =
57 {
58  "solid", // inheritance
59  "dashed" // usage
60 };
61 
62 static const char *umlEdgeColorMap[] =
63 {
64  "midnightblue", // Public
65  "darkgreen", // Protected
66  "firebrick4", // Private
67  "grey25", // "use" relation
68  "grey75", // Undocumented
69  "orange", // template relation
70  "orange" // type constraint
71 };
72 
73 static const char *umlArrowStyleMap[] =
74 {
75  "onormal", // Public
76  "onormal", // Protected
77  "onormal", // Private
78  "odiamond", // "use" relation
79  0, // Undocumented
80  0 // template relation
81 };
82 
83 static const char *umlEdgeStyleMap[] =
84 {
85  "solid", // inheritance
86  "solid" // usage
87 };
88 
90 {
92 };
93 
95 {
97 };
98 
99 static QCString escapeTooltip(const QCString &tooltip)
100 {
101  if (tooltip.isEmpty()) return tooltip;
102  QCString result;
103  const char *p=tooltip.data();
104  char c;
105  while ((c=*p++))
106  {
107  switch(c)
108  {
109  case '"': result+="\\\""; break;
110  case '\\': result+="\\\\"; break;
111  default: result+=c; break;
112  }
113  }
114  return result;
115 }
116 
118  char prot,const MemberList *ml,const ClassDef *scope,
119  bool isStatic=FALSE,const StringUnorderedSet *skipNames=nullptr)
120 {
121  if (ml)
122  {
123  int totalCount=0;
124  for (const auto &mma : *ml)
125  {
126  if (mma->getClassDef()==scope &&
127  (skipNames==nullptr || skipNames->find(mma->name().str())==std::end(*skipNames)))
128  {
129  totalCount++;
130  }
131  }
132 
133  int count=0;
134  static auto dotUmlDetails = Config_getEnum(DOT_UML_DETAILS);
135  for (const auto &mma : *ml)
136  {
137  if (mma->getClassDef() == scope &&
138  (skipNames==nullptr || skipNames->find(mma->name().str())==std::end(*skipNames)))
139  {
140  int numFields = Config_getInt(UML_LIMIT_NUM_FIELDS);
141  if (numFields>0 && (totalCount>numFields*3/2 && count>=numFields))
142  {
143  t << theTranslator->trAndMore(QCString().sprintf("%d",totalCount-count)) << "\\l";
144  break;
145  }
146  else
147  {
148  t << prot << " ";
149  QCString label;
150  if (dotUmlDetails==DOT_UML_DETAILS_t::YES)
151  {
152  label+=mma->typeString();
153  label+=" ";
154  }
155  label+=mma->name();
156  if (!mma->isObjCMethod() && (mma->isFunction() || mma->isSlot() || mma->isSignal()))
157  {
158  if (dotUmlDetails==DOT_UML_DETAILS_t::YES)
159  {
160  label+=mma->argsString();
161  }
162  else
163  {
164  label+="()";
165  }
166  }
167  t << DotNode::convertLabel(label);
168  t << "\\l";
169  count++;
170  }
171  }
172  }
173  // write member groups within the memberlist
174  for (const auto &mg : ml->getMemberGroupList())
175  {
176  if (!mg->members().empty())
177  {
178  writeBoxMemberList(t,prot,&mg->members(),scope,isStatic,skipNames);
179  }
180  }
181  }
182 }
183 
185 {
186  QCString bBefore("\\_/<({[: =-+@%#~?$"); // break before character set
187  QCString bAfter(">]),:;|"); // break after character set
188  QCString p(l);
189  if (p.isEmpty()) return QCString();
190  QCString result;
191  char c,pc=0;
192  uint idx = 0;
193  int len=p.length();
194  int charsLeft=len;
195  int sinceLast=0;
196  int foldLen = Config_getInt(DOT_WRAP_THRESHOLD); // ideal text length
197  while (idx < p.length())
198  {
199  c = p[idx++];
200  QCString replacement;
201  switch(c)
202  {
203  case '\\': replacement="\\\\"; break;
204  case '\n': replacement="\\n"; break;
205  case '<': replacement="\\<"; break;
206  case '>': replacement="\\>"; break;
207  case '|': replacement="\\|"; break;
208  case '{': replacement="\\{"; break;
209  case '}': replacement="\\}"; break;
210  case '"': replacement="\\\""; break;
211  default: replacement+=c; break;
212  }
213  // Some heuristics to insert newlines to prevent too long
214  // boxes and at the same time prevent ugly breaks
215  if (c=='\n')
216  {
217  result+=replacement;
218  foldLen = (3*foldLen+sinceLast+2)/4;
219  sinceLast=1;
220  }
221  else if ((pc!=':' || c!=':') && charsLeft>foldLen/3 && sinceLast>foldLen && bBefore.contains(c))
222  {
223  result+="\\l";
224  result+=replacement;
225  foldLen = (foldLen+sinceLast+1)/2;
226  sinceLast=1;
227  }
228  else if (charsLeft>1+foldLen/4 && sinceLast>foldLen+foldLen/3 &&
229  !isupper(c) && isupper(p[idx]))
230  {
231  result+=replacement;
232  result+="\\l";
233  foldLen = (foldLen+sinceLast+1)/2;
234  sinceLast=0;
235  }
236  else if (charsLeft>foldLen/3 && sinceLast>foldLen && bAfter.contains(c) && (c!=':' || p[idx]!=':'))
237  {
238  result+=replacement;
239  result+="\\l";
240  foldLen = (foldLen+sinceLast+1)/2;
241  sinceLast=0;
242  }
243  else
244  {
245  result+=replacement;
246  sinceLast++;
247  }
248  charsLeft--;
249  pc=c;
250  }
251  return result;
252 }
253 
255 {
256  if (!s.isEmpty() && (s[0]=='-' || s[0]=='+' || s[0]=='~' || s[0]=='#'))
257  {
258  return s.mid(1);
259  }
260  else
261  {
262  return s;
263  }
264 }
265 
266 DotNode::DotNode(int n,const QCString &lab,const QCString &tip, const QCString &url,
267  bool isRoot,const ClassDef *cd)
268  : m_number(n)
269  , m_label(lab)
270  , m_tooltip(tip)
271  , m_url(url)
272  , m_isRoot(isRoot)
273  , m_classDef(cd)
274 {
275 }
276 
278 {
279 }
280 
282  int edgeColor,
283  int edgeStyle,
284  const QCString &edgeLab,
285  const QCString &edgeURL,
286  int edgeLabCol
287 )
288 {
289  m_children.push_back(n);
290  m_edgeInfo.emplace_back(
291  edgeColor,
292  edgeStyle,
293  edgeLab,
294  edgeURL,
295  edgeLabCol==-1 ? edgeColor : edgeLabCol);
296 }
297 
299 {
300  m_parents.push_back(n);
301 }
302 
304 {
305  auto it = std::find(m_children.begin(),m_children.end(),n);
306  if (it!=m_children.end()) m_children.erase(it);
307 }
308 
310 {
311  auto it = std::find(m_parents.begin(),m_parents.end(),n);
312  if (it!=m_parents.end()) m_parents.erase(it);
313 }
314 
316 {
317  if (m_deleted) return; // avoid recursive loops in case the graph has cycles
318  m_deleted=TRUE;
319  // delete all parent nodes of this node
320  for (const auto &pn : m_parents)
321  {
322  pn->deleteNode(deletedList);
323  }
324  // delete all child nodes of this node
325  for (const auto &cn : m_children)
326  {
327  cn->deleteNode(deletedList);
328  }
329  // add this node to the list of deleted nodes.
330  deletedList.push_back(this);
331 }
332 
333 void DotNode::setDistance(int distance)
334 {
336 }
337 
338 inline int DotNode::findParent( DotNode *n )
339 {
340  auto it = std::find(m_parents.begin(),m_parents.end(),n);
341  return it!=m_parents.end() ? static_cast<int>(it-m_parents.begin()) : -1;
342 }
343 
344 /*! helper function that deletes all nodes in a connected graph, given
345 * one of the graph's nodes
346 */
348 {
349  DotNodeRefVector deletedNodes;
350  node->deleteNode(deletedNodes); // collect nodes to be deleted.
351  for (const auto &dotNode : deletedNodes)
352  {
353  delete dotNode;
354  }
355 }
356 
358  GraphType gt,
359  GraphOutputFormat /*format*/,
360  bool hasNonReachableChildren) const
361 {
362  const char *labCol =
363  m_url.isEmpty() ? "grey75" : // non link
364  (hasNonReachableChildren ? "red" : "black");
365  t << " Node" << m_number << " [label=\"";
366 
367  if (m_classDef && Config_getBool(UML_LOOK) && (gt==Inheritance || gt==Collaboration))
368  {
369  // add names shown as relations to a set, so we don't show
370  // them as attributes as well
371  StringUnorderedSet arrowNames;
372  // for each edge
373  for (const auto &ei : m_edgeInfo)
374  {
375  if (!ei.label().isEmpty()) // labels joined by \n
376  {
377  int i=ei.label().find('\n');
378  int p=0;
379  QCString lab;
380  while ((i=ei.label().find('\n',p))!=-1)
381  {
382  lab = stripProtectionPrefix(ei.label().mid(p,i-p));
383  arrowNames.insert(lab.str());
384  p=i+1;
385  }
386  lab = stripProtectionPrefix(ei.label().right(ei.label().length()-p));
387  arrowNames.insert(lab.str());
388  }
389  }
390 
391  //printf("DotNode::writeBox for %s\n",qPrint(m_classDef->name()));
392  t << "{" << convertLabel(m_label) << "\\n";
393  static auto dotUmlDetails = Config_getEnum(DOT_UML_DETAILS);
394  if (dotUmlDetails!=DOT_UML_DETAILS_t::NONE)
395  {
396  t << "|";
404  if (Config_getBool(EXTRACT_PRIVATE))
405  {
408  }
409  t << "|";
418  if (Config_getBool(EXTRACT_PRIVATE))
419  {
423  }
425  {
426  for (const auto &mg : m_classDef->getMemberGroups())
427  {
428  if (!mg->members().empty())
429  {
430  writeBoxMemberList(t,'*',&mg->members(),m_classDef,FALSE,&arrowNames);
431  }
432  }
433  }
434  }
435  t << "}";
436  }
437  else // standard look
438  {
439  t << convertLabel(m_label);
440  }
441  t << "\",height=0.2,width=0.4";
442  if (m_isRoot)
443  {
444  t << ",color=\"black\", fillcolor=\"grey75\", style=\"filled\", fontcolor=\"black\"";
445  }
446  else
447  {
448  if (!Config_getBool(DOT_TRANSPARENT))
449  {
450  t << ",color=\"" << labCol << "\", fillcolor=\"";
451  t << "white";
452  t << "\", style=\"filled\"";
453  }
454  else
455  {
456  t << ",color=\"" << labCol << "\"";
457  }
458  if (!m_url.isEmpty())
459  {
460  int anchorPos = m_url.findRev('#');
461  if (anchorPos==-1)
462  {
463  t << ",URL=\"" << addHtmlExtensionIfMissing(m_url) << "\"";
464  }
465  else
466  {
467  t << ",URL=\"" << addHtmlExtensionIfMissing(m_url.left(anchorPos))
468  << m_url.right(m_url.length()-anchorPos) << "\"";
469  }
470  }
471  }
472  if (!m_tooltip.isEmpty())
473  {
474  t << ",tooltip=\"" << escapeTooltip(m_tooltip) << "\"";
475  }
476  else
477  {
478  t << ",tooltip=\" \""; // space in tooltip is required otherwise still something like 'Node0' is used
479  }
480  t << "];\n";
481 }
482 
484  GraphType gt,
485  GraphOutputFormat format,
486  const DotNode *cn,
487  const EdgeInfo *ei,
488  bool topDown,
489  bool pointBack) const
490 {
491  t << " Node";
492  if (topDown)
493  t << cn->number();
494  else
495  t << m_number;
496  t << " -> Node";
497  if (topDown)
498  t << m_number;
499  else
500  t << cn->number();
501  t << " [";
502 
503  const EdgeProperties *eProps = Config_getBool(UML_LOOK) ? &umlEdgeProps : &normalEdgeProps;
504  QCString aStyle = eProps->arrowStyleMap[ei->color()];
505  bool umlUseArrow = aStyle=="odiamond";
506 
507  if (pointBack && !umlUseArrow) t << "dir=\"back\",";
508  t << "color=\"" << eProps->edgeColorMap[ei->color()]
509  << "\",fontsize=\"" << Config_getInt(DOT_FONTSIZE) << "\",";
510  t << "style=\"" << eProps->edgeStyleMap[ei->style()] << "\"";
511  if (!ei->label().isEmpty())
512  {
513  t << ",label=\" " << convertLabel(ei->label()) << "\" ";
514  }
515  if (Config_getBool(UML_LOOK) &&
516  eProps->arrowStyleMap[ei->color()] &&
517  (gt==Inheritance || gt==Collaboration)
518  )
519  {
520  bool rev = pointBack;
521  if (umlUseArrow) rev=!rev; // UML use relates has arrow on the start side
522  if (rev)
523  t << ",arrowtail=\"" << eProps->arrowStyleMap[ei->color()] << "\"";
524  else
525  t << ",arrowhead=\"" << eProps->arrowStyleMap[ei->color()] << "\"";
526  }
527 
528  if (format==GOF_BITMAP) t << ",fontname=\"" << Config_getString(DOT_FONTNAME) << "\"";
529  t << "];\n";
530 }
531 
533  GraphType gt,
534  GraphOutputFormat format,
535  bool topDown,
536  bool toChildren,
537  bool backArrows) const
538 {
539  //printf("DotNode::write(%d) name=%s this=%p written=%d visible=%d\n",m_distance,qPrint(m_label),this,m_written,m_visible);
540  if (m_written) return; // node already written to the output
541  if (!m_visible) return; // node is not visible
542  writeBox(t,gt,format,m_truncated==Truncated);
543  m_written=TRUE;
544  if (toChildren)
545  {
546  auto it = m_edgeInfo.begin();
547  for (const auto &cn : m_children)
548  {
549  if (cn->isVisible())
550  {
551  //printf("write arrow %s%s%s\n",qPrint(label()),backArrows?"<-":"->",qPrint(cn->label()));
552  writeArrow(t,gt,format,cn,&(*it),topDown,backArrows);
553  }
554  cn->write(t,gt,format,topDown,toChildren,backArrows);
555  ++it;
556  }
557  }
558  else // render parents
559  {
560  for (const auto &pn : m_parents)
561  {
562  if (pn->isVisible())
563  {
564  const auto &children = pn->children();
565  auto child_it = std::find(children.begin(),children.end(),this);
566  size_t index = child_it - children.begin();
567  //printf("write arrow %s%s%s\n",qPrint(label()),backArrows?"<-":"->",qPrint(pn->label()));
568  writeArrow(t,
569  gt,
570  format,
571  pn,
572  &pn->edgeInfo()[index],
573  FALSE,
574  backArrows
575  );
576  }
577  pn->write(t,gt,format,TRUE,FALSE,backArrows);
578  }
579  }
580  //printf("end DotNode::write(%d) name=%s\n",distance,qPrint(m_label));
581 }
582 
583 void DotNode::writeXML(TextStream &t,bool isClassGraph) const
584 {
585  t << " <node id=\"" << m_number << "\">\n";
586  t << " <label>" << convertToXML(m_label) << "</label>\n";
587  if (!m_url.isEmpty())
588  {
589  QCString url(m_url);
590  int dollarPos = url.find('$');
591  if (dollarPos!=-1)
592  {
593  t << " <link refid=\"" << convertToXML(url.mid(dollarPos+1)) << "\"";
594  if (dollarPos>0)
595  {
596  t << " external=\"" << convertToXML(url.left(dollarPos)) << "\"";
597  }
598  t << "/>\n";
599  }
600  }
601  auto it = m_edgeInfo.begin();
602  for (const auto &childNode : m_children)
603  {
604  const EdgeInfo &edgeInfo = *it;
605  t << " <childnode refid=\"" << childNode->number() << "\" relation=\"";
606  if (isClassGraph)
607  {
608  switch(edgeInfo.color())
609  {
610  case EdgeInfo::Blue: t << "public-inheritance"; break;
611  case EdgeInfo::Green: t << "protected-inheritance"; break;
612  case EdgeInfo::Red: t << "private-inheritance"; break;
613  case EdgeInfo::Purple: t << "usage"; break;
614  case EdgeInfo::Orange: t << "template-instance"; break;
615  case EdgeInfo::Orange2: t << "type-constraint"; break;
616  case EdgeInfo::Grey: ASSERT(0); break;
617  }
618  }
619  else // include graph
620  {
621  t << "include";
622  }
623  t << "\">\n";
624  if (!edgeInfo.label().isEmpty())
625  {
626  int p=0;
627  int ni;
628  while ((ni=edgeInfo.label().find('\n',p))!=-1)
629  {
630  t << " <edgelabel>"
631  << convertToXML(edgeInfo.label().mid(p,ni-p))
632  << "</edgelabel>\n";
633  p=ni+1;
634  }
635  t << " <edgelabel>"
636  << convertToXML(edgeInfo.label().right(edgeInfo.label().length()-p))
637  << "</edgelabel>\n";
638  }
639  t << " </childnode>\n";
640  ++it;
641  }
642  t << " </node>\n";
643 }
644 
645 void DotNode::writeDocbook(TextStream &t,bool isClassGraph) const
646 {
647  t << " <node id=\"" << m_number << "\">\n";
648  t << " <label>" << convertToXML(m_label) << "</label>\n";
649  if (!m_url.isEmpty())
650  {
651  QCString url(m_url);
652  int dollarPos = url.find('$');
653  if (dollarPos!=-1)
654  {
655  t << " <link refid=\"" << convertToXML(url.mid(dollarPos+1)) << "\"";
656  if (dollarPos>0)
657  {
658  t << " external=\"" << convertToXML(url.left(dollarPos)) << "\"";
659  }
660  t << "/>\n";
661  }
662  }
663  auto it = m_edgeInfo.begin();
664  for (const auto &childNode : m_children)
665  {
666  const EdgeInfo &edgeInfo = *it;
667  t << " <childnode refid=\"" << childNode->number() << "\" relation=\"";
668  if (isClassGraph)
669  {
670  switch(edgeInfo.color())
671  {
672  case EdgeInfo::Blue: t << "public-inheritance"; break;
673  case EdgeInfo::Green: t << "protected-inheritance"; break;
674  case EdgeInfo::Red: t << "private-inheritance"; break;
675  case EdgeInfo::Purple: t << "usage"; break;
676  case EdgeInfo::Orange: t << "template-instance"; break;
677  case EdgeInfo::Orange2: t << "type-constraint"; break;
678  case EdgeInfo::Grey: ASSERT(0); break;
679  }
680  }
681  else // include graph
682  {
683  t << "include";
684  }
685  t << "\">\n";
686  if (!edgeInfo.label().isEmpty())
687  {
688  int p=0;
689  int ni;
690  while ((ni=edgeInfo.label().find('\n',p))!=-1)
691  {
692  t << " <edgelabel>"
693  << convertToXML(edgeInfo.label().mid(p,ni-p))
694  << "</edgelabel>\n";
695  p=ni+1;
696  }
697  t << " <edgelabel>"
698  << convertToXML(edgeInfo.label().right(edgeInfo.label().length()-p))
699  << "</edgelabel>\n";
700  }
701  t << " </childnode>\n";
702  ++it;
703  }
704  t << " </node>\n";
705 }
706 
707 
709 {
710  const char* nodePrefix = " node-";
711 
712  t << " node = {\n";
713  t << nodePrefix << "id = " << m_number << ";\n";
714  t << nodePrefix << "label = '" << m_label << "';\n";
715 
716  if (!m_url.isEmpty())
717  {
718  QCString url(m_url);
719  int dollarPos = url.find('$');
720  if (dollarPos!=-1)
721  {
722  t << nodePrefix << "link = {\n" << " "
723  << nodePrefix << "link-id = '" << url.mid(dollarPos+1) << "';\n";
724  if (dollarPos>0)
725  {
726  t << " " << nodePrefix << "link-external = '"
727  << url.left(dollarPos) << "';\n";
728  }
729  t << " };\n";
730  }
731  }
732  auto it = m_edgeInfo.begin();
733  for (const auto &childNode : m_children)
734  {
735  const EdgeInfo &edgeInfo = *it;
736  t << " node-child = {\n";
737  t << " child-id = '" << childNode->number() << "';\n";
738  t << " relation = ";
739 
740  switch (edgeInfo.color())
741  {
742  case EdgeInfo::Blue: t << "public-inheritance"; break;
743  case EdgeInfo::Green: t << "protected-inheritance"; break;
744  case EdgeInfo::Red: t << "private-inheritance"; break;
745  case EdgeInfo::Purple: t << "usage"; break;
746  case EdgeInfo::Orange: t << "template-instance"; break;
747  case EdgeInfo::Orange2: t << "type-constraint"; break;
748  case EdgeInfo::Grey: ASSERT(0); break;
749  }
750  t << ";\n";
751 
752  if (!edgeInfo.label().isEmpty())
753  {
754  t << " edgelabel = <<_EnD_oF_dEf_TeXt_\n"
755  << edgeInfo.label() << "\n"
756  << "_EnD_oF_dEf_TeXt_;\n";
757  }
758  t << " }; /* node-child */\n";
759  ++it;
760  }
761  t << " }; /* node */\n";
762 }
763 
764 
766 {
768  for (const auto &pn : m_parents) if (pn->isWritten()) pn->clearWriteFlag();
769  for (const auto &cn : m_children) if (cn->isWritten()) cn->clearWriteFlag();
770 }
771 
773 {
774  for (const auto &cn : m_children)
775  {
776  if (cn->subgraphId()==-1) // uncolored child node
777  {
778  cn->setSubgraphId(curColor);
779  cn->markAsVisible();
780  cn->colorConnectedNodes(curColor);
781  //printf("coloring node %s (%p): %d\n",qPrint(cn->label()),cn,cn->subgraphId());
782  }
783  }
784 
785  for (const auto &pn : m_parents)
786  {
787  if (pn->subgraphId()==-1) // uncolored parent node
788  {
789  pn->setSubgraphId(curColor);
790  pn->markAsVisible();
791  pn->colorConnectedNodes(curColor);
792  //printf("coloring node %s (%p): %d\n",qPrint(pn->label()),pn,pn->subgraphId());
793  }
794  }
795 }
796 
797 #define DEBUG_RENUMBERING 0
798 
799 void DotNode::renumberNodes(int &number)
800 {
801  if (!isRenumbered())
802  {
803 #if DEBUG_RENUMBERING
804  static int level = 0;
805  printf("%3d: ",subgraphId());
806  for (int i = 0; i < level; i++) printf(" ");
807  printf("> %s old = %d new = %d\n",qPrint(m_label),m_number,number);
808  level++;
809 #endif
810  m_number = number++;
811  markRenumbered();
812  for (const auto &cn : m_children)
813  {
814  cn->renumberNodes(number);
815  }
816  for (const auto &pn : m_parents)
817  {
818  pn->renumberNodes(number);
819  }
820 #if DEBUG_RENUMBERING
821  level--;
822  printf("%3d: ",subgraphId());
823  for (int i = 0; i < level; i++) printf(" ");
824  printf("< %s assigned = %d\n",qPrint(m_label),m_number);
825 #endif
826  }
827 }
828 
829 
830 
831 
DotNode::writeXML
void writeXML(TextStream &t, bool isClassGraph) const
Definition: dotnode.cpp:583
normalEdgeProps
static EdgeProperties normalEdgeProps
Definition: dotnode.cpp:89
DotNode::m_deleted
bool m_deleted
used to mark a node as deleted
Definition: dotnode.h:121
DotNode::addChild
void addChild(DotNode *n, int edgeColor=EdgeInfo::Purple, int edgeStyle=EdgeInfo::Solid, const QCString &edgeLab=QCString(), const QCString &edgeURL=QCString(), int edgeLabCol=-1)
Definition: dotnode.cpp:281
MemberListType_priStaticMethods
@ MemberListType_priStaticMethods
Definition: types.h:114
MemberListType_priStaticAttribs
@ MemberListType_priStaticAttribs
Definition: types.h:125
Config_getEnum
#define Config_getEnum(name)
Definition: config.h:35
membergroup.h
MemberListType_pacStaticAttribs
@ MemberListType_pacStaticAttribs
Definition: types.h:124
DotNode::setDistance
void setDistance(int distance)
Definition: dotnode.cpp:333
QCString::length
uint length() const
Returns the length of the string, not counting the 0-terminator.
Definition: qcstring.h:147
EdgeInfo::Red
@ Red
Definition: dotnode.h:34
dotnode.h
DotNode::write
void write(TextStream &t, GraphType gt, GraphOutputFormat f, bool topDown, bool toChildren, bool backArrows) const
Definition: dotnode.cpp:532
DotNode::m_number
int m_number
Definition: dotnode.h:114
QCString::findRev
int findRev(char c, int index=-1, bool cs=TRUE) const
Definition: qcstring.cpp:86
MemberListType_priAttribs
@ MemberListType_priAttribs
Definition: types.h:121
QCString::isEmpty
bool isEmpty() const
Returns TRUE iff the string is empty
Definition: qcstring.h:144
DotNode::m_classDef
const ClassDef * m_classDef
class representing this node (can be 0)
Definition: dotnode.h:125
DotNode::writeDEF
void writeDEF(TextStream &t) const
Definition: dotnode.cpp:708
MemberListType_priSlots
@ MemberListType_priSlots
Definition: types.h:117
QCString::str
std::string str() const
Definition: qcstring.h:442
DotNode::deleteNodes
static void deleteNodes(DotNode *node)
Definition: dotnode.cpp:347
EdgeProperties::edgeStyleMap
const char *const * edgeStyleMap
Definition: dotnode.cpp:44
DotNode::DotNode
DotNode(int n, const QCString &lab, const QCString &tip, const QCString &url, bool rootNode=FALSE, const ClassDef *cd=0)
Definition: dotnode.cpp:266
DotNode::addParent
void addParent(DotNode *n)
Definition: dotnode.cpp:298
DotNode::findParent
int findParent(DotNode *n)
Definition: dotnode.cpp:338
textstream.h
DotNode::isRenumbered
bool isRenumbered() const
Definition: dotnode.h:95
TextStream
Text streaming class that buffers data.
Definition: textstream.h:33
QCString::find
int find(char c, int index=0, bool cs=TRUE) const
Definition: qcstring.cpp:38
MemberListType_proAttribs
@ MemberListType_proAttribs
Definition: types.h:119
MemberListType_pubMethods
@ MemberListType_pubMethods
Definition: types.h:107
DotNode::~DotNode
~DotNode()
Definition: dotnode.cpp:277
Definition::getLanguage
virtual SrcLangExt getLanguage() const =0
Returns the programming language this definition was written in.
DotNode::colorConnectedNodes
void colorConnectedNodes(int curColor)
Definition: dotnode.cpp:772
escapeTooltip
static QCString escapeTooltip(const QCString &tooltip)
Definition: dotnode.cpp:99
EdgeInfo::Orange
@ Orange
Definition: dotnode.h:34
end
DirIterator end(const DirIterator &) noexcept
Definition: dir.cpp:128
EdgeInfo::label
QCString label() const
Definition: dotnode.h:41
DotNode::Truncated
@ Truncated
Definition: dotnode.h:65
QCString::contains
int contains(char c, bool cs=TRUE) const
Definition: qcstring.cpp:138
StringUnorderedSet
std::unordered_set< std::string > StringUnorderedSet
Definition: containers.h:28
DotNode::removeParent
void removeParent(DotNode *n)
Definition: dotnode.cpp:309
uint
unsigned uint
Definition: qcstring.h:40
DotNode::writeDocbook
void writeDocbook(TextStream &t, bool isClassGraph) const
Definition: dotnode.cpp:645
umlEdgeStyleMap
static const char * umlEdgeStyleMap[]
Definition: dotnode.cpp:83
DotNode::m_written
bool m_written
used to mark a node as written
Definition: dotnode.h:122
addHtmlExtensionIfMissing
QCString addHtmlExtensionIfMissing(const QCString &fName)
Definition: util.cpp:5275
DotNode
A node in a dot graph
Definition: dotnode.h:56
MemberListType_pubSlots
@ MemberListType_pubSlots
Definition: types.h:115
ClassDef
A abstract class representing of a compound symbol.
Definition: classdef.h:103
Config_getInt
#define Config_getInt(name)
Definition: config.h:34
MemberListType_proStaticMethods
@ MemberListType_proStaticMethods
Definition: types.h:112
QCString::left
QCString left(size_t len) const
Definition: qcstring.h:212
DotNode::number
int number() const
Definition: dotnode.h:90
DotNode::writeBox
void writeBox(TextStream &t, GraphType gt, GraphOutputFormat f, bool hasNonReachableChildren) const
Definition: dotnode.cpp:357
GraphType
GraphType
Definition: dotgraph.h:29
umlEdgeColorMap
static const char * umlEdgeColorMap[]
Definition: dotnode.cpp:62
theTranslator
Translator * theTranslator
Definition: language.cpp:156
NONE
@ NONE
Definition: htmldocvisitor.cpp:42
writeBoxMemberList
static void writeBoxMemberList(TextStream &t, char prot, const MemberList *ml, const ClassDef *scope, bool isStatic=FALSE, const StringUnorderedSet *skipNames=nullptr)
Definition: dotnode.cpp:117
doxygen.h
DotNode::m_tooltip
QCString m_tooltip
node's tooltip
Definition: dotnode.h:116
language.h
DotNode::subgraphId
int subgraphId() const
Definition: dotnode.h:94
EdgeProperties::edgeColorMap
const char *const * edgeColorMap
Definition: dotnode.cpp:42
TRUE
#define TRUE
Definition: qcstring.h:36
EdgeInfo::Blue
@ Blue
Definition: dotnode.h:34
DotNode::clearWriteFlag
void clearWriteFlag()
Definition: dotnode.cpp:765
SrcLangExt_Fortran
@ SrcLangExt_Fortran
Definition: types.h:53
MemberListType_pacAttribs
@ MemberListType_pacAttribs
Definition: types.h:120
stripProtectionPrefix
static QCString stripProtectionPrefix(const QCString &s)
Definition: dotnode.cpp:254
Collaboration
@ Collaboration
Definition: dotgraph.h:29
memberlist.h
umlArrowStyleMap
static const char * umlArrowStyleMap[]
Definition: dotnode.cpp:73
MemberListType_pubStaticAttribs
@ MemberListType_pubStaticAttribs
Definition: types.h:122
DotNode::m_url
QCString m_url
url of the node (format: remote$local)
Definition: dotnode.h:117
DotNode::edgeInfo
const EdgeInfoVector & edgeInfo() const
Definition: dotnode.h:111
DotNode::writeArrow
void writeArrow(TextStream &t, GraphType gt, GraphOutputFormat f, const DotNode *cn, const EdgeInfo *ei, bool topDown, bool pointBack=TRUE) const
Definition: dotnode.cpp:483
MemberListType_proMethods
@ MemberListType_proMethods
Definition: types.h:108
normalEdgeColorMap
static const char * normalEdgeColorMap[]
Definition: dotnode.cpp:35
EdgeInfo
Attributes of an edge of a dot graph
Definition: dotnode.h:31
classdef.h
QCString::mid
QCString mid(size_t index, size_t len=static_cast< size_t >(-1)) const
Definition: qcstring.h:224
MemberListType_pacMethods
@ MemberListType_pacMethods
Definition: types.h:109
GOF_BITMAP
@ GOF_BITMAP
Definition: dotgraph.h:27
EdgeProperties::arrowStyleMap
const char *const * arrowStyleMap
Definition: dotnode.cpp:43
DotNode::removeChild
void removeChild(DotNode *n)
Definition: dotnode.cpp:303
MemberListType_proStaticAttribs
@ MemberListType_proStaticAttribs
Definition: types.h:123
umlEdgeProps
static EdgeProperties umlEdgeProps
Definition: dotnode.cpp:94
DotNode::m_truncated
TruncState m_truncated
does the node have non-visible children/parents
Definition: dotnode.h:127
EdgeInfo::style
int style() const
Definition: dotnode.h:40
EdgeProperties
Helper struct holding the properties of a edge in a dot graph.
Definition: dotnode.cpp:27
Config_getBool
#define Config_getBool(name)
Definition: config.h:33
DotNode::distance
int distance() const
Definition: dotnode.h:93
EdgeInfo::color
int color() const
Definition: dotnode.h:39
MemberListType_priMethods
@ MemberListType_priMethods
Definition: types.h:110
EdgeInfo::Green
@ Green
Definition: dotnode.h:34
DotNode::m_isRoot
bool m_isRoot
indicates if this is a root node
Definition: dotnode.h:124
DotNode::m_distance
int m_distance
shortest path to the root node
Definition: dotnode.h:128
MemberListType_proSlots
@ MemberListType_proSlots
Definition: types.h:116
DotNode::m_edgeInfo
EdgeInfoVector m_edgeInfo
edge info for each child
Definition: dotnode.h:120
qPrint
const char * qPrint(const char *s)
Definition: qcstring.h:589
Config_getString
#define Config_getString(name)
Definition: config.h:32
EdgeInfo::Purple
@ Purple
Definition: dotnode.h:34
Inheritance
@ Inheritance
Definition: dotgraph.h:29
DotNode::renumberNodes
void renumberNodes(int &number)
Definition: dotnode.cpp:799
DotNode::m_visible
bool m_visible
is the node visible in the output
Definition: dotnode.h:126
config.h
MemberListType_pubAttribs
@ MemberListType_pubAttribs
Definition: types.h:118
ASSERT
#define ASSERT(x)
Definition: qcstring.h:44
QCString::data
const char * data() const
Returns a pointer to the contents of the string in the form of a 0-terminated C string
Definition: qcstring.h:153
ClassDef::getMemberList
virtual MemberList * getMemberList(MemberListType lt) const =0
Returns the members in the list identified by lt
convertToXML
QCString convertToXML(const QCString &s, bool keepEntities)
Definition: util.cpp:3948
normalEdgeStyleMap
static const char * normalEdgeStyleMap[]
Definition: dotnode.cpp:56
GraphOutputFormat
GraphOutputFormat
Definition: dotgraph.h:27
EdgeInfo::Orange2
@ Orange2
Definition: dotnode.h:34
MemberListType_pacStaticMethods
@ MemberListType_pacStaticMethods
Definition: types.h:113
DotNode::convertLabel
static QCString convertLabel(const QCString &l)
Definition: dotnode.cpp:184
DotNode::m_children
DotNodeRefVector m_children
list of child nodes (outgoing arrows)
Definition: dotnode.h:119
ClassDef::getMemberGroups
virtual const MemberGroupList & getMemberGroups() const =0
Returns the member groups defined for this class
MemberListType_properties
@ MemberListType_properties
Definition: types.h:134
Translator::trAndMore
virtual QCString trAndMore(const QCString &number)=0
DotNode::deleteNode
void deleteNode(DotNodeRefVector &deletedList)
Definition: dotnode.cpp:315
util.h
A bunch of utility functions.
MemberListType_pubStaticMethods
@ MemberListType_pubStaticMethods
Definition: types.h:111
MemberList
A list of MemberDef objects as shown in documentation sections.
Definition: memberlist.h:81
DotNode::m_parents
DotNodeRefVector m_parents
list of parent nodes (incoming arrows)
Definition: dotnode.h:118
DotNodeRefVector
std::vector< DotNode * > DotNodeRefVector
Definition: dotnode.h:52
QCString::right
QCString right(size_t len) const
Definition: qcstring.h:217
DotNode::m_label
QCString m_label
label text
Definition: dotnode.h:115
EdgeInfo::Grey
@ Grey
Definition: dotnode.h:34
normalArrowStyleMap
static const char * normalArrowStyleMap[]
Definition: dotnode.cpp:46
DotNode::children
const DotNodeRefVector & children() const
Definition: dotnode.h:109
FALSE
#define FALSE
Definition: qcstring.h:33
QCString
This is an alternative implementation of QCString.
Definition: qcstring.h:108
DotNode::markRenumbered
void markRenumbered()
Definition: dotnode.h:101