]> gerrit.simantics Code Review - simantics/platform.git/blob - bundles/org.simantics.graphviz/src/org/simantics/graphviz/Record.java
Migrated source code from Simantics SVN
[simantics/platform.git] / bundles / org.simantics.graphviz / src / org / simantics / graphviz / Record.java
1 /*******************************************************************************\r
2  * Copyright (c) 2007, 2010 Association for Decentralized Information Management\r
3  * in Industry THTH ry.\r
4  * All rights reserved. This program and the accompanying materials\r
5  * are made available under the terms of the Eclipse Public License v1.0\r
6  * which accompanies this distribution, and is available at\r
7  * http://www.eclipse.org/legal/epl-v10.html\r
8  *\r
9  * Contributors:\r
10  *     VTT Technical Research Centre of Finland - initial API and implementation\r
11  *******************************************************************************/\r
12 package org.simantics.graphviz;\r
13 \r
14 import java.util.ArrayList;\r
15 \r
16 /**\r
17  * A helper class for creating record shaped nodes.\r
18  * \r
19  * @author Hannu Niemistö\r
20  */\r
21 public class Record {\r
22  \r
23     static class IdentifiableField {\r
24         String id;\r
25         String label;\r
26         \r
27         public IdentifiableField(String id, String label) {\r
28             super();\r
29             this.id = id;\r
30             this.label = label;\r
31         }            \r
32     }\r
33     \r
34     static class Field {\r
35         String label;\r
36 \r
37         public Field(String label) {\r
38             super();\r
39             this.label = label;\r
40         }        \r
41     }\r
42     \r
43     ArrayList<Object> fields = new ArrayList<Object>();\r
44     boolean rotated = false;\r
45     \r
46     public Record() {        \r
47     }\r
48     \r
49     /**\r
50      * Adds a simple nonreferable field to a record.\r
51      */\r
52     public void add(String label) {\r
53         fields.add(new Field(label));\r
54     }\r
55 \r
56     /**\r
57      * Adds a field to a record that can be referred in \r
58      * connections. Example\r
59      * <blockquote><pre>\r
60      *   Record r = new Record();\r
61      *   r.add("A field");\r
62      *   r.add("id1", "An another field");\r
63      *   Node n1 = r.toField(g);\r
64      *   Node n2 = new Node(g2);\r
65      *   new Edge(n1.getPort("id1"), n2);\r
66      * </pre></blockquote>\r
67      */\r
68     public void add(String id, String label) {\r
69         fields.add(new IdentifiableField(id, label));\r
70     }\r
71     \r
72     /**\r
73      * Puts a record inside this record. This is most useful\r
74      * if the record added is rotated. In this way, one can\r
75      * build records that both horizontally and vertically\r
76      * divided areas.\r
77      */\r
78     public void add(Record record) {\r
79         fields.add(record);\r
80     }\r
81     \r
82     /**\r
83      * Creates a node whose shape is build according to the\r
84      * record definition.\r
85      */\r
86     public Node toNode(Graph g) {\r
87         Node node = new Node(g);\r
88         node.setShape("record");\r
89         StringBuilder b = new StringBuilder();\r
90         toString(b);\r
91         node.setLabel(b.toString());\r
92         return node;\r
93     }\r
94     \r
95     private void toString(StringBuilder b) {\r
96         if(rotated)\r
97             b.append('{');\r
98         for(int i=0;i<fields.size();++i) {\r
99             Object f = fields.get(i);\r
100             if(i > 0)\r
101                 b.append('|');\r
102             if(f instanceof Field) {\r
103                 Field ff = (Field)f;\r
104                 b.append(ff.label);\r
105             }\r
106             else if(f instanceof IdentifiableField) {\r
107                 IdentifiableField ff = (IdentifiableField)f;\r
108                 b.append('<');\r
109                 b.append(ff.id);\r
110                 b.append('>');\r
111                 b.append(ff.label);\r
112             }\r
113             else if(f instanceof Record) {\r
114                 ((Record)f).toString(b);\r
115             }\r
116         }\r
117         if(rotated)\r
118             b.append('}');\r
119     }\r
120     \r
121     /**\r
122      * Tells if the record has opposite orientation from\r
123      * its surroundings. If the record is converted into\r
124      * node, this means the rankdir of the graph. If\r
125      * the record is put inside other record, then rotation\r
126      * is relative to the orientation of the parent record.\r
127      */\r
128     public void setRotated(boolean rotated) {\r
129         this.rotated = rotated;\r
130     }\r
131 }\r