-/*******************************************************************************\r
- * Copyright (c) 2005, 2007 IBM Corporation and others.\r
- * All rights reserved. This program and the accompanying materials\r
- * are made available under the terms of the Eclipse Public License v1.0\r
- * which accompanies this distribution, and is available at\r
- * http://www.eclipse.org/legal/epl-v10.html\r
- *\r
- * Contributors:\r
- * IBM Corporation - initial API and implementation\r
- *******************************************************************************/\r
-package org.simantics.browsing.ui;\r
-\r
-import java.util.Arrays;\r
-\r
-import org.eclipse.core.runtime.Assert;\r
-import org.eclipse.core.runtime.IAdaptable;\r
-\r
-/**\r
- * A {@link GraphExplorer} tree {@link NodeContext} path denotes a model element\r
- * in a tree viewer. Tree path objects have value semantics. A model element is\r
- * represented by a path of elements in the tree from the root element to the\r
- * leaf element.\r
- * <p>\r
- * Clients may instantiate this class. Not intended to be subclassed.\r
- * </p>\r
- * \r
- * <p>\r
- * Directly imitated for the Simantics browsing framework from JFace\r
- * <code>org.eclipse.jface.viewer.TreePath</code> class.\r
- * </p>\r
- * \r
- * @author Tuukka Lehtonen\r
- */\r
-public final class NodeContextPath implements IAdaptable {\r
-\r
- public static final NodeContextPath[] NONE = {};\r
-\r
- /**\r
- * Constant for representing an empty tree path.\r
- */\r
- public static final NodeContextPath EMPTY = new NodeContextPath(NodeContext.NONE);\r
-\r
- private final NodeContext[] segments;\r
-\r
- private int hash;\r
-\r
- /**\r
- * Constructs a path identifying a leaf node in a tree.\r
- * \r
- * @param segments\r
- * path of elements to a leaf node in a tree, starting with the\r
- * root element\r
- */\r
- public NodeContextPath(NodeContext... segments) {\r
- Assert.isNotNull(segments);\r
- for (int i = 0; i < segments.length; i++) {\r
- Assert.isNotNull(segments[i]);\r
- }\r
- this.segments = segments;\r
- }\r
-\r
- /**\r
- * Returns the element at the specified index in this path.\r
- * \r
- * @param index\r
- * index of element to return\r
- * @return element at the specified index\r
- */\r
- public NodeContext getSegment(int index) {\r
- return segments[index];\r
- }\r
-\r
- /**\r
- * Returns the number of elements in this path.\r
- * \r
- * @return the number of elements in this path\r
- */\r
- public int getSegmentCount() {\r
- return segments.length;\r
- }\r
-\r
- /**\r
- * Returns the first element in this path, or <code>null</code> if this\r
- * path has no segments.\r
- * \r
- * @return the first element in this path\r
- */\r
- public NodeContext getFirstSegment() {\r
- if (segments.length == 0) {\r
- return null;\r
- }\r
- return segments[0];\r
- }\r
-\r
- /**\r
- * Returns the last element in this path, or <code>null</code> if this\r
- * path has no segments.\r
- * \r
- * @return the last element in this path\r
- */\r
- public NodeContext getLastSegment() {\r
- if (segments.length == 0) {\r
- return null;\r
- }\r
- return segments[segments.length - 1];\r
- }\r
-\r
- /**\r
- * @return all the segments in the path as an array\r
- */\r
- public NodeContext[] getSegments() {\r
- if (segments.length == 0)\r
- return segments;\r
- return Arrays.copyOf(segments, segments.length);\r
- }\r
-\r
- /*\r
- * (non-Javadoc)\r
- * \r
- * @see java.lang.Object#equals(java.lang.Object)\r
- */\r
- public boolean equals(Object other) {\r
- if (!(other instanceof NodeContextPath)) {\r
- return false;\r
- }\r
- return equals((NodeContextPath) other);\r
- }\r
-\r
- /**\r
- * (non-Javadoc)\r
- * \r
- * @see java.lang.Object#hashCode()\r
- */\r
- public int hashCode() {\r
- if (hash == 0) {\r
- hash = hashCode0();\r
- }\r
- return hash;\r
- }\r
-\r
- /**\r
- * Returns a hash code computed from the hash codes of the segments, using\r
- * the given comparer to compute the hash codes of the segments.\r
- * \r
- * @param comparer\r
- * comparer to use or <code>null</code> if the segments' hash\r
- * codes should be computed by calling their hashCode() methods.\r
- * @return the computed hash code\r
- */\r
- private int hashCode0() {\r
- int result = 0;\r
- for (int i = 0; i < segments.length; i++) {\r
- result += segments[i].hashCode();\r
- }\r
- return result;\r
- }\r
-\r
- /**\r
- * Returns whether this path is equivalent to the given path using the\r
- * specified comparer to compare individual elements.\r
- * \r
- * @param otherPath\r
- * tree path to compare to\r
- * @param comparer\r
- * comparator to use or <code>null</code> if segments should be\r
- * compared using equals()\r
- * @return whether the paths are equal\r
- */\r
- public boolean equals(NodeContextPath otherPath) {\r
- if (otherPath == null) {\r
- return false;\r
- }\r
- if (segments.length != otherPath.segments.length) {\r
- return false;\r
- }\r
- for (int i = 0; i < segments.length; i++) {\r
- if (!segments[i].equals(otherPath.segments[i])) {\r
- return false;\r
- }\r
- }\r
- return true;\r
- }\r
-\r
- /**\r
- * Returns whether this path starts with the same segments as the given\r
- * path, using the given comparer to compare segments.\r
- * \r
- * @param treePath\r
- * path to compare to\r
- * @param comparer\r
- * the comparer to use, or <code>null</code> if equals() should\r
- * be used to compare segments\r
- * @return whether the given path is a prefix of this path, or the same as\r
- * this path\r
- */\r
- public boolean startsWith(NodeContextPath treePath) {\r
- int thisSegmentCount = getSegmentCount();\r
- int otherSegmentCount = treePath.getSegmentCount();\r
- if (otherSegmentCount == thisSegmentCount) {\r
- return equals(treePath);\r
- }\r
- if (otherSegmentCount > thisSegmentCount) {\r
- return false;\r
- }\r
- for (int i = 0; i < otherSegmentCount; i++) {\r
- Object otherSegment = treePath.getSegment(i);\r
- if (!otherSegment.equals(segments[i])) {\r
- return false;\r
- }\r
- }\r
- return true;\r
- }\r
-\r
- /**\r
- * Returns a copy of this tree path with one segment removed from the end,\r
- * or <code>null</code> if this tree path has no segments.\r
- * @return a tree path\r
- */\r
- public NodeContextPath getParentPath() {\r
- int segmentCount = getSegmentCount();\r
- if (segmentCount < 1) {\r
- return null;\r
- } else if (segmentCount == 1) {\r
- return EMPTY;\r
- }\r
- NodeContext[] parentSegments = new NodeContext[segmentCount - 1];\r
- System.arraycopy(segments, 0, parentSegments, 0, segmentCount - 1);\r
- return new NodeContextPath(parentSegments);\r
- }\r
-\r
- /**\r
- * Returns a copy of this tree path with the given segment added at the end.\r
- * @param newSegment \r
- * @return a tree path\r
- */\r
- public NodeContextPath createChildPath(NodeContext newSegment) {\r
- int segmentCount = getSegmentCount();\r
- NodeContext[] childSegments = new NodeContext[segmentCount + 1];\r
- if(segmentCount>0) {\r
- System.arraycopy(segments, 0, childSegments, 0, segmentCount);\r
- }\r
- childSegments[segmentCount] = newSegment;\r
- return new NodeContextPath(childSegments);\r
- }\r
-\r
- @SuppressWarnings("unchecked")\r
- @Override\r
- public <T> T getAdapter(Class<T> adapter) {\r
- if (NodeContext.class == adapter)\r
- return (T) getLastSegment();\r
- NodeContext last = getLastSegment();\r
- if (last instanceof IAdaptable)\r
- return ((IAdaptable) last).getAdapter(adapter);\r
- return null;\r
- }\r
-\r
-}\r
+/*******************************************************************************
+ * Copyright (c) 2005, 2007 IBM Corporation and others.
+ * All rights reserved. This program and the accompanying materials
+ * are made available under the terms of the Eclipse Public License v1.0
+ * which accompanies this distribution, and is available at
+ * http://www.eclipse.org/legal/epl-v10.html
+ *
+ * Contributors:
+ * IBM Corporation - initial API and implementation
+ *******************************************************************************/
+package org.simantics.browsing.ui;
+
+import java.util.Arrays;
+
+import org.eclipse.core.runtime.Assert;
+import org.eclipse.core.runtime.IAdaptable;
+
+/**
+ * A {@link GraphExplorer} tree {@link NodeContext} path denotes a model element
+ * in a tree viewer. Tree path objects have value semantics. A model element is
+ * represented by a path of elements in the tree from the root element to the
+ * leaf element.
+ * <p>
+ * Clients may instantiate this class. Not intended to be subclassed.
+ * </p>
+ *
+ * <p>
+ * Directly imitated for the Simantics browsing framework from JFace
+ * <code>org.eclipse.jface.viewer.TreePath</code> class.
+ * </p>
+ *
+ * @author Tuukka Lehtonen
+ */
+public final class NodeContextPath implements IAdaptable {
+
+ public static final NodeContextPath[] NONE = {};
+
+ /**
+ * Constant for representing an empty tree path.
+ */
+ public static final NodeContextPath EMPTY = new NodeContextPath(NodeContext.NONE);
+
+ private final NodeContext[] segments;
+
+ private int hash;
+
+ /**
+ * Constructs a path identifying a leaf node in a tree.
+ *
+ * @param segments
+ * path of elements to a leaf node in a tree, starting with the
+ * root element
+ */
+ public NodeContextPath(NodeContext... segments) {
+ Assert.isNotNull(segments);
+ for (int i = 0; i < segments.length; i++) {
+ Assert.isNotNull(segments[i]);
+ }
+ this.segments = segments;
+ }
+
+ /**
+ * Returns the element at the specified index in this path.
+ *
+ * @param index
+ * index of element to return
+ * @return element at the specified index
+ */
+ public NodeContext getSegment(int index) {
+ return segments[index];
+ }
+
+ /**
+ * Returns the number of elements in this path.
+ *
+ * @return the number of elements in this path
+ */
+ public int getSegmentCount() {
+ return segments.length;
+ }
+
+ /**
+ * Returns the first element in this path, or <code>null</code> if this
+ * path has no segments.
+ *
+ * @return the first element in this path
+ */
+ public NodeContext getFirstSegment() {
+ if (segments.length == 0) {
+ return null;
+ }
+ return segments[0];
+ }
+
+ /**
+ * Returns the last element in this path, or <code>null</code> if this
+ * path has no segments.
+ *
+ * @return the last element in this path
+ */
+ public NodeContext getLastSegment() {
+ if (segments.length == 0) {
+ return null;
+ }
+ return segments[segments.length - 1];
+ }
+
+ /**
+ * @return all the segments in the path as an array
+ */
+ public NodeContext[] getSegments() {
+ if (segments.length == 0)
+ return segments;
+ return Arrays.copyOf(segments, segments.length);
+ }
+
+ /*
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#equals(java.lang.Object)
+ */
+ public boolean equals(Object other) {
+ if (!(other instanceof NodeContextPath)) {
+ return false;
+ }
+ return equals((NodeContextPath) other);
+ }
+
+ /**
+ * (non-Javadoc)
+ *
+ * @see java.lang.Object#hashCode()
+ */
+ public int hashCode() {
+ if (hash == 0) {
+ hash = hashCode0();
+ }
+ return hash;
+ }
+
+ /**
+ * Returns a hash code computed from the hash codes of the segments, using
+ * the given comparer to compute the hash codes of the segments.
+ *
+ * @param comparer
+ * comparer to use or <code>null</code> if the segments' hash
+ * codes should be computed by calling their hashCode() methods.
+ * @return the computed hash code
+ */
+ private int hashCode0() {
+ int result = 0;
+ for (int i = 0; i < segments.length; i++) {
+ result += segments[i].hashCode();
+ }
+ return result;
+ }
+
+ /**
+ * Returns whether this path is equivalent to the given path using the
+ * specified comparer to compare individual elements.
+ *
+ * @param otherPath
+ * tree path to compare to
+ * @param comparer
+ * comparator to use or <code>null</code> if segments should be
+ * compared using equals()
+ * @return whether the paths are equal
+ */
+ public boolean equals(NodeContextPath otherPath) {
+ if (otherPath == null) {
+ return false;
+ }
+ if (segments.length != otherPath.segments.length) {
+ return false;
+ }
+ for (int i = 0; i < segments.length; i++) {
+ if (!segments[i].equals(otherPath.segments[i])) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Returns whether this path starts with the same segments as the given
+ * path, using the given comparer to compare segments.
+ *
+ * @param treePath
+ * path to compare to
+ * @param comparer
+ * the comparer to use, or <code>null</code> if equals() should
+ * be used to compare segments
+ * @return whether the given path is a prefix of this path, or the same as
+ * this path
+ */
+ public boolean startsWith(NodeContextPath treePath) {
+ int thisSegmentCount = getSegmentCount();
+ int otherSegmentCount = treePath.getSegmentCount();
+ if (otherSegmentCount == thisSegmentCount) {
+ return equals(treePath);
+ }
+ if (otherSegmentCount > thisSegmentCount) {
+ return false;
+ }
+ for (int i = 0; i < otherSegmentCount; i++) {
+ Object otherSegment = treePath.getSegment(i);
+ if (!otherSegment.equals(segments[i])) {
+ return false;
+ }
+ }
+ return true;
+ }
+
+ /**
+ * Returns a copy of this tree path with one segment removed from the end,
+ * or <code>null</code> if this tree path has no segments.
+ * @return a tree path
+ */
+ public NodeContextPath getParentPath() {
+ int segmentCount = getSegmentCount();
+ if (segmentCount < 1) {
+ return null;
+ } else if (segmentCount == 1) {
+ return EMPTY;
+ }
+ NodeContext[] parentSegments = new NodeContext[segmentCount - 1];
+ System.arraycopy(segments, 0, parentSegments, 0, segmentCount - 1);
+ return new NodeContextPath(parentSegments);
+ }
+
+ /**
+ * Returns a copy of this tree path with the given segment added at the end.
+ * @param newSegment
+ * @return a tree path
+ */
+ public NodeContextPath createChildPath(NodeContext newSegment) {
+ int segmentCount = getSegmentCount();
+ NodeContext[] childSegments = new NodeContext[segmentCount + 1];
+ if(segmentCount>0) {
+ System.arraycopy(segments, 0, childSegments, 0, segmentCount);
+ }
+ childSegments[segmentCount] = newSegment;
+ return new NodeContextPath(childSegments);
+ }
+
+ @SuppressWarnings("unchecked")
+ @Override
+ public <T> T getAdapter(Class<T> adapter) {
+ if (NodeContext.class == adapter)
+ return (T) getLastSegment();
+ NodeContext last = getLastSegment();
+ if (last instanceof IAdaptable)
+ return ((IAdaptable) last).getAdapter(adapter);
+ return null;
+ }
+
+}