lib/rsyntaxtree/svg_graph.rb in rsyntaxtree-1.0.8 vs lib/rsyntaxtree/svg_graph.rb in rsyntaxtree-1.1.0
- old
+ new
@@ -1,43 +1,43 @@
-#!/usr/bin/env ruby
-# -*- coding: utf-8 -*-
+# frozen_string_literal: true
#==========================
# svg_graph.rb
#==========================
#
# Parses an element list into an SVG tree.
-# Copyright (c) 2007-2021 Yoichiro Hasebe <yohasebe@gmail.com>
+# Copyright (c) 2007-2023 Yoichiro Hasebe <yohasebe@gmail.com>
require "tempfile"
-require 'base_graph'
-require 'utils'
+require_relative 'base_graph'
+require_relative 'utils'
module RSyntaxTree
class SVGGraph < BaseGraph
attr_accessor :width, :height
- def initialize(element_list, params)
+ def initialize(element_list, params, global)
@height = 0
@width = 0
@extra_lines = []
- @fontset = params[:fontset]
- @fontsize = params[:fontsize]
+ @fontset = params[:fontset]
+ @fontsize = params[:fontsize]
@transparent = params[:transparent]
@color = params[:color]
@fontstyle = params[:fontstyle]
@margin = params[:margin].to_i
@polyline = params[:polyline]
- @line_styles = "<line style='stroke:black; stroke-width:#{FONT_SCALING};' x1='X1' y1='Y1' x2='X2' y2='Y2' />\n"
- @polyline_styles = "<polyline style='stroke:black; stroke-width:#{FONT_SCALING}; fill:none;'
+ @line_styles = "<line style='stroke:black; stroke-width:#{FONT_SCALING};' x1='X1' y1='Y1' x2='X2' y2='Y2' />\n"
+ @polyline_styles = "<polyline style='stroke:black; stroke-width:#{FONT_SCALING}; fill:none;'
points='CHIX CHIY MIDX1 MIDY1 MIDX2 MIDY2 PARX PARY' />\n"
- @polygon_styles = "<polygon style='fill: none; stroke: black; stroke-width:#{FONT_SCALING};' points='X1 Y1 X2 Y2 X3 Y3' />\n"
- @text_styles = "<text white-space='pre' alignment-baseline='text-top' style='fill: COLOR; font-size: fontsize' x='X_VALUE' y='Y_VALUE'>CONTENT</text>\n"
- @tree_data = String.new
+ @polygon_styles = "<polygon style='fill: none; stroke: black; stroke-width:#{FONT_SCALING};' points='X1 Y1 X2 Y2 X3 Y3' />\n"
+ @text_styles = "<text white-space='pre' alignment-baseline='text-top' style='fill: COLOR; font-size: fontsize' x='X_VALUE' y='Y_VALUE'>CONTENT</text>\n"
+ @tree_data = String.new
@visited_x = {}
@visited_y = {}
- super(element_list, params)
+ @global = global
+ super(element_list, params, global)
end
def svg_data
metrics = parse_list
@height = metrics[:height] + @margin * 2
@@ -47,36 +47,36 @@
y1 = 0 - @margin
x2 = @width + @margin
y2 = @height + @margin
extra_lines = @extra_lines.join("\n")
- as2 = $h_gap_between_nodes / 2 * 0.8
+ as2 = @global[:h_gap_between_nodes] / 2 * 0.8
as = as2 / 2
- header =<<EOD
-<?xml version="1.0" standalone="no"?>
-<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
- <svg width="#{@width}" height="#{@height}" viewBox="#{x1}, #{y1}, #{x2}, #{y2}" version="1.1" xmlns="http://www.w3.org/2000/svg">
- <defs>
- <marker id="arrow" markerUnits="strokeWidth" markerWidth="#{as2}" markerHeight="#{as2}" viewBox="0 0 #{as2} #{as2}" refX="#{as}" refY="0">
- <polyline fill="none" stroke="#{@col_path}" stroke-width="1" points="0,#{as2},#{as},0,#{as2},#{as2}" />
- </marker>
- <pattern id="hatchBlack" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse" patternTransform="rotate(45)">
- <line x1="0" y="0" x2="0" y2="10" stroke="black" stroke-width="4"></line>
- </pattern>
- <pattern id="hatchForNode" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse" patternTransform="rotate(45)">
- <line x1="0" y="0" x2="0" y2="10" stroke="#{@col_node}" stroke-width="4"></line>
- </pattern>
- <pattern id="hatchForLeaf" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse" patternTransform="rotate(45)">
- <line x1="0" y="0" x2="0" y2="10" stroke="#{@col_leaf}" stroke-width="4"></line>
- </pattern>
- </defs>
-EOD
+ header = <<~HDR
+ <?xml version="1.0" standalone="no"?>
+ <!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
+ <svg width="#{@width}" height="#{@height}" viewBox="#{x1}, #{y1}, #{x2}, #{y2}" version="1.1" xmlns="http://www.w3.org/2000/svg">
+ <defs>
+ <marker id="arrow" markerUnits="strokeWidth" markerWidth="#{as2}" markerHeight="#{as2}" viewBox="0 0 #{as2} #{as2}" refX="#{as}" refY="0">
+ <polyline fill="none" stroke="#{@col_path}" stroke-width="1" points="0,#{as2},#{as},0,#{as2},#{as2}" />
+ </marker>
+ <pattern id="hatchBlack" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse" patternTransform="rotate(45)">
+ <line x1="0" y="0" x2="0" y2="10" stroke="black" stroke-width="4"></line>
+ </pattern>
+ <pattern id="hatchForNode" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse" patternTransform="rotate(45)">
+ <line x1="0" y="0" x2="0" y2="10" stroke="#{@col_node}" stroke-width="4"></line>
+ </pattern>
+ <pattern id="hatchForLeaf" x="10" y="10" width="10" height="10" patternUnits="userSpaceOnUse" patternTransform="rotate(45)">
+ <line x1="0" y="0" x2="0" y2="10" stroke="#{@col_leaf}" stroke-width="4"></line>
+ </pattern>
+ </defs>
+ HDR
- rect =<<EOD
-<rect x="#{x1}" y="#{y1}" width="#{x2}" height="#{y2}" stroke="none" fill="white" />"
-EOD
+ rect = <<~RCT
+ <rect x="#{x1}" y="#{y1}" width="#{x2}" height="#{y2}" stroke="none" fill="white" />"
+ RCT
footer = "</svg>"
if @transparent
header + @tree_data + extra_lines + footer
@@ -84,22 +84,20 @@
header + rect + @tree_data + extra_lines + footer
end
end
def draw_a_path(s_x, s_y, t_x, t_y, target_arrow = :none)
+ x_spacing = @global[:h_gap_between_nodes] * 1.25
+ y_spacing = @global[:height_connector] * 0.65
- x_spacing = $h_gap_between_nodes * 1.25
- y_spacing = $height_connector * 0.65
-
ymax = [s_y, t_y].max
- if ymax < @height
- new_y = @height + y_spacing
- else
- new_y = ymax + y_spacing
- end
+ new_y = if ymax < @height
+ @height + y_spacing
+ else
+ ymax + y_spacing
+ end
-
if @visited_x[s_x]
new_s_x = s_x - x_spacing * @visited_x[s_x]
@visited_x[s_x] += 1
else
new_s_x = s_x
@@ -112,71 +110,68 @@
else
new_t_x = t_x
@visited_x[t_x] = 1
end
- s_y += $h_gap_between_nodes / 2
- t_y += $h_gap_between_nodes / 2
- new_y += $h_gap_between_nodes / 2
+ s_y += @global[:h_gap_between_nodes] / 2
+ t_y += @global[:h_gap_between_nodes] / 2
+ new_y += @global[:h_gap_between_nodes] / 2
dashed = true if target_arrow == :none
- if target_arrow == :single
+ case target_arrow
+ when :single
@extra_lines << generate_line(new_s_x, s_y, new_s_x, new_y, @col_path, dashed)
@extra_lines << generate_line(new_s_x, new_y, new_t_x, new_y, @col_path, dashed)
- @extra_lines << generate_line(new_t_x, new_y, new_t_x, t_y, @col_path ,dashed, true)
- elsif target_arrow == :double
+ @extra_lines << generate_line(new_t_x, new_y, new_t_x, t_y, @col_path, dashed, true)
+ when :double
@extra_lines << generate_line(new_s_x, new_y, new_s_x, s_y, @col_path, dashed, true)
@extra_lines << generate_line(new_s_x, new_y, new_t_x, new_y, @col_path, dashed)
- @extra_lines << generate_line(new_t_x, new_y, new_t_x, t_y, @col_path ,dashed, true)
+ @extra_lines << generate_line(new_t_x, new_y, new_t_x, t_y, @col_path, dashed, true)
else
@extra_lines << generate_line(new_s_x, s_y, new_s_x, new_y, @col_path, dashed)
@extra_lines << generate_line(new_s_x, new_y, new_t_x, new_y, @col_path, dashed)
- @extra_lines << generate_line(new_t_x, new_y, new_t_x, t_y, @col_path ,dashed)
+ @extra_lines << generate_line(new_t_x, new_y, new_t_x, t_y, @col_path, dashed)
end
@height = new_y if new_y > @height
end
def draw_element(element)
- top = element.vertical_indent
-
- left = element.horizontal_indent
- bottom = top +$single_line_height
- right = left + element.content_width
-
+ top = element.vertical_indent
+ left = element.horizontal_indent
+ right = left + element.content_width
txt_pos = left + (right - left) / 2
- if(element.type == ETYPE_LEAF)
- col = @col_leaf
- else
- col = @col_node
- end
+ col = if element.type == ETYPE_LEAF
+ @col_leaf
+ else
+ @col_node
+ end
text_data = @text_styles.sub(/COLOR/, col)
text_data = text_data.sub(/fontsize/, @fontsize.to_s + "px;")
text_x = txt_pos - element.content_width / 2
- text_y = top + $single_line_height - $height_connector_to_text
+ text_y = top + @global[:single_line_height] - @global[:height_connector_to_text]
text_data = text_data.sub(/X_VALUE/, text_x.to_s)
text_data = text_data.sub(/Y_VALUE/, text_y.to_s)
- new_text = ""
+ new_text = +""
this_x = 0
this_y = 0
- bc = {:x => text_x - $h_gap_between_nodes / 2 , :y => top, :width => element.content_width + $h_gap_between_nodes, :height => nil}
+ bc = { x: text_x - @global[:h_gap_between_nodes] / 2, y: top, width: element.content_width + @global[:h_gap_between_nodes], height: nil }
element.content.each_with_index do |l, idx|
case l[:type]
when :border, :bborder
x1 = text_x
- if idx == 0
+ if idx.zero?
text_y -= l[:height]
- elsif
+ else
text_y += l[:height]
end
- y1 = text_y - $single_line_height / 8
+ y1 = text_y - @global[:single_line_height] / 8
x2 = text_x + element.content_width
y2 = y1
- this_width = x2 - x1
case l[:type]
when :border
stroke_width = FONT_SCALING
when :bborder
stroke_width = FONT_SCALING * 2
@@ -190,108 +185,87 @@
l[:elements].each do |e|
ewidth += e[:width]
end
this_x = txt_pos - (ewidth / 2)
end
- text_y += l[:elements].map{|e| e[:height]}.max if idx != 0
+ text_y += l[:elements].map { |e| e[:height] }.max if idx != 0
- l[:elements].each_with_index do |e, idx|
+ l[:elements].each do |e|
escaped_text = e[:text].gsub('>', '>').gsub('<', '<');
decorations = []
- if e[:decoration].include?(:overline)
- decorations << "overline"
- end
+ decorations << "overline" if e[:decoration].include?(:overline)
+ decorations << "underline" if e[:decoration].include?(:underline)
+ decorations << "line-through" if e[:decoration].include?(:linethrough)
+ decoration = "text-decoration=\"" + decorations.join(" ") + "\""
- if e[:decoration].include?(:underline)
- decorations << "underline"
- end
-
- if e[:decoration].include?(:linethrough)
- decorations << "line-through"
- end
- decoration ="text-decoration=\"" + decorations.join(" ") + "\""
-
style = "style=\""
if e[:decoration].include?(:small)
style += "font-size: #{(SUBSCRIPT_CONST.to_f * 100).to_i}%; "
- this_y = text_y - (($single_X_metrics.height - $single_X_metrics.height * SUBSCRIPT_CONST) / 4) + 2
+ this_y = text_y - ((@global[:single_x_metrics].height - @global[:single_x_metrics].height * SUBSCRIPT_CONST) / 4) + 2
elsif e[:decoration].include?(:superscript)
style += "font-size: #{(SUBSCRIPT_CONST.to_f * 100).to_i}%; "
- this_y = text_y - ($single_X_metrics.height / 4) + 1
+ this_y = text_y - (@global[:single_x_metrics].height / 4) + 1
elsif e[:decoration].include?(:subscript)
style += "font-size: #{(SUBSCRIPT_CONST.to_f * 100).to_i}%; "
this_y = text_y + 4
else
this_y = text_y
end
- if e[:decoration].include?(:bold) || e[:decoration].include?(:bolditalic)
- style += "font-weight: bold; "
- end
-
- if e[:decoration].include?(:italic) || e[:decoration].include?(:bolditalic)
- style += "font-style: italic; "
- end
-
+ style += "font-weight: bold; " if e[:decoration].include?(:bold) || e[:decoration].include?(:bolditalic)
+ style += "font-style: italic; " if e[:decoration].include?(:italic) || e[:decoration].include?(:bolditalic)
style += "\""
case @fontstyle
when /(?:cjk)/
fontstyle = "'WenQuanYi Zen Hei', 'Noto Sans', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', sans-serif"
when /(?:sans)/
- if e[:cjk]
- fontstyle = "'Noto Sans JP', 'Noto Sans', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', sans-serif"
- else
- fontstyle = "'Noto Sans', 'Noto Sans JP', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', sans-serif"
- end
+ fontstyle = if e[:cjk]
+ "'Noto Sans JP', 'Noto Sans', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', sans-serif"
+ else
+ "'Noto Sans', 'Noto Sans JP', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', sans-serif"
+ end
when /(?:serif)/
- if e[:cjk]
- fontstyle = "'Noto Serif JP', 'Noto Serif', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', serif"
- else
- fontstyle = "'Noto Serif', 'Noto Serif JP', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', serif"
- end
+ fontstyle = if e[:cjk]
+ "'Noto Serif JP', 'Noto Serif', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', serif"
+ else
+ "'Noto Serif', 'Noto Serif JP', OpenMoji, 'OpenMoji Color', 'OpenMoji Black', serif"
+ end
end
if e[:decoration].include?(:box) || e[:decoration].include?(:circle) || e[:decoration].include?(:bar)
enc_height = e[:height]
enc_y = this_y - e[:height] * 0.8 + FONT_SCALING
+ enc_width = e[:width]
+ enc_x = this_x
- if e[:text].size == 1
- enc_width = e[:width]
- enc_x = this_x
- else
- enc_width = e[:width]
- enc_x = this_x
- end
-
if e[:decoration].include?(:hatched)
case element.type
when ETYPE_LEAF
- if @color
- fill = "url(#hatchForLeaf)"
- else
- fill = "url(#hatchBlack)"
- end
+ fill = if @color
+ "url(#hatchForLeaf)"
+ else
+ "url(#hatchBlack)"
+ end
when ETYPE_NODE
- if @color
- fill = "url(#hatchForNode)"
- else
- fill = "url(#hatchBlack)"
- end
+ fill = if @color
+ "url(#hatchForNode)"
+ else
+ "url(#hatchBlack)"
+ end
end
else
fill = "none"
end
enc = nil
- bar = nil
- if e[:decoration].include?(:bstroke)
- stroke_width = FONT_SCALING * 2.5
- else
- stroke_width = FONT_SCALING
- end
+ stroke_width = if e[:decoration].include?(:bstroke)
+ FONT_SCALING * 2.5
+ else
+ FONT_SCALING
+ end
if e[:decoration].include?(:box)
enc = "<rect style='stroke: #{col}; stroke-width:#{stroke_width};'
x='#{enc_x}' y='#{enc_y}'
width='#{enc_width}' height='#{enc_height}'
@@ -317,57 +291,54 @@
if e[:decoration].include?(:arrow_to_r)
r_arrowhead = "<polyline stroke-linejoin='bevel' fill='none' stroke='#{col}' stroke-width='#{stroke_width}' points='#{x2 - ar_hwidth},#{y2 - ar_hwidth / 2} #{x2},#{y2} #{x2 - ar_hwidth},#{y2 + ar_hwidth / 2}' />\n"
@extra_lines << r_arrowhead
end
-
-
end
@extra_lines << enc if enc
- if e[:text].size == 1
- this_x += (e[:height] - e[:content_width]) / 2
- else
- this_x += $width_half_X / 2
- end
+ this_x += if e[:text].size == 1
+ (e[:height] - e[:content_width]) / 2
+ else
+ @global[:width_half_x] / 2
+ end
+
new_text << set_tspan(this_x, this_y, style, decoration, fontstyle, escaped_text)
- if e[:text].size == 1
- this_x += e[:content_width]
- this_x += (e[:height] - e[:content_width]) / 2
- else
- this_x += e[:content_width]
- this_x += $width_half_X / 2
- end
+ this_x += if e[:text].size == 1
+ e[:content_width] + (e[:height] - e[:content_width]) / 2
+ else
+ e[:content_width] + @global[:width_half_x] / 2
+ end
elsif e[:decoration].include?(:whitespace)
this_x += e[:width]
next
else
new_text << set_tspan(this_x, this_y, style, decoration, fontstyle, escaped_text)
this_x += e[:width]
end
-
end
end
@height = text_y if text_y > @height
end
- bc[:y] = bc[:y] + $height_connector_to_text * 3 / 4
- bc[:height] = text_y - bc[:y] + $height_connector_to_text
- if element.enclosure == :brackets
- @extra_lines << generate_line(bc[:x], bc[:y], bc[:x] + $h_gap_between_nodes / 2, bc[:y], col)
+ bc[:y] = bc[:y] + @global[:height_connector_to_text] * 3 / 4
+ bc[:height] = text_y - bc[:y] + @global[:height_connector_to_text]
+ case element.enclosure
+ when :brackets
+ @extra_lines << generate_line(bc[:x], bc[:y], bc[:x] + @global[:h_gap_between_nodes] / 2, bc[:y], col)
@extra_lines << generate_line(bc[:x], bc[:y], bc[:x], bc[:y] + bc[:height], col)
- @extra_lines << generate_line(bc[:x], bc[:y] + bc[:height], bc[:x] + $h_gap_between_nodes / 2, bc[:y] + bc[:height], col)
- @extra_lines << generate_line(bc[:x] + bc[:width], bc[:y], bc[:x] + bc[:width] - $h_gap_between_nodes / 2, bc[:y], col)
+ @extra_lines << generate_line(bc[:x], bc[:y] + bc[:height], bc[:x] + @global[:h_gap_between_nodes] / 2, bc[:y] + bc[:height], col)
+ @extra_lines << generate_line(bc[:x] + bc[:width], bc[:y], bc[:x] + bc[:width] - @global[:h_gap_between_nodes] / 2, bc[:y], col)
@extra_lines << generate_line(bc[:x] + bc[:width], bc[:y], bc[:x] + bc[:width], bc[:y] + bc[:height], col)
- @extra_lines << generate_line(bc[:x] + bc[:width], bc[:y] + bc[:height], bc[:x] + bc[:width] - $h_gap_between_nodes / 2, bc[:y] + bc[:height], col)
- elsif element.enclosure == :rectangle
+ @extra_lines << generate_line(bc[:x] + bc[:width], bc[:y] + bc[:height], bc[:x] + bc[:width] - @global[:h_gap_between_nodes] / 2, bc[:y] + bc[:height], col)
+ when :rectangle
@extra_lines << generate_line(bc[:x], bc[:y], bc[:x] + bc[:width], bc[:y], col)
@extra_lines << generate_line(bc[:x], bc[:y], bc[:x], bc[:y] + bc[:height], col)
@extra_lines << generate_line(bc[:x] + bc[:width], bc[:y], bc[:x] + bc[:width], bc[:y] + bc[:height], col)
@extra_lines << generate_line(bc[:x], bc[:y] + bc[:height], bc[:x] + bc[:width], bc[:y] + bc[:height], col)
- elsif element.enclosure == :brectangle
+ when :brectangle
@extra_lines << generate_line(bc[:x], bc[:y], bc[:x] + bc[:width], bc[:y], col, false, false, 2)
@extra_lines << generate_line(bc[:x], bc[:y], bc[:x], bc[:y] + bc[:height], col, false, false, 2)
@extra_lines << generate_line(bc[:x] + bc[:width], bc[:y], bc[:x] + bc[:width], bc[:y] + bc[:height], col, false, false, 2)
@extra_lines << generate_line(bc[:x], bc[:y] + bc[:height], bc[:x] + bc[:width], bc[:y] + bc[:height], col, false, false, 2)
end
@@ -382,24 +353,22 @@
"<tspan style='fill:none;'>" + "■" * num_spaces + "</tspan>"
end
"<tspan x='#{this_x}' y='#{this_y}' #{style} #{decoration} font-family=\"#{fontstyle}\">#{text}</tspan>\n"
end
-
def draw_paths
- rockbottom = 0
path_pool_target = {}
path_pool_other = {}
path_pool_source = {}
path_flags = []
# elist = @element_list.get_elements.reverse
elist = @element_list.get_elements
elist.each do |element|
x1 = element.horizontal_indent + element.content_width / 2
y1 = element.vertical_indent + element.content_height
- y1 += $height_connector_to_text if element.enclosure != :none
+ y1 += @global[:height_connector_to_text] if element.enclosure != :none
et = element.path
et.each do |tr|
if /\A>(\d+)\z/ =~ tr
tr = $1
if path_pool_target[tr]
@@ -415,116 +384,108 @@
end
else
path_pool_source[tr] = [x1, y1]
end
path_flags << tr
- if path_flags.tally.any?{|k, v| v > 2}
- raise RSTError, "Error: input text contains a path having more than two ends:\n > #{tr}"
- end
+ raise RSTError, "Error: input text contains a path having more than two ends:\n > #{tr}" if path_flags.tally.any? { |_k, v| v > 2 }
end
end
path_flags.tally.each do |k, v|
- if v == 1
- raise RSTError, "Error: input text contains a path having only one end:\n > #{k}"
- end
+ raise RSTError, "Error: input text contains a path having only one end:\n > #{k}" if v == 1
end
paths = []
path_pool_source.each do |k, v|
path_flags.delete(k)
- if targets = path_pool_target[k]
+ if (targets = path_pool_target[k])
targets.each do |t|
- paths << {x1: v[0], y1: v[1], x2: t[0], y2: t[1], arrow: :single}
+ paths << { x1: v[0], y1: v[1], x2: t[0], y2: t[1], arrow: :single }
end
- elsif others = path_pool_other[k]
+ elsif (others = path_pool_other[k])
others.each do |t|
- paths << {x1: v[0], y1: v[1], x2: t[0], y2: t[1], arrow: :none}
+ paths << { x1: v[0], y1: v[1], x2: t[0], y2: t[1], arrow: :none }
end
end
end
path_flags.uniq.each do |k|
targets = path_pool_target[k]
fst = targets.shift
targets.each do |t|
- paths << {x1: fst[0], y1: fst[1], x2: t[0], y2: t[1], arrow: :double}
+ paths << { x1: fst[0], y1: fst[1], x2: t[0], y2: t[1], arrow: :double }
end
end
paths.each do |t|
- draw_a_path(t[:x1], t[:y1] + $height_connector_to_text / 2,
- t[:x2], t[:y2] + $height_connector_to_text / 2,
+ draw_a_path(t[:x1], t[:y1] + @global[:height_connector_to_text] / 2,
+ t[:x2], t[:y2] + @global[:height_connector_to_text] / 2,
t[:arrow])
end
paths.size
end
def generate_line(x1, y1, x2, y2, col, dashed = false, arrow = false, stroke_width = 1)
- if arrow
- string = "marker-end='url(#arrow)' "
- else
- string = ""
- end
+ string = if arrow
+ "marker-end='url(#arrow)' "
+ else
+ ""
+ end
dasharray = dashed ? "stroke-dasharray='8 8'" : ""
swidth = FONT_SCALING * stroke_width
"<line x1='#{x1}' y1='#{y1}' x2='#{x2}' y2='#{y2}' style='fill: none; stroke: #{col}; stroke-width:#{swidth}' #{dasharray} #{string}/>"
end
# Draw a line between child/parent elements
def line_to_parent(parent, child)
- if (child.horizontal_indent == 0 )
- return
- end
+ return if child.horizontal_indent.zero?
if @polyline
chi_x = child.horizontal_indent + child.content_width / 2
- chi_y = child.vertical_indent + $height_connector_to_text / 2
+ chi_y = child.vertical_indent + @global[:height_connector_to_text] / 2
par_x = parent.horizontal_indent + parent.content_width / 2
- par_y = parent.vertical_indent + parent.content_height + $height_connector_to_text
+ par_y = parent.vertical_indent + parent.content_height + @global[:height_connector_to_text]
mid_x1 = chi_x
- mid_y1 = par_y + (chi_y - par_y) / 2
+ mid_y1 = par_y + (chi_y - par_y) / 2
mid_x2 = par_x
mid_y2 = mid_y1
@tree_data += @polyline_styles.sub(/CHIX/, chi_x.to_s)
- .sub(/CHIY/, chi_y.to_s)
- .sub(/MIDX1/, mid_x1.to_s)
- .sub(/MIDY1/, mid_y1.to_s)
- .sub(/MIDX2/, mid_x2.to_s)
- .sub(/MIDY2/, mid_y2.to_s)
- .sub(/PARX/, par_x.to_s)
- .sub(/PARY/, par_y.to_s)
+ .sub(/CHIY/, chi_y.to_s)
+ .sub(/MIDX1/, mid_x1.to_s)
+ .sub(/MIDY1/, mid_y1.to_s)
+ .sub(/MIDX2/, mid_x2.to_s)
+ .sub(/MIDY2/, mid_y2.to_s)
+ .sub(/PARX/, par_x.to_s)
+ .sub(/PARY/, par_y.to_s)
else
x1 = child.horizontal_indent + child.content_width / 2
- y1 = child.vertical_indent + $height_connector_to_text / 2
+ y1 = child.vertical_indent + @global[:height_connector_to_text] / 2
x2 = parent.horizontal_indent + parent.content_width / 2
- y2 = parent.vertical_indent + parent.content_height + $height_connector_to_text
+ y2 = parent.vertical_indent + parent.content_height + @global[:height_connector_to_text]
line_data = @line_styles.sub(/X1/, x1.to_s)
line_data = line_data.sub(/Y1/, y1.to_s)
line_data = line_data.sub(/X2/, x2.to_s)
@tree_data += line_data.sub(/Y2/, y2.to_s)
end
end
# Draw a triangle between child/parent elements
def triangle_to_parent(parent, child)
- if (child.horizontal_indent == 0)
- return
- end
+ return if child.horizontal_indent.zero?
x1 = child.horizontal_indent
- y1 = child.vertical_indent + $height_connector_to_text / 2
+ y1 = child.vertical_indent + @global[:height_connector_to_text] / 2
x2 = child.horizontal_indent + child.content_width
- y2 = child.vertical_indent + $height_connector_to_text / 2
+ y2 = child.vertical_indent + @global[:height_connector_to_text] / 2
x3 = parent.horizontal_indent + parent.content_width / 2
- y3 = parent.vertical_indent + parent.content_height + $height_connector_to_text
+ y3 = parent.vertical_indent + parent.content_height + @global[:height_connector_to_text]
polygon_data = @polygon_styles.sub(/X1/, x1.to_s)
polygon_data = polygon_data.sub(/Y1/, y1.to_s)
polygon_data = polygon_data.sub(/X2/, x2.to_s)
polygon_data = polygon_data.sub(/Y2/, y2.to_s)