source: josm/trunk/src/org/openstreetmap/josm/gui/dialogs/relation/RelationTreeModel.java@ 13171

Last change on this file since 13171 was 10306, checked in by Don-vip, 8 years ago

sonar - pmd:ImmutableField + remove unused code

  • Property svn:eol-style set to native
File size: 6.0 KB
Line 
1// License: GPL. For details, see LICENSE file.
2package org.openstreetmap.josm.gui.dialogs.relation;
3
4import java.util.List;
5import java.util.concurrent.CopyOnWriteArrayList;
6
7import javax.swing.event.TreeModelEvent;
8import javax.swing.event.TreeModelListener;
9import javax.swing.tree.TreeModel;
10import javax.swing.tree.TreePath;
11
12import org.openstreetmap.josm.data.osm.Relation;
13import org.openstreetmap.josm.data.osm.RelationMember;
14
15/**
16 * This is a {@link TreeModel} which provides the hierarchical structure of {@link Relation}s
17 * to a {@link javax.swing.JTree}.
18 *
19 * The model is initialized with a root relation or with a list of {@link RelationMember}s, see
20 * {@link #populate(Relation)} and {@link #populate(List)} respectively.
21 *
22 * @since 1828
23 */
24public class RelationTreeModel implements TreeModel {
25 /** the root relation */
26 private Relation root;
27
28 /** the tree model listeners */
29 private final CopyOnWriteArrayList<TreeModelListener> listeners;
30
31 /**
32 * constructor
33 */
34 public RelationTreeModel() {
35 this.root = null;
36 listeners = new CopyOnWriteArrayList<>();
37 }
38
39 /**
40 * Replies the number of children of type relation for a particular
41 * relation <code>parent</code>
42 *
43 * @param parent the parent relation
44 * @return the number of children of type relation
45 */
46 protected int getNumRelationChildren(Relation parent) {
47 if (parent == null) return 0;
48 int count = 0;
49 for (RelationMember member : parent.getMembers()) {
50 if (member.isRelation()) {
51 count++;
52 }
53 }
54 return count;
55 }
56
57 /**
58 * Replies the i-th child of type relation for a particular relation
59 * <code>parent</code>.
60 *
61 * @param parent the parent relation
62 * @param idx the index
63 * @return the i-th child of type relation for a particular relation
64 * <code>parent</code>; null, if no such child exists
65 */
66 protected Relation getRelationChildByIdx(Relation parent, int idx) {
67 if (parent == null) return null;
68 int count = 0;
69 for (RelationMember member : parent.getMembers()) {
70 if (!(member.isRelation())) {
71 continue;
72 }
73 if (count == idx)
74 return member.getRelation();
75 count++;
76 }
77 return null;
78 }
79
80 /**
81 * Replies the index of a particular <code>child</code> with respect to its
82 * <code>parent</code>.
83 *
84 * @param parent the parent relation
85 * @param child the child relation
86 * @return the index of a particular <code>child</code> with respect to its
87 * <code>parent</code>; -1 if either parent or child are null or if <code>child</code>
88 * isn't a child of <code>parent</code>.
89 *
90 */
91 protected int getIndexForRelationChild(Relation parent, Relation child) {
92 if (parent == null || child == null) return -1;
93 int idx = 0;
94 for (RelationMember member : parent.getMembers()) {
95 if (!(member.isRelation())) {
96 continue;
97 }
98 if (member.getMember() == child) return idx;
99 idx++;
100 }
101 return -1;
102 }
103
104 /**
105 * Populates the model with a root relation
106 *
107 * @param root the root relation
108 * @see #populate(List)
109 *
110 */
111 public void populate(Relation root) {
112 if (root == null) {
113 root = new Relation();
114 }
115 this.root = root;
116 fireRootReplacedEvent();
117 }
118
119 /**
120 * Populates the model with a list of relation members
121 *
122 * @param members the relation members
123 */
124 public void populate(List<RelationMember> members) {
125 if (members == null) return;
126 Relation r = new Relation();
127 r.setMembers(members);
128 this.root = r;
129 fireRootReplacedEvent();
130 }
131
132 /**
133 * Notifies tree model listeners about a replacement of the
134 * root.
135 */
136 protected void fireRootReplacedEvent() {
137 TreeModelEvent e = new TreeModelEvent(this, new TreePath(root));
138 for (TreeModelListener l : listeners) {
139 l.treeStructureChanged(e);
140 }
141 }
142
143 /**
144 * Notifies tree model listeners about an update of the
145 * trees nodes.
146 *
147 * @param path the tree path to the node
148 */
149 protected void fireRefreshNode(TreePath path) {
150 TreeModelEvent e = new TreeModelEvent(this, path);
151 for (TreeModelListener l : listeners) {
152 l.treeStructureChanged(e);
153 }
154
155 }
156
157 /**
158 * Invoke to notify all listeners about an update of a particular node
159 *
160 * @param pathToNode the tree path to the node
161 */
162 public void refreshNode(TreePath pathToNode) {
163 fireRefreshNode(pathToNode);
164 }
165
166 /* ----------------------------------------------------------------------- */
167 /* interface TreeModel */
168 /* ----------------------------------------------------------------------- */
169 @Override
170 public Object getChild(Object parent, int index) {
171 return getRelationChildByIdx((Relation) parent, index);
172 }
173
174 @Override
175 public int getChildCount(Object parent) {
176 return getNumRelationChildren((Relation) parent);
177 }
178
179 @Override
180 public int getIndexOfChild(Object parent, Object child) {
181 return getIndexForRelationChild((Relation) parent, (Relation) child);
182 }
183
184 @Override
185 public Object getRoot() {
186 return root;
187 }
188
189 @Override
190 public boolean isLeaf(Object node) {
191 Relation r = (Relation) node;
192 if (r.isIncomplete()) return false;
193 return getNumRelationChildren(r) == 0;
194 }
195
196 @Override
197 public void addTreeModelListener(TreeModelListener l) {
198 if (l != null) {
199 listeners.addIfAbsent(l);
200 }
201 }
202
203 @Override
204 public void removeTreeModelListener(TreeModelListener l) {
205 listeners.remove(l);
206 }
207
208 @Override
209 public void valueForPathChanged(TreePath path, Object newValue) {
210 // do nothing
211 }
212}
Note: See TracBrowser for help on using the repository browser.