]> granicus.if.org Git - graphviz/commitdiff
tests: SVGAnalyzer: add support for retrieving the Graphviz edge color
authorMagnus Jacobsson <Magnus.Jacobsson@berotec.se>
Tue, 23 Aug 2022 08:55:14 +0000 (10:55 +0200)
committerMagnus Jacobsson <Magnus.Jacobsson@berotec.se>
Mon, 5 Sep 2022 06:52:12 +0000 (08:52 +0200)
tests/CMakeLists.txt
tests/graphviz_edge.cpp
tests/graphviz_edge.h
tests/test_edge_color.cpp [new file with mode: 0644]

index beced86bf20debb2d935cbd21842679a5ea733fc..9e29151139b63cb28a07316bbc5ab66702c4d2e6 100644 (file)
@@ -78,6 +78,7 @@ endmacro()
 
 CREATE_TEST(AGraph_construction)
 CREATE_TEST(clusters)
+CREATE_TEST(edge_color)
 CREATE_TEST(edge_penwidth)
 CREATE_TEST(engines)
 CREATE_TEST(GVContext_construction)
index 893580b9df62db0d1531e3945923e4fbbe47cf95..88eb1ef7d1ef1f7c5e4995d85872f8dbeaf62e69 100644 (file)
@@ -1,3 +1,5 @@
+#include <string>
+
 #include "graphviz_edge.h"
 
 GraphvizEdge::GraphvizEdge(SVG::SVGElement &svg_g_element)
@@ -13,6 +15,15 @@ SVG::SVGRect GraphvizEdge::bbox() const { return m_svg_g_element.bbox(); }
 
 SVG::SVGPoint GraphvizEdge::center() const { return bbox().center(); }
 
+std::string GraphvizEdge::color() const {
+  const auto stroke = m_svg_g_element.attribute_from_subtree<std::string>(
+      &SVG::SVGAttributes::stroke, &SVG::SVGElement::is_shape_element, "");
+  const auto stroke_opacity = m_svg_g_element.attribute_from_subtree<double>(
+      &SVG::SVGAttributes::stroke_opacity, &SVG::SVGElement::is_shape_element,
+      1);
+  return SVG::to_dot_color(stroke, stroke_opacity);
+}
+
 double GraphvizEdge::penwidth() const {
   return m_svg_g_element.attribute_from_subtree<double>(
       &SVG::SVGAttributes::stroke_width, &SVG::SVGElement::is_shape_element, 1);
index fdc0a0d9d42c0c78862d7f1987893ddd4672a9d2..6840127d72dc77d5aab0784a71b84c55534f5345 100644 (file)
@@ -19,6 +19,9 @@ public:
   SVG::SVGRect bbox() const;
   /// Return the center of the edge's bounding box
   SVG::SVGPoint center() const;
+  /// Return the edge's `color` attribute in RGB hex format if the opacity is
+  /// 100 % or in RGBA hex format otherwise.
+  std::string color() const;
   /// Return the 'edgeop' according to the DOT language specification. Note that
   /// this is not the same as the 'id' attribute of an edge.
   std::string_view edgeop() const;
diff --git a/tests/test_edge_color.cpp b/tests/test_edge_color.cpp
new file mode 100644 (file)
index 0000000..0ef3c07
--- /dev/null
@@ -0,0 +1,43 @@
+#include <catch2/catch.hpp>
+#include <fmt/format.h>
+
+#include "svg_analyzer.h"
+#include "test_utilities.h"
+
+TEST_CASE("Edge color",
+          "Test that the Graphviz `color` attribute is used to set the "
+          "`stroke` and `stroke-opacity` attributes correctly for edges in the "
+          "generated SVG") {
+
+  const auto primitive_arrow_shape =
+      GENERATE(from_range(all_primitive_arrow_shapes));
+  INFO(fmt::format("Primitive arrow shape: {}", primitive_arrow_shape));
+
+  const auto edge_rgb_color = GENERATE("#000000", "#ffffff", "#5580aa");
+  const auto opacity = GENERATE(0, 100, 255);
+  const auto edge_rgba_color = fmt::format("{}{:02x}", edge_rgb_color, opacity);
+  INFO(fmt::format("Edge color: {}", edge_rgba_color));
+
+  auto dot =
+      fmt::format("digraph g1 {{edge [arrowhead={} color=\"{}\"]; a -> b}}",
+                  primitive_arrow_shape, edge_rgba_color);
+
+  const auto engine = "dot";
+  auto svg_analyzer = SVGAnalyzer::make_from_dot(dot, engine);
+
+  const auto expected_edge_color = [&]() -> const std::string {
+    if (opacity == 255) {
+      return edge_rgb_color;
+    }
+    if (opacity == 0) {
+      return "#00000000"; // transparent/none
+    }
+    return edge_rgba_color;
+  }();
+
+  for (const auto &graph : svg_analyzer.graphs()) {
+    for (const auto &edge : graph.edges()) {
+      CHECK(edge.color() == expected_edge_color);
+    }
+  }
+}