書きたいダイアグラムが書けなかった。
開発環境
- Linux Mint 17.3 MATE 32bit
- Python 3.4.3
- blockdiag 1.5.3
前回まで
- 型とクラス、オブジェクトとインスタンスの違い
- ここにある図を書きたかったが面倒なので放置していた
- 作図ツールblockdiagをインストールする
目標
型 -> <生成する> -> 物 人の認識層 △ -|--------------------------------------------------- | Type -> <生成する> -> Object メモリ空間層 △ -|--------------------------------------------------- | Class -> <生成する> -> Instance オブジェクト指向層 ------------------------------------------------------
- これをカッコイイ図にしたい
- テキストから構造を指定することでSVGを簡単に編集できること
- できればHTMLに直接構造テキストを書くだけで図が表示されると最高
結果
SVGファイル出力には成功。しかし目標達成できず。とりあえず書けたところまでを表示しようと試みるも、Base64文字列に変換しないとHTML表示できなかった。
問題1: blockdiagでは1つの矢印しか出せない
blockdiagでは目標を作図できない。
- 1ブロックから2方向の矢印を出せない
目標の図は、以下2種類の矢印がある。しかしblockdiagでは1つの矢印しか出せない。
- 帰属する
- 生成する
以下のように1箇所から矢印を出して分岐することはできる。しかしこれでは異なる意味を持った矢印の表現ができない。
+-->□ | □--+ | +-->□
問題2: はてなブログでSVG画像を表示するにはBase64変換が必要?
SVG画像のURLを参照するだけでは表示できなかった。私が何か間違っているのか、はてなの仕様なのか不明。
やってみた
作図
test.diag
blockdiag { 型 [style = "1,8"] Type [style = "4,8"] Class [style = "4,4"] 型 -> 物 [label = "生成"]; Type -> Object [label = "Create"]; Class -> Instance [label = "Create"]; group {型; 物;} group {Type; Object;} group {Class; Instance;} }
継承関係の矢印を書けない。矢印は1つの意味しかもたせられない。blockdiagの仕様と思われる。とりあえず継承関係は書かず生成関係のみに絞る。
SVG出力
blockdiag -Tsvg test.diag
アップロード
はてなブログ埋め込み(失敗)
参考先に感謝。
SVG表示できると思うのだが、成功したのはBase64変換したものだけ。ほかは真っ白な画面が表示されるだけでSVGが表示されない。
img
<img src="https://raw.githubusercontent.com/ytyaru/structure.text.Upload.201703120923/master/res/tmp/2017/0504/test2.svg"></img>
base64変換
ファイルをBase64文字列に変換するWebツール。感謝。SVGファイルを変換してimgタグのsrc属性に設定する。
以下、一部手動で修正したもの。
<img class="http-image" src="data:image/svg+xml;base64,(省略)" />
embed
<embed type="image/svg+xml" width="448" height="280" src="https://raw.githubusercontent.com/ytyaru/structure.text.Upload.201703120923/master/res/tmp/2017/0504/test2.svg"></embed>
object
<object type="image/svg+xml" data="https://raw.githubusercontent.com/ytyaru/structure.text.Upload.201703120923/master/res/tmp/2017/0504/test2.svg" height="448px" width="280px" id="svgID"></object>
SVGソースコード
<svg viewBox="0 0 448 280" xmlns="http://www.w3.org/2000/svg" xmlns:inkspace="http://www.inkscape.org/namespaces/inkscape" xmlns:xlink="http://www.w3.org/1999/xlink"> <defs id="defs_block"> <filter height="1.504" id="filter_blur" inkspace:collect="always" width="1.1575" x="-0.07875" y="-0.252"> <feGaussianBlur id="feGaussianBlur3780" inkspace:collect="always" stdDeviation="4.2" /> </filter> </defs> <title>blockdiag</title> <desc>blockdiag { # orientation = portrait 型 [style = "1,8"] Type [style = "4,8"] Class [style = "4,4"] 型 -> 物 [label = "生成"]; Type -> Object [label = "Create"]; Class -> Instance [label = "Create"]; group {型; 物;} group {Type; Object;} group {Class; Instance;} } </desc> <rect fill="rgb(243,152,0)" height="60" style="filter:url(#filter_blur)" width="336" x="56" y="30" /> <rect fill="rgb(243,152,0)" height="60" style="filter:url(#filter_blur)" width="336" x="56" y="110" /> <rect fill="rgb(243,152,0)" height="60" style="filter:url(#filter_blur)" width="336" x="56" y="190" /> <rect fill="rgb(0,0,0)" height="40" stroke="rgb(0,0,0)" style="filter:url(#filter_blur);opacity:0.7;fill-opacity:1" width="128" x="67" y="46" /> <rect fill="rgb(0,0,0)" height="40" stroke="rgb(0,0,0)" style="filter:url(#filter_blur);opacity:0.7;fill-opacity:1" width="128" x="259" y="46" /> <rect fill="rgb(0,0,0)" height="40" stroke="rgb(0,0,0)" style="filter:url(#filter_blur);opacity:0.7;fill-opacity:1" width="128" x="67" y="126" /> <rect fill="rgb(0,0,0)" height="40" stroke="rgb(0,0,0)" style="filter:url(#filter_blur);opacity:0.7;fill-opacity:1" width="128" x="259" y="126" /> <rect fill="rgb(0,0,0)" height="40" stroke="rgb(0,0,0)" style="filter:url(#filter_blur);opacity:0.7;fill-opacity:1" width="128" x="67" y="206" /> <rect fill="rgb(0,0,0)" height="40" stroke="rgb(0,0,0)" style="filter:url(#filter_blur);opacity:0.7;fill-opacity:1" width="128" x="259" y="206" /> <rect fill="rgb(255,255,255)" height="40" stroke="rgb(0,0,0)" stroke-dasharray="1 8" width="128" x="64" y="40" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="6" x="128.0" y="66">型</text> <rect fill="rgb(255,255,255)" height="40" stroke="rgb(0,0,0)" width="128" x="256" y="40" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="12" x="320.0" y="66">物</text> <rect fill="rgb(255,255,255)" height="40" stroke="rgb(0,0,0)" stroke-dasharray="4 8" width="128" x="64" y="120" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="24" x="128.0" y="146">Type</text> <rect fill="rgb(255,255,255)" height="40" stroke="rgb(0,0,0)" width="128" x="256" y="120" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="36" x="320.0" y="146">Object</text> <rect fill="rgb(255,255,255)" height="40" stroke="rgb(0,0,0)" stroke-dasharray="4 4" width="128" x="64" y="200" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="30" x="128.0" y="226">Class</text> <rect fill="rgb(255,255,255)" height="40" stroke="rgb(0,0,0)" width="128" x="256" y="200" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="48" x="320.0" y="226">Instance</text> <path d="M 192 60 L 248 60" fill="none" stroke="rgb(0,0,0)" /> <polygon fill="rgb(0,0,0)" points="255,60 248,56 248,64 255,60" stroke="rgb(0,0,0)" /> <path d="M 192 140 L 248 140" fill="none" stroke="rgb(0,0,0)" /> <polygon fill="rgb(0,0,0)" points="255,140 248,136 248,144 255,140" stroke="rgb(0,0,0)" /> <path d="M 192 220 L 248 220" fill="none" stroke="rgb(0,0,0)" /> <polygon fill="rgb(0,0,0)" points="255,220 248,216 248,224 255,220" stroke="rgb(0,0,0)" /> <rect fill="white" height="15" stroke="rgb(0,0,0)" width="28" x="210" y="38" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="12" x="224.0" y="51">生成</text> <rect fill="white" height="15" stroke="rgb(0,0,0)" width="52" x="198" y="118" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="36" x="224.0" y="131">Create</text> <rect fill="white" height="15" stroke="rgb(0,0,0)" width="52" x="198" y="198" /> <text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="36" x="224.0" y="211">Create</text> </svg>
blockdiagで出力したままのSVGだと「生成」の「生」と「成」の文字が重なって表示されていた。SVGのコードを直接手動で編集すると解決できた。以下のtextLength="12"
の12
を24
にすると解決した。
<text fill="rgb(0,0,0)" font-family="sans-serif" font-size="11" font-style="normal" font-weight="normal" text-anchor="middle" textLength="12" x="224.0" y="51">生成</text>
blockdiagはラベルに日本語を書くと文字幅を自動調整できないのか?それとも設定不足?textLength
の値が何なのかもよくわからない。
できたこと
できなかったこと
- 1ブロックから2方向の矢印を出せない
- 「継承する」と「生成する」の異なる2つの意味をもった矢印を、それぞれY軸(上下方向)とX軸(佐右方向)に割り当てたかった
- 矢印と方向に意味をもたせることで理解しやすい図になる予定だったのに…
- 「継承する」と「生成する」の異なる2つの意味をもった矢印を、それぞれY軸(上下方向)とX軸(佐右方向)に割り当てたかった
- SVGのURLを参照しても表示されない
- GitHubから直リンすれば表示されると見込んでいたが…
blockdiagでの不都合
- ラベルに漢字を使うと文字が重なってしまった
- 日本語だと文字幅を自動調整できない?
バグなのか使い方が間違っているのか設定不足なのか原因不明。
課題
- 作図ツールは別のものを探す必要がある
- はたして目標のものを作図できるツールはあるのか。作図ツールは探すのも難しい
- HTML表示までの手順が多すぎる
所感
問題が多すぎて目標達成できず。Cacooのように1ブロックの複数辺から矢印を出せればいいのだが。Cacooはblockdiagのようにテキスト編集で操作できて欲しい。編集が辛すぎる。理想の作図ツールを自作するしかないのか…。